学习者问题:编码Typescript / React时,为什么需要使用单独的props文件?

时间:2019-11-21 08:34:55

标签: reactjs typescript sharepoint-online spfx

我正在学习(!)TypeScript,并且在开始学习简单方法后,在较小程度上进行了反应。

我对单独的道具和状态文件的需求感到困惑,特别是它们如何与父子组件一起使用以及父子如何利用它们。我认为我的主要问题是了解TypeScript以及如何使用道具和状态。

我正在创建一个看起来像这样的应用程序:

import * as React from 'react';
import styles from './Dibf.module.scss';
import { HashRouter as Router, Route } from 'react-router-dom';
import { Page1 } from './Page1/Page1';
import { Page2 } from './Page2/Page2';
import { Header } from './Header/Header';
import { Footer } from './Footer/Footer';
import { Product } from './Product/Product';

import { IDibfProps } from './IDibfProps';
import { escape } from '@microsoft/sp-lodash-subset';

export default class Dibf extends React.Component<IDibfProps, {}> {
  constructor(props) {
    super(props);
    this.state = {
      CurrentUserTitle: null,
      CurrentUser: null,
      CurrentUserGroups: null,
      CurrentUserID: null,
      CurrentUserEmail: null,
      FullName: null,
      UniId: null,
      FilteredItems: [],
      Author: null,
      CurrentUserRole: null,
      Items: [],
      DepartmentsList: [],
      SelectedDept: undefined,
      Id: null,
      JobRef: null,
      Title: null,
      JobTitle: null,
      DateOfBreach: null,
      DateOfDiscovery: null,
      IncidentDetails: null,
      PersonalData: null,
      FormStatus: null,     
      PhoneNo: null,
      Department: null,
      SubDepartment: null,
      LoggedInUser: null,
      LoggedInUserPPDefaultItems: [],
    };
  }
  public render(): React.ReactElement<IDibfProps> {
    return (
      <Router>
        <div>
          <h2>App</h2>

          <Header HOW WOULD I GET THIS CHILD FUNCTION TO UPDATE THE STATE OF ITS THIS PARENT?/>

          {/* The different screens will be re-rendered here */}

          <Route path="/screen1" component={Page1} />
          <Route path="/screen2" component={Page2} />
          <Route path="/products/:id" component={Product} />

          <Footer />
        </div>
      </Router>
    );
  }
}

因此您可以看到不同的子组件。 ,等等...

我将在每个这些子组件上具有结构UI字段和控件。 什么是最容易做到的?:

  1. 像上面一样,在Parent中拥有所有控件的状态,然后使用props和state接口文件以某种方式将控件中发生的任何更改传递到状态(使用处理程序功能将状态提升?)

  2. 还是为每个子组件设置了状态并在兄弟姐妹之间传递道具?单独的道具/状态界面文件在该实例中如何工作?

我了解如何使用React传递props / state,但我不了解TypeScript如何使用接口来实现。我猜这与类和渲染声明有关,但不确定。

我需要一些来自这里社区的帮助,因为我目前对此有点怀疑。想象一下,学习几个月后发现自己什么都不知道!

有人可以为我提供带有代码示例的简单说明,而不是提供链接。

谢谢

更新:我已经更新了代码-请查看带有请求的Header函数。请提供一个代码示例。

T

1 个答案:

答案 0 :(得分:1)

需要指出的是Typescript是鸭子类型的。这两个接口是等效的

interface PorpsOne{     
  caption:string     
} 

interface PropsTwo{     
  caption:string     
} 

鉴于这些接口,以下构造可以。

function userOne(item:PropsOne){return item.caption;} 
function userTwo(item:PropsTwo){return item.caption;} 


const item = {caption:"Item caption", other:42, properties:null}; 
userOne(item); 
userTwo(item); 

话虽如此,您可以定义期望与子组件多次使用的属性,每个组件文件一次。您也可以提取公用部分,一次定义,然后将其导入父级和每个子级组件文件中。

Typescript不执行任何操作来在父子之间传递状态,运行时javascript则执行。 Typescript可帮助您通过键入和检查这些类型来确保传递必要的信息

INHO,尝试提取共享状态并将其放入父级并使用(1)处理函数进行更新是一个很好的方向。

因此

  

我将如何获得此孩子的功能以更新其状态   父母?

interface HeaderCanChangeCurrentUser{
  onCurrentUserTitle(title: string): void;
}
//...can be a field of parent class instead of const in render
const onCurrentUserTitle:HeaderCanChangeCurrentUser["onCurrentUserTitle"] = (value:string)=>{this.setState({CurrentUserTitle:value});};
<Header onCurrentUserTitle={onCurrentUserTitle}/>

Typescript可帮助您确定组件所依赖的状态的哪一部分。

再次。不必将接口声明放在单独的文件中。声明也可以从组件文件中导出。但是,分开的东西还是可以提高可读性的,不是吗?毕竟这是个人和团队的喜好。

我也可以用另一种方式解释这个问题。打字稿会帮助我为子组件声明道具以更新父状态。那就是如果我有一个充满字段的接口,它将创建充满onXxx方法的“派生/依赖”接口来更改父状态。是的,它确实。

但是同样不能将这种解释与“单独的文件”部分联系起来。