How to bind json object to angular material form - json

I'm currently making a simple form using angular framework with the json file given to me. Inside the json were some arrays and objects. Well, I successfully binded the json arrays. My problem now is I don't know how to do it with the json object. I cannot bind the columns stated in json file to my form, instead the number of columns was diplayed in the UI. I already tried using the ngFor but the error says ngFor only supports binding to iterables such as arrays. I'm actually new to angular and this angular material. Any help will be appreciated
Below is the form i am making. Numbers encircled in red supposed to be the columns.
This is the json file. json Object encircled in red was the column i want to bind in my form
This is my app.component.html. I do think this is where my mistake resides
this is what i mean for the columns. as you can see. item 1 and item 1A are in two columns. item 2 is only in one column

You don't need the colums field value. You can simply use display: flex for the <section>:
<section style="display:flex; justify-content: space-between;" class="section" *ngFor="let inputSection of inputs.sections">
<div class="section-content" *ngFor="let field of inputSection.fields; let i = index;">
[...]
</div>
</section>

Related

How to use .slice().reverse() in *ngFor with | keyvalue?

I often use .slice().reverse() in *ngFor to display elements in reverse order. But now I have a problem, because I also use | keyvalue. How to use .slice().reverse() with | keyvalue?
<div *ngFor="let order of orderData.order.slice().reverse() | keyvalue ">
Sum: {{order.value.sum}}
</div>
This solution works but I am getting an error:
I don't think that you issue is with the keyvalue pipe. Probably the orderData is still not loaded whenever you are trying to use it and order is undefined.
You can do optional chaining/safe navigation operator in templates and adding a ? checks to see if the item on the left side has this property and and if it does it just returns it, if it doesn't it returns undefined and in this case if order is undefined inside the pipe transform method as value you will get undefined and if it exists you will get your array.
<div *ngFor="let order of orderData.order?.slice()?.reverse() | keyvalue ">
Sum: {{order.value.sum}}
</div>
Or you can just check if orderData has the order array and then render using the ngIf directive.
I suggest that you don't do slice().reverse() inside the templates like this because on every change detection cycle you will be creating a new array and reversing it. It would be a good idea to create a new pure pipe called reverse that reverses the array only if the instance has changed because otherwise you might get in trouble when working with larger arrays. Also if you are working with larger arrays providing a TrackByFunction on the ngFor will also increase performance.
I think the problem is here orderData.order, is undefined. That's why it throwing that error. You can make sure orderData.order is present then iterate the list like the below.
Note: ng-container is just a wrapper and Angular doesn't put it in the DOM.
<ng-container *ngIf="orderData.order">
<div *ngFor="let order of orderData.order.slice().reverse() | keyvalue">
Sum: {{order.value.sum}}
</div>
</ng-container>
We can get the last entries of the array by specifying the number inside slice with reverse function.
<div *ngFor="let order of orderData.order?.slice(-10)?.reverse() | keyvalue ">
Sum: {{order.value.sum}}
</div>

How to add an offset to an index in a *ngFor angular directive?

