TypeScript 3.0下react默认属性DefaultProps解决方案
ts和react的默认属性的四种解决方案
- Non-null assertion operator(非空断言语句)
- Component type casting(组件类型重置)
- High order function for defining defaultProps(高阶组件)
- Props getter function(Getter函数)
1、 非空断言语句
1、const color = this.props.color!;
2、this.props.onBlur ? this.props.onBlur(e): undefined;
2、组件类型重置
以通过匿名类创建组件,并将其分配给常量,我们将使用适当的道具类型将其转换为最终结果组件,同时保留实现中定义的所有“defaultProps”
3、高阶组件
globals.d.ts
declare type Omit<T, K> = Pick<T, Exclude<keyof T, K>>
在uitls中定义withDefaultProps
export const withDefaultProps = <P extends object, DP extends Partial<P> = Partial<P>>(
defaultProps: DP,
Cmp: React.ComponentType<P>
) => {
type RequiredProps = Omit<P, keyof DP>
type Props = Partial<DP> & RequiredProps
Cmp.defaultProps = defaultProps
return (Cmp as React.ComponentType<any>) as React.ComponentType<Props>
}
说明
使用上面或者下面的实现都可以
input组件为一个完整的例子:
import classnames from 'classnames';
import * as React from 'react';
import { withDefaultProps } from '../utils';
import './style/input.styl';
const defaultProps = {
type: 'text',
value: '',
disabled: false,
readonly: false,
maxlength: 60,
placehololder: '',
autofocus: false,
autocomplete: '',
clearable: false,
passShow: false
}
type DefaultProps = Readonly<typeof defaultProps>;
type InputInnerProps = {
prepend?: React.ReactNode;
append?: React.ReactNode;
className?: string;
style?: React.CSSProperties;
onChange?: (value: string) => void;
onBlur?: (e: React.FocusEvent<HTMLInputElement>) => void;
onFocus?: (e: React.FocusEvent<HTMLInputElement>) => void;
} & DefaultProps;
const InputState = {
isFocus: false,
inputValue: '',
open: false
};
type State = Readonly<typeof InputState>;
const Input = withDefaultProps(
defaultProps,
class extends React.Component<InputInnerProps, State> {
readonly state: State = InputState;
private inputRef: React.RefObject<any> = React.createRef();
getDerivedStateFromProps() {
this.setState({
open: this.props.passShow,
inputValue: this.props.value
})
}
private changeHander = (e: React.ChangeEvent<HTMLInputElement>):void => {
this.setState({
inputValue: e.target.value
})
this.props.onChange ? this.props.onChange(e.target.value) : undefined;
}
private handleFoucus = (e: React.FocusEvent<HTMLInputElement>):void => {
this.props.onFocus ? this.props.onFocus(e): undefined;
this.setState({
isFocus: true
})
}
private handleBlur = (e: React.FocusEvent<HTMLInputElement>):void => {
this.props.onBlur ? this.props.onBlur(e): undefined;
this.setState({
isFocus: true
})
}
private handleClear = ():void => {
this.setState({
inputValue: ''
})
this.inputRef.current.focus();
}
private handlePwdEye = ():void => {
this.setState({
open: !this.state.open
})
}
public render() {
const {
type,
disabled,
readonly,
autocomplete,
autofocus,
clearable,
passShow,
className,
style,
prepend,
append,
...restProps
} = this.props;
const {
isFocus,
inputValue,
open
} = this.state;
const inputCls = classnames('afo-input', className, {
'afo-input--active': isFocus
})
const inputType:string = type === 'password' && passShow ? 'text': type;
const showClear:boolean = clearable && inputValue && !readonly && !disabled ? true: false;
const showPwdEye:boolean = type === 'password' && passShow && !disabled ? true: false;
return (
<div className={inputCls} style={style}>
{
prepend ? <div className="afo-input__prepend">{prepend}</div> : ''
}
<input
className="afo-input__field"
ref={this.inputRef}
value={inputValue}
{...restProps}
type={inputType}
disabled={disabled}
readOnly={readonly}
autoComplete={autocomplete}
autoFocus={autofocus}
onFocus={(e) => this.handleFoucus(e)}
onBlur={(e) => this.handleBlur(e)}
onChange={(e) => this.changeHander(e)}
/>
{
append || showClear || showPwdEye?
<div className="afo-input__append">
{
showClear ? <div className="afo-input__clear" onClick={() => this.handleClear()}>
<i className="afo-wrong" />
</div> : ''
}
{
showPwdEye ?
<div className="afo-input__eye" onClick={() => this.handlePwdEye()}>
<i className={open ? 'afo-inupt__eye--visible' : 'afo-inupt__eye--invisible'} />
</div> : ''
}
{append}
</div> :''
}
</div>
)
}
}
)
export default Input;
4、Props getter function
条件类型映射的简陋工厂/闭包标识函数模式。
注意,我们使用了与withDefaultProps函数类似的类型映射构造,但我们不将defaultProps映射为可选的,因为它们在组件实现中是不可选的。
TypeScript 3.0下react默认属性DefaultProps解决方案的更多相关文章
- IE10-IE11在NET4.0下出现“__doPostBack未定义”解决方案
IE10在NET4.0下出现"__doPostBack未定义"的办法 参考文章: http://blogs.msdn.com/b/scott_hanselman/archive/2 ...
- React 学习(二) ---- props验证与默认属性
在上一节中, 我们提到了props, 组件之间数据的传递使用props. 我们调用组件时可以设置props, 组件内部通过props获取. 为了props 使用更加友好, React 提供了简单的验证 ...
- 关于div容器在ie6下默认高度不为0(存在默认高度)
最近做项目的时候遇到一个问题,相信很多人都遇到过,就是在测试兼容性的时候,在ie6下小于12px 的背景的高度不等于原高,或许这样说你可能不是很明白,那就举个例子吧! 如图所示: 锯齿状的背景图本来是 ...
- CDH 6.0.1 版本 默认配置下 HUE | happybase 无法访问 Hbase 的问题
第一个问题 HUE 无法直接连接到 HBase 在默认配置下 CDH 6.0.1 版本下的 HBase2.0 使用了默认配置 hbase.regionserver.thrift.compact = T ...
- React组件属性部类(propTypes)校验
React组件属性类型(propTypes)校验 Prop 验证 随着应用不断变大,保证组件被正确使用变得非常有用.为此我们引入propTypes.React.PropTypes 提供很多验证器 (v ...
- 在 Typescript 2.0 中使用 @types 类型定义
在 Typescript 2.0 中使用 @type 类型定义 基于 Typescript 开发的时候,很麻烦的一个问题就是类型定义.导致在编译的时候,经常会看到一连串的找不到类型的提示.解决的方式经 ...
- Vue.js 2.0 和 React、Augular
Vue.js 2.0 和 React.Augular 引言 这个页面无疑是最难编写的,但也是非常重要的.或许你遇到了一些问题并且先前用其他的框架解决了.来这里的目的是看看Vue是否有更好的解决方案.那 ...
- 使用Typescript重构axios(十五)——默认配置
0. 系列文章 1.使用Typescript重构axios(一)--写在最前面 2.使用Typescript重构axios(二)--项目起手,跑通流程 3.使用Typescript重构axios(三) ...
- TypeScript 2.0开启空值的严格检查
摘要:在编程过程成空指针是最常见的bug之一,但是在TypeScript中我们无法使用具体的类型来表示特定的变量不能为空!幸运的是,TypeScript 2.0 解决了这个问题. 本文分享自华为云社区 ...
随机推荐
- ILSVRC2014检测总结
ILSVRC 2014结束一段时间了.从下面的表格来看,基本都是RCNN的路子,但是这些牛队都做了改进.自己和人家比差的太远啊,努力. team results Spotlights and impr ...
- Vue nodejs商城项目-搭建express框架环境
1.express-project 搭建express框架环境 安装express generator生成器 通过生成器自动创建项目 配置分析 安装 cnpm i -g express-generat ...
- ES6初识-解构赋值
数组解构赋值 [a,b]=[1,2]; . 方法返回 function f(){ return [1,2] } let a,b; [a,b]=f();//a=1,b=2 function f1() ...
- SSI框架下,用jxl实现导出功能
SSI框架下,用jxl实现导出功能 先说明一下,这个是SSI框架下,前端用ExtJs,应用在一个企业级的系统中的导出功能,因为是摸索着做的,所以里面有一些代码想整理一下,如果有人看到了,请视自己的架构 ...
- lintcode_114_不同的路径
不同的路径 描述 笔记 数据 评测 有一个机器人的位于一个 m × n 个网格左上角. 机器人每一时刻只能向下或者向右移动一步.机器人试图达到网格的右下角. 问有多少条不同的路径? 注意事项 n和 ...
- cordforce Educational Codeforces Round 47 补题笔记 <未完>
题目链接 http://codeforces.com/contest/1009 A. Game Shopping 直接模拟即可,用了一个队列来存储账单 #include <iostream> ...
- 原生js获取页面中所有checkbox
var inputs = document.getElementsByTagName("input");//获取所有的input标签对象 var checkboxArray = [ ...
- 使用cookie登陆知乎
只是想说明一个问题,Cookie可以维持登录状态,有些网页当中,访问之后的cookie里面带有登陆账号,和登陆密码,这样可以使用cookie直接访问网页,如知乎,首先登录知乎,将Headers中的Co ...
- 工作中遇到的比较奇怪的一些sql(一些子查询)
在列中进行子查询 1.在一个表中有多个员工ID,比如一个下单员工,一个修改订单的员工,可以使用在列中进行子查询,具体如下: ( SELECT staff_name FROM sp_staff_basi ...
- 笔记-scrapy-请求-下载-结果处理流程
笔记-scrapy-请求-下载-结果处理流程 在使用时发现对scrpy的下载过程中的处理逻辑还是不太明晰,-写个文档温习一下. 1. 请求-下载-结果处理流程 从哪开始呢? engine.p ...