javascript - Errors upon Injecting services into my component in Angular 2 -
i working on app portfolio angular 2 have filtering functionality via checkboxes. these checkboxes apply name filtering lists of technologies i've used each project i've worked on. in app have functionality allows indicate project. app need keep track of number of likes each project receives. in code add service project component allows me not loose number of likes , filtered projects switch views router. in code have array of project objects, each take following form- new project( "web design business website", ["wordpress", "bootstrap","php","html5","css3"], 0 )
able filtering , favoriting functionality work if don't use service, need use 1 aformentioned reasons , when attempt import in service , use it, unable see template html on screen , following errors-
exception: error: uncaught (in promise): exception: error in :0:0 original exception: typeerror: cannot read property 'filter' of undefined
error context: [object object]
my project component code follows:
import { router_directives, routes } '@angular/router'; import { component, oninit } '@angular/core'; import { project } './project'; import { projectservice } './project.service'; @component({ selector: 'my-app', host: {class: 'dashboard'}, templateurl: 'app/app.component.html', providers: [projectservice] }) export class projectscomponent implements oninit { allprojects: project[]; constructor(private projectservice: projectservice) { this.updateselectedlist(); } getprojects(){ this.allprojects = this.projectservice.getprojects(); } ngoninit(){ this.getprojects(); } title: string = 'filter projects technology'; /* possible tech */ technologylist : array<any> = [ { name:"javascript", checked: true }, { name: "php", checked: true }, { name: "html5", checked: true }, { name: "css3", checked: true }, { name: "angularjs", checked: true }, { name: "backbonejs", checked: true }, { name: "knockoutjs", checked: true }, { name: "bootstrap", checked: true }, { name: "wordpress", checked: true }, { name: "photoshop", checked: true } ]; /* projects match selected tech */ matchedprojects: array<any> = [] /* checked items in list */ selectedtechnology: array<string> = []; favup(project): boolean { project.favup(); return false; } oninteractionevent(event: event) { var item = this.technologylist.find( (val) => val.name === event.target.value ); item.checked = !item.checked; this.updateselectedlist(); } updateselectedlist() { let checkednames = this.technologylist.filter( (val) => val.checked === true).map(n => n.name); this.matchedprojects = this.allprojects.filter(project => { return this.containsany(project.technologies, checkednames) }); } containsany(arr1, arr2) { for(var in arr1) { if(arr2.indexof( arr1[i] ) > -1){ return true; } } return false; }; }
my project class located in file import , follows:
export class project { name: string; technologies: array<any>; favs: number; constructor(name: string, technologies: array<any>, favs: number) { this.name = name; this.technologies = technologies; this.favs = favs || 0; } favup(): void { this.favs += 1; } }
my array of project objects located in file , follows:
import { project } './project'; /* projects worked on */ export var allprojects: project[] = [ new project( "web design business website", ["wordpress", "bootstrap","php","html5","css3"], 0 ), new project( "vocab immersion trainer app", ["angularjs","javascript","bootstrap","html5","css3"], 0) ];
my project service located in file import , follows:
import { injectable } '@angular/core'; import { allprojects } './all-projects'; @injectable() export class projectservice { getprojects() { return allprojects; } }
my template html project component follows:
<p> <a class="btn btn-large btn-primary" data-toggle="collapse" href="#collapseexample" aria-expanded="false" aria-controls="collapseexample"> {{title}} </a> </p> <div class="collapse" id="collapseexample"> <div class="card card-block"> <label *ngfor="let item of technologylist"> <input type="checkbox" value="{{item.name}}" [checked]="item.checked" (change)="oninteractionevent($event)"> {{ item.name }} </label> </div> </div> <h2>featured projects</h2> <div *ngfor="let project of matchedprojects" class="container"> <div class="row"> <div class="col-sm-4 col-sm-offset-1 card"> <img src="http://placehold.it/350x150" class="card-img-top img-fluid img-rounded center-block" data-src="..." alt="card image cap"> <div class="card-block text-xs-center"> <h4 class="card-title">project name: {{project.name}} </h4> <p class="card-text">some quick example text build on card title , make bulk of card's content. alot of text. adds length paragraph. adds bulk. had it. necessary example</p> <a class="btn btn-primary">see live site</a> </div> <p> {{ project.favs }} likes <a href (click)="favup(project)">like</a></p> </div> <div class="col-sm-6 text-xs-center"> <h2 >technology used</h2> <p>{{project.technologies}}</p> </div> </div> </div>
my previous project component code works doesn't retain data between views follows
import { router_directives, routes } '@angular/router'; import { component } '@angular/core'; /* import { suggestion, suggestionscomponent, suggestionsview } './suggestions.component'; */ export class project { name: string; technologies: array<any>; favs: number; constructor(name: string, technologies: array<any>, favs: number) { this.name = name; this.technologies = technologies; this.favs = favs || 0; } favup(): void { this.favs += 1; } } @component({ selector: 'my-app', host: {class: 'dashboard'}, templateurl: 'app/projects.component.html' }) export class projectscomponent { title: string = 'filter projects technology'; /* possible tech */ technologylist : array<any> = [ { name:"javascript", checked: true }, { name: "php", checked: true }, { name: "html5", checked: true }, { name: "css3", checked: true }, { name: "angularjs", checked: true }, { name: "backbonejs", checked: true }, { name: "knockoutjs", checked: true }, { name: "bootstrap", checked: true }, { name: "wordpress", checked: true }, { name: "photoshop", checked: true } ]; /* projects worked on */ allprojects = [ new project( "web design business website", ["wordpress", "bootstrap","php","html5","css3"], 0 ), new project( "vocab immersion trainer app", ["angularjs","javascript","bootstrap","html5","css3"], 0) ]; /* projects match selected tech */ matchedprojects: array<any> = [] /* checked items in list */ selectedtechnology: array<string> = []; favup(project): boolean { project.favup(); return false; } constructor() { this.updateselectedlist(); } oninteractionevent(event: event) { var item = this.technologylist.find( (val) => val.name === event.target.value ); item.checked = !item.checked; this.updateselectedlist(); } updateselectedlist() { let checkednames = this.technologylist.filter( (val) => val.checked === true).map(n => n.name); this.matchedprojects = this.allprojects.filter(project => { return this.containsany(project.technologies, checkednames) }); } containsany(arr1, arr2) { for(var in arr1) { if(arr2.indexof( arr1[i] ) > -1){ return true; } } return false; }; }
here github link working version of project before incorporation of service: portfolio application link