【问题标题】:Access objects inside array Angular2访问数组 Angular2 中的对象
【发布时间】:2017-06-12 13:43:24
【问题描述】:

当我尝试访问数组内的对象时遇到问题。这是我的代码:

import { Component, OnInit } from '@angular/core';
import {FirebaseService} from '../../services/firebase.service';
import { AngularFire, FirebaseListObservable, FirebaseObjectObservable } from 'angularfire2';
import {Router, ActivatedRoute, Params} from '@angular/router';
import * as firebase from 'firebase';
import { Observable } from 'rxjs';
import { FlashMessagesService } from 'angular2-flash-messages';

@Component({
  selector: 'app-search',
  templateUrl: './search.component.html',
  styleUrls: ['./search.component.css']
})
export class SearchComponent implements OnInit {

  listings:any;
  search:any;
  imageUrls: any = [];
  images:any;
  myimage:any;
  count:any;
  constructor(
    private firebaseService: FirebaseService,
    private router:Router,
    public af:AngularFire,
    private route:ActivatedRoute,    
    private flashMessage:FlashMessagesService) {
    
    this.firebaseService.getListings().subscribe(listings => {
      this.listings = listings;
      this.count = listings.length;
    });  
  }
  ngOnInit() {   

    this.firebaseService.getListings().subscribe(listings => { 


      this.listings = listings;
      for(var i = 0;i<this.listings.length;i++){
        this.getImageUrl(listings[i].$key);
      }

      console.log(this.imageUrls);
      console.log(this.imageUrls[1].ImageUrl);
    });  
  }
  searchProps(){    
    this.firebaseService.getListingsByTitle(this.search.toLowerCase()).subscribe(listings => { 
      this.listings = listings;
    });
  }

  getImageUrl(prodid){
    this.imageUrls = []; 
    this.firebaseService.getListingImages(prodid).subscribe(images => { 
      this.images = images[0];
      let image = images[0];
      let storageRef = firebase.storage().ref();
      let spaceRef = storageRef.child(image.path);
      storageRef.child(image.path).getDownloadURL().then((url) => {
        // Set image url
        this.imageUrls.push(new ImageUrl(image.$key,url));        
      }).catch((error) => {
        console.log(error);
      });        
      });
  }

}
export class ImageUrl {
  url: string;
  id:string;
  constructor(_id:string,_url: string) {
     this.url = _url
     this.id = _id;
  }
}

我的控制台日志显示了这一点,但我无法访问 this.imageUrls[0]:

我想访问 this.imageUrls[0] 并获取 url 但显示“未定义”我不知道为什么我不能这样做。请如果有人可以帮助我解决这个问题,我在这里太累了。

编辑 2017 年 6 月 13 日

在@JesúsPallares 的帮助下,现在总是显示相同的图像。现在我想为每个列出图像。我在这里粘贴我的前端代码:

    <div class="col-md-4" *ngFor="let listing of listings  | orderby:'!$key'"  >
        <div class="card">
            <div class="card-image">
                <img class="img-responsive" [src]="imgSelected">

                <span class="card-title">{{listing.title}}</span>
            </div>
            
            <div class="card-content">
                <p>Cards for display in portfolio style material design by Google.</p>
            </div>
            
            <div class="card-action">
                <a [routerLink]="['/listing/'+listing.$key]">+ Info</a>
                <a [routerLink]="['/listing/'+listing.$key]">Contacto</a>
            </div>
        </div>
    </div>

【问题讨论】:

  • ... this but i can't access to this.imageUrls[0]: How to Ask 和minimal reproducible example 以帮助澄清您的问题。
  • 也许可以试试 console.log(this.imageUrls[1]);
  • @Igor 说未定义。我编辑了帖子。谢谢。
  • @Rabolf 说未定义
  • 这是How do I return the response from an asynchronous call? 的副本。您正在调用 getImageUrl,它执行异步调用并进行进一步处理以添加图像 url,但对该方法的调用是同步的,然后假定图像 url 立即可用。通读此副本,以更好地了解在处理异步调用(如 http 调用)时如何编写代码。

