React combinado con el componente Cascader de antd para realizar el control de la ciudad de selección del lado de la PC
Necesidades comerciales, busqué mucho en línea y descubrí que no estaban satisfechas, así que escribí una.
1. La implementación es la siguiente
Consejo:
haga clic en la dirección de datos https://xf-1252186245.cos.ap-chengdu.myqcloud.com/data/data.js para copiarlo y colocarlo en el directorio del mismo nivel del componente y asígnele el nombre data.js.
Si la dirección data.js anterior está distorsionada, haga clic en la dirección del almacén de github https://github.com/lxf/react-city-select para clonar el código localmente, hay data.js en el código fuente, o puede acceder directamente a la dirección del almacén de github de data.js Camino .
Dependencia: reaccionar antd rc-form prop-types, etc., primero instale las dependencias, se omiten los pasos.
Archivo CitySelect.jsx
import React, {
Component } from "react";
import {
createForm } from "rc-form";
import {
Cascader } from "antd";
import city from "./data"; // 数据见上提示
import PropTypes from "prop-types";
//先配置修饰器 没有配置的话用把 @createForm()删掉
//然后把最后一行 export default CitySelect; 换成 export default createForm()(CitySelect)
@createForm()
class CitySelect extends Component {
// props类型检查
static propTypes = {
// 监听选择
onChange: PropTypes.func,
// 获取选择值
getSelectedValues: PropTypes.func,
// 默认值
value: PropTypes.array
};
onCascaderChange = selectedValues => {
const {
onChange, getSelectedValues } = this.props;
const result = [];
// 递归查询城市所有数据
function findCityData(city) {
city.forEach(item => {
const {
id, label, value, children } = item;
if (selectedValues.includes(value)) {
result.push({
id, label, value });
}
if (children && children.length) {
findCityData(children);
}
});
}
findCityData(city);
// 分发监听
onChange && onChange(selectedValues);
getSelectedValues && getSelectedValues(result);
};
componentDidMount() {
const {
form: {
setFieldsValue },
value: selectedValues
} = this.props;
if (!selectedValues || !selectedValues.length) {
return;
}
const result = [];
// 递归查询城市名称数据
function findLabel(children) {
children.forEach(item => {
const {
label, value, children } = item;
if (selectedValues.includes(label)) {
result.push(value);
}
if (children && children.length) {
findLabel(children);
}
});
}
// 卡省份解决县或市名称一样的问题
city.forEach(item => {
const {
label, value, children } = item;
if (selectedValues.includes(label)) {
result.push(value);
if (children && children.length) {
findLabel(children);
}
}
});
// 设置默认值
setFieldsValue({
city: result });
}
render() {
const {
getFieldProps } = this.props.form;
return (
<div>
<Cascader
options={
city}
{
...getFieldProps("city", {
onChange: this.onCascaderChange,
rules: [{
required: true }]
})}
placeholder="请选择城市"
/>
</div>
);
}
}
export default CitySelect;
2. Utilice
import React, {
Component } from "react";
import {
Form, Button, message, Icon } from "antd";
import CitySelect from "@/components/CitySelect";
import "./hotel.less";
const FormCreate = Form.create;
const FormItem = Form.Item;
@FormCreate()
class HotelSetting extends Component {
state = {
selectedValues: []
};
handleReset = () => {
this.props.form.resetFields();
};
// 获取选择值
getSelectedValues = selectedValues => {
this.setState({
selectedValues
});
};
handleSumit = e => {
const {
form } = this.props;
e.preventDefault();
form.validateFields((err, formData) => {
console.log(formData, "formData");
if (err) {
message.destroy();
return message.warning("请完整填写表单");
}
const data = {
...formData,
selectedValues: this.state.selectedValues
};
console.log(data, "data");
});
};
render() {
const {
getFieldDecorator } = this.props.form;
const defaultCity = ["陕西省", "西安市", "碑林区"];
return (
<Form
className="custom-form custom-vertical-hotel-form"
layout="vertical"
labelAlign="left"
onSubmit={
e => {
this.handleSumit(e);
}}
style={
{
background: "#fff", padding: 24 }}
>
{
/* 数据绑定 拿到的city字段是城市编码 getSelectedValues监听可以拿到选择的数据对象 */}
<FormItem label="城市选择:">
{
getFieldDecorator("city", {
initialValue: defaultCity,
rules: [{
required: true, message: "请选择城市选择" }]
})(<CitySelect getSelectedValues={
this.getSelectedValues} />)}
</FormItem>
<FormItem label="城市选择:">
<CitySelect
getSelectedValues={
this.getSelectedValues}
value={
defaultCity}
/>
</FormItem>
<FormItem style={
{
paddingBottom: 0 }}>
<Button type="primary" htmlType="submit">
<Icon type="arrow-up" />
保存
</Button>
</FormItem>
</Form>
);
}
}
export default HotelSetting;
hotel.less
:global(.custom-vertical-hotel-form .ant-form-item-label) {
width: 90px;
vertical-align: top;
}
:global(.custom-vertical-hotel-form .ant-form-item-control-wrapper) {
width: 340px;
display: inline-block;
}
3. El efecto y el valor obtenido