流程启动后,流程节点便进入到了任务相关的部分。可以看到我之前的做法是在启动节点就绑定了form表单,启动时就填写相关的数据。实际上在之前我的做法是不对开始节点做任何操作,知道任务节点的时候再填写相关的数据进行设置。
至于这两种方式的优劣,我暂时还不太确定,单独从功能上来说都是可以实现的,因此大家可以都试一试,然后视不同的情况而定,按自己究竟要用哪种。
而在任务相关的部分,我是把用户任务分成了两种,一种是我的申请,一种是我的任务。区别就是我发起的任务,和别人提交给我的或者反馈给我的任务。
那么流程一启动,第一个自然就是自己的申请了,这里便说明这个问题。
在这一篇中,需要注意的并不在于form表单,而是如何判断是不是初次申请,我一开始用的是流程节点来判断,这样就需要拿到流程节点并进行相关的遍历。
但是后来我回过头来再看时便发现其实远不止着一种方法,比如也可以通过任务来区分,如果整个流程实例只有一个任务,那么这个任务自然就是申请。当然了,前提是要限制任务是不能删除的。
还有就是,每一个任务都有启动时间,根据这个时间进行排序也应该可以进行判断,只是这个我还没有尝试,可行性究竟如何还有待确定。
那么下边就又到了上代码的时刻:
后台代码如下:
/** * @throwsXMLStreamException * 查询我申请未提交的任务 * * @author:tuzongxun * @Title: findTask * @param@return * @return Object * @date Mar 17, 20162:44:11 PM * @throws */ @RequestMapping(value = "/findFirstTask.do", method = RequestMethod.POST, produces = "application/json;charset=utf-8") @ResponseBody public Object findFirstTask(HttpServletRequest req) throws XMLStreamException { Map<String, Object> map = new HashMap<String, Object>(); boolean isLogin = this.isLogin(req); if (isLogin) { List<TaskModel> taskList = new ArrayList<TaskModel>(); HttpSession session = req.getSession(); String assginee = (String) session.getAttribute("userName"); List<Task> taskList1 = taskService.createTaskQuery() .taskAssignee(assginee).list(); if (taskList1 != null && taskList1.size() > 0) { for (Task task : taskList1) { TaskModel taskModel = new TaskModel(); // 获取部署名 String processdefintionId = task.getProcessDefinitionId(); ProcessDefinition processDefinition = repositoryService .createProcessDefinitionQuery() .processDefinitionId(processdefintionId) .singleResult(); // 根据taskname和节点判断是否是第一个 String taskName = task.getName(); Iterator<FlowElement> iterator = this .findFlow(processdefintionId); String row0 = null; String eleName0 = null; while (iterator.hasNext()) { FlowElement flowElement0 = iterator.next(); // 下一个节点 FlowElement flowElement = iterator.next(); String eleName = flowElement.getName(); if (taskName.equals(eleName)) { row0 = flowElement0.getXmlRowNumber() + ""; eleName0 = flowElement0.getClass().getSimpleName(); break; } } // 提交申请时 if (eleName0.equals("StartEvent")) { /////////////////////////// // 获取流程变量 Map<String, Object> variables = runtimeService .getVariables(task.getProcessInstanceId()); Set<String> keysSet = variables.keySet(); Iterator<String> keySet = keysSet.iterator(); Map<String, String> formData = new HashMap<String,String>(); taskModel.setLastForm(this .getStartForm1((String) variables .get("deploymentId"))); taskModel.setAssignee(task.getAssignee()); taskModel.setCreateTime(task.getCreateTime()); taskModel.setId(task.getId()); taskModel.setName(task.getName()); taskModel.setProcessInstanceId(task .getProcessInstanceId()); taskModel .setProcessDefId(task.getProcessDefinitionId()); taskModel.setFormKey(task.getFormKey()); String deploymentId = processDefinition .getDeploymentId(); Deployment deployment = repositoryService .createDeploymentQuery() .deploymentId(deploymentId).singleResult(); String deploymentName = deployment.getName(); taskModel.setDeploymentName(deploymentName); while (keySet.hasNext()) { String key = keySet.next(); String value = (String) variables.get(key); if (key.contains(row0)) { formData.put(key, value); } } taskModel.setFormData(formData); taskList.add(taskModel); } } } map.put("isLogin", "yes"); map.put("userName", (String) req.getSession().getAttribute("userName")); map.put("result", "success"); map.put("data", taskList); } else { map.put("isLogin", "no"); } return map; }
注意上边的方法中有调用getStartForm1这个方法,可在上一篇中找到。另外一个调用查询流程节点的方法如下:
/** * @throwsXMLStreamException * 查询流程节点 * * @author:tuzongxun * @Title: findFlow * @param@return * @return Iterator<FlowElement> * @date Mar 21, 20169:31:42 AM * @throws */ public Iterator<FlowElement> findFlow(String processDefId) throws XMLStreamException { List<ProcessDefinition> lists = repositoryService .createProcessDefinitionQuery() .processDefinitionId(processDefId) .orderByProcessDefinitionVersion().desc().list(); ProcessDefinition processDefinition = lists.get(0); processDefinition.getCategory(); String resourceName = processDefinition.getResourceName(); InputStream inputStream = repositoryService.getResourceAsStream( processDefinition.getDeploymentId(), resourceName); BpmnXMLConverter converter = new BpmnXMLConverter(); XMLInputFactory factory = XMLInputFactory.newInstance(); XMLStreamReader reader = factory.createXMLStreamReader(inputStream); BpmnModel bpmnModel = converter.convertToBpmnModel(reader); Process process = bpmnModel.getMainProcess(); Collection<FlowElement> elements = process.getFlowElements(); Iterator<FlowElement> iterator = elements.iterator(); return iterator; }
前台的代码,我想经过这么久的代码罗列,app.js和html中的写法应该没有必要再写了,业务逻辑如下:
angular.module('activitiApp') .controller('findFirstTaskCtr', ['$rootScope','$scope','$http','$location','$state', function($rootScope,$scope,$http,$location,$state){ $scope.init=function(){ $http.post("./findFirstTask.do").success(function(result) { if(result.isLogin==="yes"){ $rootScope.userName=result.userName; $scope.taskList=result.data; }else{ $location.path("/login"); } }); } //查看findDetail(task) $scope.findDetail=function(task){ console.log(task); $('#findDetail').html('').dialog({ title:'节点名称[' + task.name + ']', modal:true, width:$.common.window.getClientWidth() * 0.6, height:$.common.window.getClientHeight() * 0.9, open:function() { // 获取json格式的表单数据,就是流程定义中的所有field var dialog = this; // 读取启动时的表单 // 获取的form是字符行,html格式直接显示在对话框内就可以了,然后用form包裹起来 $(dialog).append("<div class='formContent' />"); $('.formContent').html('').wrap("<form id='findDetailForm' class='formkey-form1'method='post' />"); var $form = $('.formkey-form1'); //设置部署的Id $form.append("任务Id:<input type='text' readonly='readonly'style='background-color:#DEDCDC;margin-top:10px' name='taskId' value="+task.id+"></br>"); $form.append("申请时间:<input type='text' readonly='readonly'style='background-color:#DEDCDC;margin-top:10px' name='createTime' value="+new Date(task.createTime).format('yyyy-MM-dd hh:mm:ss')+"></br>"); //根据formData设置申请页面 //处理form字符串 var form=task.lastForm; //console.log(form); varindex0=form.lastIndexOf(">"); var p=form.split("<p>"); for(var i=1;i<p.length;i++){ var pName=p[i].substring(0,p[i].indexOf(":")+1); var index1=p[i].indexOf('name="'); var p0=p[i].substring(index1,p[i].lastIndexOf(">")); var index2=p0.indexOf('"'); var keyName=p[i].substring(index1+6,index2+index1+7); var value=null; for(var key in task.formData){ // var keyString=key+""; // if(keyString===keyName){ // value=(task.formData)[key]; var keyString=key.substring(0,key.length-1); if(keyString===keyName){ value=(task.formData)[key]; } } $form.append(pName+"<input type='text' readonly='readonly'style='background-color:#DEDCDC;margin-top:10px' name='createTime'value='"+value+"'></br>"); } // 初始化日期组件 $form.find('.datetime').datetimepicker({ stepMinute: 5 }); $form.find('.date').datepicker(); // 表单验证 $form.validate($.extend({},$.common.plugin.validator)); }, buttons:[{ text:'关闭', click:function() { $("#findDetail").dialog("close"); //sendStartupRequest(); } }] }).position({ //my:"center", //at:"center", offset:'300 300', of: window, collision:"fit" }); } //完成任务 $scope.completeTaskTo=function(task){ console.log(task); $('#comTask').html('').dialog({ title:'节点名称[' + task.name + ']', modal:true, width:$.common.window.getClientWidth() * 0.6, height:$.common.window.getClientHeight() * 0.9, open:function() { // 获取json格式的表单数据,就是流程定义中的所有field var dialog = this; // 读取启动时的表单 // 获取的form是字符行,html格式直接显示在对话框内就可以了,然后用form包裹起来 $(dialog).append("<div class='formContent' />"); $('.formContent').html('').wrap("<form id='completeTask' class='formkey-form'method='post' />"); var $form = $('.formkey-form'); // 设置表单action getStartFormAndStartProcess $form.attr('action', './completeTask'); //设置部署的Id $form.append("任务Id:<input type='text' readonly='readonly'style='background-color:#DEDCDC;margin-top:10px' name='taskId' value="+task.id+"></br>"); $form.append("申请时间:<input type='text' readonly='readonly'style='background-color:#DEDCDC;margin-top:10px' value="+new Date(task.createTime).format('yyyy-MM-dd hh:mm:ss')+"></br>"); //根据formData设置申请页面 //处理form字符串 varform=task.lastForm; //console.log(form); varindex0=form.lastIndexOf(">"); var p=form.split("<p>"); for(var i=1;i<p.length;i++){ var pName=p[i].substring(0,p[i].indexOf(":")+1); var index1=p[i].indexOf('name="'); varp0=p[i].substring(index1,p[i].lastIndexOf(">")); var index2=p0.indexOf('"'); var keyName=p[i].substring(index1+6,index2+index1+7); var value=null; for(var key in task.formData){ var keyString=key.substring(0,key.length-1); if(keyString===keyName){ value=(task.formData)[key]; } } $form.append(pName+"<input type='text' readonly='readonly'style='background-color:#DEDCDC;margin-top:10px' value='"+value+"'></br>"); } /////////////////////////////////////// $.post('./getTaskForm.do',task.formKey, function(result) { //设置部署的Id //$form.append("<inputtype='hidden' name='deploymentId' value="+deploymentId+">"); $form.append(result.form); }); //////////////////////////////////////// // 初始化日期组件 $form.find('.datetime').datetimepicker({ stepMinute: 5 }); $form.find('.date').datepicker(); // 表单验证 $form.validate($.extend({},$.common.plugin.validator)); }, buttons:[{ text:'提交', click:function() { $("#comTask").dialog("close"); sendStartupRequest(); } }] }).position({ //my:"center", //at:"center", offset:'300 300', of: window, collision:"fit" }); } /** * 提交表单 * @return {[type]} [description] */ functionsendStartupRequest() { if ($(".formkey-form").valid()) { var url = './completeTask.do'; var args = $('#completeTask').serialize(); $.post(url,args, function(data){ $("#comTask").dialog("close"); //$location.path("/processList"); window.location.href=("#/processList"); setTimeout(function(){ //$location.path("/findFirstTask"); window.location.href =("#/findFirstTask"); },1500); }); } } }])