使用bootstrap 和 gooflow 完成demo
参考 Jquery版API文档
用到最主要的两个数据结构定义1、描述单个节点信息的Json结构体。
NodeItem 类型:Json Object描述单个节点信息的Json结构体。
属性类型默认值描述nameString('node_'+序列号)节点的显示名称。leftNumber0节点相对于工作区的左边距,单位像素。topNumber0节点相对于工作区的顶距,单位像素。widthNumber104节点宽度,单位像素;仅非圆形节点时有效。heightNumber26节点高度,单位像素;仅非圆形节点时有效。typeString''必填项:节点类型名称,可用户自定义;其对应的图标样式为'ico_'+节点类型
; 类型名中如果有' round'
,则为圆形节点,如果有' mix'
,则为复合节点(变换背景色)。markedBoolean(undefined)节点是否已被标注。altBoolean(undefined)在编辑模式下节点是否被用户编辑过。areaIdString(undefined)该节点所属分组泳道的id,当为undefined
时表示不属于任何分组。colorString(undefined)选填项。该节点对象特有的背景颜色,优先级高于GooFlow.color.node
。fontColorString(undefined)选填项。该节点对象特有的文字颜色,优先级高于GooFlow.color.font
。……Object(undefined)任意类型、任意数量的自定义属性,由用户根据需要自行添加。
2、描述单条连线信息的Json结构体。
LineItem 类型:Json Object描述单条连线信息的Json结构体。
属性类型默认值描述nameString(undefiend)连线的显示名称,未定义时连线上无文字。fromString(undefiend)必填项,连线的起始节点id。toString(undefiend)必填项,连线的目标节点id。typeStringsl连线类型,取值有三种:'sl'
直线;'lr'
中段可左右移动的折线';'tb'
中段可上下移动的折线。MNumber(undefiend)一种抽象值,单位为像素。 当type='lr'
时为必填项,表示中段线相对于工作区的X坐标值; 当type='tb'
时为必填项,表示中段线相对于工作区的Y坐标值。 当type='sl'
时无任何意义。markedBoolean(undefined)连线是否已被标注。altBoolean(undefined)在编辑模式下连线是否被用户编辑过。dashedBoolean(undefined)是否为虚线样式,当为undefined
时表示默认实线。noArrowBoolean(undefined)是否有箭头,当为undefined
时表示默认为有向线,反之则为无向线段。colorString(undefined)选填项。该连线对象特有的线条颜色,优先级高于GooFlow.color.line
。fontColorString(undefined)选填项。该连线对象特有的文字颜色,优先级高于GooFlow.color.lineFont
。……Object(undefined)任意类型、任意数量的自定义属性,由用户根据需要自行添加。
一、创建两个div 布局
1、引入 js 和 css 文件 参考 GooFlow入门使用
2、一个 div 初始化 GooFlow 实例,另一个一个显示信息
节点属性
节点ID:
名称:
类型:
属性:
左边距:
上边距:
宽度:
高度:
连接属性
起始节点:
结束节点:
是否虚线:
自定义配置属性
姓名
性别
input 中的 name 名和数据结构定义的属性名保持一致(需要什么显示什么),也可以自定义 name 名 。例如 节点id 和 属性等
input 也可以自定义属性(用于业务处理),例如 comtype 属性等
二、js 初始化 GooFlow 实例
1、需要用到 事件钩子 和 内部属性等,举两个,其他参考文档
1.1 组件获得焦点事件
this.onItemFocus() 返回值:boolean当操作某个元素(节点/连线)被由不选中变成选中时,触发的方法。
传参:( id, type )
'node'
节点、'line'
连线两种
1.2 组件失去焦点事件
this.onItemBlur() 返回值:boolean当操作某个元素(节点/连线)被由选中变成不选中时,触发的方法。
传参:( id, type )
'node'
节点、'line'
连线两种。
2、在获取失去焦点时,回显和删除 form 表单的信息
var options = {
//width:800,
//height:500,
//initLabelText: "流程图",
toolBtns: ["start round mix", "end round mix", "task", "node", "chat", "state", "plug", "join", "fork", "complex mix"],
haveHead: true,
headLabel: true,
headBtns: ["new", "save", "undo", "redo", "reload", "print", "exportImg"],//如果haveHead=true,则定义HEAD区的按钮
haveTool: true,
haveDashed: true,
haveGroup: true,
useOperStack: true
};
//设定左侧工具栏中每一种节点或按钮的说明文字
GooFlow.prototype.remarks.toolBtns = {
cursor: "选择指针",
direct: "连接线",
dashed: "连接线(虚线)",
start: "开始节点",
"end": "结束节点",
"task": "事项节点",
group: "区块编辑开关"
};
//设定顶部栏中每个按钮的说明文字
GooFlow.prototype.remarks.headBtns = {
"new": "新建流程",
open: "打开流程",
save: "保存结果",
undo: "撤销",
redo: "重做",
reload: "重置流程",
print: "打印流程图",
exportImg: "导出流程图"
};
GooFlow.prototype.remarks.extendRight = "工作区向右扩展";
GooFlow.prototype.remarks.extendBottom = "工作区向下扩展";
var superviseDataStr; //全局模板初始流程图数据字符串
var flowsuperviseTemp; //GooFlow实例本身
//模拟数据
//superviseDataStr = "";
$(document).ready(function () {
flowsuperviseTemp = $.createGooFlow($("#flowsuperviseTemp"), options); //用jquery扩展方法初始化GooFlow
//flowsuperviseTemp = GooFlow.init("#flowsuperviseTemp",options);; //用jquery扩展方法初始化GooFlow
flowsuperviseTemp.setTitle("事项流程图");
//flowsuperviseTemp.loadData($.parseJSON(superviseDataStr)); //初始流程图数据
//组件获得焦点事件
flowsuperviseTemp.onItemFocus = function(id, type){
var $form = $("#flowsuperviseItemForm");
$form[0].reset();
$form.find("input[name='compid']").val(id);
$form.find("input[name='model']").val(type);
var obj;
if(type == "line"){
obj = this.$lineData[id];
}else if(type == "node"){
obj=this.$nodeData[id];
}
$.each(obj, function (i, n) {
$form.find("input[name='"+i+"']").val(n);
});
//alert(id + ":" + type);
return true;
}
//组件失去焦点事件
flowsuperviseTemp.onItemBlur=function(id, type){
var $form = $("#flowsuperviseItemForm");
$form[0].reset();
return true;
};
//保存按钮事件
flowsuperviseTemp.onBtnSaveClick = function () {
saveflowsupervise();
}
//组件删除事件(默认是取消的)
flowsuperviseTemp.onItemDel=function(id,type){
this.blurItem(); //取消所选节点/连线被选定的状态。
return true;
}
//重置按钮事件
flowsuperviseTemp.onFreshClick = function () {
flowsuperviseTemp.clearData();
//flowsuperviseTemp.loadData($.parseJSON(superviseDataStr));
}
//打印事件
flowsuperviseTemp.onPrintClick = function () {
flowsuperviseTemp.print(1);
}
//导出图片事件
var exportName = "事项流程图";
//flowsuperviseTemp.setNodeRemarks(GooFlow.prototype.remarks.toolBtns);
flowsuperviseTemp.onExportImgClick = function () {
flowsuperviseTemp.exportDiagram(exportName);
}
});
三、保存节点信息
function saveflowsupervise() {
var nodeCount = flowsuperviseTemp.$nodeCount; //节点数(包含开始结束节点数)
if(nodeCount > 0){
var flowchart = JSON.stringify(flowsuperviseTemp.exportData());
console.log(flowchart);
alert(flowchart);
}else{
alert("请先绘制流程图");
}
}
function editflowsuperviseItem(){
var $form = $("#flowsuperviseItemForm");
//获取节点ID 和 属性(node/line)
var comp_id = $form.find("input[name='compid']").val();
var comp_model = $form.find("input[name='model']").val();
if(comp_id){
var flowchartdata = flowsuperviseTemp.exportData();
if(comp_model && comp_model == "node"){
$.each(flowchartdata.nodes, function (i, n) {
if(i == comp_id){
//将form表单信息更新到node节点事项各个属性中
$form.find("input").each(function(){
if($(this).prop('name') && $(this).prop('name') != 'compid'){//组件ID 不相等就不修改了
if(!($(this).attr('comptype')) || $(this).attr('comptype')=='node'){
n[$(this).prop('name')] = $(this).val();
// name 名 和 节点属性对应,把值放进去,跟回显信息相反
// alert($(this).prop('name') + ":" + $(this).val());
}
}
});
//n['name'] = $form.find("input[name='name']").val();
flowchartdata.nodes[i]=n;
}
});
}
if(comp_model && comp_model=='line'){
$.each(flowchartdata.lines, function (i, n) {
if(i == comp_id){
//将form表单信息更新到line节点事项各个属性中
$form.find("input").each(function(){
if($(this).prop('name') && $(this).prop('name') != 'compid'){//组件ID就不修改了
if(!($(this).attr('comptype')) || $(this).attr('comptype')=='line'){
if($(this).prop('name') == "dash"){
if($(this).val() == "false"){
n[$(this).prop('name')]=false;
}
if($(this).val() == "true"){
n[$(this).prop('name')]=true;
}
}else{
n[$(this).prop('name')]=$(this).val();
}
}
}
});
// n['name']=$form.find("input[name='name']").val();
flowchartdata.lines[i]=n;
}
});
}
flowsuperviseTemp.clearData();
flowsuperviseTemp.loadData(flowchartdata);
}else{
alert('请先选择节点!');
}
}
1、 确定按钮 保存单个节点的信息到节点实例中
2、流程图保存按钮
获取 json 结构的流程数据, ajax 请求 交互后台
3、用到一些 GooFlow de 内部属性
{
"title":"事项流程图",
"nodes":{
"1553438226938":{"name":"开始","left":267,"top":88,"type":"start round mix","width":28,"height":28,"alt":true},
"1553438229007":{"name":"结束","left":277,"top":412,"type":"end round mix","width":28,"height":28,"alt":true},
"1553438231623":{"name":"节点1","left":"237","top":"169","type":"task","width":"104","height":"28","alt":true,"model":"node","xm":"张三","xb":"男"},
"1553438232544":{"name":"节点2左","left":"107","top":"251","type":"task","width":"104","height":"28","alt":true,"model":"node","xm":"李四","xb":"女"},
"1553438233100":{"name":"节点2右","left":"382","top":"251","type":"task","width":"104","height":"28","alt":true,"model":"node","xm":"王五","xb":"男"},
"1553438235571":{"name":"节点3","left":"242","top":"333","type":"task","width":"104","height":"28","alt":true,"model":"node","xm":"赵柳","xb":"不详"}
},
"lines":{
"1553438237966":{"type":"sl","from":"1553438226938","to":"1553438231623","name":"","dash":false},
"1553438238928":{"type":"sl","from":"1553438231623","to":"1553438233100","name":"","dash":false},
"1553438240303":{"type":"sl","from":"1553438231623","to":"1553438232544","name":"","dash":false},
"1553438241365":{"type":"sl","from":"1553438232544","to":"1553438235571","name":"","dash":false},
"1553438243677":{"type":"sl","from":"1553438233100","to":"1553438235571","name":"","dash":false},
"1553438245066":{"type":"sl","from":"1553438235571","to":"1553438229007","name":"","dash":false}
},
"areas":{},
"initNum":13
}
大体 GooFlow 的一个 节点信息 与 自定义字段的 回显/保存 有了一点了解,
多查看文档 end ~