跳到主要内容
极客日志极客日志面向AI+效率的开发者社区
首页博客GitHub 精选镜像AI 生图工具UI配色美学隐私政策关于联系
搜索内容 / 工具 / 仓库 / 镜像...⌘K搜索
注册
博客列表
JavaScriptSaaS大前端

宜搭低代码高级认证:待办列表自定义页面实战指南

本指南详细介绍了在钉钉宜搭平台构建待办列表应用的完整流程。内容涵盖从基础表单设计、自定义页面布局搭建,到核心的 JavaScript 逻辑实现。重点讲解了如何通过远程 API 调用实现数据的增删改查、分页搜索以及状态流转(如从进行中移至已完成)。文中提供了完整的代码示例和关键参数获取方法,适合希望掌握宜搭低代码高级认证实操技能的开发者参考。

RedisGeek发布于 2026/4/9更新于 2026/7/2733 浏览
宜搭低代码高级认证:待办列表自定义页面实战指南

宜搭低代码高级认证:待办列表自定义页面实战指南

本文档详细记录了在钉钉宜搭平台中,通过自定义页面实现待办事项管理功能的完整流程。主要涉及表单设计、自定义页面搭建以及 JavaScript 逻辑编写,涵盖数据的增删改查及状态流转。

1. 基础环境准备

首先需要在钉钉组织中完成相关配置。如果二维码扫描失效,可通过手机钉钉右下角【我的】->【客服与帮助】->【快捷工具】->【加入团队】搜索组织名称加入。

1.1 创建数据表单

我们需要两个核心表单:'进行中待办'和'已完成待办'。

  • 进行中待办:包含待办事项(单行文本)、分类(单选)、重要度(评分,默认值 1)、提醒日期(日期)、详情(多行文本)。
  • 已完成待办:复制上述表单并修改名称即可。

注意:组件的唯一标识(如 rateField_me2n0yf0)每次创建都会不同,后续代码中需替换为你实际获取到的标识。

文章配图

2. 自定义页面搭建

新建自定义页面时,选择【工作台模板 -01】作为基础,删除不需要的布局容器,将标题改为'待办列表'。

2.1 页面布局

使用分组组件将页面分为'进行中待办'和'已完成待办'两部分。每个部分内部放置表格组件,并根据表单字段调整列显示。 对于'重要度'等枚举字段,需在表格配置中定义样式映射,例如:

[ { "color": "grey", "text": "1", "value": 1 }, ... ]

设置页面背景色为白色以保持界面整洁。

2.2 关键参数获取

在编写 JS 逻辑前,需要获取应用编码(AppType)和表单 UUID(formUuid)。

  • AppType: 浏览器地址栏中查找 appType 参数。
  • formUuid: 在表单设计器顶部地址栏或属性面板中获取。 这些参数是调用后端 API 的必填项。

文章配图

3. 功能逻辑实现

3.1 数据展示与分页

在数据源中添加远程 API getTodoData,请求 /v1/form/searchFormDatas.json。 数据处理回调中,需要将返回的 formData 映射到表格字段,并保留 formInstId 作为主键。 分页和搜索功能通过绑定表格的触发事件实现,监听 onFetchTodoData,根据用户输入更新 searchKey 和 page 状态,并重新加载数据源。

3.2 新增与编辑

点击'新增待办'按钮弹出对话框。

  • 打开弹窗: 重置表单字段默认值。
  • 提交保存: 校验必填项后,调用 insert 接口。
  • 编辑回显: 点击行内编辑时,将当前行数据回填至对话框,并将操作标志位 flag 设为 edit。
  • 保存逻辑: 根据 flag 判断是调用新增接口还是更新接口 (updateFormData.json)。
3.3 删除与状态流转
  • 删除: 弹出确认框,获取选中行的 instid,调用删除接口。
  • 移至已完成: 开启表格行选择器,单选模式下,选中某条记录后自动执行删除'进行中'数据并插入'已完成'数据的逻辑。

4. 完整代码参考

以下是自定义页面 JS 面板的核心逻辑汇总,包含了生命周期、数据交互及业务处理函数。请根据实际组件 ID 进行适配。

// 页面加载完成后初始化
export function didMount() {
  console.log(`「页面 JS」:当前页面地址 ${location.href}`);
}

// 分页/搜索触发
export function onFetchTodoData(params) {
  if (params.from === 'search') { params.currentPage = 1; }
  this.setState({ "searchKey": params.searchKey, "page": params.currentPage });
}

