how to access the index of a ng-repeat?
I have the following code:
<ion-item ng-repeat="item in items track by $index" href="#/tab/friend/$index">
foo
</ion-item>
then I click a item from the list I get to: http://localhost:8100/#/tab/friend/$index
But I want to get to e.g. http://localhost:8100/#/tab/friend/12
what did I wrong?
Angular variables are only recognized automatically within ng- attributes. To use those variables within regular html attributes, you must use double braces:
<ion-item ng-repeat="item in items track by $index" href="#/tab/friend/{{$index}}">
foo
</ion-item>
You have placed $index in the string and there is no way for angular to know that it's an expression. To make angular evaluate it, you need to use it as an expression e.g. {{ $index }}. Modify your href as
href="#/tab/friend/{{$index}}"
Related
I have this html code
<empty-list [hidden]="!emptylist" text="There is currently No User"</empty-list>
<div *ngFor="let userObser of userObservables">
<ion-item #emptylist *ngIf="userObser | async as user">
<h2>{{user.displayName}}</h2>
<h3>{{user.email}}</h3>
</ion-item>
</div>
I want to show the empty list if there is no user & hide it if there is at least one.
I know I can do it using a subscribe method,but I want to use async pipe also I need to unsubscribe each time I use a subscribe which is really not efficient.
My question is there a way I could create a local variable inside the ion-item the ntest test if it exists outside & therefore use it in the hidden input ? It's just a suggestion I can't really seem to make it work.
You can use a simple else inside the ngIf to display another template if the condition doesn't match:
<ng-container *ngIf="userObservables.length > 0; else emptyList">
<ng-container *ngFor="let user of userObservables">
<ion-item *ngIf="user | async as user">…</ion-item>
</ng-container>
</ng-container>
<ng-template #emptyList>
<empty-list>…</empty-list>
</ng-template>
Note that I also replaced your seemingly unnecessary div with a ng-container to avoid unnecessary DOM nodes.
As a side note to your own suggestion: template references cannot be accessed from outside the template boundary. Structural directives like *ngIf and *ngFor create their own template, so this becomes a boundary. That's why
<h2>{{ ref.innerText }}</h2>
<ng-container>
<span #ref>Hello, World</span>
</ng-container>
will work, but
<h2>{{ ref.innerText }}</h2>
<ng-container *ngIf="true">
<span #ref>Hello, World</span>
</ng-container>
won't work.
How does one force a directive to update if it nested in a ng-repeat which has a filter?
Input Box
<input type="text" class="name-search" ng-model="search.text">
HTML
<ul>
<li ng-repeat="user in users track by $index | filter:search">
<profile-photo user="user"></profile-photo>
<span>{{ user.name }}</span>
<li>
</ul>
As I type in the input box, the users filter properly but the profile-photo directive doesnt have the proper user.
Any help would be greatly appreciated!
Heres a dumbed down Plunker of my actual code. If you start typing, you will notice that it filters but the image doesnt update.
https://plnkr.co/edit/FWD2bFdIh7jQa5aqdkjrPlunker
your link's function code only executes once, when compiling the directive. After that, scope.photoUrl does not change even if you change the user, because you're not $watching the value. You can add a watch, or directly, use this in the template
ng-src="{{user.photoUrl}}"
I am trying to use ngIf within an ngFor but it's just breaking my code. Below is my code:
<ion-row *ngIf="{{i % 3}}===0" *ngFor="let category of categories; let i=index">
I need to check if the index mod 3 is equal to zero
You can overwrite your code like:
<ion-row *ngFor="let category of categories; let i=index">
<ng-container *ngIf="{{i % 3}}===0">
...
</ng-container>
</ion-row>
ng-container behaves the same as template but you can use common syntax like *ngIf and *ngFor
you can't put ngIf on the same component as ngFor
Angular disallows such construction
Using i before initializing it in ngFor will never work
If you *ngIf gets a false value the *ngFor would never be created in the first place - see point 1:-)
I am trying to limit an object coming in by filtering (because there will be an option to show all eventually), however I am running into issues when trying to limitTo and track by index. Here is the code :
<div ng-repeat="item in filter.values track by $index | limitTo:filterLimit" class="cengage-builder-result-filter-value" value="item" update-filter="updateFilter">
In the controller:
$scope.filterLimit = 5;
It's saying I have dupes in the angular error so I'm thinking the track by $index isn't working here. Can't seem to find a proper way to do this, could use some help. Thanks!
Filters, like limitTo, orderBy, etc... must come before track by, since they apply to the array source, rather than to the track by expression.
<div ng-repeat="item in filter.values | limitTo:filterLimit track by $index">
Try this
Use limitTo
before track by
<div ng-repeat="item in filter.values | limitTo:filterLimit track by $index" class="cengage-builder-result-filter-value" value="item" update-filter="updateFilter">
<div ng-repeat="(key,x) in selectedPoll.questions">
<p>{{x}}</p>
<p>{{key}}</p>
<canvas chart-directive data="arrayResult.{{key}}" id="{{ $index }}">
</canvas>
</div>
When i use {{key}} in global scope for chart-directive, {{ $index}} is not accessible, although when i delete {{key}} and leave just arrayResult, ng-repeat is working.
Explanation: i use id {{ $index }} which is searched by chart-directive for each x in ng-repeat, thanks to this i can create as many chart-directives as i need.
Then in order to everything work properly i have to pass proper dataset, each dataset for chart-directive has the same ending as {{ key }} of x in ng-repeat so for example:
data="arrayResult.q1 "
to make it dynamic i would like to switch it to:
data="arrayResult.{{ key }}
but when i add {{ key }} ng-repeat stop with one result which as i assume is happening because it cannot read id value of {{ $index }}
It is the first time i use key and $index with ng-repeat, and it is first time when i repeat custom directive, so i don't know if the problem is with repeating custom directives or rather wrong use of {{ key }} value.
Just when i added the question some solution came to my head, it could be that it is happening because in my custom directive my scope.data looks like this
scope: {
data:'='
},
So If I am right if somebody can tell me if it is possible and if it is how to make scope data open for expression like this "arrayResult.{{ key }} ??
Using # is only relevant if your chart data are strings.
You can keep the = of your directive, but you need to change:
data="arrayResult.{{key}}"
into this:
data="arrayResult[key]"
The curcly brackets will only work with a # scoping indeed, but you would get the string "arrayResult.q1" instead of the actual value of what is in arrayResult.q1, so = is the way to go.
See a snippet simulating it below:
angular.module("test", []).controller("test", function($scope) {
$scope.questions = {q1: "do you like apples?", q2: "do you like bananas?"};
$scope.arrayResult = {q1: true, q2: false};
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="test" ng-controller="test">
<div ng-repeat="(key,x) in questions">
<p>question: {{x}}</p>
<p>key: {{key}}</p>
<div>result: {{arrayResult[key]}}</div>
</canvas>
</div>
</div>