ng-model not attaching to controller $scope when inserting modal form from Django - angularjs

I'm serving a form from Django into an angular-ui-bootstrap modal using the template property:
function openFinderModal() {
var modalInstance = $modal.open({
template: vm.modalTemplate,
});
The relevant part of the modal template served from a form view:
<div class="modal-body" >
<form ng-controller="ServiceFinderModalController">
{% csrf_token %}
{{ form }}
</form>
</div>
I'm then using django-angular to create an ng-model on each form field (see the docs), corresponding to my simple form below:
class ServiceSelectionForm(NgModelFormMixin, NgForm):
service_0 = forms.BooleanField()
However, when I attempt to access this form field from $scope I get undefined.
function ServiceFinderModalController($scope) {
console.log($scope.service_0);
}
I've inspected the source of the page and it seems as though it should work (see second last line):
<form ng-controller="ServiceFinderModalController" class="ng-pristine ng-valid ng-scope">
<input type="hidden" name="csrfmiddlewaretoken" value="dkH6aiHyIqqkJlN5xAbiYaX0c37tXb9U">
<ul class="djng-form-errors ng-hide" ng-show="U2VydmljZVNlbGVjdGlvbkZvcm0.$pristine">
<li ng-show="U2VydmljZVNlbGVjdGlvbkZvcm0.$message" class="invalid ng-binding ng-hide" ng-bind="U2VydmljZVNlbGVjdGlvbkZvcm0.$message"></li>
</ul>
<ul class="djng-form-errors ng-hide" ng-show="U2VydmljZVNlbGVjdGlvbkZvcm0.$dirty"></ul>
<label for="id_service_0">Test 2</label>
<ul class="djng-field-errors ng-hide" ng-show="U2VydmljZVNlbGVjdGlvbkZvcm0.service_0.$pristine">
<li ng-show="U2VydmljZVNlbGVjdGlvbkZvcm0.service_0.$message" class="invalid ng-binding ng-hide" ng-bind="U2VydmljZVNlbGVjdGlvbkZvcm0.service_0.$message"></li>
</ul>
<ul class="djng-field-errors ng-hide" ng-show="U2VydmljZVNlbGVjdGlvbkZvcm0.service_0.$dirty"></ul>
<input id="id_service_0" name="service_0" ng-model="service_0" type="checkbox" class="ng-pristine ng-untouched ng-valid ng-empty">
</form>
I've tried doing things like $scope.$digest() but get [$rootScope:inprog] errors.
UPDATE
The $scope becomes aware of this field once it has been toggled. Now I just need to figure out a way to do this from the get go...

Related

AngularJs: Input value changes in display too using ng-model. I have tried ng-value and ng-bind too

<div class="form-group">
Name <input type="text" class="form-control" placeholder="item" ng-model="shoppingItem.itemName" required>
</div>
<div class="form-group">
Image URL <input type="url" class="form-control" placeholder="item" ng-model="shoppingItem.imgUrl" required>
</div>
<div class="form-group">
<button type="button" class="btn btn-success" ng-click="save()" >Success</button>
</div>
app.controller('recipebookController',function($scope,$routeParams,RecipeService,$location){
$scope.shoppingItems =RecipeService.shoppingItems;
$scope.rp="Route parameter value"+RecipeService.shoppingItems[0].itemName;
$scope.save = function(){
RecipeService.save($scope.shoppingItem);
$location.path("/");
}
});
<div class="col-xs-12">
<ul class="list-group">
<li ng-repeat="item in shoppingItems"class="list-group-item text-center clearfix">
<span style="font-weight:bold">{{item.itemName}}</span>
<img ng-src="{{ item.imgUrl }}" width="40" height="40"/>`
</li>
</ul>
</div>
When I enter save, the new data is saving row wise perfectly and displaying but when I re-enter new value into the input. The previously save value get changes as I type.
The issue that you're facing is that when you call RecipeService.save($scope.shoppingItem);, the RecipeService is saving the reference to your scope variable.
So, instead of assigning the variable directly, I might try doing something like this:
RecipeService.save(angular.copy($scope.shoppingItem));
This will create a new copy of the object referenced by $scope.shoppingItem and will allow you to edit one of those objects without affecting the other.

How to integrate the add function from html to angular js?

I have my add button in my index.html and I need to create a function in angularjs
controller. The select option in the code below needs to get the data from another table. All I need is when the [tag:add button] is clicked, it will be temporarily be added in the angular controller.
<div class="form-group">
<div class="col-md-12">
<div class="col-md-12"><label class="control-label">Board Member</label></div>
<div class="col-md-4">
<select class="form-control" ng-model="Board" ng-init="">
<option value=""> -- Select --</option>
</select>
</div>
<div class="col-md-8">
<button type="button" class="btn btn-success" ng-click=""><span class="glyphicon glyphicon-plus"></span>Add</button>
</div>
</div>
</div>
in the ng-click directive name your function like so ng-click="add()".
then in your controller define the add function:
$scope.add = function(){
//whatever your function needs to do
}

how to get selected value of ng-options inside ng-repeat in a form

I'm trying to get the selected value when clicking the submit button of a form which contain ng-repeat and the select generated by ng-options. But I can not reach the selected value, can you please take a look at my code and tell me what I'm I missing?
<form class="form-horizontal">
<!-- Options -->
<div class="product-page-options">
<div class="form-group clearfix" ng-repeat="option in product.options.data">
<label class="col-md-4 control-label pull-left">{{ option.name }}</label>
<div class="col-md-8">
<select class="form-control" ng-options="value.name for value in option.values.data" ng-model="selectedValue">
<option value="">Select {{ option.name }}</option>
</select>
</div>
</div>
</div>
<!-- Add to cart -->
<div class="product-page-cart">
<div class="product-quantity">
<input type="number" value="1" class="form-control input-sm">
</div>
<button class="btn btn-primary" type="submit" ng-click="add(selectedValue)">Add to cart</button>
I have tried to print the selected value by putting {{ selectedValue }} inside the ng-repeat div and it display perfectly as expected, however if I try to put it outside of the div then nothing print out.
The json data which i'm used to build the form here http://pastebin.com/nah3Pt5r
// Edit:
I just googled and found a fiddle doing like me: http://jsfiddle.net/DrQ77/ so I decided to modify the ng-model to selected[option.name] but the $scope.selected still show undefined.
// Edit 2:
Okay, problem solved by adding the $scope.selected = {}; in the controller.
Thank you for your time!
Your ng-options has an isolated scope. So inside the selectedValue is known, but outside it's not (as you state in your question).
Define a variable on your parent scope and assign that to your ng-model of your ng-options and you should be able to access that variable outside your ng-options.

Angular JS ng-show/ hide based on drop-down list selected value

in the following code I have one drop-down list (serviceSmallId) for type of service.
It is populated using model info.
There is a second field check-box which should only be visible when drop-down has a selected value of 'Weekly'. I am trying to use ng-show/ hide of angular.
I tried to search for possible solutions but no luck.
Can anyone please guide me what I am doing wrong.
<section id="scrubber-view" class="mainbar" data-ng-controller="scrubber as vm">
<section class="matter">
<div class="container">
<div>
<button class="btn btn-info" ng-click="vm.goBack()"><i class="fa fa-arrow-left"></i>Back</button>
<button class="btn btn-info" ng-click="vm.cancel()" ng-disabled="!vm.canSave"><i class="fa fa-undo"></i>Cancel</button>
<button class="btn btn-info" ng-click="vm.save()" ng-disabled="!vm.canSave"><i class="fa fa-save"></i>Save</button>
<span ng-show="vm.hasChanges" style="color:orange" class="dissolve-animation ng-hide"><i class="fa fa-asterisk"></i></span>
</div>
<div class="row">
<div class="widget wblue">
<div data-cc-widget-header title="{{vm.title}}" subtitle="{{vm.scrubber.scrubberId}}"></div>
<form class="form-horizontal">
<div class="form-group">
<label for="serviceSmallId" class="col-sm-2">Service</label>
<div class="col-sm-4">
<select class="form-control" id="serviceSmallId" ng-model="vm.scrubber.serviceSmallId"
ng-options="item.dataLookupId as item.description for item in vm.serviceSmalls | orderBy:['sortOrder','description']">
</select>
</div>
</div>
<div class="form-group" ng-show="vm.scrubber.serviceSmallId.value=='Weekly'">
<input class="form-control" type="checkbox" id="fullyFlanged" value="Bar" />
</div>
</form>
</div>
</div>
</div>
</section>
</section>
There probably is a more elegant "angular way" solution,
but I updated you code to work here - http://jsbin.com/tupisoriho/1/edit?html,js,output
Explanation of changes
Provided ng-show a value vm.checker
added ng-change to the select element and gave it a function checkerGo which tested to see if dropdown == 'weekly', if yes change vm.checker
Update
there is a more "angular way" - using expressions!
As per #Omri Aharon fiddle/comment below.
You don't need to get the value property because a ng-model don't hold the element but the value itself;
<div class="form-group" ng-show="vm.scrubber.serviceSmallId.value=='Weekly'">
must be
<div class="form-group" ng-show="vm.scrubber.serviceSmallId == 'Weekly'">
EDIT: In your case vm.scrubber.serviceSmallId will contain the ID and not the description Weekly. I suggest you to use ng-change directive to call a function in your controller that will find the item based on ID and set in the controller to be visible for ng-show.
<select class="form-control" id="serviceSmallId" ng-model="vm.scrubber.serviceSmallId"
ng-options="item.dataLookupId as item.description for item in vm.serviceSmalls | orderBy:['sortOrder','description']"
ng-change="vm.selectObj()">
vm.selectObj() will find and set the current selected object in the scope to an controller variable (ex.: vm.selectedItem) and:
<div class="form-group" ng-show="vm.selectedItem.description=='Weekly'">

Issue with ng-model and ng-repeat, duplicate forms

I have a page where multiple forms are created based on ng-repeat. Everything works fine until write something into the input and everything gets duplicated on all the other repeated forms input elements. I have used ng-model="Notify.message" which is nothing but object which takes the value from the input and sends to control on button submit and hence rest of the logic.
I am looking for when if one form is been filled, other forms should keep quite and shouldn't duplicate the values written in input text of form 1.
Here is the code:
<div data-ng-show="alluserposts.length > 0">
<div id="b{{userpost.id}}" data-ng-repeat="userpost in alluserposts" >
<div class="row" style="margin-left: -5px">
<form class="text-center" role="form" id=f1{{userpost.id}} name="userForm"
ng-submit="notify(userForm.$valid, userpost, apiMe)" novalidate>
<div class="row">
<div class="col-xs-8 col-md-4">
<div class="form-group">
<input data-container="body" data-toggle="popover" data-placement="top"
data-content="Any message which you would like to convey to post owner"
type="text" ng-model="Notify.message" data-ng-init="Notify.message=''"
id="u{{userpost.id}}"
placeholder="Enter a Message or Phone number" class="form-control"
required>
<p ng-show="userForm.name.$invalid && !userForm.name.$pristine" class="help-block">It is
required.</p>
<script>$(function () {
$("[data-toggle='popover']").popover();
});
</script>
<input type="hidden" ng-model="Notify.loggedInEmail"
ng-init="Notify.loggedInEmail = result.email"/>
<input type="hidden" ng-model="Notify.postId" ng-init="Notify.postId = userpost.id"/>
<input type="hidden" ng-model="Notify.destEmail"
ng-init="Notify.destEmail = userpost.userEmail"/>
</div>
</div>
<div ng-show="loginStatus.status == 'connected'" class="col-xs-4 col-md-2">
<button class="btn btn-primary" ng-disabled="userForm.$invalid || !userForm.$dirty"
type="submit">
Notify Post Owner
</button>
</div>
</div>
</form>
</p>
</div>
</div>
</div>
</div>
Issue fiddle - jsfiddle
Here you can when something is written in one input, other gets filled too :( . Also Notify is a Java mapped object and message is a variable inside it. Pls let me know how can this can be segragated!
You bind all of your inputs to same variable on $scope.
You must bind every text box to a distinct variable on $scope:
View:
<ul ng-repeat="post in posts">
<li>{{$index}}
<input type="text" ng-model="emails[$index]"/>
</li>
</ul>
Controller:
$scope.emails = [];
I am also at the starting phase of angularjs.
I have faced the same issue few days ago and resolved it by providing dynamic model name in ng-model like
<input type="text" ng-model="Notify[post.userEmail]" ng-init="Notify[post.userEmail] = post.userEmail" />
Working fiddle: Fiddle

Resources