// 新增按钮回调
export function onActionBarItemClick() {
  this.setState({ flag:'insert' });
  this.$('dialog_me9xwn20').show(() => {
    // 重置表单字段
    this.$('textField_me9xwn22').reset();
    this.$('radioField_me9xwn23').reset();
    this.$('rateField_me9xwn24').setValue(1);
    this.$('dateField_me9xwn25').reset();
    this.$('textareaField_me9xwn26').reset();
    this.$('textField_mea9fcw1').reset();
  });
}

// 确定按钮逻辑(含新增与编辑判断)
export function onOk() {
  const createFieldList = [ 'textField_me9xwn22', 'radioField_me9xwn23', 'rateField_me9xwn24', 'dateField_me9xwn25' ];
  const data1 = {
    "textField_me2n0yey": this.$('textField_me9xwn22').getValue(),
    "radioField_me2n0yez": this.$('radioField_me9xwn23').getValue(),
    "rateField_me2n0yf0": this.$('rateField_me9xwn24').getValue(),
    "dateField_me2n0yf1": this.$('dateField_me9xwn25').getValue(),
    "textareaField_me2n0yf2": this.$('textareaField_me9xwn26').getValue()
  };
  const param = {
    formUuid: "FORM-50859B5DAD37446FA143EDCB4CF3A44375VP",
    appType: "APP_L0MRPK82DM5SNZ2UIHPM",
    formDataJson: JSON.stringify(data1)
  };

  this.fieldsValidate(createFieldList).then((errorList) => {
    setTimeout(() => {
      if (errorList.length > 0) return;
      if(this.state.flag === 'insert'){
        this.dataSourceMap["insert"].load(param).then(res => {
          this.utils.toast({ title: '新增成功', type: 'success', size: 'large' });
          this.$('dialog_me9xwn20').hide();
          setTimeout(() => { this.dataSourceMap['getTodoData'].load(); }, 1000);
        });
      } else {
        const param2 = {
          formInstId: this.$('textField_mea9fcw1').getValue(),
          updateFormDataJson: JSON.stringify(data1)
        };
        this.dataSourceMap['updateData'].load(param2).then(res => {
          this.utils.toast({ title: "修改成功", type: "success", size: "large" });
          this.$('dialog_me9xwn20').hide();
          setTimeout(() => { this.dataSourceMap['getTodoData'].load(); }, 1000);
        });
      }
    }, 0);
  });
}

// 辅助校验函数
export async function fieldsValidate(fieldList = []) {
  const result = [];
  for (let i = 0; i < fieldList.length; i++) {
    await this.$(fieldList[i]).validate((errors, values) => {
      if (!errors) return;
      result.push({
        fieldId: fieldList[i],
        errors: this.utils.isMobile() ? errors.errors[fieldList[i]].errors : errors[fieldList[i]].errors
      });
    });
  }
  return result;
}

// 删除逻辑
export function onDeleteClick(rowData) {
  this.$('dialog_mea9fcvy').show(() => {
    this.$('textField_mea9fcw0').setValue(rowData.instid);
  });
}

export function onDeleteTodoData() {
  const param = { formInstId: this.$('textField_mea9fcw0').getValue() };
  this.dataSourceMap['deleteData'].load(param).then(res => {
    this.utils.toast({ title: "删除成功", type: "success", size: "large" });
    this.$('dialog_mea9fcvy').hide();
    setTimeout(() => {
      this.dataSourceMap['getTodoData'].load();
      this.dataSourceMap['getDoneData'].load();
    }, 1000);
  });
}

// 编辑逻辑
export function onEditClick(rowData) {
  this.setState({ flag:'edit' });
  this.$('dialog_me9xwn20').show(() => {
    this.$('textField_me9xwn22').setValue(rowData.textField_me2n0yey);
    this.$('radioField_me9xwn23').setValue(rowData.radioField_me2n0yez);
    this.$('rateField_me9xwn24').setValue(rowData.rateField_me2n0yf0);
    this.$('dateField_me9xwn25').setValue(rowData.dateField_me2n0yf1);
    this.$('textareaField_me9xwn26').setValue(rowData.textareaField_me2n0yf2);
    this.$('textField_mea9fcw1').setValue(rowData.instid);
  });
}

