弹窗或抽屉表单视图rootRecord获取不到对应的数据

在平台默认的实现中,rootRecord 代表的是根视图的数据。比如,在表格页面点击按钮打开了弹窗,弹窗里面包含一个表单视图,但是该视图获取 rootRecord 却是最外层的视图数据。

如果期望 rootRecord 数据是弹窗的视图数据,需要手动修改表单的 rootRecord。下面的代码演示了如何重写 rootData 以确保其数据是弹窗的数据:

@SPI.ClassFactory(
  BaseElementWidget.Token({
    viewType: ViewType.Form,
    widget: 'MyCustomFormWidgetFormWidget'
  })
)
export class MyCustomFormWidgetFormWidget extends FormWidget {
  @Widget.Reactive()
  @Widget.Provide()
  public get rootData(): any[] | undefined {
    return this.activeRecords;
  }
}

上述代码重写了 rootData,这样就可以确保 rootData 的数据是弹窗的数据。

接下来就是注册:

registerLayout(
  `
<view type="FORM">
    <element widget="actionBar" slot="actionBar" slotSupport="action">
        <xslot name="actions" slotSupport="action" />
    </element>
    <element widget="MyCustomFormWidgetFormWidget" slot="form">
        <xslot name="fields" slotSupport="pack,field" />
    </element>
</view>
`,
  {
    viewType: ViewType.Form,
    model: '弹窗模型',
    viewName: '弹窗视图名称'
  }
)

Oinone社区 作者:汤乾华原创文章,如若转载,请注明出处:https://doc.oinone.top/frontend/4524.html

访问Oinone官网:https://www.oinone.top获取数式Oinone低代码应用平台体验

Like (0)
汤乾华's avatar汤乾华数式员工
Previous 2023年11月11日 pm5:01
Next 2023年11月15日 am11:06

