【问题标题】:Angular2 : How to pass value through a form to another componentAngular2:如何通过表单将值传递给另一个组件
【发布时间】:2018-03-22 08:52:34
【问题描述】:

我是 Angular2 的新手,我想做一些简单的事情:

  1. 提交表单以进行订购。
  2. 通过外部 API 将订单保存到数据库中
  3. 在保留订单对象的同时进入支付页面

我的第一个问题:保存后如何将对象传递到其他页面?

我的第二个问题:我什至是以最好的方式做这整个“形式的事情”吗?

form.html

<form [formGroup]="orderForm" #formDir="ngForm" (ngSubmit)="submitForm(formDir.value)">
    [...]
</form>

form.component

submitForm(): void {
    this.orderService.saveOrder(this.order)
        .then(() => this.router.navigateByUrl('/payment', ['order', this.order]));
}

支付组件

order: Order;

constructor(route: ActivatedRoute) {
    route.queryParams.subscribe(params => {
        this.order = params['order'];
    });
}

【问题讨论】:

  • 你必须指定一个接收订单作为参数的路由。
  • 您可以使用@Input 或使用共享服务将值传递给其他组件。如果您分享您的 html 结构,我们可以提供更多帮助。

标签: javascript angular angular2-routing angular2-forms


【解决方案1】:

@omeralper 的评论是正确的,您需要使用服务来传递复杂的数据类型,例如对象文字,或您不想在 URL 中显示的任何数据,这就是 params 的情况。

数据服务

import { Injectable } from '@angular/core';

@Injectable() 
export class DataService {
  data: {[key: string]: any}; 
}

组件 X

import {Component} from '@angular/core'

import { DataService } from './data.service';

@Component() 
export class X {

  get data(): {[key: string]: any}{ 
    return this.dataService.data; 
  }

  set data(value: {[key: string]: any}) { 
    this.dataService.data = value; 
  } 

  constructor(public dataService: DataService) { } 

  submitForm(): void {
    this.dataService.set(this.order); // Store order for use by next component
    this.orderService.saveOrder(this.order)
      .then(() => this.router.navigateByUrl('/y'));
  }
}

组件 Y

import {Component} from '@angular/core'

import { DataService } from './data.service';

@Component() 
export class Y { 

  data: { [key: string]: any };

  get data(): {[key: string]: any}{ 
    return this.dataService.data; 
  } 

  set data(value: {[key: string]: any}) { 
    this.dataService.data = value; 
  } 

  constructor(public dataService: DataService) { }

  ngOnInit() {
    this.data = this.dataService.get(); // Route component loads and you retrieve the data
  }
}

您会想要加强服务,也许称它为RouteDataService,但这将允许组件间通信。

如果您已经拥有可用数据,您不想再提出请求。这样做一两次并没有什么坏处,但是随着您的应用程序的增长,您的策略会降低性能。

否则,我更喜欢响应式表单而不是模板驱动的表单,以保持控制器中的逻辑和模板的复杂性,但您没有做错任何事情,这只是一种偏好。如果您还没有检查过响应式表单,这是一个不错的介绍 tutorial 供您比较两者。

【讨论】:

    【解决方案2】:

    保存后如何将对象传递到其他页面?

    表单保存操作完成后,从API返回当前保存的订单对象,然后重定向传递order.id已保存在DB中。还要确保在路由定义的路由参数中提及order 参数。

    submitForm(): void {
        this.orderService.saveOrder(this.order)
            .then((savedOrderObj) => this.router.navigateByUrl('/payment', ['order', savedOrderObj.id]));
    }
    

    我什至是以最好的方式做这整个“形式的事情”吗?

    是的,这似乎是正确的。在导航到路由时,您正在传递 order(id) 参数。因此paymentComponent 组件可以根据传递给路由的order 参数检索该订单。

    您应该考虑将routeParams 订阅代码移动到ngOnInit 挂钩,因为构造函数不应该有任何启动逻辑。创建一个OrderService,它将完全负责检索order 数据。它可以有不同的方法,其中一种方法是根据 id 检索数据。

    constructor(private route: ActivatedRoute, private orderService: OrderService) {
    }
    ngOnInit() {
        this.route.queryParams.subscribe(params => {
            this.orderService.getOrderById(params['order']).subscribe(
               (order) => this.order = order
            );
        });
    }
    

    【讨论】:

    • @omeralper 我将永远相信数据库中保存的任何内容。我不喜欢太聪明。如果一个 ajax 调用能够为我提供更多的数据一致性,那么值得这样做(可能需要几毫秒)
    • 如果您的动态页面具有快速的页面转换,毫秒很重要。
    • @omeralper 你是认真的你还想这样做吗?在本地保持应用程序状态并取回它很好,但是如果我要获得数据一致性,等待 10-100 毫秒对我来说很重要。
    • 没关系*
    猜你喜欢
    • 2020-01-25
    • 1970-01-01
    • 2021-10-17
    • 2016-05-13
    • 1970-01-01
    • 2019-01-14
    • 1970-01-01
    • 1970-01-01
    • 2021-12-31
    相关资源
    最近更新 更多