苍穹开发指南(一)

 

  1. 概述
    1. 概念介绍
      1. 为什么要开发插件

使用应用开发平台的设计器开发业务对象,全程配置,简单易学,但不够灵活。

 

配置业务对象时使用的业务语意,需要预先定义,遇到未考虑的业务场景,则无法处理。

 

业务对象设计器,目标是实现常见的80%业务语意,利用开放的插件开发,实现剩余20%的功能。

 

      1. 插件如何工作?

 

界面加载、及用户与界面交互时,系统会调用插件接口方法,即触发插件事件,通知插件工作;

 

插件通过实现事件接口方法,捕获插件事件,完成对此事件的干预。

 

      1. 什么是视图模型、控件编程模型?

下一代金蝶云,是B/S结构的,使用不同的客户端(PC端、移动端),通过网络连接到统一的服务端。

 

用户看到的交互界面,是运行在客户端的,而业务逻辑和业务插件,则运行在服务端;

 

业务插件,也是运行在服务端,没办法直接获取到客户端界面上控件,不能直接控制前端控件。

 

但插件可以通过系统封装的视图模型接口IFormView,间接的访问、控制前端界面;

通过系统封装的各种控件代理对象,间接的访问、控制前端界面上的控件;这些运行在服务端的控件代理对象,称为控件编程模型,或简称为控件、编程模型等。

 

插件可以通过this.getView()方法,获取表单的视图模型接口实例;

可以通过this.getView().getControl(String key)方法,获取到控件编程模型实例;

 

      1. 什么是数据模型

表单的界面与数据,是分离:

  • 界面显示在客户端浏览器或者移动端,在服务端会提供视图模型及;
  • 数据存储在服务端,在服务端;

 

动态表单、单据、基础资料设计完毕,系统会为界面创建一个主实体模型,包含界面上全部的字段、单据体;

 

运行时,系统会基于主实体模型中的结构,创建一个界面数据包,存储用户在界面上录入的字段值;

 

另外,系统封装了数据模型接口,访问界面数据。

 

因此,完整的数据模型包含如下部分:

  • 界面数据模型接口:IDataModel,提供了各种方法,访问界面数据;
  • 主实体模型:MainEntityType,一个界面对应一个主实体模型,包含:
    1. 实体:EntityType,对应单据体、子单据体等;
    2. 属性:DynamicProperty,对应字段;
  • 界面数据包:DynamicObject,包含界面各单据体、字段值;
    1. 如何开发插件
      1. 确定应用场景,选择插件基类

不同的业务对象类型,提供特定的业务功能,有适用的应用场景。

 

系统为各种业务对象类型、各种应用场景,封装了相应的插件接口、事件方法,定义了抽象插件基类,实现最基本的插件接口。

 

进行业务功能设计时,首先需要根据业务需求特点,分析业务应用场景,选择业务对象类型;

 

如果需要进行插件开发,则根据前面确定好的业务对象类型及应用场景,从下表中选择对应插件基类进行扩展:

业务对象类型

应用场景

预置的Java插件基类

动态表单

PC端界面

AbstractFormPlugin

移动端界面

AbstractMobFormPlugin

单据

基础资料

PC端界面

AbstractBillPlugIn

移动端界面

AbstractMobBillPlugIn

单据列表

AbstractListPlugin

树形单据列表

AbstractTreeListPlugin

树形基础资料列表

StandardTreeListPlugin

移动端单据列表

AbstractMobListPlugin

业务操作

AbstractOperationServicePlugIn

单据转换

AbstractConvertPlugIn

关联反写

AbstractWriteBackPlugIn

生成凭证

AbstractBuildVchPlugin

报表

界面

暂缺

 

取数

暂缺

 

      1. 确定事件源与控件

有交互界面的应用场景(如表单、单据列表等),在界面加载、关闭时,会触发相应的插件事件;

 

另外,用户与界面,以及界面上的控件交互时,也会触发插件事件。

 

各种控件有自己的功能特点,适用不同的业务需求,提供相应的插件事件;

 

在进行功能设计时,需要根据业务需求,选用合适的控件,确定需要重写的插件接口方法,响应插件事件。

 

