I have a dynamic Form in AngularJS, the input tags get replaced according to question type selected by the user. So the problem is, when user left a input tag blank which is required and switched to another type of questions, the form remains invalid(even the current form is valid).
I am adding the JsFiddle for it, you will get the idea.
HTML
<body ng-app="myApp" ng-controller="myCtrl">
<form name="myForm" novalidate>
<div><input name='name' type='text' ng-model='name' ng-required='true' placeholder='name'></div>
<div compile="myHtml"></div>
<input type="radio" ng-required='true' ng-click="addQuestion(1)" ng-model="radio" value="1"> Question 1 & 3
<input type="radio" ng-required='true' ng-click="addQuestion(2)" ng-model="radio" value="2"> Question 2 & 4
<input type="submit" name="submit" ng-click="" ng-disabled="myForm.$invalid">
</form>
</body>
Javascript
// the main (app) module
var myApp = angular.module("myApp", []);
// add a controller
myApp.controller("myCtrl", function($scope) {
$scope.name = "John Doe";
$scope.myHtml = "";
$scope.radio="1";
$scope.question1 = 1;
$scope.question2 = 2;
$scope.question4 = 4;
$scope.addQuestion = function(id) {
$scope.myHtml = "";
if(id == 1) {
$scope.myHtml += "<div><input name='question1' type='text' ng-model='question1' ng-required='true' placeholder='Question 1'></div>";
$scope.myHtml += "<div><input name='question3' type='text' ng-model='question3' ng-required='true' placeholder='Question 3'></div>";
};
if(id == 2) {
$scope.myHtml += "<div><input name='question2' type='text' ng-model='question2' ng-required='true' placeholder='Question 2'></div>";
$scope.myHtml += "<div><input name='question4' type='text' ng-model='question4' ng-required='true' placeholder='Question 4'></div>";
};
};
$scope.addQuestion(1);
});
// add a directive
myApp.directive('compile', ['$compile', function ($compile) {
return function(scope, element, attrs) {
scope.$watch(
function(scope) {
// watch the 'compile' expression for changes
return scope.$eval(attrs.compile);
},
function(value) {
// when the 'compile' expression changes
// assign it into the current DOM
element.html(value);
// compile the new DOM and link it to the current
// scope.
// NOTE: we only compile .childNodes so that
// we don't get into infinite loop compiling ourselves
$compile(element.contents())(scope);
}
);
};
}]);
Server JSON for question
$scope.fields = [{
"caption": "Gender",
"questionType": "RADIO",
"optionValues": ["Male", "Female"],
"fieldPriority": "REQUIRED"
}, {
"caption": "City",
"questionType": "TEXT",
"optionValues": "",
"fieldPriority": "REQUIRED"
}, {
"caption": "Address",
"questionType": "PARAGRAPH_TEXT",
"optionValues": "",
"fieldPriority": "REQUIRED"
}, {
"caption": "Nationality",
"questionType": "LIST",
"optionValues": ["Indian", "American"],
"fieldPriority": "REQUIRED"
}, {
"caption": "Tea/Coffee",
"questionType": "CHECKBOX",
"optionValues": ["Tea", "Coffee"],
"fieldPriority": "REQUIRED"
}];
Thanks
Do not store plane html in controller. Just use ng-if or ng-show to handle your logic.