J.DD
J.DD

Reputation: 388

Create new array from exisiting properties

I have an object as such:

export var PROJECT: any = {
    id: "1",
    name: "Hunkemoller",
    teammembers: [
        {
            id: 1,
            name: "Sarah Johnson",
            firstname: "Sarah",
            role: "Manager"
        },
        {
            id: 2,
            name: "Christian Johnson",
            firstname: "Christian",
            role: "Employee"
        }

etc.

I'm making an app and I want to add a search element in it, so you can search for the different teammembers. I want to initialize all the properties 'name' out of every teammember. That's the only thing that needs to be filtered.

I've thought of 2 ways:

  1. Create a new Array with only the names of the project > teammembers in it.
  2. Just initialize the names. But I haven't succeeded with this.

Can you help me make the right choice and explain to me how I can succeed? I don't even now how to make a new Array out of the existing one. I was thinking something like this:

var teamMembers = project.teammembers.name();

But apart from that option, it would be the best if I could just use the name property out of the object.

I was this far (I'm using Ionic 2 / Angular 2)

<ion-searchbar (ionInput)="getTeammembers($event)" [(ngModel)]="searchQuery"></ion-searchbar>
<ion-list>
   <ion-item *ngFor="let teammember of project.teammembers">
       {{ teammember.name }}
   </ion-item>
</ion-list>

In my typescript file I have the following:

  initializeTeammembers() {
    this.project.teammembers;
  }

  getTeammembers(ev) {
    // reset teammembers back to all of the teammembers
    this.initializeTeammembers();

    // set val to the value of the searcbar
    let val = ev.target.value;

    // if the value is empty string, don't filter teammembers
    if (val && val.trim() != '') {
      this.project.teammembers.name = this.project.teammembers.name.filter((teammember) => {
        return (teammember.toLowerCase().indexOf(val.toLowerCase()) > -1);
      })
    }
  }

But it doesn't work. I get the error : Cannot read property 'filter' of undefined.

Is there someone who please could help me? Thanks in advance.

Upvotes: 0

Views: 89

Answers (4)

J.DD
J.DD

Reputation: 388

Eventually I succeeded. I started again from the beginning, from a hard-coded array to get the items from my existing object.

For anyone with the same problem, this is my final code:

HTML:

   <ion-searchbar (ionInput)="getNames($event)"></ion-searchbar>
   <ion-list>
      <ion-item *ngFor="let name of names">
         {{ name }}
      </ion-item>
   </ion-list>

Typescript:

export class Page1 {
    names;
}

constructor () {
    this.initializeNames();
}

initializeNames() {
    this.names = this.project.teammembers.map(function(item){ return item.name }); // Thanks a lot Amir for this !
  }

getNames(ev) {
    // Reset items back to all of the items
    this.initializeNames();

    // set val to the value of the searchbar
    let val = ev.target.value;

    // if the value is an empty string don't filter the items
    if (val && val.trim() != '') {
      this.names = this.names.filter((item) => {
        return (item.toLowerCase().indexOf(val.toLowerCase()) > -1);
      })
    }
  }

I think the project.teammembers.name was a bit of a problem. Now with the new variable of just 'names', it succeeded. Thanks a lot for your help guys!

Upvotes: 0

Dmitri Algazin
Dmitri Algazin

Reputation: 3456

or use underscore _.map() http://underscorejs.org/#map

var teamMembers = _.map(project.teammembers, function(item){ 
   return item.name 
});

Upvotes: 0

Thalaivar
Thalaivar

Reputation: 23632

It should not be this.project.teammembers.name and should just this.project.teammembers and then use teammebers.name in resulting filter

if (val && val.trim() != '') {
      this.project.teammembers.name = 
                    this.project.teammembers.filter((teammember) => {
        return (teammember.name.toLowerCase().indexOf(val.toLowerCase()) > -1);
      })
    }

Or you could try out something like this to filter the name...

this.project.teammembers.name = this.project.teammembers.filter(function(el) {
    return (el.name === val.toLowerCase());
}).map(function(el) {
    return el.firstname;
}).sort();

SO basically you are filtering through name and then if you want a new array with their firstnames in sorted order... you could do the map and sort

Upvotes: 1

Amir Popovich
Amir Popovich

Reputation: 29836

You can create a new different array using Array.prototype.map:

var teamMembers = project.teammembers.map(function(item){ return item.name });

var project = {
    id: "1",
    name: "Hunkemoller",
    teammembers: [
        {
            id: 1,
            name: "Sarah Johnson",
            firstname: "Sarah",
            role: "Manager"
        },
        {
            id: 2,
            name: "Christian Johnson",
            firstname: "Christian",
            role: "Employee"
        }
      ]
   };

console.log(project.teammembers.map(function(item){ return item.name }));

The better way is to create a pipe that will filter your results using Array.prototype.filter.

Upvotes: 1

Related Questions