my goal is to understand how to use angularJS correctly. I want to be able to tie a selection of variable to dynamically changing the DOM structure using angularJS. I dont think I'm quite understanding the documentation that angular provides and I haven't found any examples here or otherwise. Any help is appreciated.
The idea is that I have this use case where I first start with the selection of the type and from that type selected, the appropriate input type elements will be created and then recorded later with the ng-model (from textareas to checkboxes for example), all the while controlled by the angularjs controller for validation/restrictions. I'm used to the idea of having clone-able elements on the page and destroying and creating new with jQuery, but I've been reading that controllers should not have this logic and should instead be created with directives/widgets. I dont see any examples of directives or widgets being manipulated in this way however so I'm not even sure how to proceed. Can I use directives to manipulate the DOM in this way, not just once but multiple times based on a watched element?
Example of what I would like to do.
$scope.types = ['Type1','Type2']
// something along the lines of...
$scope.layouts = {'Type1':['textarea','textarea'], 'Type2':['numeric','datepicker']}
Select Type 1:
Select Type 2:
This is how I would do it. Note that this is a just a starting point. There is still a matter of binding to particular values in the corresponding inputs. I hope it helps.
Markup:
<html ng-app="App" ng-controller="MainCtrl">
<body>
<component index="0"></component>
<component index="1"></component>
Current type: {{type}}
<button ng-click="toggleType()">Toggle</button>
</body>
</html>
Directive:
var ngApp = angular.module('App', []).directive('component', function() {
var link = function(scope, element, attrs) {
var render = function() {
var t = scope.layouts[scope.type][attrs.index];
if (t === 'textarea') {
element.html('<' + t + ' /><br>');
}
else {
element.html('<input type="' + t + '"><br>');
}
};
//key point here to watch for changes of the type property
scope.$watch('type', function(newValue, oldValue) {
render();
});
render();
};
return {
restrict : 'E',
link : link
}
});
Controller:
var MainCtrl = function MainCtrl($scope) {
$scope.type = 'Type1';
$scope.types = [ 'Type1', 'Type2' ];
$scope.layouts = {
'Type1' : [ 'textarea', 'textarea' ],
'Type2' : [ 'number', 'text' ]
};
$scope.toggleType = function() {
if ($scope.type === 'Type1') {
$scope.type = 'Type2';
}
else {
$scope.type = 'Type1';
}
};
};