后面的控件与字段章节,将详细列出各种控件的功能特定及支持的插件事件,供您参考。

 

  • 特别说明:

没有交互界面的应用场景(如单据操作、单据转换、关联反写、生产凭证等),不会与用户发生交互,其插件事件是由服务引擎按顺序触发的。

 

这些应用场景,不需要关注事件源、控件;只需要根据业务需求,捕获合适的插件事件即可。

 

      1. 响应插件事件

系统会在适当的时机,调用插件接口的方法,传入上下文参数,触发插件事件。

 

不同的插件事件,触发的时机、传入的上下文参数、可以控制的功能,差异非常大。

 

因此,必须根据业务需求,选择合适的插件事件响应。

 

后文会详细介绍各种应用场景、字段、控件,提供的插件事件,及其触发时机、事件参数。

 

本节介绍业务插件如何响应(捕捉)插件事件:

        1. 无交互界面的场景

没有交互界面的应用场景,插件基类已经实现了必要的插件接口,插件只需要扩展插件基类,重写事件方法即可完成事件的捕捉:

 

Java

 

package kd.bos.metadata.botp;

 

import kd.bos.entity.plugin.AbstractOperationServicePlugIn;

import kd.bos.entity.plugin.args.BeforeOperationArgs;

 

public class WriteBackRuleOpPlug extends AbstractOperationServicePlugIn {

@Override

public void beforeExecuteOperationTransaction(BeforeOperationArgs e) {

// TODO : 在此添加业务逻辑

}

}

说明:插件基类AbstractOperationServicePlugIn已经实现业务操作插件接口,插件直接重写需要响应的事件方法即可。

 

        1. 有交互界面的场景

有交互界面的应用场景,插件基类实现了表单界面支持的插件接口,但没有实现各种控件的插件接口。

 

如果只是要捕获表单界面事件,则扩展插件基类,重写表单事件方法即可。

 

如果要捕获各种控件事件,则需要:

  • 在插件类定义,实现控件支持的插件事件接口,例如树形控件支持的节点勾选插件事件接口TreeNodeCheckListener;
  • 实现控件的插件事件接口中的方法,完成事件的捕捉;
  • 在表单界面插件registerListener事件,向控件实例注册本插件实例,完成控件与插件实例的绑定:控件事件发生时,即触发其所绑定的插件事件;

 

如下例,插件需要响应树形控件的节点勾选treeNodeCheck事件:

Java

 

package kd.bos.plugin.sample.dynamicform.pcform.control.template;

 

import java.util.EventObject;

import java.util.List;

 

import kd.bos.dataentity.utils.StringUtils;

import kd.bos.form.control.TreeView;

import kd.bos.form.control.events.TreeNodeCheckEvent;

import kd.bos.form.control.events.TreeNodeCheckListener;

import kd.bos.form.plugin.AbstractFormPlugin;

 

public class TreeViewTreeNodeCheck extends AbstractFormPlugin implements TreeNodeCheckListener {

 

private final static String KEY_TREEVIEW1 = "treeviewap1";

 

@Override

public void registerListener(EventObject e) {

super.registerListener(e);

 

// 侦听树节点勾选事件

TreeView treeView = this.getView().getControl(KEY_TREEVIEW1);

treeView.addTreeNodeCheckListener(this);

}

 

@Override

public void beforeBindData(EventObject e) {

super.beforeBindData(e);

TreeView treeView = this.getView().getControl(KEY_TREEVIEW1);

treeView.setMulti(true); // 支持多选

}

 

@Override

public void treeNodeCheck(TreeNodeCheckEvent arg0) {

TreeView treeView = (TreeView) arg0.getSource();

if (StringUtils.equals(treeView.getKey(), KEY_TREEVIEW1)){

List<String> selectNodeIds = treeView.getTreeState().getCheckedNodeIds();

// TODO 在此添加业务逻辑

}

}

}

说明:插件基类AbstractFormPlugin没有实现树形控件的节点点击事件接口TreeNodeCheckListener,插件需要自行实现

  • 1
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

书耳朵

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值