How to handle checkbox using json object in angularjs 4 - json

I had displayed below data in checkbox,
roomLists = {'4': {'name': 'Standard Room', 'typeID': '4', 'price': 100}, '5': {'name': 'Delux Room', 'typeID': '5', 'price': 100}}
this json object is retrieve using http. For testing purpose i have store it in roomlist.
Using pipe, data are getting display properly inside modal
<app-modal #modal1>
<div class="app-modal-body">
<div *ngFor="let room of roomLists | jsonPipe">
<label>
<input type="checkbox"/>{{room.name}}
</label>
</div>
</div>
but when I try to click on check box its not getting click. Is something i m missing in code.

Guess you are pairing checkbox with its own label, you can try give checkbox an id and and give label a for property which bind to the id of checkbox.
<div *ngFor="let room of roomLists | jsonPipe; let i = index;">
<label for="{{'checkbox' + i}}">
<input id="{{'checkbox' + i}}" type="checkbox"/>{{room.name}}
</label>
</div>

Related

Angular - Display different dropdown values based on condition

I am displaying data value as dropdown if below condition in html is met.
I would like to add another condition where on change of another dropdown which contains companies name I show data1value. For example if 1st dropdown (companies name) is changed toAmazonthen I only displaydata1` as its value
<dd>
<mat-select *ngIf="editMode"; else showData" [disabled]="!editMode"
[(ngModel)]="term.data" (ngModelChange)="recordModified.emit()">
<mat-option *ngFor="let tag of data" [value]="tag.value">{{tag.text}}</mat-option>
</mat-select>
<ng-template #showData>{{term.data}}</ng-template>
</dd>
data = [
{value: '1', text: 'Amazon'},
{value: '2', text: 'Google'},
{value: '3', text: 'Apple'},
data1 = [
{value: '1', text: 'Amazon'},
From what I can gather you want to access the data that has been selected by the dropdown, correct? You're close... check out this demo for a working version https://stackblitz.com/edit/angular-ivy-xmxqpg?file=src%2Fapp%2Fapp.component.ts

SQL Alchemy + WTForms FormField with default but don't insert empty data

So I have this wtforms:
ProfessionalAddress = FormField(AdressForm, default=lambda: ProfessionalAddress())
which links a sub form to my main form. To make sure the subform shows up, I added the default behavior that creates the empty ProfessionalAddress if the relationship doesn't exists.
But the problem is that in some cases I don't need this subform and it is not shown, hence no fields are submitted.
But when I call form = MainForm(formdata=request.form), as no fields are submitted, form.ProfessionalAddress is set to ProfessionalAddress() which generates an error as my DB doesn't allow empty entries there.
I could handle it at controller level (something like if form.ProfessionalAddress is empty: form.ProfessionalAddress = None) but it feels hacky, and I'd rather deal with this in the Form description.
How can I handle this case?
Can I differentiate the form generation case from the form population case?
Or can I populate the default value later (eg. at view generation time)?
Or is my approach completely wrong?
Hope it's clear!
Thanks
One way to do this would be to override the formfield's data property, forcing it to return None if all the formfield's fields' values are None (or whatever test you wish to apply).
class MyFormField(wtforms.FormField):
#property
def data(self):
data = {name: f.data for name, f in self._fields.items()}
if any(filter(lambda v: v is not None, data.values())):
return data
return None
class MyForm(wtforms.Form):
name = wtforms.StringField()
professional_address = MyFormField(AddressForm, default=ProfessionalAddress())
if we try it out
form = MyForm(data={'name': 'Alice'})
for f in form:print(f)
form = MyForm(formdata=MultiDict({'name': 'Alice'}))
form.validate()
print(form.data)
form = MyForm(data={'name': 'Bob', 'professional_address': ProfessionalAddress(line1='1 High Street', line2='Dullsville')})
for f in form:print(f)
form = MyForm(formdata=MultiDict([('name', 'Bob'), ('professional_address-line1', '1 High Street')]))
form.validate()
print(form.data)
we can see that the form is rendered as expected, and None is returned if the professional address fields are not populated.
<input id="name" name="name" type="text" value="Alice">
<table id="professional_address"><tr><th><label for="professional_address-line1">Line1</label></th><td><input id="professional_address-line1" name="professional_address-line1" required type="text" value=""></td></tr><tr><th><label for="professional_address-line2">Line2</label></th><td><input id="professional_address-line2" name="professional_address-line2" required type="text" value=""></td></tr></table>
{'name': 'Alice', 'professional_address': None}
<input id="name" name="name" type="text" value="Bob">
<table id="professional_address"><tr><th><label for="professional_address-line1">Line1</label></th><td><input id="professional_address-line1" name="professional_address-line1" required type="text" value="1 High Street"></td></tr><tr><th><label for="professional_address-line2">Line2</label></th><td><input id="professional_address-line2" name="professional_address-line2" required type="text" value="Dullsville"></td></tr></table>
{'name': 'Bob', 'professional_address': {'line1': '1 High Street', 'line2': None}}

AngularJs - Input text box is not populated by the initial value id

I really hope you can help me with this. I am having trouble showing the ID population the textbox when I modify the form.
Let me explain it to you in detail
This is my list:
myList = [{ 'id':100, 'name': 'test mission 1' },
{ 'id':102, 'name': 'test mission 2' },
{ 'id':103, 'name': 'test mission 3' },
{ 'id':104, 'name': 'test mission 4' },]
This is my HTML with a workable typeahead function.
<input type="text"
ng-model="selected"
typeahead="mission as mission.name for mission in myList | filter:{name:$viewValue} | limitTo:8"
name="mission_name"
disabled>
<input type="hidden"
name="mission_id"
ng-model="selected"
value="{{field.value}}">
so whatever name value you type from the textbox naming mission_name, the id of that name will automatically populate the textbox naming mission_id. This is already workable and this is not the real problem. Because the only value that I want to save to the database is the mission_id. Let me show you my controller first.
This is my controller
angular.module('actinbox.web').controller('TypeaheadCtrl_{{ field.id_for_label }}', function($scope) {
$scope.selected = "{{ mission.name }}";
$scope.myList = {{ Mission|safe }};
});
The problem is, when I want to modify this data and i go to the form, I can only see that mission_name is populated by the data, it must be because i put an initial value such as $scope.selected = "{{ mission.name }}". However in mission_id textbox, the initial value is also the same as the value of mission_name maybe bacause of ng-model. What I want to do is to see the mission_id value and not the mission_name value.
I hope my explanation is clear. I really need help to this.
Try chaning this
<input type="hidden"
name="mission_id"
ng-model="selected"
value="{{field.value}}">
to
<input type="hidden"
name="mission_id"
ng-model="selected1"
value="{{field.value}}">
Then in js
$scope.selected = "{{ mission.name }}";
$scope.selected1 = "{{ mission.id }}";
$scope.myList = {{ Mission|safe }};

What's the correct expression for the Angular-UI Typeahead directive?

I'm trying to get the name to show for each element, but I'm getting the same name for each element. Here's the code:
View:
<li class="list-group-item" ng-controller="MenuItemEditTypeaheadCtrl">
<input type="text" ng-model="selectedItem" typeahead="menuItem.name for name in menuItems | limitTo:3" class="typeahead">
</li>
JSON:
[{name: "Soda", price: "2.99"}, {name: "Chips", price: "0.99"}]
text=[{name: "Soda", price: "2.99"}, {name: "Chips", price: "0.99"}];
obj=JSON.parse(text);
Print obj using loop
obj[0].name will print "Soda"
obj[1].name will print "Chips"
This is the correct answer:
"menuItem.name for menuItem in menuItems | limitTo:5 | filter:{name:$viewValue}"
try like below
Script:
$scope.menuItems = [{name: "Soda", price: "2.99"}, {name: "Chips", price: "0.99"}];
HTML:
<li class="list-group-item" ng-controller="MenuItemEditTypeaheadCtrl">
<input type="text" ng-model="selectedItem" typeahead="menuItem.name for menuItem in menuItems | filter:$viewValue | limitTo:3 " class="typeahead">
</li>
Note: $viewValue corresponds to a value entered by a user
And if you want to tie your angular typeahead with a server then refer this below link
How to tie angular-ui's typeahead with a server via $http for server side optimization?

Knockout Clone Whole Item In foreach

I am trying to clone elements when clicking a button. I was trying to use ko.toJS. On page load it works fine, but when I want clone the items, it is unable to bind the items (like, value, Text, etc.).
Here is the HTML:
<div class="stockItems-inner" data-bind="foreach: StockItems">
<div data-bind="if: Type=='Input'">
<div class="stock_container_input">
<input type="text" data-bind="value: Value" />
</div>
</div>
<div data-bind="if: Type=='Radio'">
<div class="stock_container_control">
<div data-bind="foreach: Options">
<div class="stockLbl">
<input type="radio" data-bind="text: Text, checked:$parent.Value, attr:{'id':Id, 'name': $parent.Text, 'value': Value}" />
<label data-bind="attr:{'for':Id}, text: Text"></label>
</div>
</div>
</div>
</div>
</div>
<div class="addItem">
<button type="button" data-bind="click: CloneItem"><img src="images/add.png" alt="" /></button>
</div>
The View Model:
ConfigurationStockViewModel = function() {
var self = this;
this.StockItems = ko.observableArray();
this.ApplyData = function(data){
self.StockItems(data.Items);
}
this.CloneItem = function(StockItems){
self.StockItems.push(ko.toJS(StockItems));
};
};
When clicking the button, an error is thrown: Unable to process binding. I am using JSON data for binding.
Not exactly sure what end result you want without working code, but sounds like you want to clone the last item in array and add to array?
If so, I think you have an error - your add button click binding will never pass anything to the function you defined, since it is outside the foreach. You need something like this:
this.CloneItem = function() {
var toClone = self.StockItems()[self.StockItems().length - 1]
self.StockItems.push(toClone);
};
Here is a simplified example without radio buttons, etc:
http://jsfiddle.net/5J47L/