dt-antd

antd for DTchuxing.com's Background management system

Usage no npm install needed!

<script type="module">
  import dtAntd from 'https://cdn.skypack.dev/dt-antd';
</script>

README

dt-antd

数据智能改变公共出行的产品二部基于antdesign开发的后台公共组件。仅适用于公交云产品二部三个平台。

目录

代码说明

启动

clone此代码,然后执行yarn命令进行安装。之后即可对其进行编译

yarn

目录说明

lib               // 编辑后的文件
|
node_modules      // 依赖包
|
src               // 源文件
|
other
├── .babelrc      // Babel设置
├── index.js      // 文件入口
└── package.json  // 设置

lib --- Babel

为了把 ES6 代码编译成 ES5,需要安装 Babel,这个工具可以说野心极大,一次编译可以让 JavaScript 运行在所有地方。(听起来是不是有点 Java 的作风)

目前最常用的是 Babel5 版本,但是 Babel6 版本的设计更为精巧,已经非常推荐更新。也正是由于 Babel 有两个版本,所以开发过程中很有可能遇到这样的情况, 模块 A 的开发依赖于 Babel5 版本,而模块 B 依赖于 Babel6 版本。

解决这个问题最好的做法就是把 A 和 B 拆开,独立开发和发布。并且在发布到 NPM 的时候发布是的编译后的,也就是 ES5 版本的代码。

所以如果你的机器上的 babel 是全局安装的,是时候卸载它了,因为它的版本不是 5 就是 6 ,会导致一些不可预见的问题。

npm uninstall babel-cli --global

正确的安装方式是把 babel-cli 作为 development 依赖

npm install babel-cli --save-dev

使用的时候并不是直接调用全局的 babel 而是调用依赖里的 babel 可执行文件

./node_modules/.bin/babel

使用Babel之后会将src里面的代码编译成ES5并输出到lib相应的目录中

package.json --- 命令详解

具体解释一下各个命令的作用:

第一条命令 ./node_modules/.bin/rimraf lib

作用 编译前清空之前的 lib 目录,这是一个好习惯,可以杜绝对 lib 下的文件的任何手动更改。

第二条命令

./node_modules/.bin/babel src --out-dir lib --source-maps --extensions .es6,.es,.jsx --copy-files

作用 遍历 src 目录下的文件,如果后缀名是 .es/.es6/.jsx 中的一种,就编译成 ES5,否则就直接拷贝到输出目录 lib 下

参数详解:

--out-dir lib 指定输出目录为 lib

--extensions .es6,.es,.jsx 指定需要编译的文件类型

--copy-files 对于不需要编译的文件直接拷贝

--source-maps 生成 souce-map 文件

.babelrc 文件

编译过程中还隐含了一个步骤就是加载 .babelrc 文件里的配置,该文件内容如下

{
  "presets": [
    "es2015",
    "stage-0",
    "react"
  ]
}

这是因为 Babel6 采用了插件化的设计,做到了灵活配置:如果要转换 JSX 语法文件,就加上 React 的 preset,同时项目依赖里要添加 babel-preset-react

npm install babel-preset-react --save-dev

SiderMenu

整体框架组件,结构:左上下模式,左边分title和菜单,上边分左(收起展开按钮)和右(登陆员信息)

调用方法:

import {SiderMenu} from 'dt-antd';

const path = {
  siderMenu: {
    logo,
    title,
    menu,
    logoLink,
  },
  pageHead: {
    user: {
      userName,
      userPhoto,
      logOut,
      userChange,
      userItem,
    },
    other,
  }
}

<SiderMenu {...path}>
  // 中间部分的内容
</SiderMenu>

path参数说明