I want to display some data from a json but i can't simply add an offset to the index and show all te data from a certain offset but get
ERROR TypeError: Cannot read property 'id' of undefinedand the text in the div doesn't appear.
I have already tried to directly add a fixed number in the html file and it works (see the code below). But when it comes to use a variable "offset" (type:number) from typescript that is supposed to be updated with an input, the return type becomes undifined and the error appears. I also tried to use a method in my typescript file instead of doing the addition in the html file, and return the new index but it doesn't work and show the error. I also tried to call the method using {{addition(i,offset)}} and put the result in a variable that I use as an index but it still showing the error.
For exemple, this html file is working fine :
<ng-container *ngFor="let article of data; let i = index">
<ng-container *ngIf="i<(nbElements)">
<div (click)="checkArticle(data[(i+3)].id)">
<p class="text-center"> {{data[(i+3)][dataKey]}}</p>
</div>
</ng-container>
</ng-container>
The div reacts to my click and the text appears.
However, this html file is not working, even if the offset is set as 3 (as the html above) using an input in the parent component :
<ng-container *ngFor="let article of data; let i = index">
<ng-container *ngIf="i<(nbElements)">
<div (click)="checkArticle(data[(i+offset)].id)">
<p class="text-center"> {{data[(i+offset)][dataKey]}}</p>
</div>
</ng-container>
</ng-container>
The error appears.
The offset (type:number) is defined in my typescript file this way, and is changed by the parent component and can easily be displayed by the child component using console.log(offset):
export class AppColumnComponent implements OnInit {
#Input() offset : number ;
I expect the output to be texts showing the articles of my data json, but as I change the offset using an input like that data[(i+offset)] the result is an error, maybe it's impossible to use an other index using an other variable that a fixed number ?
Thank you for your support, it's my first post on stackoverflow i hope i did it well ! :)
If you want to make a pagination component, you should not rely solely on your HTML and some bindings.
Your component should have an "advanced" logic, in the sense that it should be able to know when it reaches the end/start of the collection (among other things).
Basically, this goes as follow :
Get the full collection (let's say 100 items)
Splice it to your item per page number (let's say 10, so results range is 0-10)
Test if items exist before the range
Test if items exist after the range
Allow/block page changing based on those variables.
This leaves you with
1 variable for the collection
1 variable (or 1 pipe) for the subset of the collection
1 variable for the items per page number
1 variable for the offset
2 booleans to disable pagination buttons.
Try working with this, and if you still have issues, then please provide a stackblitz with what you have tried !
You are accessing an index out of bounds.
data[(i+offset)] will be undefined for the last offset amount of elements in your data array so you are basically trying to do undefined.id which leads to your error.
You should change your method signature to only recieve the index as parameter and handle that case in your component.ts file

Return value from Object Array in Angular 7

I am relatively new to Angular, but I have a lot going on. Let me explain. I have an array of objects and a successful service running as shown below.
array of Objects
I have a input created as a search that is using the ngx-bootstrap TypeAheadModule so I can show typeahead values in the search. This is successful if I use a hard coded string array.
The html markup for the component shown below based on that ngx-bootstrap documentation.
<input [(ngModel)]="selected"
[typeahead]="points"
class="form-control">
This [typeahead] attribute looks to only accept a string array.
So here is my issue. I have an array of objects from my service, but I only need the name value from each object to fill what will become a string array for my search. I have been all over the internet looking for the best way to retrieve just a value from my array. I feel like I am missing some extremely simple.
Below is where I currently left it. I have my api call for points loading into a point array until I can figure out how to access the values inside the array.
points: Point[] = [];
this.service.getPoints().subscribe(response=> {
this.points = response as Point[]
});
This current returns [Object Object] in my TypeAhead. How can I access the values into my array and return them as a string array?
Thanks everyone!
try this.. I think you missed a div with ngFor
<div *ngFor="let point as points; let i of index">
<input [(ngModel)]="point[i]"
[typeahead]="point"
class="form-control">
</div>
your trying to print points array directly, I hope this approach will solve your issue.
I missed a small section on the ngx-bootstrap documentation. There is an additional attribute 'typeaheadOptionField' that lets you select the field out of a more complex object array.

Nested ng-repeat with attribute from parent ng-repeat

I have a JSON object (tbls) which contains an array called sections. This array contains titles (n) and IDs (viewid) of "rooms" that are also a part of the JSON object. This means you can do tbls.[roomid] and get the array that contains the objects of each room. I have a hard time making this work in Angular.
It was built this way because it makes it easy to work with when it comes to UITableViews in iOS (where it's implemented and works). Therefore I cannot change the data. I tried below solution, but that gives me an error. Is there an effective way to do this in Angular?
<tbody data-ng-repeat="section in tbls.sections">
<tr>
<td>{{::section.n}}</td>
</tr>
<tr data-ng-repeat="table in tbls.{{section.viewid}}">
<td>{{::table.n}}</td>
</tr>
</tbody>
JSON JSFiddle: https://jsfiddle.net/Lu2ocqku/
Edit: removed tableObj as it's not relevant to the question and doesn't match data example exactly. Same logical problem though.
Edit: Since I asked this question I have changed it to be properly nested with an array of sections containing what is in that section as well. Don't do what I did in this question, originally.
You just need to use standard [] javascript object syntax:
<tr data-ng-repeat="table in tbls[section.viewid]">

How to use item renderer to view multiple fields?

Our app contacts the server, and get a json based array, each item has:
First_Name
Last_Name
Image_Url
So, how to use the item renderer so that we can use custom data template to view name and image?
Also, can we have access to the json item being rendered from inside the renderer code?
Any examples would be highly appreciated.
http://help.adobe.com/en_US/flex/using/WS77c1dbb1bd80d3836ecbb5ec129ec77b1e1-8000.html
just above the 'Controlling the background display of an item renderer' section, there is a custom itemrenderer example, you can use it.
Find below link to add custom item renderer
http://www.adobe.com/devnet/flex/videotraining/exercises/ex4_03.html