react学习

1,event是SyntheticEvent ,模拟出来DOM事件所有能力

2,event.nativeEvent是原生事件对象

3,所有事件,都被挂载到document上

4,和DOM事件不一样,和vue事件也不一样

 

label关联input用for

<form>
  <label for="male">Male</label>
  <input type="radio" name="sex" id="male" />
  <br />
  <label for="female">Female</label>
  <input type="radio" name="sex" id="female" />
</form>

在react中for是关键字,所以应htmlFor


  <label htmlFor="female">Female</label>
  <input id="female" value={this.state.sex} onChange={this.change}/>

一般情况setState是异步事件,

自己定义dom事件的时候setState是同步事件,比如setTimeout,document.body.addEventListener('click',()=>{this.setState(count:this.state.count+1)})

setTimeout=(()=>{
    this.setState({count:this.state.count+1})
},100)

react的非受控组件,在进行文件上传时候可能会用到

//在constructor里创建
this.fileInput = React.createRef()
/在组件上应用
<input defaultValue={this.state.name} ref={this.fileInput} />
<button onClick={this.alertName}>按钮</button>
//在方法alertName中可以获取
alertName=()=>{
    const elem=this.fileInput.current //通过ref获取Dom节点
    
}

portals使用场景(应对css兼容性的时候)

1,父组件设置了overflow:hidden

2,父组件z-index值太小

3,fixed需要放在body第一层级

ReactDOM.createPortal(
    <div class="app-root">{this.props.children}</div>,
    document.body
)

Context 提供了一种在组件之间共享此类值的方式,而不必显式地通过组件树的逐层传递 props。

const ThemeContext = React.createContext('light'); //light为默认值
class App extends React.Component {
  render() {
    // 使用一个 Provider 来将当前的 theme 传递给以下的组件树。
    // 无论多深,任何组件都能读取这个值。
    // 在这个例子中,我们将 “dark” 作为当前的值传递下去。
    return (
      <ThemeContext.Provider value="dark">{/*dark为动态值,如果不填就是创建时候的默认值light*/}
        <Toolbar />
      </ThemeContext.Provider>
    );
  }
}

// 中间的组件再也不必指明往下传递 theme 了。
function Toolbar() {
  return (
    <div>
      <ThemedButton />
    </div>
  );
}

//class的时候
class ThemedButton extends React.Component {
  // 指定 contextType 读取当前的 theme context。
  // React 会往上找到最近的 theme Provider,然后使用它的值。
  // 在这个例子中,当前的 theme 值为 “dark”。
  static contextType = ThemeContext;// 或者在class外写 ThemedButton.contextType = ThemeContext;
  render() {
    return <Button theme={this.context} />;
  }
}
//函数式编程的时候
function ThemedButton (){
    return(
        <ThemeContext.Consumer>
          {value => /* 基于 context 值进行渲染*/}
        </ThemeContext.Consumer>
    )
}

中级层级不需要而只有最后一级需要的时候,可以不用context

function Page(props) {
  const user = props.user;
  const userLink = (
    <Link href={user.permalink}>
      <Avatar user={user} size={props.avatarSize} />
    </Link>
  );
  return <PageLayout userLink={userLink} />;
}

// 现在,我们有这样的组件:
<Page user={user} avatarSize={avatarSize} />
// ... 渲染出 ...
<PageLayout userLink={...} />
// ... 渲染出 ...
<NavigationBar userLink={...} />
// ... 渲染出 ...
{props.userLink}

异步组件加载(官网上的代码分割),懒加载

使用之前:(静态加载)

import OtherComponent from './OtherComponent';

使用之后:(异步加载)

const OtherComponent = React.lazy(() => import('./OtherComponent'));

如果模块加载失败(如网络问题),它会触发一个错误。你可以通过异常捕获边界(Error boundaries)技术来处理这些情况,以显示良好的用户体验并管理恢复事宜

import React, { Suspense } from 'react';
import MyErrorBoundary from './MyErrorBoundary';

const OtherComponent = React.lazy(() => import('./OtherComponent'));
const AnotherComponent = React.lazy(() => import('./AnotherComponent'));

const MyComponent = () => (
  <div>
    <MyErrorBoundary>
      <Suspense fallback={<div>Loading...</div>}>
        <section>
          <OtherComponent />
          <AnotherComponent />
        </section>
      </Suspense>
    </MyErrorBoundary>
  </div>
);

fallback 属性接受任何在组件加载过程中你想展示的 React 元素。你可以将 Suspense 组件置于懒加载组件之上的任何位置。你甚至可以用一个 Suspense 组件包裹多个懒加载组件

 

shouldComponentUpdate默认返回true,父组件更新,子组件则无条件更新,所以如果要性能优化,则可用这个钩子进行数据的深比较(耗费性能)判断返回false阻止更新,需要配合“不可变值”(比如setState中添加数组的时候不要用push。可以用immutable.js全面拥抱不可变值)

const listnew=this.state.list.slice()
this.setState({
    list1:this.state.list.concat(100),//追加
    list2:[...this.state.list,100],//追加
    list3:this.state.list.slice(0,3),//截取
    list4:this.state.list.filter((item)=>item>100),//筛选
    list5:listnew,//其他操作
})
//不能直接对this.state.list 进行 push,pop,splice等

//对象
this.setState({
    obj1:Object.assign({},this.state.obj1,{a:100}),
    obj2:{...obj1,a:100}
})
//不能直接对this.state.obj1进行属性设置

浅比较,class组件用PureComponent,函数组件用memo

class Mouse extends React.PureComponent {
  // 代码......
}

//函数式
function MyComponent(){
    //代码
}
function areEqual(preProps,nextProps){
    //判断
}
export default React.memo(MyComponent,areEqual){
    //代码
}

高阶组件

//定义高阶组件
const HOCFactory = (Component) => {
    class HOC extends React.Component {
        //逻辑
        render(){
            return <Component { ...this.props } />
        }
    }
    return HOC
}

//用法
export default HOCFactory(WrappedComponent)

redux单相数据流

redux的action异步,1,redux-thunk,2,redux-promise,3,redux-sage

react-redux 主要有provider,connect

hash模式(默认),如 https://abc.com/#/user/10,中后台系统,pc端的,toB

history模式,如http://abc.com/user/10,需要server端支持,因此如无特殊要求选择前者,toC

动态路由path="/project/:id",可以匹配http://abc.com/project/100,id对应100,通过userParams获取到这个id,

跳转用Link,或者用history.push(),需要引入userHistory

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值