参数名 子参数 三级参数 描述 类型 是否必填
siderMenu 框架左边的内容 object
logo logo图片 string 否(默认为公交云logo)
title 左侧头部文字 string
menu 左侧菜单(详情见下面表格) object
logoLink logo点击后的跳转地址(默认#) string
pageHead 框架上面的内容 object
user 最右侧用户头像+用户名+下拉部分的参数 object
userName 用户名 string 是(如果启用了userChange则选填)
userPhoto 用户头像 string 否(默认ant头像)
logOut 退出登陆方法 func 是(如果启用了userChange则选填)
userChange 不满足用户名+头像模式的自定义书写 object
userItem 不满足只有退出登陆的下拉菜单模式而自定义书写 object
other 头部右边默认只有一个头像+用户名,要加其它东西在这里自定义书写,会累加 object
theme 皮肤设置 object
navTheme 框架颜色(默认为dark黑色,可选light白色) string
isTop 菜单栏是否在顶部(默认为false,可选true) bool

左侧菜单menu说明文档

左侧菜单栏为了兼容主数据已定的返回模式,如果返回格式不一致,请对数据重新处理为以下格式:

let menu = [{
    code: 'userManage',
    name: '用户管理',
    icon: 'user',
    subMenus: [{
      code: 'userManage.userManage',
      name: '用户列表',
      url: '/userManage'
    }]
  }];

参数说明:

参数名 子参数 描述 类型 是否必填
code 识别的主键,不能重复 string
name 标题 string
icon 图标 string
subMenus 二级菜单目录 object
code 识别的主键,不能重复 string
name 标题 string
url 访问的路由路径,为了兼容主数据,要有/ string

另外为了方便页面指向左侧菜单的选中和展开,在定义页面其它路由时,如新增编辑详情等,页面路由定义格式为: {对应父级的path[也就是菜单栏menu中的url字段]}/你要定义的路由(如新增add,编辑edit/:id,详情detail/:id等)

PageHeaderLayout

面包屑以及头部调用方法,分头部,面包屑,页面标题,children正文,版本四个部分。

调用方法:

import {PageHeaderLayout} from 'dt-antd';

const breadMenu = [{
  path: '',
  title: '供应商管理'
}, {
  path: 'cardManage/cardTypeList',
  title: '二级供应商',
}, {
  path: '',
  title: '车辆管理'
}]

const tabList = [{
  key: 0,
  tab: '配置信息',
},{
   key: 1,
   tab: '页面地址',
},{
   key: 2,
   tab: '充值信息',
},{
   key: 3,
   tab: '协议内容',
}]

<PageHeaderLayout
  nav={breadMenu}
  title='车辆管理列表'
  content='二级供应商下所有的车辆'
  logo='https://gw.alipayobjects.com/zos/rmsportal/BiazfanxmamNRoxxVxka.png'
  action='按钮'
  extraContent='右侧展示内容'
  tabList={tabList}
  tabDefaultActiveKey='0'
  tabActiveKey='0'
  tabBarExtraContent='额外元素'
  onTabChange={(tabsKey) => {...})
  copyright='公交云版权所有'
  top='头部显示的类容'
>
  // 中间部分的内容
</PageHeaderLayout>

path参数说明

参数名 描述 类型 是否必填 备注
nav 面包屑 array 格式见上代码的breadMenu定义格式
title 页面标题 string 展示效果可见:https://preview.pro.ant.design/dashboard/workplace
content 标题下的副标题 string 展示效果可见:https://preview.pro.ant.design/dashboard/workplace
logo 需要图片时展示 string 展示效果可见:https://preview.pro.ant.design/dashboard/workplace
action 右侧需要按钮丛时预留 object 展示效果可见:https://preview.pro.ant.design/profile/advanced
extraContent 右侧额外显示信息 object 展示效果可见: https://preview.pro.ant.design/profile/advanced
tabList tab切换选项 array 格式见上代码的tabList定义格式,展示效果可见https://preview.pro.ant.design/profile/advanced
tabDefaultActiveKey tab默认选中的key string 默认第一个
tabActiveKey tab选中的key string 默认第一个
onTabChange tab点击之后的回调方法 function 返回参数为对应的key
copyright 页面版权信息 object
top 头部内容 object

ReviewImage

查看大图,利用antd-design的Modal组件,实现点击小图查看大图的功能,只有简单的显示,没有缩略图,左右滑动的功能。

调用方法:

import {ReviewImage} from 'dt-antd';

{showModal &&
  <ReviewImage
    picUrl={ModalImg}
    onCancel={()=>{
      this.setState({showModal: false})
    }}
  />
}

path参数说明

参数名 描述 类型 是否必填
picUrl 查看大图的图片地址 string
onCancel 点击关闭的回调函数 function

DrawerDetail

抽屉查看详情,只展示字段部分。

调用方法:

import {DrawerDetail} from 'dt-antd';

const data = [{
  title: '基本信息',
  children: [{
    title: '姓名',
    content: 'string类型',
    col: 24, 
  }, {
    title: '头像',
    picUrl: '图片url',
    col: 24, 
  }, {
    title: '博客',
    linkUrl: '链接地址',
    col: 24, 
  }, {
    title: '标签',
    tags: ['网购达人','运动健儿','00后'],,
    col: 24, 
  }]
}, {
  title: '技能信息',
  children: [{
    title: '额外技能',
    content: '英语八级',
    col: 24,
  }]
}]

{data && <Detail data={data} />}

path参数说明

参数名 子参数 描述 类型 是否必填
title 显示的副标题 string
children 要显示的详情数据 array
title label字段 string
col 显示的占比,默认为24(占整行),可选12(占半行)。
content label对应的值,文字 string 和下面的参数必选其一
picUrl 展示的图片url,可查看大图 string
linkUrl 带链接的链接地址 string
tags 标签,用的antdesign的Tag标签 array

TableSearch

抽屉查看详情,只展示字段部分。

调用方法:

import {TableSearch} from 'dt-antd';

const searchMenu = {
  // 常在的选项
  open: [{
    id: 'rule',
    label: '规则编号',
    type: 'input', // input输入框
    placeholder: '请输入规则编号',
    defaultValue: '默认值',
    isRequire: true, // 是否必填
    other: {}, // 其它的属性        
  }, {
    id:'status',
    label: '选择时间',
    type: 'timePicker', 
    placeholder: '请输入时间',
    other: {}, // 其它的属性     
  },{
    id: 'rule1',
    label: '选择日期范围',
    type: 'rangePicker', 
    placeholder: '请输入选择日期范围'
    other: {}, // 其它的属性     
  }, {
    id:'status1',
    label: '使用状态',
    type: 'select', // 下拉框
    defaultValue: '', // 默认值
    option: [{
      label: '关闭',
      value: 4,
    }], 
    other: {}, // 其它的属性     
  },],
  // 被隐藏起来的选项,如果默认全部显示,则不调用
  hidden: [{
    id: 'date',
    label: '更新日期',
    type: 'datePicker', // 日期选择器
    placeholder: '请输入更新日期',
    other: {}, // 其它的属性     
  }],
  // 新增按钮,默认白色背景的按钮,需要更改请重写组件  
  btns:[{
    text: '导出',
    callBack: this.handleOut,
  }],
  searchCallBack: (values) => console.log(values), // 查询的回调函数
  resetCallBack: this.handleFormReset, // 重置的回调函数
  // 除查询和重置外还要加的按钮组,默认加载查询前面,如不满足,重改组件。暂时用不到,所以没做,如果需要,请再对组件进行拓展
  btns: [{
    type: 'button',
    label: '导出',
    callBack: this.handleSearch, // 回调函数
  }]
}

<TableSearch {...searchMenu} />

path参数说明

参数名 子参数 三级参数 描述 类型 是否必填
open 常开的搜索选项 array
id 字段名 string
label label名 string
type 类型 string
input 输入框
timePicker 选择时间
rangePicker 选择日期
select 下拉框
option 下拉框的选项 array type为select时必填
label 显示的文字
value 对应的key
placeholder 默认提示文字 string
defaultValue 默认值 string
isRequire 是否必填,默认否 bool
other 其它的拓展属性 object
hidden 默认隐藏的搜索选项,点展开才出现(参数配置和open一致) array
searchCallBack 搜索按钮的回调函数,返回参数values是json function
resetCallBack 充值按钮的回调函数,无返回参数 function
btns 默认有搜索和重置,除此之外还需要添加其它按钮再这里配置 array
type 类型,目前只支持'button' string
label 按钮上显示的文字 string
callBack 回调函数,无参数返回 function

TableSearchSmall

参数与TableSearch一样,只是启用此种模式后,没有title没有更多所有搜索项直接平铺过来

StandardTable

表格的封装组件,只能满足部分功能:【列表展示,全选,列固定宽度底部有横向滚动条,左侧和右侧某列固定,页脚】

调用方法:

import {StandardTable} from 'dt-antd';

const data={
  list: list && list.data, // 数据
  pagination: { // 分页
    total: list ? list.rowCount : 1, // 总条数
    pageSize: pageSize, // 总页数
    current: currentNo, // 当前页码
  },
}

const columns = [{
  title: '一级供应商名称', // 表头名
  dataIndex: 'enterpriseName', // 字段名
  key: 'enterpriseName', // 字段名,不能少
  render: (text, record) => record.id, // 拓展
  width: 500, // 宽度
  fixed: 'left', // 固定侧
}]

const selectBtns = [{
  title: '批量删除',
  judgeShow: true,
  callBack: () => console.log(this.state.selectedRows)
}] 

<StandardTable            
  loading={loading}
  data={data}
  columns={columns}
  rowKey={columns => columns.id}
  onChange={(selectedRowKeys, selectedRows)=>console.log(selectedRowKeys, selectedRows)}
  noCheck={true}
  footer=footer={() =><span>实收总金额: 5元</span>}
  onSelectRow={rows=>console.log(rows)}
  selectBtns={selectBtns}
  scroll={{x: 500}}
  cleanSelectRow={true}
/> 

path参数说明

参数名 子参数 描述 类型 是否必填 备注
loading 显示加载框 bool
data 展示的数据 object
list 表格数据 array
pagination 分页设置 object 配置参看antdesign官网的pagination组件,https://ant.design/components/pagination-cn/
columns 表头设置 array 具体配置项看antdesign的table组件,https://ant.design/components/table-cn/
rowKey 每行对应的key,每行不能重复,建议用id string或int
onChange 表格分页状态改变之后 function Function(selectedRowKeys, selectedRows)
onSelectRow 勾选之后 function function(rows),返回被勾选的rows
cleanSelectRow 清空所有勾选项 bool true表示清空,常用于外部按钮控制,需要再onSelectRow回调函数里重置为false以不影响正常使用
noCheck 是否有全选,默认为false bool
checkOther 选择之后的显示自定义,启用后除了自定义内容什么都不显示 object
selectBtns 如果有全选,选中之后的公用操作 object
title 显示的文字 string
judgeShow 是否要选中行才显示 bool
callBack 点击的回调函数 function 没有返回参数,可自行去onChange里取已经勾选的值
footer 页脚 function
scroll 横向宽度 object 这个值必须等于所有列的width相加之和,具体看antdesign官网的table组件

UploadImage

三个方法的参数是一样的,所以写在一起。

UploadImage:上传图片,困图模式(官方示例用户头像例子),官方示例:https://ant.design/components/upload-cn/ UploadImageSmall: 上传图片,官方示例图片列表样式 UploadImageAvatar: 上传图片。定制公交新增线路专用

调用方法:

import {UploadImage} from 'dt-antd';

<UploadImage
  url={`${url.uploadImage}?identityType=1`}
  name='bizLicCodeAttach'
  imageUrl={detail && detail.bizLicCodeAttach}
  headers={headers}
  data={data}
  handleUploadImg= {(imageUrl)=>{                                       
    this.setState({
      bizLicCodeAttach: imageUrl
    }) 
  }}
/> 

path参数说明

参数名 描述 类型 是否必填 备注
url 上传的服务器地址 string
name 字段名,类似id string
imageUrl 默认图片URL string
headers 请求对应的headers object
data 请求对应的参数 object
handleUploadImg 上传后的回调函数 function 返回参数为oss地址

Drag

拖拽排序组件。

调用方法:

import {Drag} from 'dt-antd';

const value = [
  {content: 'div1',code: '01',sort: 0},
  {content: 'div2',code: '02',sort: 1},
  {content: 'div3',code: '03',sort: 2},
  {content: 'div4',code: '04',sort: 3},
  {content: 'div5',code: '05',sort: 4},
]
<Drag
  value={value}
  sortKey='sort'
  codeKey='code'
  style={{color: '#fff'}}
  onChange={data => console.log(data)}
/>

path参数说明

参数名 子参数 描述 类型 是否必填 备注
value 展示的数据 object
conent 展示的内容 object
code 这个字段作为拖拽元素的key string 这个字段名可改,但必须要有这个字段
sort 这个字段作为排序 int 这个字段名可改,但必须要有这个字段
style 样式 object
sortKey 排序的对应字段,示例中对应的是value中的sort string 默认sort
codeKey 拖拽元素的对应字段,示例中对应的是value中的code string 默认为code
onChange 拖拽后的事件,返回重新排序后的value数据 function

Utils

一些常见的公用方法,可直接重复调用。

调用方法:

import {Utils} from 'dt-antd';

const date = Utils.FormatDate(1535701322000); // 2018-10-25
const name = Utils.getQueryString('name'); // 1
const price = Utils.FormatPrice(100000, true, 2, ',', '.'); // 1,000.00

path参数说明

方法名 参数 描述 类型 是否必填 备注
getQueryString 获取url参数 如https://a.com?name=1&b=2获取name,b的值
name 参数名 string 返回对应的值
FormatDate 格式化时间,时间戳转为[yyyy-MM-dd hh:mm:ss]
times 要转化的时间戳 int
format 格式化后的格式 string 默认 yyyy-MM-dd hh:mm:ss
FormatPrice 格式化金额,并加千分位
number 要格式化的数 int
isMoney 传进来的金额单位是否为分,默认为true bool 默认true
decimals 保留几位小数 int 默认2
thousands_sep 千分位符号 string 默认,
dec_point 小数点符号 string 默认.
getTimeDistance 获取时间区间
type 获取时间区间格式,today今日,yestoday昨日,oneWeek最近7天,twoWeek最近14天,week本周,month本月,year今年 string 目前只有定制公交的优惠券用到

FormStyle

用到from编辑页的formItem的样式。

调用方法:

import {FormStyle} from 'dt-antd';

<FormItem {...FormStyle.editFormDrawer} label=""></FormItem>
<FormItem {...FormStyle.editFormDrawer} label=""></FormItem>
<FormItem {...FormStyle.editFormDrawer} label=""></FormItem>
<FormItem {...FormStyle.editFormDrawer} label=""></FormItem>


path参数说明

样式名 描述
editFormDrawer 编辑时的一行显示一列的fromItemStyle
editFormDrawerSmall 编辑时的一行显示一列的fromItemStyle,label占比只有5
formItemLayout 新开页面的formItem样式
submitFormLayout 提交按钮行

TableCommon

一些常见的公用方法,可直接重复调用。

调用方法:

import {TableCommon} from 'dt-antd';

handleStandardTableChange = (pagination, filtersArg, sorter) =>{
  TableCommon.tableChange({
    state: this.state,
    pagination,
    callBack: (json) => {
      console.log(json)
      this.setState(json);
      this.props.getList(json.searchList);
    }
  });    
}

handleSearch = (values) => {
    TableCommon.tableSearch({
      state: this.state,
      values,
      callBack: (json)=>{
        this.setState(json);
        this.props.getList(json.searchList);
      }
    });    
  }

path参数说明

方法名 参数 描述 类型 是否必填
tableChange 表格更改之后的方法,改变state重新查询
state 当前的state,searchList表示搜索条件,每个页面需一致 object
callBack 回调函数,改变state,并重新搜索 function
pagination 分页的返回参数 object
tableSearch 搜索表格(搜索按钮点击)
state 当前的state,searchList表示搜索条件,每个页面需一致 object
values 搜索的条件,只接收最终的值 object
callBack 回调函数,改变state,并重新搜索 function
tableSearchCustom 和tableSearch一样,只限定制公交项目使用

InputVerify

输入的验证规则,正则表达式。

调用方法:

import {InputVerify} from 'dt-antd';

<FormItem {...FormStyle.editFormDrawer} label="mobile">
  {getFieldDecorator('mobile', {    
    rules: [{
      required: true, 
      whitespace: true,
      pattern: InputVerify.mobile,
      message: 'please input your mobile'
    }],
  })(
    <Input maxLength={30} placeholder="input your mobile" />
  )}
</FormItem>


path参数说明

样式名 描述
mobile 手机号
carNo 车牌号
IDnumber 身份证号
passwordM 不能输入汉字

发布

发布前,还有一件事就是为你的模块添加一个入口文件 index.js,全部指向编译后的代码

export { default as MyComponent } from './lib/MyComponent';
export { default as SiderMenu } from './lib/SiderMenu/index';
export { default as PageHeaderLayout } from './lib/pageHeaderLayout/index';
...

接下来就可以发布到 NPM 了。

npm run compile
npm publish lib

首次发布需要输入用户名密码描述等,教程可百度。之后每次发布只需要publish即可。

注意:每次发布时,package.json里的版本号version都要变更,不能与以往提交的代码冲突,否则会导致发布不成功,切记!

使用

可以直接通过 NPM 安装

npm install dt-antd --save-dev

然后在父级项目的代码里导入模块

import MyComponent,{SiderMenu,PageHeaderLayout} from 'dt-antd'

此时导入的直接是 ES5 代码,跳过了组件的编译过程从而避免了出现组件 Babel 版本和父级项目 Babel 版本不一致的问题,并且速度更快,是不是很棒!

使用源码

如果只想用其中的一个或某几个,这时可以这样导入:

import MyComponent from 'react-component-example/src/MyComponent.jsx'

这种情况下,导入的是 ES6 代码,并且会被加入父级项目的编译过程。此外,父级项目在编译这个文件的时候会读取组件的 .babelrc 配置文件。

如何后续开发

clone此源码到本地,起初尝试时请修改package.json的name,改一个自定义的名字如vivy-learn,发布后npm install vivy-learn,并import组件引入,确认每个组件都能正常引用后,再将name改回dt-antd,并提交到git。

关于

本文使用的 babel 版本

./node_modules/.bin/babel --version 6.4.5 (babel-core 6.4.5)

LICENSE

MIT