2021-01-31 09:58:27 +01:00
import React from 'react' ;
2021-02-01 06:36:14 +01:00
import classNames from 'classnames' ;
2021-01-31 09:58:27 +01:00
import { Input , InputNumber } from 'antd' ;
import { FieldUpdaterFunc } from '../../../types/config-section' ;
2021-02-01 06:36:14 +01:00
// import InfoTip from '../info-tip';
2021-01-31 09:58:27 +01:00
import { StatusState } from '../../../utils/input-statuses' ;
2021-02-01 06:36:14 +01:00
import InputStatusInfo from './input-status-info' ;
2021-01-31 09:58:27 +01:00
export const TEXTFIELD_TYPE_TEXT = 'default' ;
export const TEXTFIELD_TYPE_PASSWORD = 'password' ; // Input.Password
export const TEXTFIELD_TYPE_NUMBER = 'numeric' ; // InputNumber
export const TEXTFIELD_TYPE_TEXTAREA = 'textarea' ; // Input.TextArea
export const TEXTFIELD_TYPE_URL = 'url' ;
export interface TextFieldProps {
fieldName : string ;
2021-01-31 10:38:20 +01:00
2021-01-31 09:58:27 +01:00
onSubmit ? : ( ) = > void ;
onPressEnter ? : ( ) = > void ;
className? : string ;
disabled? : boolean ;
label? : string ;
maxLength? : number ;
placeholder? : string ;
required? : boolean ;
status? : StatusState ;
tip? : string ;
type ? : string ;
value? : string | number ;
onBlur? : FieldUpdaterFunc ;
onChange? : FieldUpdaterFunc ;
}
export default function TextField ( props : TextFieldProps ) {
const {
className ,
disabled ,
fieldName ,
label ,
maxLength ,
onBlur ,
onChange ,
onPressEnter ,
placeholder ,
required ,
status ,
tip ,
type ,
value ,
} = props ;
// if field is required but value is empty, or equals initial value, then don't show submit/update button. otherwise clear out any result messaging and display button.
const handleChange = ( e : any ) = > {
const val = type === TEXTFIELD_TYPE_NUMBER ? e : e.target.value ;
// if an extra onChange handler was sent in as a prop, let's run that too.
if ( onChange ) {
onChange ( { fieldName , value : val } ) ;
}
} ;
// if you blur a required field with an empty value, restore its original value in state (parent's state), if an onChange from parent is available.
const handleBlur = ( e : any ) = > {
const val = e . target . value ;
if ( onBlur ) {
onBlur ( { value : val } ) ;
}
} ;
const handlePressEnter = ( ) = > {
if ( onPressEnter ) {
onPressEnter ( ) ;
}
2021-01-31 10:38:20 +01:00
} ;
2021-01-31 09:58:27 +01:00
// display the appropriate Ant text field
2021-01-31 10:38:20 +01:00
let Field = Input as
| typeof Input
| typeof InputNumber
| typeof Input . TextArea
| typeof Input . Password ;
2021-01-31 09:58:27 +01:00
let fieldProps = { } ;
if ( type === TEXTFIELD_TYPE_TEXTAREA ) {
Field = Input . TextArea ;
fieldProps = {
autoSize : true ,
} ;
} else if ( type === TEXTFIELD_TYPE_PASSWORD ) {
Field = Input . Password ;
fieldProps = {
visibilityToggle : true ,
} ;
} else if ( type === TEXTFIELD_TYPE_NUMBER ) {
Field = InputNumber ;
fieldProps = {
type : 'number' ,
min : 1 ,
2021-01-31 10:38:20 +01:00
max : 10 * * maxLength - 1 ,
2021-01-31 09:58:27 +01:00
onKeyDown : ( e : React.KeyboardEvent ) = > {
2021-01-31 10:38:20 +01:00
if ( e . target . value . length > maxLength - 1 ) e . preventDefault ( ) ;
2021-01-31 09:58:27 +01:00
return false ;
2021-01-31 10:38:20 +01:00
} ,
2021-01-31 09:58:27 +01:00
} ;
} else if ( type === TEXTFIELD_TYPE_URL ) {
fieldProps = {
type : 'url' ,
} ;
}
const fieldId = ` field- ${ fieldName } ` ;
2021-02-01 06:36:14 +01:00
const { type : statusType } = status || { } ;
2021-01-31 09:58:27 +01:00
2021-02-01 06:36:14 +01:00
const containerClass = classNames ( {
'textfield-container' : true ,
[ ` type- ${ type } ` ] : true ,
required ,
[ ` status- ${ statusType } ` ] : status ,
} ) ;
2021-01-31 09:58:27 +01:00
return (
2021-02-01 06:36:14 +01:00
< div className = { containerClass } >
2021-01-31 19:13:35 +01:00
{ label ? (
< div className = "label-side" >
< label htmlFor = { fieldId } className = "textfield-label" >
2021-02-01 06:36:14 +01:00
{ label }
2021-01-31 19:13:35 +01:00
< / label >
< / div >
) : null }
< div className = "input-side" >
< div className = "input-group" >
< Field
id = { fieldId }
className = { ` field ${ className } ${ fieldId } ` }
{ . . . fieldProps }
allowClear
placeholder = { placeholder }
maxLength = { maxLength }
onChange = { handleChange }
onBlur = { handleBlur }
onPressEnter = { handlePressEnter }
disabled = { disabled }
value = { value }
/ >
< / div >
2021-02-01 06:36:14 +01:00
< InputStatusInfo status = { status } / >
< p className = "field-tip" >
{ tip }
{ /* <InfoTip tip={tip} /> */ }
2021-01-31 19:13:35 +01:00
< / p >
2021-01-31 09:58:27 +01:00
< / div >
< / div >
2021-01-31 10:38:20 +01:00
) ;
2021-01-31 09:58:27 +01:00
}
TextField . defaultProps = {
className : '' ,
// configPath: '',
disabled : false ,
// initialValue: '',
label : '' ,
maxLength : null ,
placeholder : '' ,
required : false ,
status : null ,
tip : '' ,
type : TEXTFIELD_TYPE_TEXT ,
value : '' ,
onSubmit : ( ) = > { } ,
onBlur : ( ) = > { } ,
onChange : ( ) = > { } ,
onPressEnter : ( ) = > { } ,
} ;