amis 1.3.5-beta.6 → 1.4.1-echarts-5.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (219) hide show
  1. package/lib/components/Badge.d.ts +15 -2
  2. package/lib/components/Badge.js +47 -4
  3. package/lib/components/Badge.js.map +2 -2
  4. package/lib/components/Button.d.ts +24 -22
  5. package/lib/components/Button.js +13 -7
  6. package/lib/components/Button.js.map +2 -2
  7. package/lib/components/Checkbox.d.ts +1 -1
  8. package/lib/components/Checkbox.js +1 -1
  9. package/lib/components/Checkbox.js.map +2 -2
  10. package/lib/components/Drawer.js +1 -1
  11. package/lib/components/Drawer.js.map +2 -2
  12. package/lib/components/Modal.js +1 -1
  13. package/lib/components/Modal.js.map +2 -2
  14. package/lib/components/RichText.d.ts +6 -1
  15. package/lib/components/RichText.js +243 -8
  16. package/lib/components/RichText.js.map +2 -2
  17. package/lib/components/Select.d.ts +7 -0
  18. package/lib/components/Select.js.map +2 -2
  19. package/lib/components/Steps.d.ts +3 -3
  20. package/lib/components/Steps.js.map +1 -1
  21. package/lib/components/WithRemoteConfig.d.ts +8 -0
  22. package/lib/components/WithRemoteConfig.js +28 -2
  23. package/lib/components/WithRemoteConfig.js.map +2 -2
  24. package/lib/components/calendar/DaysView.js +2 -2
  25. package/lib/components/calendar/DaysView.js.map +2 -2
  26. package/lib/components/condition-builder/Field.js +0 -1
  27. package/lib/components/condition-builder/Field.js.map +2 -2
  28. package/lib/components/condition-builder/Value.js +2 -1
  29. package/lib/components/condition-builder/Value.js.map +2 -2
  30. package/lib/components/condition-builder/types.d.ts +5 -0
  31. package/lib/components/condition-builder/types.js.map +1 -1
  32. package/lib/components/icons.js +2 -0
  33. package/lib/components/icons.js.map +2 -2
  34. package/lib/factory.d.ts +5 -1
  35. package/lib/factory.js +9 -4
  36. package/lib/factory.js.map +2 -2
  37. package/lib/helper.css.map +1 -1
  38. package/lib/icons/loading-outline.js +7 -0
  39. package/lib/index.js +1 -1
  40. package/lib/locale/de-DE.js +1 -0
  41. package/lib/locale/de-DE.js.map +2 -2
  42. package/lib/locale/en-US.js +2 -1
  43. package/lib/locale/en-US.js.map +2 -2
  44. package/lib/locale/zh-CN.js +2 -1
  45. package/lib/locale/zh-CN.js.map +2 -2
  46. package/lib/renderers/Action.d.ts +9 -1
  47. package/lib/renderers/Action.js +5 -5
  48. package/lib/renderers/Action.js.map +2 -2
  49. package/lib/renderers/CRUD.d.ts +2 -2
  50. package/lib/renderers/CRUD.js +11 -20
  51. package/lib/renderers/CRUD.js.map +2 -2
  52. package/lib/renderers/Collapse.d.ts +1 -1
  53. package/lib/renderers/Collapse.js +5 -1
  54. package/lib/renderers/Collapse.js.map +2 -2
  55. package/lib/renderers/Dialog.d.ts +0 -252
  56. package/lib/renderers/Dialog.js +1 -1
  57. package/lib/renderers/Dialog.js.map +2 -2
  58. package/lib/renderers/DropDownButton.d.ts +8 -0
  59. package/lib/renderers/DropDownButton.js +6 -4
  60. package/lib/renderers/DropDownButton.js.map +2 -2
  61. package/lib/renderers/Form/ButtonGroupSelect.js +3 -0
  62. package/lib/renderers/Form/ButtonGroupSelect.js.map +2 -2
  63. package/lib/renderers/Form/DiffEditor.d.ts +0 -2
  64. package/lib/renderers/Form/Editor.d.ts +0 -2
  65. package/lib/renderers/Form/Editor.js +1 -1
  66. package/lib/renderers/Form/Editor.js.map +2 -2
  67. package/lib/renderers/Form/InputExcel.d.ts +5 -0
  68. package/lib/renderers/Form/InputExcel.js +24 -3
  69. package/lib/renderers/Form/InputExcel.js.map +2 -2
  70. package/lib/renderers/Form/InputImage.d.ts +8 -0
  71. package/lib/renderers/Form/InputImage.js +2 -1
  72. package/lib/renderers/Form/InputImage.js.map +2 -2
  73. package/lib/renderers/Form/InputTable.d.ts +23 -5
  74. package/lib/renderers/Form/InputTable.js +32 -3
  75. package/lib/renderers/Form/InputTable.js.map +2 -2
  76. package/lib/renderers/Json.js +5 -1
  77. package/lib/renderers/Json.js.map +2 -2
  78. package/lib/renderers/Nav.d.ts +52 -22
  79. package/lib/renderers/Nav.js +100 -15
  80. package/lib/renderers/Nav.js.map +2 -2
  81. package/lib/renderers/Page.js +4 -1
  82. package/lib/renderers/Page.js.map +2 -2
  83. package/lib/renderers/Service.d.ts +10 -1
  84. package/lib/renderers/Service.js +85 -3
  85. package/lib/renderers/Service.js.map +2 -2
  86. package/lib/renderers/Steps.d.ts +4 -4
  87. package/lib/renderers/Steps.js +5 -2
  88. package/lib/renderers/Steps.js.map +2 -2
  89. package/lib/renderers/Table/TableBody.d.ts +1 -1
  90. package/lib/renderers/Table/TableBody.js +5 -1
  91. package/lib/renderers/Table/TableBody.js.map +2 -2
  92. package/lib/renderers/Table/TableContent.d.ts +1 -1
  93. package/lib/renderers/Table/TableContent.js +4 -0
  94. package/lib/renderers/Table/TableContent.js.map +2 -2
  95. package/lib/renderers/Table/index.d.ts +8 -3
  96. package/lib/renderers/Table/index.js +80 -45
  97. package/lib/renderers/Table/index.js.map +2 -2
  98. package/lib/store/app.d.ts +0 -1
  99. package/lib/store/combo.d.ts +0 -2
  100. package/lib/store/crud.d.ts +3 -3
  101. package/lib/store/crud.js +41 -36
  102. package/lib/store/crud.js.map +2 -2
  103. package/lib/store/form.d.ts +0 -1
  104. package/lib/store/modal.d.ts +1 -1
  105. package/lib/store/modal.js +4 -0
  106. package/lib/store/modal.js.map +2 -2
  107. package/lib/store/root.d.ts +0 -1
  108. package/lib/store/service.d.ts +0 -1
  109. package/lib/store/service.js +0 -13
  110. package/lib/store/service.js.map +2 -2
  111. package/lib/store/table.d.ts +1 -2
  112. package/lib/store/table.js +44 -3
  113. package/lib/store/table.js.map +2 -2
  114. package/lib/themes/ang-ie11.css +597 -57
  115. package/lib/themes/ang.css +597 -57
  116. package/lib/themes/ang.css.map +1 -1
  117. package/lib/themes/antd-ie11.css +597 -57
  118. package/lib/themes/antd.css +597 -57
  119. package/lib/themes/antd.css.map +1 -1
  120. package/lib/themes/cxd-ie11.css +705 -177
  121. package/lib/themes/cxd.css +705 -177
  122. package/lib/themes/cxd.css.map +1 -1
  123. package/lib/themes/dark-ie11.css +597 -57
  124. package/lib/themes/dark.css +597 -57
  125. package/lib/themes/dark.css.map +1 -1
  126. package/lib/themes/default.css +705 -177
  127. package/lib/themes/default.css.map +1 -1
  128. package/lib/utils/api.js +12 -0
  129. package/lib/utils/api.js.map +2 -2
  130. package/lib/utils/attachmentAdpator.d.ts +7 -0
  131. package/lib/utils/attachmentAdpator.js +82 -0
  132. package/lib/utils/attachmentAdpator.js.map +13 -0
  133. package/lib/utils/helper.js.map +2 -2
  134. package/lib/utils/validations.js +62 -5
  135. package/lib/utils/validations.js.map +2 -2
  136. package/package.json +46 -39
  137. package/schema.json +343 -44
  138. package/scss/_mixins.scss +29 -0
  139. package/scss/_properties.scss +27 -11
  140. package/scss/components/_badge.scss +67 -2
  141. package/scss/components/_button.scss +35 -3
  142. package/scss/components/_image-gallery.scss +1 -1
  143. package/scss/components/_markdown.scss +266 -0
  144. package/scss/components/_nav.scss +109 -35
  145. package/scss/components/_spinner.scss +6 -2
  146. package/scss/components/form/_group.scss +4 -0
  147. package/scss/themes/_common.scss +1 -0
  148. package/scss/themes/_cxd-variables.scss +20 -20
  149. package/sdk/ang-ie11.css +741 -59
  150. package/sdk/ang.css +755 -59
  151. package/sdk/antd-ie11.css +731 -51
  152. package/sdk/antd.css +755 -59
  153. package/sdk/charts.js +13 -13
  154. package/sdk/color-picker.js +67 -67
  155. package/sdk/cropperjs.js +2 -2
  156. package/sdk/cxd-ie11.css +1200 -520
  157. package/sdk/cxd.css +863 -179
  158. package/sdk/dark-ie11.css +741 -59
  159. package/sdk/dark.css +755 -59
  160. package/sdk/exceljs.js +1 -1
  161. package/sdk/helper.css.map +1 -1
  162. package/sdk/locale/de-DE.js +1 -0
  163. package/sdk/markdown.js +69 -69
  164. package/sdk/papaparse.js +1 -1
  165. package/sdk/renderers/Form/CityDB.js +1 -1
  166. package/sdk/rest.js +22 -24
  167. package/sdk/rich-text.js +62 -64
  168. package/sdk/sdk-ie11.css +1200 -520
  169. package/sdk/sdk.css +863 -179
  170. package/sdk/sdk.js +1118 -1112
  171. package/sdk/thirds/hls.js/hls.js +1 -1
  172. package/sdk/thirds/mpegts.js/mpegts.js +1 -1
  173. package/sdk/tinymce.js +57 -57
  174. package/sdk.zip +0 -0
  175. package/src/components/Badge.tsx +111 -20
  176. package/src/components/Button.tsx +23 -7
  177. package/src/components/Checkbox.tsx +5 -2
  178. package/src/components/Drawer.tsx +3 -2
  179. package/src/components/Modal.tsx +3 -2
  180. package/src/components/RichText.tsx +284 -3
  181. package/src/components/Select.tsx +1 -0
  182. package/src/components/Steps.tsx +3 -3
  183. package/src/components/WithRemoteConfig.tsx +37 -2
  184. package/src/components/calendar/DaysView.tsx +2 -2
  185. package/src/components/condition-builder/Field.tsx +1 -2
  186. package/src/components/condition-builder/Value.tsx +3 -0
  187. package/src/components/condition-builder/types.ts +6 -0
  188. package/src/components/icons.tsx +2 -0
  189. package/src/factory.tsx +13 -3
  190. package/src/icons/loading-outline.svg +4 -0
  191. package/src/locale/de-DE.ts +1 -0
  192. package/src/locale/en-US.ts +2 -1
  193. package/src/locale/zh-CN.ts +2 -1
  194. package/src/renderers/Action.tsx +66 -13
  195. package/src/renderers/CRUD.tsx +13 -33
  196. package/src/renderers/Collapse.tsx +5 -1
  197. package/src/renderers/Dialog.tsx +1 -1
  198. package/src/renderers/DropDownButton.tsx +21 -4
  199. package/src/renderers/Form/ButtonGroupSelect.tsx +3 -0
  200. package/src/renderers/Form/Editor.tsx +19 -20
  201. package/src/renderers/Form/InputExcel.tsx +28 -3
  202. package/src/renderers/Form/InputImage.tsx +23 -8
  203. package/src/renderers/Form/InputTable.tsx +88 -9
  204. package/src/renderers/Json.tsx +10 -1
  205. package/src/renderers/Nav.tsx +165 -36
  206. package/src/renderers/Page.tsx +3 -1
  207. package/src/renderers/Service.tsx +101 -3
  208. package/src/renderers/Steps.tsx +12 -9
  209. package/src/renderers/Table/TableBody.tsx +3 -2
  210. package/src/renderers/Table/TableContent.tsx +3 -1
  211. package/src/renderers/Table/index.tsx +61 -13
  212. package/src/store/crud.ts +34 -38
  213. package/src/store/modal.ts +4 -0
  214. package/src/store/service.ts +0 -19
  215. package/src/store/table.ts +48 -0
  216. package/src/utils/api.ts +11 -0
  217. package/src/utils/attachmentAdpator.ts +90 -0
  218. package/src/utils/helper.ts +1 -0
  219. package/src/utils/validations.ts +80 -12
