一、引言
在Web应用开发过程中,搜索功能是提升用户体验的重要环节。本文将带领大家使用React和Ant Design库,构建一个动态搜索表单与数据表格组件。通过本文,您将学习到如何实现表单的动态渲染、数据表格的分页加载以及与后端服务的交互。
二、主要技术栈
- React:用于构建用户界面的JavaScript库。
- TypeScript:为JavaScript提供类型支持,提高代码可维护性。
- Ant Design:一套企业级的UI设计语言和React组件库。
- Axios:基于Promise的HTTP客户端,用于与后端服务进行数据交互。
- Moment.js:处理日期时间的JavaScript库。
三、组件设计
- 接口定义 首先,我们定义两个接口和一个类型,用于描述搜索表单项和数据表格列的结构:
export interface SearchFormItem {
name: string;
label: string;
type: 'input' | 'select' | 'datePicker';
options?: { label: string; value: string; }[];
}
type TableColumn = {
title: string;
dataIndex: string;
key: string;
};
interface SearchFormTableProps {
searchItems: SearchFormItem[];
tableColumns: TableColumn[];
fetchDataUrl: string;
}
- 组件实现
接下来,我们实现
SearchFormTable组件,该组件包含以下功能:
- 动态渲染搜索表单
- 根据表单值查询数据
- 显示数据表格并支持分页
const SearchFormTable: React.FC<SearchFormTableProps> = ({
searchItems,
tableColumns,
fetchDataUrl,
}) => {
// 组件代码(省略部分代码,详见上文)
};
四、关键功能实现
- 动态渲染搜索表单
根据
searchItems数组,我们使用map方法动态生成表单项:
const renderFormItem = (item: SearchFormItem) => {
// 表单项渲染逻辑(省略)
};
- 数据查询与表格显示
在
handleSearch函数中,我们首先验证表单,然后调用fetchData函数获取数据:
const handleSearch = () => {
// 查询逻辑(省略)
};
fetchData函数负责与后端服务交互,获取数据并更新表格:
const fetchData = async (params: any) => {
// 数据获取逻辑(省略)
};
五、代码示例
import React, { useState, useEffect } from 'react';
import { Form, Select, Input, Button, Table, message, DatePicker, Row, Col } from 'antd';
import axios from 'axios';
import moment from 'moment';
import './SearchFormTable.less';
// 定义搜索表单项接口
interface SearchFormItem {
name: string;
label: string;
type: 'input' | 'select' | 'datePicker';
options?: { label: string; value: string; }[];
}
// 定义表格列接口
interface TableColumn {
title: string;
dataIndex: string;
key: string;
}
// 组件属性接口
interface SearchFormTableProps {
searchItems: SearchFormItem[];
tableColumns: TableColumn[];
fetchDataUrl: string;
}
const SearchFormTable: React.FC<SearchFormTableProps> = ({
searchItems,
tableColumns,
fetchDataUrl,
}) => {
const [form] = Form.useForm();
const [data, setData] = useState([]);
const [loading, setLoading] = useState(false);
// 动态渲染表单项
const renderFormItem = (item: SearchFormItem) => {
switch (item.type) {
case 'input':
return <Input placeholder={`请输入${item.label}`} />;
case 'select':
return (
<Select placeholder={`请选择${item.label}`} allowClear>
{item.options?.map(option => (
<Select.Option key={option.value} value={option.value}>
{option.label}
</Select.Option>
))}
</Select>
);
case 'datePicker':
return <DatePicker style={{ width: '100%' }} />;
default:
return <Input />;
}
};
// 查询数据
const handleSearch = () => {
form.validateFields()
.then(values => {
setLoading(true);
fetchData(values);
})
.catch(info => {
console.log('Validate Failed:', info);
});
};
// 重置表单
const handleReset = () => {
form.resetFields();
};
// 获取数据
const fetchData = async (params: any) => {
try {
const response = await axios.get(fetchDataUrl, { params });
setData(response.data);
setLoading(false);
} catch (error) {
message.error('数据加载失败');
setLoading(false);
}
};
useEffect(() => {
// 组件挂载时获取数据
fetchData({});
}, []);
return (
<div>
<Form form={form} layout="vertical">
<Row gutter={16}>
{searchItems.map(item => (
<Col span={8} key={item.name}>
<Form.Item
name={item.name}
label={item.label}
rules={[{ required: false }]}
>
{renderFormItem(item)}
</Form.Item>
</Col>
))}
<Col span={8} offset={8} style={{ textAlign: 'right' }}>
<Button type="primary" htmlType="submit" onClick={handleSearch}>
查询
</Button>
<Button style={{ marginLeft: 8 }} onClick={handleReset}>
重置
</Button>
</Col>
</Row>
</Form>
<Table
columns={tableColumns}
dataSource={data}
loading={loading}
pagination={{ pageSize: 10 }}
/>
</div>
);
};
export default SearchFormTable;
在这个代码示例中,我们定义了SearchFormItem和TableColumn接口,用于描述表单项和表格列的结构。SearchFormTable组件接受searchItems、tableColumns和fetchDataUrl作为属性,动态生成表单和表格,并处理数据查询逻辑。
六、 模拟数据和运行
首先,我们定义一些模拟的搜索表单项和表格列:
// 模拟的搜索表单项
const searchItems: SearchFormItem[] = [
{
name: 'username',
label: '用户名',
type: 'input',
},
{
name: 'role',
label: '角色',
type: 'select',
options: [
{ label: '管理员', value: 'admin' },
{ label: '普通用户', value: 'user' },
{ label: '访客', value: 'guest' },
],
},
{
name: 'registerDate',
label: '注册日期',
type: 'datePicker',
},
];
// 模拟的表格列
const tableColumns: TableColumn[] = [
{
title: '用户名',
dataIndex: 'username',
key: 'username',
},
{
title: '角色',
dataIndex: 'role',
key: 'role',
},
{
title: '注册日期',
dataIndex: 'registerDate',
key: 'registerDate',
},
];
// 模拟的API端点
const fetchDataUrl = 'https://api.example.com/users';
现在我们可以使用SearchFormTable组件,并将模拟数据传递给它:
import React from 'react';
import ReactDOM from 'react-dom';
import SearchFormTable from './components/SearchFormTable';
const App: React.FC = () => {
return (
<div>
<SearchFormTable
searchItems={searchItems}
tableColumns={tableColumns}
fetchDataUrl={fetchDataUrl}
/>
</div>
);
};
ReactDOM.render(<App />, document.getElementById('root'));
假设后端API返回以下格式的数据:
[
{
"username": "Alice",
"role": "admin",
"registerDate": "2023-01-01"
},
{
"username": "Bob",
"role": "user",
"registerDate": "2023-02-15"
},
{
"username": "Charlie",
"role": "guest",
"registerDate": "2023-03-10"
}
]
当用户在SearchFormTable组件中执行搜索时,fetchData函数会被调用,并使用表单的值作为查询参数向fetchDataUrl发送GET请求,后端应处理这些参数并返回相应的数据。
在实际应用中,您需要确保后端API端点fetchDataUrl是正确的,并且能够处理传入的查询参数,返回正确的数据格式。