如何在没有ngOnInit()的情况下在Angular中显示数据?

时间:2019-01-31 06:50:56

标签: angular ionic-framework ionic4

我在Ionic 4中有一个香烟柜台应用程序。此处的堆叠闪电:https://stackblitz.com/edit/ionic-8xrdgo。当用户按下计数器细分中的“添加一个”按钮时,我需要在历史记录细分中显示最新的消费数据。由于某些原因,需要重新加载应用程序才能在历史记录段中显示最新数据。

重现该问题:

  1. 启动存储中没有consumption的应用
  2. 单击“添加一个”按钮。新的消耗已成功添加到存储中。
  3. 再次单击“添加一个”按钮。现在应该更新现有的消耗量,但是由于某种原因没有更新。另外,历史记录段不会显示数据。
  4. 重新加载应用。
  5. 单击“添加一个”按钮。现在,现有消耗量已成功更新到存储中,并且消耗量显示在历史记录段中。

这里的问题是,必须重新加载应用程序才能将现有消耗量更新到存储并显示。

完整代码在这里:

home.page.html:

<ion-header>
  <ion-toolbar>
    <ion-segment [(ngModel)]="segment" color="dark">
      <ion-segment-button value="info">
        Info
      </ion-segment-button>
      <ion-segment-button value="counter">
        Counter
      </ion-segment-button>
      <ion-segment-button value="history">
        History
      </ion-segment-button>
    </ion-segment>
  </ion-toolbar>
</ion-header>

<ion-content padding>

  <div *ngIf="segment == 'info'">
    <h1 class="center">Cigarette pack info</h1>
    <ion-item>
      <ion-input placeholder="Price" type="number" [(ngModel)]="pack.price"></ion-input>
    </ion-item>
    <ion-item>
      <ion-input placeholder="Cigarette count" type="number" [(ngModel)]="pack.cigarettecount"></ion-input>
    </ion-item>
    <br>
    <ion-button expand="block" color="dark" (click)="savePack()">Save</ion-button>
  </div>

  <div *ngIf="segment == 'counter'">
    <h1 class="center">Consumption today</h1>
    <p class="center">{{ today.date }}</p>
    <p class="center">{{ today.consumption }}</p>
    <p class="center">{{ today.last_smoked }}</p>
    <ion-button expand="block" color="dark" (click)="addOne()">Add one</ion-button>
  </div>

  <div *ngIf="segment == 'history'">
    <h1 class="center">Recent consumption</h1>
    <ion-grid>
      <ion-row>
        <ion-col><b>Date</b></ion-col>
        <ion-col><b>Consumption</b></ion-col>
      </ion-row>
      <ion-row *ngFor="let history of histories">
        <ion-col>{{ history.date }}</ion-col>
        <ion-col>{{ history.consumption }}</ion-col>
      </ion-row>
      <ion-row>
        <ion-col>-{{ money_consumption_tostring  }} €</ion-col>
      </ion-row>
    </ion-grid>
  </div>

</ion-content>

界面:

export interface pack {
    price: number,
    cigarettecount: number
}

export interface consumption {
    date: string,
    consumption: number,
    last_smoked: string
}

home.page.ts:

import { Component } from '@angular/core';
import { pack } from '../pack.interface';
import { consumption } from '../consumption.interface';
import { ConsumptionService } from '../consumption.service';

@Component({
  selector: 'app-home',
  templateUrl: 'home.page.html',
  styleUrls: ['home.page.scss'],
})
export class HomePage {

  constructor(private service: ConsumptionService) { }

  segment: string = "info";
  pack: pack[] = [];
  today = {} as consumption;
  histories: consumption[] = [];
  price: number = 0;
  money_consumption: number = 0;
  money_consumption_tostring: string = "0";

  ngOnInit() {

    this.service.getConsumptions().then((data: consumption[]) => {
      if (data == null) {
        this.today.consumption = 0;
        this.today.date = new Date().toLocaleDateString();
        this.today.last_smoked = new Date().toLocaleTimeString();
      } else {
        for (let consumption of data) {
          if (consumption.date == new Date().toLocaleDateString()) {
            this.today = consumption;
          }
        }
      }

      this.service.getConsumptions().then((data: consumption[]) => {
        this.histories = data;
      })
    })

    this.service.getPack().then((data) => {
      if (data != null) {
        this.segment = "counter";
      }
    })

  }