// 行选择移动状态
export function onSelect(selected, rowData, selectedRows) {
  const param1 = { formInstId: rowData.instid };
  this.dataSourceMap['deleteData'].load(param1).then(res => {
    setTimeout(() => { this.dataSourceMap['getTodoData'].load(); }, 1000);
  });

  const data1 = {
    "textField_me2ndu46": rowData.textField_me2n0yey,
    "radioField_me2ndu47": rowData.radioField_me2n0yez,
    "rateField_me2ndu48": rowData.rateField_me2n0yf0,
    "dateField_me2ndu49": rowData.dateField_me2n0yf1,
    "textareaField_me2ndu4a": rowData.textareaField_me2n0yf2
  };
  const param2 = {
    formUuid: "FORM-17BD995E61214B80BCEE9BB6EADF8DC8JNTV",
    appType: "APP_L0MRPK82DM5SNZ2UIHPM",
    formDataJson: JSON.stringify(data1)
  };
  this.dataSourceMap["insert"].load(param2).then(res => {});
  setTimeout(() => { this.dataSourceMap['getDoneData'].load(); }, 1000);
}

// 已完成列表搜索
export function onFetchDoneData(params) {
  if (params.from === 'search') { params.currentPage = 1; }
  this.setState({ "doneSearchKey": params.searchKey, "donePage": params.currentPage });
}

通过以上步骤,即可完成一个具备基本 CRUD 及状态流转功能的待办列表应用。实际开发中请注意替换具体的 AppType 和 FormUuid,并根据业务需求调整字段映射。

目录

  1. 宜搭低代码高级认证:待办列表自定义页面实战指南
  2. 1. 基础环境准备
  3. 1.1 创建数据表单
  4. 2. 自定义页面搭建
  5. 2.1 页面布局
  6. 2.2 关键参数获取
  7. 3. 功能逻辑实现
  8. 3.1 数据展示与分页
  9. 3.2 新增与编辑
  10. 3.3 删除与状态流转
  11. 4. 完整代码参考
  • 免费图片AI生成工具免费生成了解详情
  • Magick API 一键接入全球大模型注册送1000万token查看
  • 免费图片视频在线生成30秒,将你的创意变成现实开始设计
  • X/Twitter免费视频下载器免登陆无限额度免费视频解析下载了解详情
  • 100+免费在线小游戏爽一把
极客日志微信公众号二维码

微信扫一扫,关注极客日志

微信公众号「极客日志V2」,在微信中扫描左侧二维码关注。展示文案:极客日志V2 zeeklog

更多推荐文章

查看全部
  • Java ThreadLocal 原理、使用场景及内存泄漏解析
  • AXURE 11 结合 AI 的智能原型设计体验
  • faster-whisper 部署指南:从环境配置到生产级应用
  • 数据结构:堆的实现与应用
  • OpenClaw 大龙虾机器人安装与配置指南
  • 2026 传媒行业趋势:Agent 成入口,AIGC 重塑供给
  • 大疆无人机日志导出与解析方法
  • Vue 3 开发实战:10 个提升效率的核心技巧
  • 线性动态规划经典四题实战解析
  • 基于 AI Agent 的通用米家智能家居控制方案
  • 安卓陀螺仪开发笔记:从角速度到角度积分
  • 阿里开源纯前端浏览器自动化框架 PageAgent 解析与实战
  • 老款 Intel Mac 部署 OpenClaw 极简指南
  • Llama.cpp 低配置电脑部署大模型指南
  • Python 实现 PDF 文件批量自动下载爬虫实战
  • FPGA Flash 烧写步骤详解(基于 Vivado)
  • Windows 7 编译运行 llama.cpp 部署 Qwen 模型指南
  • 基于 STM32 的智慧农业大棚系统设计
  • Spring Boot 3.3 至 3.5 版本深度对比与演进分析
  • C++ 包管理工具 vcpkg 配置国内镜像源

相关免费在线工具

  • Keycode 信息

    查找任何按下的键的javascript键代码、代码、位置和修饰符。 在线工具,Keycode 信息在线工具,online

  • Escape 与 Native 编解码

    JavaScript 字符串转义/反转义;Java 风格 \uXXXX(Native2Ascii)编码与解码。 在线工具,Escape 与 Native 编解码在线工具,online

  • JavaScript / HTML 格式化

    使用 Prettier 在浏览器内格式化 JavaScript 或 HTML 片段。 在线工具,JavaScript / HTML 格式化在线工具,online

  • JavaScript 压缩与混淆

    Terser 压缩、变量名混淆,或 javascript-obfuscator 高强度混淆(体积会增大)。 在线工具,JavaScript 压缩与混淆在线工具,online

  • Base64 字符串编码/解码

    将字符串编码和解码为其 Base64 格式表示形式即可。 在线工具,Base64 字符串编码/解码在线工具,online

  • Base64 文件转换器

    将字符串、文件或图像转换为其 Base64 表示形式。 在线工具,Base64 文件转换器在线工具,online