@@ -118,7 +118,7 @@ export default class EditorControl extends React.Component<EditorProps, any> {
118
118
  static defaultProps: Partial<EditorProps> = {
119
119
  language: 'javascript',
120
120
  editorTheme: 'vs',
121
- allowFullscreen: false,
121
+ allowFullscreen: true,
122
122
  options: {
123
123
  automaticLayout: true,
124
124
  selectOnLineNumbers: true,
@@ -294,26 +294,25 @@ export const availableLanguages = [
294
294
  'yaml'
295
295
  ];
296
296
 
297
- export const EditorControls: Array<
298
- typeof EditorControl
299
- > = availableLanguages.map((lang: string) => {
300
- @FormItem({
301
- type: `${lang}-editor`,
302
- sizeMutable: false
303
- })
304
- class EditorControlRenderer extends EditorControl {
305
- static lang = lang;
306
- static displayName = `${lang[0].toUpperCase()}${lang.substring(
307
- 1
308
- )}EditorControlRenderer`;
309
- static defaultProps = {
310
- ...EditorControl.defaultProps,
311
- language: lang
312
- };
313
- }
297
+ export const EditorControls: Array<typeof EditorControl> =
298
+ availableLanguages.map((lang: string) => {
299
+ @FormItem({
300
+ type: `${lang}-editor`,
301
+ sizeMutable: false
302
+ })
303
+ class EditorControlRenderer extends EditorControl {
304
+ static lang = lang;
305
+ static displayName = `${lang[0].toUpperCase()}${lang.substring(
306
+ 1
307
+ )}EditorControlRenderer`;
308
+ static defaultProps = {
309
+ ...EditorControl.defaultProps,
310
+ language: lang
311
+ };
312
+ }
314
313
 
315
- return EditorControlRenderer;
316
- });
314
+ return EditorControlRenderer;
315
+ });
317
316
 
318
317
  @FormItem({
319
318
  type: 'js-editor',
@@ -28,6 +28,11 @@ export interface InputExcelControlSchema extends FormBaseControl {
28
28
  * 是否包含空内容,主要用于二维数组模式
29
29
  */
30
30
  includeEmpty: boolean;
31
+
32
+ /**
33
+ * 纯文本模式
34
+ */
35
+ plainText: boolean;
31
36
  }
32
37
 
33
38
  export interface ExcelProps
@@ -48,12 +53,15 @@ export default class ExcelControl extends React.PureComponent<
48
53
  static defaultProps: Partial<ExcelProps> = {
49
54
  allSheets: false,
50
55
  parseMode: 'object',
51
- includeEmpty: true
56
+ includeEmpty: true,
57
+ plainText: true
52
58
  };
53
59
  state: ExcelControlState = {
54
60
  open: false
55
61
  };
56
62
 
63
+ ExcelJS: any;
64
+
57
65
  @autobind
58
66
  handleDrop(files: File[]) {
59
67
  const {allSheets, onChange} = this.props;
@@ -63,6 +71,7 @@ export default class ExcelControl extends React.PureComponent<
63
71
  reader.onload = async () => {
64
72
  if (reader.result) {
65
73
  import('exceljs').then(async (ExcelJS: any) => {
74
+ this.ExcelJS = ExcelJS;
66
75
  const workbook = new ExcelJS.Workbook();
67
76
  await workbook.xlsx.load(reader.result);
68
77
  if (allSheets) {
@@ -88,7 +97,7 @@ export default class ExcelControl extends React.PureComponent<
88
97
  */
89
98
  readWorksheet(worksheet: any) {
90
99
  const result: any[] = [];
91
- const {parseMode} = this.props;
100
+ const {parseMode, plainText} = this.props;
92
101
 
93
102
  if (parseMode === 'array') {
94
103
  worksheet.eachRow((row: any, rowNumber: number) => {
@@ -107,7 +116,23 @@ export default class ExcelControl extends React.PureComponent<
107
116
  const data: any = {};
108
117
  row.eachCell((cell: any, colNumber: any) => {
109
118
  if (firstRowValues[colNumber]) {
110
- data[firstRowValues[colNumber]] = cell.value;
119
+ let value = cell.value;
120
+ if (plainText) {
121
+ const ExcelValueType = this.ExcelJS.ValueType;
122
+ if (cell.type === ExcelValueType.Hyperlink) {
123
+ value = cell.value.hyperlink;
124
+ } else if (cell.type === ExcelValueType.Formula) {
125
+ value = cell.value.result;
126
+ } else if (cell.type === ExcelValueType.RichText) {
127
+ value = cell.value.richText
128
+ .map((item: any) => item.text)
129
+ .join('');
130
+ } else if (cell.type === ExcelValueType.Error) {
131
+ value = '';
132
+ }
133
+ }
134
+
135
+ data[firstRowValues[colNumber]] = value;
111
136
  }
112
137
  });
113
138
  result.push(data);
@@ -110,6 +110,16 @@ export interface ImageControlSchema extends FormBaseControl {
110
110
  scalable?: boolean;
111
111
  };
112
112
 
113
+ /**
114
+ * 裁剪后的图片类型
115
+ */
116
+ cropFormat?: string;
117
+
118
+ /**
119
+ * 裁剪后的质量
120
+ */
121
+ cropQuality?: number;
122
+
113
123
  /**
114
124
  * 是否允许二次裁剪。
115
125
  */
@@ -862,14 +872,19 @@ export default class ImageControl extends React.Component<
862
872
  }
863
873
 
864
874
  handleCrop() {
865
- this.cropper.getCroppedCanvas().toBlob((file: File) => {
866
- this.addFiles([file]);
867
- this.setState({
868
- cropFile: undefined,
869
- locked: false,
870
- lockedReason: ''
871
- });
872
- });
875
+ const {cropFormat, cropQuality} = this.props;
876
+ this.cropper.getCroppedCanvas().toBlob(
877
+ (file: File) => {
878
+ this.addFiles([file]);
879
+ this.setState({
880
+ cropFile: undefined,
881
+ locked: false,
882
+ lockedReason: ''
883
+ });
884
+ },
885
+ cropFormat || 'image/png',
886
+ cropQuality || 1
887
+ );
873
888
  }
874
889
 
875
890
  cancelCrop() {
@@ -30,6 +30,26 @@ export interface TableControlSchema
30
30
  */
31
31
  addable?: boolean;
32
32
 
33
+ /**
34
+ * 可复制新增
35
+ */
36
+ copyable?: boolean;
37
+
38
+ /**
39
+ * 复制按钮文字
40
+ */
41
+ copyBtnLabel?: string;
42
+
43
+ /**
44
+ * 复制按钮图标
45
+ */
46
+ copyBtnIcon?: string;
47
+
48
+ /**
49
+ * 是否显示复制按钮
50
+ */
51
+ copyAddBtn?: boolean;
52
+
33
53
  /**
34
54
  * 是否可以拖拽排序
35
55
  */
@@ -41,12 +61,12 @@ export interface TableControlSchema
41
61
  addApi?: SchemaApi;
42
62
 
43
63
  /**
44
- * 新增按钮
64
+ * 新增按钮文字
45
65
  */
46
66
  addBtnLabel?: string;
47
67
 
48
68
  /**
49
- * 新增图标
69
+ * 新增按钮图标
50
70
  */
51
71
  addBtnIcon?: string;
52
72
 
@@ -73,12 +93,12 @@ export interface TableControlSchema
73
93
  /**
74
94
  * 更新按钮名称
75
95
  */
76
- updateBtnLabel?: string;
96
+ editBtnLabel?: string;
77
97
 
78
98
  /**
79
99
  * 更新按钮图标
80
100
  */
81
- updateBtnIcon?: string;
101
+ editBtnIcon?: string;
82
102
 
83
103
  /**
84
104
  * 确认按钮文字
@@ -172,7 +192,8 @@ export default class FormTable extends React.Component<TableProps, TableState> {
172
192
  placeholder: '空',
173
193
  scaffold: {},
174
194
  addBtnIcon: 'plus',
175
- updateBtnIcon: 'pencil',
195
+ copyBtnIcon: 'copy',
196
+ editBtnIcon: 'pencil',
176
197
  deleteBtnIcon: 'minus',
177
198
  confirmBtnIcon: 'check',
178
199
  cancelBtnIcon: 'close',
@@ -188,6 +209,7 @@ export default class FormTable extends React.Component<TableProps, TableState> {
188
209
  'showAddBtn',
189
210
  'addable',
190
211
  'removable',
212
+ 'copyable',
191
213
  'editable',
192
214
  'addApi',
193
215
  'updateApi',
@@ -423,6 +445,26 @@ export default class FormTable extends React.Component<TableProps, TableState> {
423
445
  return onAction && onAction(action, ctx, ...rest);
424
446
  }
425
447
 
448
+ copyItem(index: number) {
449
+ const {needConfirm} = this.props;
450
+ const items = this.state.items.concat();
451
+
452
+ items.splice(index + 1, 0, items[index]);
453
+ index = Math.min(index + 1, items.length - 1);
454
+ this.setState(
455
+ {
456
+ items
457
+ },
458
+ () => {
459
+ if (needConfirm === false) {
460
+ this.emitValue();
461
+ } else {
462
+ this.startEdit(index, true);
463
+ }
464
+ }
465
+ );
466
+ }
467
+
426
468
  addItem(index: number) {
427
469
  const {needConfirm, scaffold, columns} = this.props;
428
470
  const items = this.state.items.concat();
@@ -653,6 +695,38 @@ export default class FormTable extends React.Component<TableProps, TableState> {
653
695
  });
654
696
  }
655
697
 
698
+ if (props.copyable && props.showCopyBtn !== false) {
699
+ btns.push({
700
+ children: ({
701
+ key,
702
+ rowIndex,
703
+ offset
704
+ }: {
705
+ key: any;
706
+ rowIndex: number;
707
+ offset: number;
708
+ }) =>
709
+ ~this.state.editIndex && needConfirm !== false ? null : (
710
+ <Button
711
+ classPrefix={ns}
712
+ size="sm"
713
+ key={key}
714
+ level="link"
715
+ tooltip={__('Table.copyRow')}
716
+ tooltipContainer={
717
+ env && env.getModalContainer ? env.getModalContainer : undefined
718
+ }
719
+ onClick={this.copyItem.bind(this, rowIndex + offset, undefined)}
720
+ >
721
+ {props.copyBtnLabel ? <span>{props.copyBtnLabel}</span> : null}
722
+ {props.copyBtnIcon ? (
723
+ <Icon icon={props.copyBtnIcon} className="icon" />
724
+ ) : null}
725
+ </Button>
726
+ )
727
+ });
728
+ }
729
+
656
730
  if (props.needConfirm === false) {
657
731
  columns = columns.map(column => {
658
732
  const quickEdit = column.quickEdit;
@@ -716,11 +790,16 @@ export default class FormTable extends React.Component<TableProps, TableState> {
716
790
  }
717
791
  onClick={() => this.startEdit(rowIndex + offset)}
718
792
  >
719
- {props.updateBtnLabel ? (
720
- <span>{props.updateBtnLabel}</span>
793
+ {props.updateBtnLabel || props.editBtnLabel ? (
794
+ <span>{props.updateBtnLabel || props.editBtnLabel}</span>
721
795
  ) : null}
722
- {props.updateBtnIcon ? (
723
- <Icon icon={props.updateBtnIcon} className="icon" />
796
+ {/* 兼容之前的写法 */}
797
+ {typeof props.updateBtnIcon !== 'undefined' ? (
798
+ props.updateBtnIcon ? (
799
+ <Icon icon={props.updateBtnIcon} className="icon" />
800
+ ) : null
801
+ ) : props.editBtnIcon ? (
802
+ <Icon icon={props.editBtnIcon} className="icon" />
724
803
  ) : null}
725
804
  </Button>
726
805
  )
@@ -97,6 +97,15 @@ export class JSONField extends React.Component<JSONProps, object> {
97
97
  }
98
98
  }
99
99
 
100
+ let jsonThemeValue = jsonTheme;
101
+ if (isPureVariable(jsonTheme)) {
102
+ jsonThemeValue = resolveVariableAndFilter(
103
+ jsonTheme,
104
+ this.props.data,
105
+ '| raw'
106
+ );
107
+ }
108
+
100
109
  // JsonView 只支持对象,所以不是对象格式需要转成对象格式。
101
110
  if (data && ~['string', 'number'].indexOf(typeof data)) {
102
111
  data = {
@@ -112,7 +121,7 @@ export class JSONField extends React.Component<JSONProps, object> {
112
121
  <JsonView
113
122
  name={false}
114
123
  src={data}
115
- theme={(jsonTheme as any) ?? 'rjv-default'}
124
+ theme={(jsonThemeValue as any) ?? 'rjv-default'}
116
125
  shouldCollapse={this.shouldExpandNode}
117
126
  enableClipboard={false}
118
127
  iconStyle="square"
@@ -1,8 +1,10 @@
1
1
  import React from 'react';
2
+ import Sortable from 'sortablejs';
2
3
  import {Renderer, RendererEnv, RendererProps} from '../factory';
3
4
  import getExprProperties from '../utils/filter-schema';
4
5
  import {filter, evalExpression} from '../utils/tpl';
5
6
  import {
7
+ guid,
6
8
  autobind,
7
9
  createObject,
8
10
  findTree,
@@ -22,6 +24,9 @@ import {
22
24
  } from '../components/WithRemoteConfig';
23
25
  import {Payload} from '../types';
24
26
  import Spinner from '../components/Spinner';
27
+ import cloneDeep from 'lodash/cloneDeep';
28
+ import {isEffectiveApi} from '../utils/api';
29
+ import {Badge, BadgeSchema} from '../components/Badge';
25
30
 
26
31
  export type NavItemSchema = {
27
32
  /**
@@ -45,6 +50,11 @@ export type NavItemSchema = {
45
50
  deferApi?: SchemaApi;
46
51
 
47
52
  children?: Array<NavItemSchema>;
53
+
54
+ /**
55
+ * 角标
56
+ */
57
+ badge?: BadgeSchema
48
58
  } & Omit<BaseSchema, 'type'>;
49
59
 
50
60
  /**
@@ -81,6 +91,26 @@ export interface NavSchema extends BaseSchema {
81
91
  * true 为垂直排列,false 为水平排列类似如 tabs。
82
92
  */
83
93
  stacked?: boolean;
94
+
95
+ /**
96
+ * 更多操作菜单列表
97
+ */
98
+ itemActions?: SchemaCollection;
99
+
100
+ /**
101
+ * 可拖拽
102
+ */
103
+ draggable?: boolean;
104
+
105
+ /**
106
+ * 保存排序的 api
107
+ */
108
+ saveOrderApi?: SchemaApi;
109
+
110
+ /**
111
+ * 角标
112
+ */
113
+ badge?: BadgeSchema;
84
114
  }
85
115
 
86
116
  export interface Link {
@@ -97,6 +127,7 @@ export interface Link {
97
127
  loading?: boolean;
98
128
  loaded?: boolean;
99
129
  [propName: string]: any;
130
+ badge?: BadgeSchema
100
131
  }
101
132
  export interface Links extends Array<Link> {}
102
133
 
@@ -113,7 +144,9 @@ export interface NavigationProps
113
144
  togglerClassName?: string;
114
145
  links?: Array<Link>;
115
146
  loading?: boolean;
116
- render: RendererProps['render']
147
+ render: RendererProps['render'];
148
+ env: RendererEnv;
149
+ reload?: any;
117
150
  }
118
151
 
119
152
  export class Navigation extends React.Component<
@@ -123,6 +156,9 @@ export class Navigation extends React.Component<
123
156
  static defaultProps = {
124
157
  indentSize: 24
125
158
  };
159
+ sortable: Sortable[] = [];
160
+ id: string;
161
+ dragRef?: HTMLElement;
126
162
 
127
163
  @autobind
128
164
  handleClick(link: Link) {
@@ -134,15 +170,85 @@ export class Navigation extends React.Component<
134
170
  this.props.onToggle?.(target);
135
171
  }
136
172
 
173
+ @autobind
174
+ dragRefFn(ref: any) {
175
+ const {draggable} = this.props;
176
+ if (ref && draggable) {
177
+ this.id = guid();
178
+ this.initDragging(ref);
179
+ }
180
+ }
181
+
182
+ initDragging(ref: HTMLElement) {
183
+ const ns = this.props.classPrefix;
184
+ this.sortable.push(new Sortable(
185
+ ref,
186
+ {
187
+ group: `nav-${this.id}`,
188
+ animation: 150,
189
+ handle: `.${ns}Nav-itemDrager`,
190
+ ghostClass: `${ns}Nav-item--dragging`,
191
+ onEnd: async (e: any) => {
192
+ // 没有移动
193
+ if (e.newIndex === e.oldIndex) {
194
+ return;
195
+ }
196
+ const id = e.item.getAttribute('data-id');
197
+ const parentNode = e.to
198
+ if (
199
+ e.newIndex < e.oldIndex &&
200
+ e.oldIndex < parentNode.childNodes.length - 1
201
+ ) {
202
+ parentNode.insertBefore(e.item, parentNode.childNodes[e.oldIndex + 1]);
203
+ } else if (e.oldIndex < parentNode.childNodes.length - 1) {
204
+ parentNode.insertBefore(e.item, parentNode.childNodes[e.oldIndex]);
205
+ } else {
206
+ parentNode.appendChild(e.item);
207
+ }
208
+ const links = cloneDeep(this.props.links) as Link[];
209
+ let parent = links;
210
+ someTree(links, (item: Link, key, level, paths: Link[]) => {
211
+ if (item.id === id) {
212
+ const len = paths.length - 1;
213
+ parent = (~len ? paths[len].children : links) as Link[];
214
+ return true;
215
+ }
216
+ return false;
217
+ });
218
+ parent.splice(e.newIndex, 0, parent.splice(e.oldIndex, 1)[0]);
219
+ const {saveOrderApi, env} = this.props;
220
+ if (saveOrderApi && isEffectiveApi(saveOrderApi)) {
221
+ await env.fetcher(saveOrderApi as SchemaApi, {data: links}, {method: 'post'});
222
+ this.props.reload();
223
+ } else {
224
+ console.warn('请配置saveOrderApi');
225
+ }
226
+ }
227
+ }
228
+ ));
229
+ }
230
+
137
231
  renderItem(link: Link, index: number, depth = 1) {
138
232
  if (link.hidden === true || link.visible === false) {
139
233
  return null;
140
234
  }
141
235
  const isActive: boolean = !!link.active;
142
- const {disabled, togglerClassName, classnames: cx, indentSize} = this.props;
236
+ const {
237
+ disabled,
238
+ togglerClassName,
239
+ classnames: cx,
240
+ indentSize,
241
+ render,
242
+ itemActions,
243
+ draggable,
244
+ links,
245
+ badge: defaultBadge
246
+ } = this.props;
143
247
  const hasSub =
144
248
  (link.defer && !link.loaded) || (link.children && link.children.length);
145
-
249
+ const id = guid();
250
+ link.id = id;
251
+ const badge = defaultBadge ? Object.assign(defaultBadge, link.badge) : link.badge;
146
252
  return (
147
253
  <li
148
254
  key={index}
@@ -152,42 +258,62 @@ export class Navigation extends React.Component<
152
258
  'is-unfolded': link.unfolded,
153
259
  'has-sub': hasSub
154
260
  })}
261
+ data-id={id}
155
262
  >
156
- <a
157
- onClick={this.handleClick.bind(this, link)}
158
- style={{paddingLeft: depth * (parseInt(indentSize as any, 10) ?? 24)}}
159
- >
160
- {generateIcon(cx, link.icon, 'Nav-itemIcon')}
263
+ <Badge classnames={cx} badge={badge} data={link}>
264
+ <a
265
+ onClick={this.handleClick.bind(this, link)}
266
+ style={{paddingLeft: depth * (parseInt(indentSize as any, 10) ?? 24)}}
267
+ >
268
+ {!disabled && draggable && links && links.length > 1 ? (
269
+ <div className={cx('Nav-itemDrager')} >
270
+ <a
271
+ key="drag"
272
+ data-position="bottom"
273
+ >
274
+ <Icon icon="drag-bar" className="icon" />
275
+ </a>
276
+ </div>
277
+ ) : null}
278
+ {link.loading ? (
279
+ <Spinner
280
+ size="sm"
281
+ show
282
+ icon="reload"
283
+ spinnerClassName={cx('Nav-spinner')}
284
+ />
285
+ ) : hasSub ? (
286
+ <span
287
+ onClick={() => this.toggleLink(link)}
288
+ className={cx('Nav-itemToggler', togglerClassName)}
289
+ >
290
+ <Icon icon="caret" className="icon" />
291
+ </span>
292
+ ) : null}
293
+ {generateIcon(cx, link.icon, 'Nav-itemIcon')}
294
+ {
295
+ link.label && (typeof link.label === 'string'
296
+ ? link.label
297
+ : render('inline', link.label as SchemaCollection))
298
+ }
299
+ </a>
161
300
  {
162
- link.label && (typeof link.label === 'string'
163
- ? link.label
164
- : this.props.render('inline', link.label as SchemaCollection))
301
+ // 更多操作
302
+ itemActions
303
+ ? <div className={cx('Nav-item-atcions')}>
304
+ {
305
+ render('inline', itemActions, {data: link})
306
+ }
307
+ </div> : null
165
308
  }
166
- </a>
167
-
168
- {link.loading ? (
169
- <Spinner
170
- size="sm"
171
- show
172
- icon="reload"
173
- spinnerClassName={cx('Nav-spinner')}
174
- />
175
- ) : hasSub ? (
176
- <span
177
- onClick={() => this.toggleLink(link)}
178
- className={cx('Nav-itemToggler', togglerClassName)}
179
- >
180
- <Icon icon="caret" className="icon" />
181
- </span>
182
- ) : null}
183
-
184
- {Array.isArray(link.children) && link.children.length ? (
185
- <ul className={cx('Nav-subItems')}>
186
- {link.children.map((link, index) =>
187
- this.renderItem(link, index, depth + 1)
188
- )}
189
- </ul>
190
- ) : null}
309
+ {Array.isArray(link.children) && link.children.length ? (
310
+ <ul className={cx('Nav-subItems')} ref={this.dragRefFn}>
311
+ {link.children.map((link, index) =>
312
+ this.renderItem(link, index, depth + 1)
313
+ )}
314
+ </ul>
315
+ ) : null}
316
+ </Badge>
191
317
  </li>
192
318
  );
193
319
  }
@@ -198,6 +324,7 @@ export class Navigation extends React.Component<
198
324
  return (
199
325
  <ul
200
326
  className={cx('Nav', className, stacked ? 'Nav--stacked' : 'Nav--tabs')}
327
+ ref={this.dragRefFn}
201
328
  >
202
329
  {Array.isArray(links)
203
330
  ? links.map((item, index) => this.renderItem(item, index))
@@ -310,6 +437,7 @@ const ConditionBuilderWithRemoteOptions = withRemoteConfig({
310
437
  data?: any;
311
438
  unfoldedField?: string;
312
439
  foldedField?: string;
440
+ reload?: any;
313
441
  }
314
442
  > {
315
443
  constructor(props: any) {
@@ -442,6 +570,7 @@ export class NavigationRenderer extends React.Component<RendererProps> {
442
570
  return (
443
571
  <ConditionBuilderWithRemoteOptions
444
572
  {...rest}
573
+ reload={this.reload}
445
574
  remoteConfigRef={this.remoteConfigRef}
446
575
  />
447
576
  );
@@ -371,6 +371,8 @@ export default class Page extends React.Component<PageProps> {
371
371
  JSON.stringify(props.cssVars) !== JSON.stringify(prevProps.cssVars)
372
372
  ) {
373
373
  this.updateVarStyle();
374
+ } else if (props.defaultData !== prevProps.defaultData) {
375
+ store.reInitData(props.defaultData);
374
376
  }
375
377
  }
376
378
 
@@ -663,7 +665,7 @@ export default class Page extends React.Component<PageProps> {
663
665
  onAction: this.handleAction,
664
666
  onQuery: initApi ? this.handleQuery : undefined,
665
667
  onChange: this.handleChange,
666
- loading: store.loading
668
+ pageLoading: store.loading
667
669
  };
668
670
 
669
671
  const hasAside = Array.isArray(regions)