# Cascader 级联选择器

- 来源：[E10 UI 组件库](https://www.e-cology.com.cn/ui/cascader/freepass)
- 平台：PC
- 维护者：屈正巍
- 设计稿：http://pd.e-cology.com.cn/pd/E10/interface/e10xiaoguotu/PC/E10zjys/#s39
- Issue：http://gitlab.ecology10.cn/FRONTEND/weapp-ui/-/issues?state=all&search=[Cascader]

## 代码演示

### 基础用法

当一个数据集合有清晰的层级结构时，可通过级联选择器逐级查看并选择

```jsx
import { Component } from "react";
import { constants, Cascader, Button, CascaderOptionType, CascaderValueType } from "@weapp/ui";
import { options } from '../mock';

const prefixCls = `${constants.uiPcClsPrefix}-demo-cascader`;

type CascaderProps = {}
type CascaderState = {
  value: CascaderValueType,
}
export default class CascaderDemo extends Component<CascaderProps, CascaderState> {

  constructor(props: CascaderDemo) {
    super(props)
    this.state = {
      value: ['hubei', 'wuhan', 'guanggu'],
    }
  }

  onChange = (value: CascaderValueType, selectedOptions?: CascaderOptionType[]) => {
    console.info('value', value)
    console.info('selectedOptions', selectedOptions)
  }
  onValueChange = (value: CascaderValueType, selectedOptions?: CascaderOptionType[]) => {
    console.info('value', value)
    console.info('selectedOptions', selectedOptions)
    this.setState({ value })
  }
  reset = () => this.setState({ value: [] })

  render() {
    return (
      <div className={prefixCls}>
        <p>基础用法</p>
        <Cascader
          options={options}
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>禁用</p>
        <Cascader
          options={options}
          defaultValue={['hubei', 'wuhan', 'guanggu']}
          disabled
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>禁用（同步weapp-ui的input）</p>
        <Cascader
          options={options}
          defaultValue={['hubei', 'wuhan', 'guanggu']}
          disabled
          disabledUseUIInput
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>只读</p>
        <Cascader
          options={options}
          defaultValue={['hubei', 'wuhan', 'guanggu']}
          readOnly
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>受控</p>
        <div style={{ display: 'flex' }}>
          <Cascader
            width={200}
            value={this.state.value}
            options={options}
            onChange={this.onValueChange}
          />
          &nbsp;
          <Button type={'primary'} size={'small'} onClick={this.reset}>重置</Button>
        </div>
        <br />
        <br />
        <p>受控不更新值</p>
        <Cascader
          width={200}
          value={['hubei', 'wuhan', 'guanggu']}
          options={options}
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>hover触发子菜单</p>
        <Cascader
          width={200}
          expandTrigger={"hover"}
          options={options}
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>自定义分隔符</p>
        <Cascader
          width={200}
          options={options}
          onChange={this.onChange}
          split={'#'}
        />
      </div>
    )
  }
}
```

### 处理数据

数据禁用、自定义数据key、空数据处理等

```jsx
import { Component } from "react";
import { constants, Cascader, CascaderOptionType, CascaderValueType, CascaderFieldNamesType } from "@weapp/ui";
import { options } from '../mock';

const prefixCls = `${constants.uiPcClsPrefix}-demo-cascader`;

type CascaderProps = {}
type CascaderState = {}

const disabledOptions: CascaderOptionType[] = [
  {
    value: 'shanghai',
    label: '上海',
    children: [
      {
        value: 'minhang',
        label: '闵行',
        children: [
          {
            value: 'fanwei',
            label: '泛微',
          },
        ],
      },
    ],
  },
  {
    value: 'hubei',
    label: '湖北',
    disabled: true,
    children: [
      {
        value: 'wuhan',
        label: '武汉',
        children: [
          {
            value: 'guanggu',
            label: '光谷',
          },
        ],
      },
    ],
  },
]
const myFieldNames: CascaderFieldNamesType = {
  value: 'myValue',
  label: 'myLabel',
  children: 'myChildren'
}
const myOptions: CascaderOptionType[] = [
  {
    myValue: 'shanghai',
    myLabel: '上海',
    myChildren: [
      {
        myValue: 'minhang',
        myLabel: '闵行',
        myChildren: [
          {
            myValue: 'fanwei',
            myLabel: '泛微',
          },
        ],
      },
    ],
  },
  {
    myValue: 'hubei',
    myLabel: '湖北',
    myChildren: [
      {
        myValue: 'wuhan',
        myLabel: '武汉',
        myChildren: [
          {
            myValue: 'guanggu',
            myLabel: '光谷',
          },
        ],
      },
    ],
  },
]

export default class CascaderDemo extends Component<CascaderProps, CascaderState> {

  constructor(props: CascaderDemo) {
    super(props)
    this.state = {
    }
  }

  onChange = (value: CascaderValueType) => console.info('value', value)

  render() {
    return (
      <div className={prefixCls}>
        <p>数据禁用</p>
        <Cascader
          width={200}
          options={disabledOptions}
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>使用 changeOnSelect 允许只选中父级选项</p>
        <Cascader
          width={200}
          expandTrigger={"hover"}
          options={options}
          onChange={this.onChange}
          changeOnSelect
        />
        <br />
        <br />
        <p>使用 fieldNames 自定义传入数据字段名</p>
        <Cascader
          width={200}
          fieldNames={myFieldNames}
          options={myOptions}
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>使用 notFoundContent 处理空数据</p>
        <Cascader
          width={200}
          options={[]}
          onChange={this.onChange}
          notFoundContent={'没有找到数据哦'}
        />
      </div>
    )
  }
}
```

### 处理选择器

自定义渲染选择器以及展开面板

```jsx
import { Component, FC, RefAttributes } from "react";
import { constants, BaseProps, Cascader, CascaderOptionType, CascaderValueType } from "@weapp/ui";

const prefixCls = `${constants.uiPcClsPrefix}-demo-cascader`;

interface MySpanProps extends BaseProps, RefAttributes<any> {
  option: CascaderOptionType;
  label: string;
  onClick?: (e: any, label: string, option: CascaderOptionType) => void;
}

const MySpan: FC<MySpanProps & RefAttributes<any>> = ({ option, label, onClick }) => {
  function handleAreaClick(e: any) {
    e.stopPropagation();
    onClick?.(e, label, option)
  }
  return (
    <span>
      {label} (<a onClick={handleAreaClick} href='/'>{option.zipCode}</a>)
    </span>
  )
}

type CascaderProps = {}
type CascaderState = {
  text: string;
}

const options: CascaderOptionType[] = [
  {
    value: 'hubei',
    label: '湖北',
    children: [
      {
        value: 'wuhan',
        label: '武汉',
        children: [
          {
            value: 'guanggu',
            label: '光谷',
            zipCode: 430070,
          },
        ],
      },
      {
        value: 'yichang',
        label: '宜昌',
        children: [
          {
            value: 'sanxia',
            label: '三峡',
            zipCode: 443000
          },
        ],
      },
    ],
  },
  {
    value: 'shanghai',
    label: '上海',
    children: [
      {
        value: 'minhang',
        label: '闵行',
        children: [
          {
            value: 'fanwei',
            label: '泛微',
            zipCode: 201100
          },
        ],
      },
    ],
  },
]

export default class CascaderDemo extends Component<CascaderProps, CascaderState> {

  constructor(props: CascaderDemo) {
    super(props)
    this.state = {
      text: '我现在没有数据哦',
    }
  }

  onChange = (value: CascaderValueType) => console.info('value', value)
  onMyChange = (value: CascaderValueType, selectedOptions?: CascaderOptionType[]) => {
    console.info('value', value)
    if (selectedOptions) {
      this.setState({
        text: selectedOptions.map((o: CascaderOptionType) => o.label).join(', '),
      })
    }
  }
  dropdownRender = (menus: any) => {
    return (
      <>
        {menus}
        <div style={{ padding: 8, borderTop: '1px solid #e5e5e5' }}>自定义底部拓展</div>
      </>
    )
  }
  handleAreaClick = (e: any, label: string, option: any) => {
    e.stopPropagation();
    console.info('clicked', label, option);
  }
  myDisplayRender = (labels: string[], selectedOptions?: CascaderOptionType[]) => {
    if (selectedOptions) {
      return (
        labels.map((label: string, i: number) => {
          const option = selectedOptions[i]
          if (i === labels.length - 1) {
            // console.log('label', label)
            return (
              <MySpan
               
                key={option.value}
                option={option}
                label={label}
                onClick={this.handleAreaClick}
              />
            )
          }
          return (<span key={option.value}>{label} / </span>)
        })
      )
    }
  }
  displayRender = (label: string[], selectedOptions?: CascaderOptionType[]) => {
    console.info('label', label)
    console.info('label[label.length - 1];', label[label.length - 1])
    return label[label.length - 1];
  }

  render() {
    return (
      <div className={prefixCls}>
        <p>仅显示最后一级</p>
        <Cascader
          width={200}
          options={options}
          onChange={this.onChange}
          displayRender={this.displayRender}
        />
        <br />
        <br />
        <p>使用 displayRender 自定义渲染已选项</p>
        <Cascader
          width={300}
          options={options}
          displayRender={this.myDisplayRender}
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>自定义弹出层类名和弹出层位置</p>
        <Cascader
          width={200}
          options={options}
          popupPlacement={`topRight`}
          placeholder={'myPlaceholder'}
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>使用 dropdownRender 对下拉菜单进行自由扩展</p>
        <Cascader
          width={200}
          options={options}
          onChange={this.onChange}
          dropdownRender={this.dropdownRender}
        />
        <br />
        <br />
        <p>自定义渲染整个选择器</p>
        <span>
          {this.state.text}
          &nbsp;
          <Cascader
           
            options={options}
            onChange={this.onMyChange}>
            <a href="/ui/cascader">点击展开弹出面板</a>
          </Cascader>
        </span>
        <br />
        <br />
      </div>
    )
  }
}
```

### 可搜索

可以快捷地搜索选项并选择

```jsx
import { Component } from "react";
import { constants, Cascader, CascaderOptionType, CascaderValueType } from "@weapp/ui";
import { options } from '../mock';

const prefixCls = `${constants.uiPcClsPrefix}-demo-cascader`;

type CascaderProps = {}
type CascaderState = {}

function filter(inputValue: string, path: CascaderOptionType[]) {
  //@ts-ignore
  return path.some((option: CascaderOptionType) => option.label.toLowerCase().indexOf(inputValue.toLowerCase()) > -1);
}

export default class CascaderDemo extends Component<CascaderProps, CascaderState> {

  onChange = (value: CascaderValueType) => console.info('value', value)

  render() {
    return (
      <div className={prefixCls}>
        <p>使用 showSearch 来自定义配置可搜索</p>
        <Cascader
          width={200}
          options={options}
          onChange={this.onChange}
          showSearch={{ filter }}
          placeholder={'试试搜索：光谷'}
        />
        <br />
        <br />
      </div>
    )
  }
}
```

### 融合城市接口

可以快捷地选择城市

```jsx
import { Component } from "react";
import { constants, Cascader, CascaderOptionType, CascaderValueType } from "@weapp/ui";
import { request, RequestResult } from '@weapp/utils'
import { options } from '../mock';

type CascaderProps = {}
type CascaderState = {}

const prefixCls = `${constants.uiPcClsPrefix}-demo-cascader`;
function filter(inputValue: string, path: CascaderOptionType[]) {
  //@ts-ignore
  return path.some((option: CascaderOptionType) => option.label.toLowerCase().indexOf(inputValue.toLowerCase()) > -1);
}

export default class CascaderDemo extends Component<CascaderProps, CascaderState> {

  state = {
    options: options
  }

  componentDidMount() {
    request({
      url: `/api/bcw/administrativeArea/cascade`,
      method: 'POST',
      data: { level: 'district' }
    }).then((result: RequestResult) => {
      if (result.status) {
        console.info('result', result)
        this.setState({ options: result.data.nodes })
      }
    })
  }

  onChange = (value: CascaderValueType) => console.info('value', value)

  render() {
    return (
      <div className={prefixCls}>
        <p>使用 城市配置接口 /api/bcw/administrativeArea/cascade 来自定义配置options内容</p>
        <Cascader
          width={1000}
          options={this.state.options}
          onChange={this.onChange}
          //此处使用 as any是因为该过滤方法需要与组件内部的filter方法结合，在此处拆分不太现实
          showSearch={{ filter } as any}
          placeholder={'试试搜索：光谷'}
        />
        <br />
        <br />
      </div>
    )
  }
}
```

### 超出省略与折行展示

只读模式在表单中可以自定义控制超出省略与折行展示

```jsx
import { Component } from "react";
import { constants, Cascader, CascaderValueType } from "@weapp/ui";
import { options } from '../mock';

const prefixCls = `${constants.uiPcClsPrefix}-demo-cascader`;

type CascaderProps = {}
type CascaderState = {
  value: CascaderValueType,
}

const longLabel = ['湖北', '武汉', '湖北', '武汉', '湖北', '武汉', '湖北', '武汉', '湖北', '武汉']

export default class CascaderDemo extends Component<CascaderProps, CascaderState> {

  render() {
    return (
      <div className={prefixCls}>
        <p>只读</p>
        <Cascader
          options={options}
          defaultValue={longLabel}
          readOnly
        />
        <br />
        <br />
        <p>折行展示</p>
        <Cascader
          options={options}
          defaultValue={longLabel}
          selectedWrap
          readOnly
        />
        <br />
        <br />
        <p>超出省略</p>
        <Cascader
          options={options}
          defaultValue={longLabel}
          selectedWrap={false}
          readOnly
        />
      </div>
    )
  }
}
```

### 级联多选

当一个数据集合有清晰的层级结构时，可通过级联选择器逐级查看并选择多个数据

```jsx
import { Component } from "react";
import { constants, Cascader, CascaderValueType, CascaderOptionType, Button, Icon } from "@weapp/ui";
import { options } from '../mock';
const { MultiCascader } = Cascader

const defaultValue = [
  [
    "shanghai"
  ],
  [
    "hubei",
    "wuhan"
  ],
  [
    "hubei",
    "yichang",
    "qutangxia"
  ],
  [
    "hubei",
    "yichang",
    "wuxia"
  ]
]

const prefixCls = `${constants.uiPcClsPrefix}-demo-cascader`;

type CascaderProps = {}
type CascaderState = {
  value: CascaderValueType[],
}
export default class CascaderDemo extends Component<CascaderProps, CascaderState> {

  constructor(props: CascaderDemo) {
    super(props)
    this.state = {
      value: [
        [
          "hubei",
          "wuhan"
        ],
        [
          "hubei",
          "yichang",
          "qutangxia"
        ],
        [
          "shanghai"
        ],
        [
          "zhejiang"
        ],
        [
          "jiangsu"
        ],
        [
          "hunan"
        ],
        [
          "xizang"
        ],
        [
          "beijing"
        ],
        [
          "tianjin"
        ],
        [
          "hubei",
          "yichang",
          "wuxia"
        ]
      ]
    }
  }

  onChange = (value: any, selectedOptions?: any[]) => {
    console.info('value', value)
    console.info('selectedOptions', selectedOptions)
  }
  onValueChange = (value: any, selectedOptions?: any) => {
    console.info('value', value)
    console.info('selectedOptions', selectedOptions)
    this.setState({ value })
  }
  reset = () => this.setState({ value: [] })
  tagRender = (props: any) => {
    const label = props.label
    return (
      <span key={`${label}_${props?.index}`} className='rc-cascader-selection-item' title={label} style={{ border: '1px solid red' }}>
        <span className='rc-cascader-selection-item-content'>
          {label}
        </span>
        <span className='rc-cascader-selection-item-remove'>
          <Icon name={'Icon-error01'} size={'xxs'} onClick={props.onClose}></Icon>
        </span>
      </span>
    )
  }
  tagRenderReadOnly = (props: any) => {
    const { label, className, value } = props
    const my_value = value[value.length - 1];
    return (
      <div key={`${label}_${props?.index}`} className={className} title={label} style={{ border: '1px solid red' }}>
        {my_value}
      </div>
    )
  }
  displayRenderReadOnly = (label: string[], selectedOptions?: any[]) => {
    return label[label.length - 1];
  }

  render() {
    const { value, } = this.state
    return (
      <div className={prefixCls}>
        <p>基础用法</p>
        <MultiCascader
          options={options}
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>禁用</p>
        <MultiCascader
          disabled
          value={defaultValue}
          options={options}
        />
        <br />
        <br />
        <p>只读</p>
        <MultiCascader
          readOnly
          value={defaultValue}
          options={options}
        />
        <br />
        <br />
        <p>受控</p>
        <div style={{ display: 'flex' }}>
          <MultiCascader
            options={options}
            value={value}
            onChange={this.onValueChange}
          />
          &nbsp;
          <Button type={'primary'} size={'small'} onClick={this.reset}>重置</Button>
        </div>
        <br />
        <br />
        <p>仅可选中最后一级</p>
        <MultiCascader
          options={options}
          onChange={this.onChange}
          mergeChild={false}
        />
        <br />
        <br />
        <p>自定义渲染tag</p>
        <MultiCascader
          options={options}
          value={defaultValue}
          onChange={this.onChange}
          tagRender={this.tagRender}
        />
        <p>只读自定义渲染tag</p>
        <MultiCascader
          readOnly
          value={defaultValue}
          options={options}
          displayRender={this.displayRenderReadOnly}
        // tagRender={this.tagRenderReadOnly}
        />
      </div >
    )
  }
}
```

### 异步数据处理

当options为异步时数据回显的处理

```jsx
import { Component } from "react";
import { constants, Cascader, CascaderOptionType, CascaderValueType, Button, Icon } from "@weapp/ui";
import { options2 } from '../mock';
const { MultiCascader } = Cascader

const prefixCls = `${constants.uiPcClsPrefix}-demo-cascader`;

type CascaderProps = {}
type CascaderState = {
  lazyOptions: CascaderOptionType[],
  options: CascaderOptionType[],
  value1: CascaderValueType,
  value2: CascaderValueType[],
  defaultLabel1?: any[],
  defaultLabel2?: any[],
}
export default class CascaderDemo extends Component<CascaderProps, CascaderState> {

  constructor(props: CascaderDemo) {
    super(props)
    this.state = {
      lazyOptions: [
        {
          value: 'hubei',
          label: '湖北',
          isLeaf: false,
        },
        {
          value: 'shanghai',
          label: '上海',
          isLeaf: false,
        },
      ],
      options: [],
      value1: ['yzy1111', 'yzy11111'],
      value2: [["yzy1111", "yzy11111"], ["yzy3333", "yzy33333"], ["yzy3333"]],
      defaultLabel1: ['金蝶', 'K33'],
      defaultLabel2: [['金蝶', 'K33'], ['泛微', 'e10'], ['泛微', 'e9']],
    }
  }

  componentDidMount() {
    setTimeout(() => {
      this.setState({
        options: options2,
        // defaultLabel1: void 0,
        // defaultLabel2: void 0,
      })
    }, 1000);
  }
  onChange = (value: any, selectedOptions?: any[]) => {
    console.info('value', value)
    console.info('selectedOptions', selectedOptions)
  }
  onValue1Change = (value: any, selectedOptions?: any) => {
    console.info('value', value)
    console.info('selectedOptions', selectedOptions)
    this.setState({ value1: value })
  }
  onValue2Change = (value: any, selectedOptions?: any) => {
    console.info('value', value)
    console.info('selectedOptions', selectedOptions)
    this.setState({ value2: value })
  }
  reset1 = () => this.setState({
    value1: [],
    defaultLabel1: []
  })
  reset2 = () => this.setState({
    value2: [],
    defaultLabel2: []
  })

  loadData = (selectedOptions?: CascaderOptionType[]) => {
    if (selectedOptions) {
      const targetOption = selectedOptions[selectedOptions.length - 1];
      targetOption.loading = true;

      // load options lazily
      setTimeout(() => {
        targetOption.loading = false;
        targetOption.children = [
          {
            label: `${targetOption.label} Dynamic 1`,
            value: 'dynamic1',
          },
          {
            label: `${targetOption.label} Dynamic 2`,
            value: 'dynamic2',
          },
        ];
        this.setState({ lazyOptions: [...this.state.lazyOptions] })
      }, 1000);
    }
  }

  render() {
    const { options, value1, value2, defaultLabel1, defaultLabel2 } = this.state
    return (
      <div className={prefixCls}>
        <h3>动态加载</h3>
        <p>使用 loadData 动态加载选项 （注意 defaultLabel、defaultLabel、value 的用法）</p>
        <Cascader
          width={200}
          defaultLabel={['上海', '上海 dynamic1']}
          defaultValue={['shanghai', 'dynamic1']}
          options={this.state.lazyOptions}
          onChange={this.onChange}
          loadData={this.loadData}
        />
        <br />
        <br />
        <h3>单选</h3>
        <p>受控</p>
        <Cascader
          options={options}
          defaultLabel={defaultLabel1}
          value={value1}
          onChange={this.onValue1Change}
        />
        <br />
        <Button type={'primary'} onClick={this.reset1}>重置</Button>
        <br />
        <br />
        <p>非受控</p>
        <Cascader
          options={options}
          defaultLabel={defaultLabel1}
          onChange={this.onChange}
        />
        <br />
        <br />
        <p>只读</p>
        <Cascader
          options={options}
          value={['yzy1111', 'yzy11111']}
          defaultLabel={defaultLabel1}
          onChange={this.onChange}
          readOnly
        />
        <br />
        <br />
        <p>禁用</p>
        <Cascader
          options={options}
          value={['yzy1111', 'yzy11111']}
          defaultLabel={defaultLabel1}
          onChange={this.onChange}
          disabled
        />
        <br />
        <br />
        <h3>多选</h3>
        <p>受控</p>
        <MultiCascader
          options={options}
          defaultLabel={defaultLabel2}
          value={value2}
          onChange={this.onValue2Change}
        // mergeChild={false}
        />
        <br />
        <Button type={'primary'} onClick={this.reset2}>重置</Button>
        <br />
        <br />
        <p>非受控</p>
        <MultiCascader
          options={options}
          defaultLabel={defaultLabel2}
          onChange={this.onChange}
        // mergeChild={false}
        />
        <br />
        <br />
        <p>只读</p>
        <MultiCascader
          options={options}
          value={[['yzy1111']]}
          defaultLabel={defaultLabel2}
          onChange={this.onChange}
          readOnly
        />
        <br />
        <br />
        <p>禁用</p>
        <MultiCascader
          options={options}
          value={[['yzy1111']]}
          defaultLabel={defaultLabel2}
          onChange={this.onChange}
          disabled
        />
      </div >
    )
  }
}
```

### 默认数据选中

新增在没有数据的时候增加默认选中的功能

```jsx
import { Component } from "react";
import { constants, Cascader, Button, CascaderOptionType, CascaderValueType } from "@weapp/ui";
import { options } from '../mock';

const initialActiveValue = ['shanghai', 'minhang', 'fanwei'];

const prefixCls = `${constants.uiPcClsPrefix}-demo-cascader`;

type CascaderProps = {}
type CascaderState = {
  value: CascaderValueType,
}
export default class CascaderDemo extends Component<CascaderProps, CascaderState> {

  constructor(props: CascaderDemo) {
    super(props)
    this.state = {
      value: ['hubei', 'wuhan', 'guanggu'],
    }
  }

  onChange = (value: CascaderValueType, selectedOptions?: CascaderOptionType[]) => {
    console.info('value', value)
    console.info('selectedOptions', selectedOptions)
  }
  onValueChange = (value: CascaderValueType, selectedOptions?: CascaderOptionType[]) => {
    console.info('value', value)
    console.info('selectedOptions', selectedOptions)
    this.setState({ value })
  }
  reset = () => this.setState({ value: [] })

  render() {
    return (
      <div className={prefixCls}>
        <p>基础用法</p>
        <Cascader
          options={options}
          onChange={this.onChange}
          initialActiveValue={initialActiveValue}
        />
        <br />
        <br />
        <p>受控</p>
        <div style={{ display: 'flex' }}>
          <Cascader
            width={200}
            value={this.state.value}
            options={options}
            onChange={this.onValueChange}
            initialActiveValue={initialActiveValue}
          />
          &nbsp;
          <Button type={'primary'} size={'small'} onClick={this.reset}>重置</Button>
        </div>
      </div>
    )
  }
}
```

## API

### 注意：

```typescript
1.在options的length不大于等一的情况下，无论value怎么变化，默认展示都会按照defaultLabel来进行渲染
```

### 类型说明：（请从@weapp/ui 中导出）

```typescript
1.option类型
type CascaderOptionType =  {
  value?: string | number;
  label?: React.ReactNode;
  disabled?: boolean;
  isLeaf?: boolean;
  loading?: boolean;
  children?: Array<CascaderOptionType>;
  [key: string]: any;
};

2.onChange抛出的value类型
type CascaderValueType = (string | number)[];

3.自定义字段名类型
type FieldNamesType =  {
  value?: string | number;
  label?: string;
  children?: string;
};

4.showSearch参数配置以及类型: (注意：loadData 与 showSearch 无法一起使用)
type FilledFieldNamesType =  {
  value: string | number;
  label: string;
  children: string;
}
type ShowSearchType ={
  filter?: (inputValue: string, path: CascaderOptionType[], names: FilledFieldNamesType) => boolean;
  render?: (
    inputValue: string,
    path: CascaderOptionType[],
    prefixCls: string | undefined,
    names: FilledFieldNamesType,
  ) => React.ReactNode;
  sort?: (
    a: CascaderOptionType[],
    b: CascaderOptionType[],
    inputValue: string,
    names: FilledFieldNamesType,
  ) => number;
  matchInputWidth?: boolean;
  limit?: number | false;
};
5.城市配置接口: '/api/bcw/administrativeArea/cascade'(维护人：师源)
```

### Cascader参数说明如下：

| 参数 | 说明 | 类型 | 是否必填 | 默认值 |
| --- | --- | --- | --- | --- |
| allowClear | 是否支持清除 | boolean |  |  |
| autoFocus | 自动获取焦点 | boolean |  |  |
| bordered | 是否有边框 | boolean |  |  |
| changeOnSelect | 选择即改变，当为 true 时允许只选中父级选项 | boolean |  |  |
| className | 自定义类名 | string |  |  |
| defaultValue | 默认的选中项 | string[] \| number[] |  |  |
| disabled | 禁用 | boolean |  |  |
| disabledUseUIInput | 禁用模式同步input组件 | boolean |  |  |
| displayRender | 选择后展示的渲染函数 | (label, selectedOptions) => ReactNode |  | label => label.join(`/`) |
| dropdownRender | 自定义下拉框内容 | (menus: ReactNode) => ReactNode |  |  |
| expandIcon | 自定义次级菜单展开图标 | ReactNode |  |  |
| expandTrigger | 次级菜单的展开方式 | `click` \| `hover` |  | `click` |
| fieldNames | 自定义 options 字段名 | object |  | { label: `label`, value: `value`, children: `children` } |
| loadData | 用于动态加载选项，无法与 `showSearch` 一起使用 | (selectedOptions) => void |  |  |
| notFoundContent | 当下拉列表为空时显示的内容 | string |  |  |
| options | 可选项数据源 | Option[] | 是 |  |
| placeholder | 输入框占位文本 | string |  |  |
| popupClassName | 自定义浮层类名 | string |  |  |
| popupPlacement | 弹出层位置 | `bottomLeft` \| `bottomRight` \| `topLeft` \| `topRight` |  | `bottomLeft` |
| popupVisible | 控制浮层显隐 | boolean |  |  |
| showSearch | 是否为搜索模式 | boolean \| 搜索模式说明 |  |  |
| style | 自定义样式 | CSSProperties |  |  |
| suffixIcon | 自定义的选择框后缀图标 | ReactNode |  |  |
| value | 指定选中项 | string[] \| number[] |  |  |
| onChange | 选择完成后的回调 | (value: CascaderValueType, selectedOptions: CascaderOptionType) => void |  |  |
| onPopupVisibleChange | 显示/隐藏浮层的回调 | (value: CascaderValueType) => void |  |  |
| getPopupContainer | 菜单渲染父节点。默认渲染到 body 上 | function(triggerNode) |  | () => document.body |
| defaultLabel | 只会在传入的value的级别数大于传入的options的级别的时候才会展示（多用于首次渲染） | string[] |  |  |
| split | 分隔符号 | string |  | / |
| mergeChild | 是否仅可选中最后一级（是否合并子节点用于优化性能） | boolean |  | true |
| isFilterIDMatchNoLabelValue | 是否过滤id匹配不到value的数据 | boolean |  | true |
| isFilterOnChange | 数据过滤后是否触发onchange抛出过滤后的value以及selectedOptions | boolean |  | true |
| initialActiveValue | 默认的选中项 -> 不作为真实的value | CascaderValueType |  |  |
| tagRender | 级联多选的每一项自定义渲染 | (props: CustomTagProps) => React.ReactElement |  |  |
### MultiCascader参数说明如下：

#### 注意

```typescript
1.其余参数与rc-cascader保持一致
2.MultiCascaderProps可以从Weapp-ui中直接导出
```

| 参数 | 说明 | 类型 | 是否必填 | 默认值 |
| --- | --- | --- | --- | --- |
| onChange | 选择完成后的回调 | (value: CascaderValueType[], selectedOptions: CascaderOptionType[]) => void |  |  |
### showSearch

`` 为对象时，其中的字段：

| 参数 | 说明 | 类型 | 默认值 |
| --- | --- | --- | --- |
| filter | 接收 `inputValue` `path` 两个参数，当 `path` 符合筛选条件时，应返回 true，反之则返回 false | function(inputValue, path): boolean | - |
| limit | 搜索结果展示数量 | number \| false | 99999 |
| matchInputWidth | 搜索结果列表是否与输入框同宽（效果） | boolean | true |
| render | 用于渲染 filter 后的选项 | function(inputValue, path): ReactNode | - |
| sort | 用于排序 filter 后的选项 | function(a, b, inputValue) | - |