  addOne = () => {
    this.today.date = new Date().toLocaleDateString();
    this.today.consumption += 1;
    this.today.last_smoked = new Date().toLocaleTimeString();

    this.service.getConsumptions().then((data: consumption[]) => {
      let consumptions = data;
      // at least one consumption found
      if (consumptions != null) {
        let current_exists = false;
        for (let consumption of consumptions) {
          // use current date
          if (consumption.date == this.today.date) {
            current_exists = true;
            consumption.date = this.today.date;
            consumption.consumption = this.today.consumption;
            consumption.last_smoked = this.today.last_smoked;

            // add current consumption to history
            for (let history of this.histories) {
              if (history.date == this.today.date) {
                history.date = this.today.date;
                history.consumption = this.today.consumption;
                history.last_smoked = this.today.last_smoked;
              }
            }

          }
        }
        // new date
        if (current_exists == false) {
          consumptions.push(this.today);
          this.histories.push(this.today);
        }
        this.service.saveConsumptions(consumptions);
      } else {
        // no consumptions found
        this.service.addConsumptions(this.today);
        this.histories = data;
      }
    })
  }

  savePack = () => {
    this.service.savePack(this.pack);
    this.segment = "counter";
  }

}

consumption.service.ts:

import { Injectable } from '@angular/core';
import { Storage } from '@ionic/storage';
import { pack } from './pack.interface';
import { consumption } from './consumption.interface';

@Injectable({
  providedIn: 'root'
})
export class ConsumptionService {

  constructor(private storage: Storage) { }

  getPack = () => {
    return new Promise((resolve, reject) => {
      this.storage.get("pack").then((pack) => {
        resolve(pack);
      })
    })
  }

  savePack = (pack: pack[]) => {
    this.storage.set("pack", pack);
  }

  getConsumptions = () => {
    return new Promise((resolve, reject) => {
      this.storage.get("consumption").then((kulutukset) => {
        resolve(kulutukset);
      })
    })
  }

  addConsumptions = (newconsumption: consumption) => {
    this.storage.get("consumption").then((data: consumption[]) => {
      let consumptions = data;
      let current_exists = false;
      if (consumptions == null) {
        consumptions = [{date: new Date().toLocaleDateString(), 
          consumption: 0, last_smoked: new Date().toLocaleTimeString()},
        ]
      }
      for (let consumption of consumptions) {
        // use current date
        if (consumption.date == newconsumption.date) {
          current_exists = true;
          consumption.date = newconsumption.date;
          consumption.consumption = newconsumption.consumption;
          consumption.last_smoked = newconsumption.last_smoked;
        }
      }
      // new date
      if (current_exists == false) {
        consumptions.push(newconsumption);
      }
      this.storage.set("consumption", consumptions);
    }
    )}

    saveConsumptions = (consumptions: consumption[]) => {
      this.storage.set("consumption", consumptions);
    }

}

2 个答案:

答案 0 :(得分:3)

了解页面/组件的生命周期在Ionic中的工作原理很重要;

  • 在放置所有组件之后,将在初始化所有其他组件之前调用构造函数;
  • 加载组件/页面时,
  • ngOnInit(OnInit Angular事件)称为 ONCE
  • 对于任何离子应用程序,都有大量的离子生命周期,例如“ ionViewDidLoad”,“ ionViewWillLoad”等,它们具有各种不同的行为,实际上可能满足您的需求

由于Ionic应用程序实际上将一页堆叠在另一页之上,以使移动应用程序的标准行为与后退按钮和所有按钮(在浏览器devtools中检查应用程序的结构并尝试打开多个页面)相匹配,因此正确的方法是以 ionViewDidLoad ionViewWillLoad 挂在离子生命​​周期上;每次加载视图,重新打开应用程序或导航到页面时,都会触发此事件。

在此处了解更多信息:https://blog.ionicframework.com/navigating-lifecycle-events/

答案 1 :(得分:1)

您可以在constructor(){}

中进行操作
data = [];
constructor(private storage: Storage) { 
  //write your code
  //for example:
  this.storage.get("pack").then((pack) => {
    this.data = pack;
  })
}