Berlin native. Bit herder. Code connoisseur. Coffee lover.
Freelance Software Entwickler & Trainer
Web – JVM – iOS
hello-angular
ng-app, ng-controller, ng-click, ...
Nicht nur Attribute, auch Elemente
$("#content form.form ul ~ input + div").on("click", fmlHandler);
vs.
You can't touch this!
You can't touch this!
You can't touch this!
hello-directive
directive()
Funktion
var module = angular.module('Example', []);
module.directive('directiveName', function() {
return {
// describe directive
};
});
x-
und data-
:
zu camelCase-
zu camelCase_
zu camelCaseapp.directive('fooBar', ...)
<foo-bar/>
<foo:bar/>
<foo_bar/>
<my-user/>
<div my-user='user'>
<div class='my-user: user;'>
<!-- directive: my-user user -->
var module = angular.module('Example', []);
module.directive('directiveName', function() {
return {
// describe directive
link: linkFunction,
restrict: 'EA'
//...etc
};
});
link
Link-Funktion
nimmt nicht am DI teil
link: function (scope, element, attribute) {
// element is jqLite/jQuery wrapped
// code to run on/with that element
}
restrict
Wo kann die directive verwendet werden
String aus den Zeichen:
'E'
Element'A'
Attribut (default)'C'
Klasse'M'
Kommentar
{
// snip
restrict: 'EA',
// ...snip
}
template
/ templateUrl
neue DOM Elemente in die Direktiven einfügen
entweder inline oder über Angulars templateCache
app.directive('placeholder', function () {
return {
restrict: 'E',
template: 'real deal!'
};
});
replace
neues template in DOM Element einfügen oder ersetzen
default ist false
app.directive('placeholder', function () {
return {
restrict: 'E',
replace: true,
template: 'real deal!'
};
});
var sound = new Howl({
urls: ['path/to/sound.mp3']
});
sound.play();
Wir brauchen:
sound
app.directive('noise', function($window) {
return {
link: function (scope, element, attrs) {
var sound = new $window.Howl({
urls: [attrs.noise]
});
element.on('click', function() {sound.play();});
}
};
})
describe('MyDirective Test', function () {
var scope, element;
// Load module
beforeEach(module('MyModule'));
// prepare directive
beforeEach(inject(function($compile, $rootScope) {
scope = $rootScope.$new();
element = angular.element('Test');
$compile(element)(scope);
}));
// actual tests
it('should do something', function() {
expect(something).toHaveHappened();
});
});
scope.$apply()
ist der Schlüssel
app.directive('noise', function($window) {
return {
link: function (scope, element, attrs) {
var sound = new $window.Howl({
urls: [attrs.noise],
onplay: function () {
scope.$apply(function () {
scope.playing = attrs.noise;
});
}
});
element.on('click', function() {sound.play();});
}
};
})
controller
app.directive('complexDirective', function () {
return {
controller: 'complexDirectiveController',
link: function(scope, elem, attr, controller) {
controller.init(elem);
};
};
});
app.controller('complexDirectiveController',
function($scope, ComplexService) {
// magic happens here
});
cross-field
require
app.directive('fooBar', function() {
return {
controller: 'fooBarController',
require: ['reqDir', '?^optDir', 'fooBar'],
link: function(s, e, a, controllers) {
var reqDir = controllers[0];
var ownController = controllers[2];
if (controllers[1]) controllers[1].interact(reqDir);
};
}
});
transclude
app.directive('messageBox', function() {
return {
transclude: true,
template: '' +
'Alert!
' +
'' +
''
};
});
Something went wrong: {{message}}
scope
false
– Direktive hat keinen eigenen Scope (default)true
– Direktive hat eigenen Child Scope{}
– Direktive hat eigenen, isolierten Scopedrinks
ermöglicht definiertes Interface einer Direktive
'@'
– unidirektionales Mapping in den Direktiven Scope'='
– bidirektionales Mapping zwischen umliegendendem Scope und Direktive'&'
– ermöglicht function calls im umliegendem Scopepriority
terminal
compile
app.directive('example', function(MagicService) {
// lazy one-time init
return {
restrict: 'EA',
link: function(scope, elem, attrs, controllers) {
// called per usage
},
// or compile: compileFn,
templateUrl: 'neatTemplate.html',
,// or template: '...'
replace: true,
transclude: true,
scope: {foo:'='},
controller: 'aController',
require: ['?^other', 'example']
priority: 100,
terminal: false
};
});
Get in touch!