标签: angular


【解决方案1】:

您必须使“getImagUrl”函数同步。例如,您可以通过使用主题来做到这一点:

import {Subject} from 'rxjs';

imgSelected: any;

ngOnInit() {   
    this.firebaseService.getListings().subscribe(listings => { 
      this.listings = listings;
      for(var i = 0;i<this.listings.length;i++){
        this.getImageUrl(listings[i].$key).subscribe(isObtained => {
          if (isObtained) {
            this.imgSelected = this.imageUrls[0].url;
          }
        });
      }
    });
 }

getImageUrl(prodid): Subject<boolean> {
    let subject: Subject<boolean> = new Subject<boolean>();
    this.imageUrls = []; 
    this.firebaseService.getListingImages(prodid).subscribe(images => { 
      this.images = images[0];
      let image = images[0];
      let storageRef = firebase.storage().ref();
      let spaceRef = storageRef.child(image.path);
      storageRef.child(image.path).getDownloadURL().then((url) => {
        // Set image url
        this.imageUrls.push(new ImageUrl(image.$key,url));
        subject.next(true);
        subject.complete();
      }).catch((error) => {
        subject.next(false);
        subject.complete();
        console.log(error);
      });        
    });
    return subject;
}

一个图像标签:

<img class="img-responsive" [src]="imgSelected">

使用 ngFor:

<img *ngFor="let img of imageUrls" class="img-responsive" [src]="img.url">

ngOnInit 更新:

ngOnInit() {
    this.firebaseService.getListings().subscribe(listings => {
      let listingsLength = listings.length;
      let count: number = 0;
      let subject: Subject<any> = new Subject<any>();
      subject.subscribe(finish => {
        listings.forEach(list => {
          list.url = this.imageUrls.find(img => img.id === list.$key).url;
        });
        this.listings = listings;
      });
      for (let i = 0; i < listingsLength; i++) {
        count++;
        this.getImageUrl(listings[i].$key).subscribe(isObtained => {
          if (count === listingsLength) {
            subject.next('complete');
            subject.complete();
          }
        });
      }
    });
 }

HTML 代码:

<div class="col-md-4" *ngFor="let listing of listings  | orderby:'!$key'"  >
    <div class="card">
        <div class="card-image">
            <img class="img-responsive" [src]="listing.url">

            <span class="card-title">{{listing.title}}</span>
        </div>

        <div class="card-content">
            <p>Cards for display in portfolio style material design by Google.</p>
        </div>

        <div class="card-action">
            <a [routerLink]="['/listing/'+listing.$key]">+ Info</a>
            <a [routerLink]="['/listing/'+listing.$key]">Contacto</a>
        </div>
    </div>
</div>

【讨论】:

  • 您好,感谢您的回复。我试试你说的但我无法访问说:TypeError:无法读取未定义的属性'ImageUrl'。所以我这样做:`console.log(this.imageUrls[0].url); this.listings[0].src = this.imageUrls[0].url; ` 我得到了第一个图片 url。如果我做 console.log 在我的 chrome 控制台上显示四倍的 url。
  • 对不起,我刚刚在 ngOnInit 中更正了如何正确访问对象。再次查看订阅“getImageUrl”的内容。 =)
  • 我想这样做: 在我的前端(稍后我将更改 0 为 $ index) 但说:原始异常:无法读取未定义的属性“url”。我不知道为什么。你有想法吗?
  • 啊,好吧。我刚刚用解决方案编辑了答案。希望这可以帮助你。
  • 现在总是显示相同的图像。我如何为每个列表做这个动态?我用完整的前端代码编辑我的帖子。请检查一下 :)。感谢您的帮助。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-03-30
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多