相关推荐

  • 自定义前端拦截器

    某种情况下,我们需要通过自定义请求拦截器来做自己的逻辑处理,平台内置了一些拦截器 登录拦截器LoginRedirectInterceptor 重定向到登录拦截器LoginRedirectInterceptor import { UrlHelper, IResponseErrorResult, LoginRedirectInterceptor } from '@kunlun/dependencies'; export class BizLoginRedirectInterceptor extends LoginRedirectInterceptor { /** * 重定向到登录页 * @param response 错误响应结果 * @return 是否重定向成功 */ public redirectToLogin(response: IResponseErrorResult): boolean { if (window.parent === window) { const redirect_url = location.pathname; // 可自定义跳转路径 location.href = `${UrlHelper.appendBasePath('login')}?redirect_url=${redirect_url}`; } else { // iframe页面的跳转 window.open(`${window.parent.location.origin}/#/login`, '_top'); } return true; } } 请求成功拦截器RequestSuccessInterceptor 请求失败拦截器 RequestErrorInterceptor 网络请求异常拦截器 NetworkErrorInterceptor 当我们需要重写某个拦截器的时候,只需要继承对应的拦截器,然后重写里面的方法即可 // 自定义登录拦截器 export class CustomLoginRedirectInterceptor extends LoginRedirectInterceptor{ public error(response: IResponseErrorResult) { // 自己的逻辑处理 return true // 必写 } } // 自定义请求成功拦截器 export class CustomRequestSuccessInterceptor extends RequestSuccessInterceptor{ public success(response: IResponseErrorResult) { // 自己的逻辑处理 return true // 必写 } } // 自定义请求失败拦截器 export class CustomRequestErrorInterceptor extends RequestErrorInterceptor{ public error(response: IResponseErrorResult) { const { errors } = response; if (errors && errors.length) { const notPermissionCodes = [ SystemErrorCode.NO_PERMISSION_ON_MODULE, SystemErrorCode.NO_PERMISSION_ON_VIEW, SystemErrorCode.NO_PERMISSION_ON_MODULE_ENTRY, SystemErrorCode.NO_PERMISSION_ON_HOMEPAGE ]; /** * 用来处理重复的错误提示 */ const executedMessages: string[] = []; for (const errorItem of errors) { const errorCode = errorItem.extensions?.errorCode; if (!notPermissionCodes.includes(errorCode as any)) { const errorMessage = errorItem.extensions?.messages?.[0]?.message || errorItem.message; if (!executedMessages.includes(errorMessage)) { // 自己的逻辑处理 } executedMessages.push(errorMessage); } } } return true; } } // 自定义网络请求异常拦截器…

    前端 2023年11月1日
    1.7K01
  • 【前端】默认布局模板(v4)

    默认母版(Mask) PC端默认母版 <mask> <multi-tabs /> <header> <widget widget="app-switcher" /> <block> <widget widget="notification" /> <widget widget="divider" /> <widget widget="language" /> <widget widget="divider" /> <widget widget="user" /> </block> </header> <container> <sidebar> <widget widget="nav-menu" height="100%" /> </sidebar> <content> <breadcrumb /> <block width="100%"> <widget width="100%" widget="main-view" /> </block> </content> </container> </mask> PC端默认内联Tabs母版(<multi-tabs inline="true" />) <mask> <header> <widget widget="app-switcher" /> <block> <widget widget="notification" /> <widget widget="divider" /> <widget widget="language" /> <widget widget="divider" /> <widget widget="user" /> </block> </header> <container> <sidebar> <widget widget="nav-menu" height="100%" /> </sidebar> <block height="100%" flex="1 0 0" flexDirection="column" alignContent="flex-start" flexWrap="nowrap" overflow="hidden"> <multi-tabs inline="true" /> <content> <breadcrumb /> <block width="100%"> <widget width="100%" widget="main-view" /> </block> </content> </block> </container> </mask> 移动端默认母版 <mask> <widget widget="user" /> <widget widget="nav-menu" app-switcher="true" menu="true" /> <widget widget="main-view" height="100%" /> </mask> PC端默认布局(Layout) 表格视图(TABLE) <view type="TABLE"> <pack widget="group"> <view type="SEARCH"> <element widget="search" slot="search" /> </view> </pack> <pack widget="group" slot="tableGroup"> <element widget="actionBar" slot="actionBar"> <xslot name="actions" /> </element> <element widget="table" slot="table"> <element widget="expandColumn" slot="expandRow" /> <xslot name="fields" /> <element widget="rowActions" slot="rowActions" /> </element> </pack> </view> 表单视图(FORM) <view type="FORM"> <element widget="actionBar" slot="actionBar"> <xslot name="actions" /> </element> <element widget="form" slot="form"> <xslot name="fields" /> </element> </view>…

    2023年11月1日
    1.6K01
  • 文件上传组件前端校验超128长度大小,不清楚怎么配置

    原因是拼上后端返回的文件全路径后超出了字段的存储长度,后端通过注解@Field.String(size=1024)修改字段的存储长度后重新运行一遍服务。

    2023年11月1日
    1.7K00
  • oio-input 输入框

    代码演示 <oio-input v-model:value="value"></oio-input> API Input 参数 说明 类型 默认值 版本 addonAfter 带标签的 input,设置后置标签 string|slot addonBefore 带标签的 input,设置前置标签 string|slot allowClear 可以点击清除图标删除内容 boolean defaultValue 输入框默认内容 string disabled 是否禁用状态,默认为 false boolean false maxlength 最大长度 number prefix 带有前缀图标的 input slot showCount 是否展示字数 boolean false suffix 带有后缀图标的 input slot type 声明 input 类型,同原生 input 标签的 type 属性,见:MDN(请直接使用 <a-textarea /> 代替 type="textarea")。 string text value(v-model:value) 输入框内容 string Input 事件 事件名称 说明 回调参数 update:value 输入框内容变化时的回调 function(e) pressEnter 按下回车的回调 function(e) Input.Search 代码演示 <oio-input-search v-model:value="value"></oio-input-search> Input.Search 事件 事件名称 说明 回调参数 search 点击搜索或按下回车键时的回调 function(value, event) 其余属性和 Input 一致。

    2023年12月18日
    2.6K00
  • 【界面设计器】自定义字段组件实战——千分位输入框

    阅读之前 此文章为实战教程,已假定你熟悉了【界面设计器】较为完整的【自定义组件】相关内容。 如果在阅读过程中出现的部分概念无法理解,请自行学习相关内容。【前端】文章目录 业务背景 用户在输入【金额】字段时,实时展示千分位格式。 业务分析 从需求来看,我们需要实现一个【千分位】组件,并且该组件允许在【表单】视图中使用。 扩展实现:该组件虽然仅要求在【表单】中使用,但也可以在【搜索】中使用完全相同的实现,因此这里我们在注册时会增加【搜索】视图,将【千分位】组件应用在【搜索】中。对于【表格】、【详情】和【画廊】来说,该组件是没有【输入】行为的展示组件,在这里我们不进行演示。 准备工作 此处你应该已经在某个业务模型下,可以完整执行当前模型的全部【增删改查】操作。 业务模型定义 (以下仅展示本文章用到的模型字段,忽略其他无关字段。) 名称 API名称 业务类型 是否多值 长度(单值长度) 编码 code 文本 否 128 名称 name 文本 否 128 金额 money 金额 否 – 创建组件、元件 准备工作完成后,我们需要根据【业务背景】确定【组件】以及【元件】相关信息,并在【界面设计器】中进行创建。 以下操作过程将省略详细步骤,仅展示可能需要确认的关键页面。 创建千分位组件 创建千分位元件 启动SDK工程进行组件基本功能开发 (npm相关操作请自行查看SDK工程中内置的README.MD) 关键点详解 数据交互类型的字段组件(以下简称展示组件)与仅展示类型的字段组件(以下简称交互组件)有一些差别。 通常情况下,在展示组件中仅需使用value属性即可展示相关内容。在交互组件中除了value用于展示外,还需使用change、focus以及blur处理用户输入时的基本交互逻辑。 数据交互方法主要功能说明: change方法:当值发生变更时调用,根据字段相关配置将值回填至表单中。 focus方法:当组件获取焦点时调用,记录当前值,并在调用blur方法时进行处理。 blur方法:当前组件失去焦点时调用,根据focus方法记录的值,进行失焦触发逻辑的执行。 这里的三个数据交互方法仅仅是对用户行为的抽象,而并非限定其使用场景。 通常来说,这三个方法的调用顺序为:focus –> change –> blur。 如在日期时间组件中,面板打开时调用了focus方法,面板值发生变更时,调用了change方法,面板关闭时调用了blur方法。 如在地图组件中,选中地图上的某个点时仅会调用change方法,用户交互上并不能体现出focus和blur的行为。因此对于这个组件而言,只会有change方法被执行。 代码实现参考 PS:oio-input-number样式必须升级到4.6.x以上的最新版本才支持 Thousandth.vue <template> <a-input-number class="oio-input-number" :value="inputValue" :formatter="formatter" :parser="parser" @update:value="change" @focus="focus" @blur="blur" /> </template> <script lang="ts"> import { InputNumber as AInputNumber } from 'ant-design-vue'; import { computed, defineComponent } from 'vue'; export default defineComponent({ name: 'Thousandth', components: { AInputNumber }, props: { value: { type: [String, Number] }, change: { type: Function }, focus: { type: Function }, blur: { type: Function } }, setup(props) { const inputValue = computed(() => { return props.value; }); const formatter = (value) => { return `${value}`.replace(/\B(?=(\d{3})+(?!\d))/g, ','); }; const parser = (value) => { return value.replace(/\$\s?|(,*)/g, ''); }; return { inputValue, formatter, parser }; } }); </script> FormMoneyThousandthFieldWidget.ts import { FormFieldWidget, ModelFieldType, SPI, ViewType } from '@kunlun/dependencies'; import Thousandth from './Thousandth.vue'; @SPI.ClassFactory( FormFieldWidget.Token({ viewType: [ViewType.Form, ViewType.Search], ttype: ModelFieldType.Currency, widget:…

    2024年4月19日
    1.7K00

Leave a Reply

Please Login to Comment