I am a beginner in AngularJS and I have an issue, here my code:
$scope.categories = [{
"id": 506,
"name": "test"
}, {
"id": 510,
"name": "aaa"
}, {
"id": 1,
"name": "bbb"
}, {
"id": 2,
"name": "ccc"
}, {
"id": 3,
"name": "eee"
}, {
"id": 4,
"name": "fff"
}];
$scope.contents = [{
"id": 0,
"categoryId": 506,
"title": "test1"
}, {
"id": 1,
"categoryId": 506,
"title": "test2"
}, {
"id": 2,
"categoryId": 506,
"title": "test3"
}, {
"id": 3,
"categoryId": 1,
"title": "test4"
}];
<div>
<label>
<input type="radio" name="category" ng-model="cc" ng-value="" checked/>all
</label>
<label ng-repeat="categoryItem in categories" ng-init="i= $parent">
<input type="radio" name="category" ng-model="i.cc" ng-value="{{categoryItem.id}}" />{{categoryItem.id}}
</label>
</div>
<ul>
<li ng-repeat="content in contents | filter:{categoryId: cc||undefined}">
<h3>id:{{content.categoryId}}</h3>
<p>{{content.title}}</p>
</li>
</ul>
I would like to be able to see all the items by selecting radio, in addition, I would like to first of them was always selected. Like right now it not work and I really don't know why.
Some issues/changes:-
Do not use interpolation with ng-value, i.e ng-value="{{categoryItem.id}}" should be ng-value="categoryItem.id". ng-value can just be an expression or a scope property that will be assigned to the ng-model.
Do not use ng-init or $parent on the view, they are not desired patterns to use. Instead use dot rule. define the filter object in the controller and set the property categoryId on the filterobject as the ng-model for the radio buttons.
<input type="radio" name="category"
ng-model="categoryFilter.categoryId" ng-value="categoryItem.id" />{{categoryItem.id}}
Just clear out the filter by setting categoryFilter to {} on click of all filter, and use ng-checked.
all
Just use the filter with the ng-repeat as follows:
<li ng-repeat="content in contents | filter:categoryFilter">
Demo
var app = angular.module('plunker', []);
app.controller('MainCtrl', function($scope) {
$scope.categoryFilter = {};
$scope.categories = [{
"id": 506,
"name": "test"
}, {
"id": 510,
"name": "aaa"
}, {
"id": 1,
"name": "bbb"
}, {
"id": 2,
"name": "ccc"
}, {
"id": 3,
"name": "eee"
}, {
"id": 4,
"name": "fff"
}];
$scope.clearFilter = function() {
$scope.categoryFilter = {};
}
$scope.contents = [{
"id": 0,
"categoryId": 506,
"title": "test1"
}, {
"id": 1,
"categoryId": 506,
"title": "test2"
}, {
"id": 2,
"categoryId": 506,
"title": "test3"
}, {
"id": 3,
"categoryId": 1,
"title": "test4"
}];
});
<!DOCTYPE html>
<html ng-app="plunker">
<head>
<meta charset="utf-8" />
<title>AngularJS Plunker</title>
<script>
document.write('<base href="' + document.location + '" />');
</script>
<link rel="stylesheet" href="style.css" />
<script data-require="angular.js#1.3.x" src="https://code.angularjs.org/1.2.23/angular.js" data-semver="1.3.9"></script>
<script src="app.js"></script>
</head>
<body ng-controller="MainCtrl">
<div>
<label>
<input type="radio" name="category1" ng-click="categoryFilter={}" ng-checked="!categoryFilter.categoryId" />all
</label>
<label ng-repeat="categoryItem in categories">
<input type="radio" name="category" ng-model="categoryFilter.categoryId" ng-value="categoryItem.id" />{{categoryItem.id}}
</label>
</div>
<ul>
<li ng-repeat="content in contents | filter:categoryFilter">
<h3>id:{{content.categoryId}}</h3>
<p>{{content.title}}</p>
</li>
</ul>
</body>
</html>
Sometimes its good to start over with your code, if you cant seem to find it.
Isn't there some filter help on the angularjs website?
Tut 9, Filters
Related
I have a JSON file with hierarchical data:
[
{
"id": 0,
"label": "Gap Inc.",
"value": "Gap Inc",
"checked": false,
"children": [
{
"id": 0,
"label": "Banana Republic",
"value": "Banana Republic",
"checked": false
},
{
"id": 1,
"label": "Gap",
"value": "Gap ",
"checked": false
},
{
"id": 2,
"label": "Hill City",
"value": "Hill City",
"checked": false
},
{
"id": 3,
"label": "Old Navy",
"value": "Old Navy",
"checked": false
}
]
},
{
"id": 1,
"label": "Home Depot",
"value": "Home Depot",
"checked": false,
"children": []
},
{
"id": 2,
"label": "TJX",
"value": "TJX Companies",
"checked": false,
"children": [
{
"id": 0,
"label": "TJ Maxx",
"value": "TJ Maxx ",
"checked": false
},
{
"id": 1,
"label": "Marshalls",
"value": "Marshalls",
"checked": false
},
{
"id": 2,
"label": "Home Goods",
"value": "Home Goods",
"checked": false
}
]
}
]
I am using it to create a set of nested HTML lists with checkboxes:
<ul class="list-unstyled">
<li *ngFor="let parent of accountList; let q = index">
<div class="form-check">
<input id="parent-{{q}}"
class="form-check-input"
type="checkbox"
[(ngModel)]="parent.checked"
(click)="selectChildren(parent, $event)"
[indeterminate]="selectedChildren.length">
<label for="parent-item" class="form-check-label">
{{parent.label}}
</label>
</div>
<ul class="list-unstyled pl-4">
<li *ngFor="let child of parent.children; let i = index;">
<div class="form-check">
<input id="child-{{i}}"
class="form-check-input"
type="checkbox"
[(ngModel)]="child.checked"
(click)="selectChild(child, $event)">
<label for="child-{{i}}" class="form-check-label">
{{child.label}}
</label>
</div>
</li>
</ul>
</li>
</ul>
What's supposed to happen
If you click a parent checkbox, it checks all the children.
If you click only one child, its parent is set to indeterminate.
What DOES happen
If you click a parent checkbox, it checks all the children.
If you click only one child, ALL parents are set to indeterminate.
I assume I screwed up something somewhere. I think I have mapped the indeterminate attribute to the length of any selected children (here selectedChildren instead of only the children of the given parent. Not sure how to fix that...
Here is the typescript:
selectedChildren = [];
selectChildren = function(data, event) {
const parentChecked = !data.checked;
data.children.forEach((child, key2) => {
child.checked = parentChecked;
});
};
selectChild = (data, event) => {
if (this.selectedChildren.indexOf(data.id) === -1) {
this.selectedChildren.push(data.id);
data.checked = true;
} else {
this.selectedChildren.splice(this.selectedChildren.indexOf(data.id), 1);
data.checked = false;
}
};
I have the following data structure thats coming from an API.
$scope.cityList = [{
"_id": {
"$oid": "584ebd7f734d1d55b6dd4e5e"
},
"cityName": "New York",
"region": "north",
"people": [
{ "id": 1, "name": "x" },
{ "id": 2, "name": "y" },
{ "id": 3, "name": "z" },
{ "id": 4, "name": "a" },
{ "id": 5, "name": "b" },
{ "id": 6, "name": "c" }
]
},
{
"_id": {
"$oid": "584ebd7f734d1d55b6dd4e5e"
},
"cityName": "New Jersey",
"region": "South",
"people": [
{ "id": 1, "name": "x" },
{ "id": 2, "name": "y" },
{ "id": 3, "name": "z" },
{ "id": 4, "name": "a" },
{ "id": 5, "name": "b" },
{ "id": 6, "name": "c" }
]
}]
I'm trying to setup two dropdowns:
the first one displays a list of the cityNames
the second displays the list of all people names from the selected city.
I also want to save the id of the selected user name into a variable.
I've tried this so far:
<select ng-model="city">
<option ng-repeat="city in cityList" value="{{city.cityName}}">{{city.cityName}}</option>
</select>
<select ng-model="selectedItem">
<optgroup ng-repeat="option in cityList | filter: city">
<option ng-repeat="x in option.people">{{x}}</option>
</select>
You should use ng-options:
<select ng-model="selectedCity"
ng-options="c as c.cityName for c in cityList">
</select>
<select ng-model="selectedPerson"
ng-options="p as p.name for p in selectedCity.people">
</select>
Demo on JSFiddle.
I have this code:
<!DOCTYPE html>
<html>
<head>
<title>Lists Test</title>
<script src="https://code.angularjs.org/1.1.1/angular.min.js"></script>
<script>
function Controller($scope) {
$scope.backupCountries = {
"id": "field10",
"items": [{
"id": "10",
"StateGroupID": "0",
"name": "United State"
}, {
"id": "2",
"StateGroupID": "1",
"name": "Canada"
}]
};
$scope.backupStates = {
"id": "field20",
"StateGroups": [{
"items": [{
"id": "1",
"name": "Alabama"
}, {
"id": "2",
"name": "Alaska"
}, {
"id": "3",
"name": "Arizona"
}, {
"id": "4",
"name": "California"
}]
},
{
"items": [{
"id": "201",
"name": "Alberta"
}, {
"id": "202",
"name": "British Columbia"
}, {
"id": "303",
"name": "Manitoba"
}, {
"id": "304",
"name": "Ontario"
}]
}]
};
$scope.Countries = $scope.backupCountries;
$scope.getStates = function () {
console.log($scope.selectedCountry);
return $scope.backupStates.StateGroups[$scope.selectedCountry].items;
};
//$scope.currentStates = $scope.backupStates.StateGroups[0];
/*$scope.$watch('currentStates', function(value, oldValue){
//alert(value);
//alert(JSON.stringify(value));
//$scope.currentStates = (value == "10") ? States.StateGroups[0] : States.StateGroups[1];
});*/
};
</script>
</head>
<body>
<div ng-app ng-controller="Controller">
<h2 class="page-title">Model</h2>
<div class="row-fluid">
<div class="span4">
<label for="cboGroup">Countries</label>
<select data-ng-model="selectedCountry">
<option value="">Please Select a Country</option>
<option ng-repeat='country in Countries.items' value='{{country.StateGroupID}}'>{{country.name}}</option>
</select>
</div>
<div class="span4">
<label for="cboItem">States</label>
<select data-ng-model="selectedState">
<option value="">Please select a state</option>
<option ng-repeat='state in getStates()'>{{state.name}}</option>
</select>
</div>
<div class="well">what I am trying to archive is that the items are changing each time the group changes.</div>
<div>Countries : {{Countries.items | json}}</div>
<div>States : {{getStates()}}</div>
</div>
What I have been struggling with is migrating this code to Angular 1.4.But I don't know what's wrong with my code or what to change in it. The code is working flawlessly in Angular 1.1.1 but when I change the angular source to a js with upper version, all goes black.
A couple of odd things stand out:
You can use ng-model, without the data-* prefix.
$scope.selectedCountry is not initialized anywhere.
need to connect your app with the ng-app directive: ng-app="my_app" id="ng-app"
you don't have a module or controller definition
My recommendation is to figure out which version of AngularJS starts to break your code and what the most recent one is that your code still works with. Then read the release docs and see what changes were made that may be breaking your code.
I have a list with items and have applied filter on those items by value from text box. I want to get new filtered list with parent and its children if parent has at least one filtered item.If doesn't, that parent should not be displayed.
For an example: If I enter "3D" in the text box I don't want to get "Day parts" and "Week parts" listed below as they don't have children anymore after filtering.
<div ng-controller="Ctrl">
<input type="text" data-ng-model="inputValue.name"/>
<ul data-ng-repeat="condition in conditions">
<div data-ng-click="setHeadingStatus(condition)">
<div>
{{condition.name}}
</div>
<li ng-repeat="item in condition.items | filter:inputValue">
<div class="custom-typeahead-list-title">{{item.name}}</div>
<div class="custom-typeahead-list-desc">{{item.description}}</div>
</li>
</div>
</ul>
function Ctrl($scope , $filter){
$scope.countryCode = 1;
$scope.conditions = [
{
"id": 1,
"name": "Experiences",
"expanded": false,
"items": [
{
"id": 1,
"name": "3D"
},
{
"id": 2,
"name": "Imax"
},
{
"id": 3,
"name": "D-Box"
},
{
"id": 4,
"name": "THX"
}
]
},
{
"id": 2,
"name": "Day parts",
"expanded": false,
"items": [
{
"id": 1,
"name": "Early Bird"
},
{
"id": 2,
"name": "Matinee"
},
{
"id": 3,
"name": "Last Night"
}
]
},
{
"id": 3,
"name": "Week parts",
"expanded": false,
"items": [
{
"id": 1,
"name": "Monday"
},
{
"id": 2,
"name": "Wednesday"
},
{
"id": 3,
"name": "Weekend"
}
]
}
]
}
Here is the example of it
http://jsfiddle.net/KJ3Nx/48/
You can put an ng-show on the div that displays each block, and set the expression to the filtered length;
<div data-ng-show="(condition.items | filter:inputValue).length > 0" data-ng-click="setHeadingStatus(condition)">
Updated fiddle
I'm currently taking an object and placing it into a select dropdown of 'Employees':
$scope.Employees = [{
"id": 1,
"name": "George",
"job": "Janitor"..
.. which populates some data depending on the selection. Works great! Here is my current fiddle:
http://jsfiddle.net/3Hgy7/2/
<select ng-model="selectedOption" ng-options="option.name for option in Employees"></select>
<br>
<br>
<p>ID: {{selectedOption.id}}</p>
<p>JOB: {{selectedOption.job}}</p><br><pre>{{selectedOption}}</pre>
From the controller you can also see a 'Vehicles' object:
$scope.Vehicles = [{
"id": 1,
"employee_id": 1,
"make": "Honda",
"model": "Civic"...
I'd like to be able to include this into my dropdown selection somehow. So when someone selects a certain employee, their vehicles would be listed. I'm really not sure how to go about doing this. I know you can take both objects into the ng-model and add some ng-options.
http://jsfiddle.net/3Hgy7/3/
<select ng-model="selectedOption.Vehicles" ng-options="option.make for option in Vehicles"></select>
..Though I'm pretty sure this isn't correct whatsoever. Any help would be greatly appreciated. Please let me know if I need to provide more info!
Thanks!
T
You can do it like so:
<div ng-controller="MyCtrl">
<select ng-model="selectedOption" ng-options="option.name for option in Employees"></select>
<br>
<br>
<p>ID: {{selectedOption.id}}</p>
<p>JOB: {{selectedOption.job}}</p>
<br><pre>{{selectedOption}}</pre>
<div>
<select class="form-control" ng-model="selectedVehicle" ng-options="v.make for v in Vehicles | filter:{employee_id: selectedOption.id}"></select>
</div>
Then your JavaScript as follows:
var myApp = angular.module('myApp', []);
function MyCtrl($scope) {
$scope.Employees = [{
"id": 1,
"name": "George",
"job": "Janitor"
}, {
"id": 2,
"name": "Frank",
"job": "Scientist"
}, {
"id": 3,
"name": "Julie",
"job": "Florist"
}, {
"id": 4,
"name": "James",
"job": "Teacher"
}];
$scope.selectedOption = $scope.Employees[0];
$scope.Vehicles = [{
"id": 1,
"employee_id": 1,
"make": "Honda",
"model": "Civic"
}, {
"id": 2,
"employee_id": 2,
"make": "BMW",
"model": "M3"
}, {
"id": 3,
"employee_id": 4,
"make": "Nissan",
"model": "Pathfinder"
}, {
"id": 4,
"employee_id": 2,
"make": "Jaguar",
"model": "XF"
}];
}
Edit - Working Fiddle