private _segmentForm()

in src/ui/editor/complex/AForm.tsx [180:270]


  private _segmentForm(objectFields: MFieldSchema[], uispec: M3UISpec, column: number) {
    const objectFieldMap = _.chain(objectFields).keyBy('name').value();
    const hideMap = MUtil.hideMap(MUtil.get(this.props.database, this.props.path), objectFields, uispec);
    if (!uispec.segments) {
      return MUtil.error("分段未定义");
    }

    // 先计算一遍label的宽度,即使有隐藏的字段,确保展示出来时也不会因为label太长布局变化。
    let labelWidth = 0;
    if (uispec.layout === "horizontal") {
      for (let segment of uispec.segments) {
        for (let fieldName of segment.fields) {
          let f = objectFieldMap[fieldName];
          if (!f) {
            return MUtil.error(`segments中的${fieldName}未定义`);
          }
          let label = f.label;
          labelWidth = Math.max(labelWidth, MUtil.antdTextWidth(label ?? ""))
        }
      }
    }

    // 然后再把表单表格画出来
    const segments = [];
    let fno = 0;
    for (let segment of uispec.segments) {
      const segHide = hideMap["segment:" + segment.label];
      const items = [];
      const segmentFieldNames: string[] = [];

      for (let fieldName of segment.fields) {
        let f = objectFieldMap[fieldName];
        if (!f) {
          items.push(MUtil.error(`字段不存在:${fieldName}`));
          continue;
        }

        const hideField = segHide || hideMap[f.name];

        // segment里的字段名都记下来
        segmentFieldNames.push(fieldName);

        items.push(this.formItem(hideField, hideMap, f, objectFields, uispec,
          ((this.props.morph === "editor" || this.state.editing[segment.label]) ? "editor" : "readable"),
          labelWidth, `${segment.label}的layout值无效:${uispec.layout}`, column))
      }

      let topRight: React.ReactNode = undefined;
      if (segment.onSubmit) {
        const onSubmit = segment.onSubmit;
        if (this.state.editing[segment.label]) {
          const saving = this.state.saving[segment.label];
          const cancel = () => {
            const prev = this.state.editing[segment.label];
            _.assign(this.props.database, prev);
            delete this.state.editing[segment.label];
            this.setState({});
          }
          topRight = <SegmentEditSwitch state={saving ? "saving" : "editor"} onClick={(e) => {
            if (e) {
              this.state.saving[segment.label] = true; // 先展示loading动画
              onSubmit(segment, _.pick(this.props.database, segmentFieldNames), () => {
                // 保存完了以后移除loading状态,并且改回readable模式
                this.setState({
                  saving: _.omit(this.state.saving, segment.label),
                  editing: _.omit(this.state.saving, segment.label),
                });
              })
            } else {
              const prev = this.state.editing[segment.label];
              const current = _.pick(this.props.database, segmentFieldNames);
              if (!_.isEqual(prev, current)) {
                Modal.confirm({
                  content: '会丢失刚才的修改,确定吗?',
                  okText: "刚才的修改不要了",
                  cancelText: "继续编辑",
                  onOk: cancel
                });
              } else {
                cancel();
              }
            }
          }} />
        } else {
          topRight = <SegmentEditSwitch state={"readable"} onClick={(e) => {
            this.setState({
              editing: _.set(this.state.editing, segment.label, _.pick(this.props.database, segmentFieldNames))
            });
          }} />
        }
      }