Last active
February 10, 2017 13:46
-
-
Save matthieusieben/b68a2cc83911e16788ce315549ff36b0 to your computer and use it in GitHub Desktop.
Chile component controller reference for angular 1.x
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const camelCase = (text) => text | |
.toLowerCase() | |
.replace(/-+(.)/g, (_, letter) => letter.toUpperCase()) | |
const getControllerScope = (scope) => | |
Object.getPrototypeOf(scope) === Object.getPrototypeOf(scope.$root) | |
? scope | |
: scope.$parent | |
/** | |
* @ngdoc directive | |
* @name # | |
* @param {String} # The name of the property of `$scope.$ctrl` to which attach | |
* the reference of the component's controller. Defaults to the child | |
* component's name (camel case). | |
* | |
* @description Allows to assign a child component's controller to a property of | |
* the current compoent's `$ctrl`. | |
* | |
* @example | |
* | |
* // app.partial.html | |
* <nav-bar on-home-click="$ctrl.sideBar.toggle()"></nav-bar> | |
* <side-bar #></side-bar> | |
* | |
* // app-bis.partial.html | |
* <nav-bar on-home-click="$ctrl.customCtrlName.toggle()"></nav-bar> | |
* <side-bar #="customCtrlName"></side-bar> | |
*/ | |
octothorpeDirective.$inject = [] | |
function octothorpeDirective () { | |
return { | |
priority: -1000, // lower than ng-view (= -400) | |
restrict: 'A', | |
scope: false, | |
link (scope, iElement, iAttr) { | |
const parentScope = getControllerScope(scope) | |
const $ctrl = parentScope.$ctrl | |
const ctrlName = camelCase(iElement[0].nodeName) | |
const refName = iAttr['#'] || ctrlName | |
if (!$ctrl) { | |
throw new Error('Missing parent controller for # directive.') | |
} else if ($ctrl.hasOwnProperty(refName)) { | |
throw new Error(`The controller already has property named "${refName}"`) | |
} | |
scope.$on('$destroy', () => { | |
$ctrl[refName] = null | |
}) | |
// If the element is compiled asynchronously then its controller may need | |
// several digests before beeing instantiated. | |
const unwatch = scope.$watch(() => { | |
const elData = iElement.data() | |
return elData[`$${ctrlName}Controller`] || elData['$ngControllerController'] | |
}, (elCtrl) => { | |
if (elCtrl) { | |
$ctrl[refName] = elCtrl | |
unwatch() | |
} | |
}) | |
} | |
} | |
} | |
export default angular | |
.module('octothorpe', []) | |
.directive('#', octothorpeDirective) | |
.name |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment