Browse Source

钉钉考勤统计查询页面功能

fancy 5 years ago
parent
commit
ca68889293

+ 68 - 57
o2web/source/x_component_Attendance/$Main/navi.json

@@ -2,141 +2,152 @@
   {
     "title": "我的考勤月报",
     "id": "10",
-    "action" : "openMyIndex"
+    "action": "openMyIndex"
   },
   {
     "title": "我的考勤统计",
     "id": "11",
-    "action" : "openMyDetail"
+    "action": "openMyDetail"
   },
   {
     "title": "我的申诉申请",
     "id": "12",
-    "action" : "openMyAppealDeal"
+    "action": "openMyAppealDeal"
   },
   {
     "title": "员工考勤申诉审批",
     "id": "13",
-    "action" : "openAppealDeal"
+    "action": "openAppealDeal"
   },
   {
-    "access" :"admin_dept",
-    "type" :"sep"
+    "access": "admin_dept",
+    "type": "sep"
   },
   {
-    "access" :"admin_dept",
+    "access": "admin_dept",
     "title": "部门考勤月报",
     "id": "15",
-    "action" : "openUnitIndex"
+    "action": "openUnitIndex"
   },
   {
-    "access" :"admin_dept",
+    "access": "admin_dept",
     "title": "个人考勤统计",
     "id": "16",
-    "action" : "openPeopleDetail"
+    "action": "openPeopleDetail"
   },
   {
-    "access" :"admin_dept",
+    "access": "admin_dept",
     "title": "部门考勤统计",
     "id": "17",
-
-    "action" : "openUnitDetail"
+    "action": "openUnitDetail"
   },
   {
-    "access" :"admin",
+    "access": "admin",
     "title": "公司考勤统计",
     "id": "18",
-    "action" : "openTopUnitDetail"
+    "action": "openTopUnitDetail"
   },
   {
-    "access" :"admin",
-    "type" :"sep"
+    "access": "dingding",
+    "title": "钉钉个人考勤统计",
+    "id": "161",
+    "action": "openDingdingPeopleDetail"
   },
   {
-    "access" :"admin",
+    "access": "dingding",
+    "title": "钉钉部门考勤统计",
+    "id": "171",
+    "action": "openDingdingUnitDetail"
+  },
+  {
+    "access": "admin",
+    "type": "sep"
+  },
+  {
+    "access": "admin",
     "title": "维护",
     "id": "20",
     "sub": [
       {
-        "access" :"admin",
+        "access": "admin",
         "title": "数据导入",
         "id": "20.3",
-        "action" : "openImporting"
+        "action": "openImporting"
       },
       {
-        "access" :"admin",
+        "access": "admin",
         "title": "导入错误信息",
         "id": "20.4",
-        "action" : "openImportedInvalidInfor"
+        "action": "openImportedInvalidInfor"
       },
       {
-        "access" :"admin",
+        "access": "admin",
         "title": "非正常出勤数据导出",
         "id": "20.42",
-        "action" : "openAbnormalExport"
+        "action": "openAbnormalExport"
       },
       {
-        "access" :"admin",
+        "access": "admin",
         "title": "员工休假记录",
         "id": "20.1",
-        "action" : "openSelfHoliday"
+        "action": "openSelfHoliday"
       }
     ]
   },
   {
-    "access" :"admin",
+    "access": "admin",
     "title": "权限和人员",
     "id": "30",
     "sub": [
       {
-        "id" : "30.10",
-        "access" : "admin",
-        "title" : "管理员设置",
-        "action" : "openPermissionSetting"
+        "id": "30.10",
+        "access": "admin",
+        "title": "管理员设置",
+        "action": "openPermissionSetting"
       },
       {
-        "id" : "30.20",
-        "access" : "admin",
-        "title" : "考勤人员配置",
-        "action" : "openPersonSetting"
+        "id": "30.20",
+        "access": "admin",
+        "title": "考勤人员配置",
+        "action": "openPersonSetting"
       }
     ]
   },
   {
-    "access" :"admin",
+    "access": "admin",
     "title": "配置",
     "id": "40",
     "sub": [
       {
-        "id" : "40.10",
-        "access" : "admin",
-        "title" : "排班设置",
-        "action" : "openScheduleSetting"
+        "id": "40.10",
+        "access": "admin",
+        "title": "排班设置",
+        "action": "openScheduleSetting"
       },
       {
-        "id" : "40.20",
-        "access" : "admin",
-        "title" : "统计周期设置",
-        "action" : "openStaticsCycleExplorer"
+        "id": "40.20",
+        "access": "admin",
+        "title": "统计周期设置",
+        "action": "openStaticsCycleExplorer"
       },
       {
-        "id" : "40.15",
-        "access" : "admin",
-        "title" : "法定假期",
-        "action" : "openHolidaySetting"
+        "id": "40.15",
+        "access": "admin",
+        "title": "法定假期",
+        "action": "openHolidaySetting"
       },
       {
-        "id" : "40.35",
-        "access" : "admin",
-        "title" : "工作场所设置",
-        "action" : "openAddressSetting"
+        "id": "40.35",
+        "access": "admin",
+        "title": "工作场所设置",
+        "action": "openAddressSetting"
       },
       {
-        "id" : "40.25",
-        "access" : "admin",
-        "target" : "_blank",
-        "title" : "申诉设置",
-        "action" : "openAppSetting"
+        "id": "40.25",
+        "access": "admin",
+        "target": "_blank",
+        "title": "申诉设置",
+        "action": "openAppSetting"
       }
     ]
   }

+ 42 - 0
o2web/source/x_component_Attendance/$PeopleDetail/listItem_dingding.json

@@ -0,0 +1,42 @@
+[
+  {
+    "title": "姓名",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function( d ){ return d.o2User.split('@')[0] }",
+    "name": "o2User",
+    "width": "20%"
+  },
+  {
+    "title": "日期",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function(d){ var date = new Date(d.userCheckTime);     return date.getFullYear()+'-'+(date.getMonth()+1)+'-'+date.getDate();}",
+    "name": "userCheckTime",
+    "width": "20%"
+  },
+  {
+    "title": "打卡类型",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function( data ){ if(data.checkType == 'OffDuty'){return '下班打卡';}else{return '上班打卡';}  }",
+    "name": "checkType",
+    "width": "20%"
+  },
+  {
+    "title": "打卡结果",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function( data ){ if(data.timeResult == 'Normal'){return '正常';}else if(data.timeResult == 'Early'){return '早退';}else if(data.timeResult == 'Late'){return '迟到';}else if(data.timeResult == 'SeriousLate'){return '严重迟到';}else if(data.timeResult == 'Absenteeism'){return '旷工迟到';}else {return '未打卡';}  }",
+    "name": "timeResult",
+    "width": "20%"
+  },
+  {
+    "title": "打卡时间",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function(d){ var date = new Date(d.userCheckTime);     return date.getHours()+':'+date.getMinutes()+':'+date.getSeconds();}",
+    "name": "userCheckTime",
+    "width": "20%"
+  }
+]

+ 42 - 0
o2web/source/x_component_Attendance/$UnitDetail/listItem_dingding.json

@@ -0,0 +1,42 @@
+[
+  {
+    "title": "姓名",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function( d ){ return d.o2User.split('@')[0] }",
+    "name": "o2User",
+    "width": "20%"
+  },
+  {
+    "title": "日期",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function(d){ var date = new Date(d.userCheckTime);     return date.getFullYear()+'-'+(date.getMonth()+1)+'-'+date.getDate();}",
+    "name": "userCheckTime",
+    "width": "20%"
+  },
+  {
+    "title": "打卡类型",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function( data ){ if(data.checkType == 'OffDuty'){return '下班打卡';}else{return '上班打卡';}  }",
+    "name": "checkType",
+    "width": "20%"
+  },
+  {
+    "title": "打卡结果",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function( data ){ if(data.timeResult == 'Normal'){return '正常';}else if(data.timeResult == 'Early'){return '早退';}else if(data.timeResult == 'Late'){return '迟到';}else if(data.timeResult == 'SeriousLate'){return '严重迟到';}else if(data.timeResult == 'Absenteeism'){return '旷工迟到';}else {return '未打卡';}  }",
+    "name": "timeResult",
+    "width": "20%"
+  },
+  {
+    "title": "打卡时间",
+    "headStyles": "normalThNode",
+    "contentStyles": "normalTdNode",
+    "item": "function(d){ var date = new Date(d.userCheckTime);     return date.getHours()+':'+date.getMinutes()+':'+date.getSeconds();}",
+    "name": "userCheckTime",
+    "width": "20%"
+  }
+]

+ 199 - 161
o2web/source/x_component_Attendance/Main.js

@@ -1,5 +1,5 @@
 MWF.xApplication.Attendance = MWF.xApplication.Attendance || {};
-MWF.require("MWF.widget.O2Identity", null,false);
+MWF.require("MWF.widget.O2Identity", null, false);
 //MWF.xDesktop.requireApp("Attendance", "Actions.RestActions", null, false);
 MWF.xDesktop.requireApp("Attendance", "Common", null, false);
 MWF.xDesktop.requireApp("Template", "MDomItem", null, false);
@@ -12,7 +12,7 @@ MWF.xApplication.Attendance.Main = new Class({
 	Implements: [Options, Events],
 
 	options: {
-		"curNaviId" : null,
+		"curNaviId": null,
 		"style": "default",
 		"name": "Attendance",
 		"icon": "icon.png",
@@ -22,10 +22,10 @@ MWF.xApplication.Attendance.Main = new Class({
 		"isMax": true,
 		"title": MWF.xApplication.Attendance.LP.title
 	},
-	onQueryLoad: function(){
+	onQueryLoad: function () {
 		this.lp = MWF.xApplication.Attendance.LP;
 	},
-	loadApplication: function(callback){
+	loadApplication: function (callback) {
 		if (!this.options.isRefresh) {
 			this.maxSize(function () {
 				this.loadLayout();
@@ -34,9 +34,10 @@ MWF.xApplication.Attendance.Main = new Class({
 			this.loadLayout();
 		}
 	},
-	loadLayout: function(){
-		this.manageUnits =[];
+	loadLayout: function () {
+		this.manageUnits = [];
 		this.manageTopUnits = [];
+		this.enableType = "";
 
 		this.restActions = MWF.Actions.get("x_attendance_assemble_control");
 		this.personActions = MWF.Actions.get("x_organization_assemble_personal");
@@ -45,263 +46,297 @@ MWF.xApplication.Attendance.Main = new Class({
 		this.createNode();
 		this.loadApplicationContent();
 	},
-	isAdmin: function(){
-		return this.isTopUnitManager() || MWF.AC.isAttendanceManager() || MWF.AC.isAdministrator() 
+	isAdmin: function () {
+		return this.isTopUnitManager() || MWF.AC.isAttendanceManager() || MWF.AC.isAdministrator()
 	},
-	isUnitManager : function(){
+	isUnitManager: function () {
 		return this.manageUnits.length > 0;
 	},
-	isTopUnitManager : function(){
+	isTopUnitManager: function () {
 		return this.manageTopUnits.length > 0;
 	},
-	getNameFlag : function(name){
+	getNameFlag: function (name) {
 		var t = typeOf(name);
-		if (t==="array"){
+		if (t === "array") {
 			var v = [];
-			name.each(function(id){
-				v.push((typeOf(id)==="object") ? (id.distinguishedName || id.id || id.unique || id.name) : id);
+			name.each(function (id) {
+				v.push((typeOf(id) === "object") ? (id.distinguishedName || id.id || id.unique || id.name) : id);
 			});
 			return v;
-		}else{
-			return [(t==="object") ? (name.distinguishedName || name.id || name.unique || name.name) : name];
+		} else {
+			return [(t === "object") ? (name.distinguishedName || name.id || name.unique || name.name) : name];
 		}
 	},
-	loadController: function(callback){
-		this.restActions.listPermission( function( json ){
+	loadController: function (callback) {
+		this.restActions.listPermission(function (json) {
 			json.data = json.data || [];
-			json.data.each(function(item){
-				if( item.adminLevel == "COMPANY" && item.adminName == layout.desktop.session.user.distinguishedName){
-					this.manageTopUnits.push( item.unitName )
-				}else if( item.adminLevel == "DEPT" && item.adminName == layout.desktop.session.user.distinguishedName ){
-					this.manageUnits.push( item.unitName )
+			json.data.each(function (item) {
+				if (item.adminLevel == "COMPANY" && item.adminName == layout.desktop.session.user.distinguishedName) {
+					this.manageTopUnits.push(item.unitName)
+				} else if (item.adminLevel == "DEPT" && item.adminName == layout.desktop.session.user.distinguishedName) {
+					this.manageUnits.push(item.unitName)
 				}
 			}.bind(this));
-			if(callback)callback(json);
+			if (callback) callback(json);
 		}.bind(this));
 	},
-	createNode: function(){
+	loadEnableType: function (callback) {
+		var action = o2.Actions.load("x_attendance_assemble_control");
+		action.AttendanceSettingAction.enableType(//平台封装好的方法
+			function (json) { //服务调用成功的回调函数, json为服务传回的数据
+				console.log(json);
+				if (json.data && json.data.value) {
+					debugger;
+					this.enableType = json.data.value;
+				}
+				if (callback) callback(json);
+			}.bind(this));
+	},
+	createNode: function () {
 		this.content.setStyle("overflow", "hidden");
 		this.node = new Element("div", {
-			"styles": {"width": "100%", "height": "100%", "overflow": "hidden"}
+			"styles": { "width": "100%", "height": "100%", "overflow": "hidden" }
 		}).inject(this.content);
 	},
-	loadApplicationContent: function(){
-		this.loadController(function(){
-			this.loaNavi();
+	loadApplicationContent: function () {
+		this.loadController(function () {
+			this.loadEnableType(function () {
+				this.loaNavi();
+			}.bind(this));
 		}.bind(this));
 		//this.loadApplicationLayout();
 	},
-	loaNavi: function(callback){
+	loaNavi: function (callback) {
 		this.naviNode = new Element("div.naviNode", {
 			"styles": this.css.naviNode
 		}).inject(this.node);
 
-		var curNavi = { "id" : "" };
-		if( this.status ){
+		var curNavi = { "id": "" };
+		if (this.status) {
 			curNavi.id = this.status.id
 		}
-		if( this.options.curNaviId ){
+		if (this.options.curNaviId) {
 			curNavi.id = this.options.curNaviId;
 		}
-		this.navi = new MWF.xApplication.Attendance.Navi(this, this.naviNode, curNavi );
+		this.navi = new MWF.xApplication.Attendance.Navi(this, this.naviNode, curNavi);
 	},
-	clearContent: function(){
-		if (this.explorerContent){
-			if (this.explorer && this.explorer.destroy ){
+	clearContent: function () {
+		if (this.explorerContent) {
+			if (this.explorer && this.explorer.destroy) {
 				this.explorer.destroy();
 			}
 			this.explorerContent.destroy();
 			this.explorerContent = null;
 		}
 	},
-	openMyIndex : function(){
-		MWF.xDesktop.requireApp("Attendance", "MyIndex", function(){
+	openMyIndex: function () {
+		MWF.xDesktop.requireApp("Attendance", "MyIndex", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.MyIndex(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.MyIndex(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openMyDetail : function(){
-		MWF.xDesktop.requireApp("Attendance", "MyDetail", function(){
+	openMyDetail: function () {
+		MWF.xDesktop.requireApp("Attendance", "MyDetail", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.MyDetail(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.MyDetail(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openUnitIndex : function(){
-		MWF.xDesktop.requireApp("Attendance", "UnitIndex", function(){
+	openUnitIndex: function () {
+		MWF.xDesktop.requireApp("Attendance", "UnitIndex", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.UnitIndex(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.UnitIndex(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openUnitDetail : function(){
-		MWF.xDesktop.requireApp("Attendance", "UnitDetail", function(){
+	openUnitDetail: function () {
+		MWF.xDesktop.requireApp("Attendance", "UnitDetail", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.UnitDetail(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.UnitDetail(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openPeopleDetail : function(){
-		MWF.xDesktop.requireApp("Attendance", "PeopleDetail", function(){
+	openDingdingUnitDetail: function () {
+		MWF.xDesktop.requireApp("Attendance", "UnitDingdingDetail", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.PeopleDetail(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.UnitDingdingDetail(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openTopUnitDetail : function(){
-		MWF.xDesktop.requireApp("Attendance", "TopUnitDetail", function(){
+	openPeopleDetail: function () {
+		MWF.xDesktop.requireApp("Attendance", "PeopleDetail", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.TopUnitDetail(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.PeopleDetail(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openSelfHoliday : function(){
-		MWF.xDesktop.requireApp("Attendance", "SelfHoliday", function(){
+	openDingdingPeopleDetail: function () {
+		MWF.xDesktop.requireApp("Attendance", "PeopleDingdingDetail", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.SelfHoliday(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.PeopleDingdingDetail(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openMyAppealDeal : function(){
-		MWF.xDesktop.requireApp("Attendance", "MyAppeal", function(){
+	openTopUnitDetail: function () {
+		MWF.xDesktop.requireApp("Attendance", "TopUnitDetail", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.MyAppeal(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.TopUnitDetail(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openAppealDeal : function(){
-		MWF.xDesktop.requireApp("Attendance", "AppealExplorer", function(){
+	openSelfHoliday: function () {
+		MWF.xDesktop.requireApp("Attendance", "SelfHoliday", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.AppealExplorer(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.SelfHoliday(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openImporting : function(){
-		MWF.xDesktop.requireApp("Attendance", "ImportExplorer", function(){
+	openMyAppealDeal: function () {
+		MWF.xDesktop.requireApp("Attendance", "MyAppeal", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.ImportExplorer(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.MyAppeal(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openImportedInvalidInfor : function(){
-		MWF.xDesktop.requireApp("Attendance", "InvalidInfor", function(){
+	openAppealDeal: function () {
+		MWF.xDesktop.requireApp("Attendance", "AppealExplorer", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.InvalidInfor(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.AppealExplorer(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openAbnormalExport : function(){
-		MWF.xDesktop.requireApp("Attendance", "AbnormalExport", function(){
+	openImporting: function () {
+		MWF.xDesktop.requireApp("Attendance", "ImportExplorer", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.AbnormalExport(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.ImportExplorer(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openScheduleSetting: function(){
-		MWF.xDesktop.requireApp("Attendance", "ScheduleExplorer", function(){
+	openImportedInvalidInfor: function () {
+		MWF.xDesktop.requireApp("Attendance", "InvalidInfor", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.ScheduleExplorer(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.InvalidInfor(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openPermissionSetting: function(){
-		MWF.xDesktop.requireApp("Attendance", "PermissionExplorer", function(){
+	openAbnormalExport: function () {
+		MWF.xDesktop.requireApp("Attendance", "AbnormalExport", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.PermissionExplorer(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.AbnormalExport(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openHolidaySetting : function(){
-		MWF.xDesktop.requireApp("Attendance", "HolidayExplorer", function(){
+	openScheduleSetting: function () {
+		MWF.xDesktop.requireApp("Attendance", "ScheduleExplorer", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.HolidayExplorer(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.ScheduleExplorer(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openStaticsCycleExplorer : function(){
-		MWF.xDesktop.requireApp("Attendance", "StatisticsCycle", function(){
+	openPermissionSetting: function () {
+		MWF.xDesktop.requireApp("Attendance", "PermissionExplorer", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.StatisticsCycle(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.PermissionExplorer(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openAppSetting : function(){
-		MWF.xDesktop.requireApp("Attendance", "AppSetting", function(){
-			var setting = new MWF.xApplication.Attendance.AppSetting(this,this.restActions);
+	openHolidaySetting: function () {
+		MWF.xDesktop.requireApp("Attendance", "HolidayExplorer", function () {
+			this.clearContent();
+			this.explorerContent = new Element("div", {
+				"styles": this.css.rightContentNode
+			}).inject(this.node);
+			this.explorer = new MWF.xApplication.Attendance.HolidayExplorer(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
+			this.explorer.load();
+		}.bind(this));
+	},
+	openStaticsCycleExplorer: function () {
+		MWF.xDesktop.requireApp("Attendance", "StatisticsCycle", function () {
+			this.clearContent();
+			this.explorerContent = new Element("div", {
+				"styles": this.css.rightContentNode
+			}).inject(this.node);
+			this.explorer = new MWF.xApplication.Attendance.StatisticsCycle(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
+			this.explorer.load();
+		}.bind(this));
+	},
+	openAppSetting: function () {
+		MWF.xDesktop.requireApp("Attendance", "AppSetting", function () {
+			var setting = new MWF.xApplication.Attendance.AppSetting(this, this.restActions);
 			setting.edit();
 		}.bind(this));
 	},
-	openAddressSetting : function(){
-		MWF.xDesktop.requireApp("Attendance", "AddressExplorer", function(){
+	openAddressSetting: function () {
+		MWF.xDesktop.requireApp("Attendance", "AddressExplorer", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.AddressExplorer(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.AddressExplorer(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	openPersonSetting : function(){
-		MWF.xDesktop.requireApp("Attendance", "PersonSetting", function(){
+	openPersonSetting: function () {
+		MWF.xDesktop.requireApp("Attendance", "PersonSetting", function () {
 			this.clearContent();
 			this.explorerContent = new Element("div", {
 				"styles": this.css.rightContentNode
 			}).inject(this.node);
-			this.explorer = new MWF.xApplication.Attendance.PersonSetting(this.explorerContent, this, this.restActions,{"isAdmin":this.isAdmin() } );
+			this.explorer = new MWF.xApplication.Attendance.PersonSetting(this.explorerContent, this, this.restActions, { "isAdmin": this.isAdmin() });
 			this.explorer.load();
 		}.bind(this));
 	},
-	recordStatus: function(){
-		return this.navi && this.navi.currentItem ?  this.navi.currentItem.retrieve("data") : {};
+	recordStatus: function () {
+		return this.navi && this.navi.currentItem ? this.navi.currentItem.retrieve("data") : {};
 	}
 });
 
@@ -309,10 +344,10 @@ MWF.xApplication.Attendance.Main = new Class({
 
 MWF.xApplication.Attendance.Navi = new Class({
 	Implements: [Options, Events],
-	options : {
-		"id" : ""
+	options: {
+		"id": ""
 	},
-	initialize: function(app, node, options){
+	initialize: function (app, node, options) {
 		this.setOptions(options);
 		this.app = app;
 		this.node = $(node);
@@ -324,61 +359,64 @@ MWF.xApplication.Attendance.Navi = new Class({
 		this.elements = [];
 		this.load();
 	},
-	load: function(){
-		this.scrollNode = new Element("div.naviScrollNode", { "styles" : this.css.naviScrollNode }).inject( this.node );
-		this.areaNode = new Element("div.naviAreaNode", { "styles" : this.css.naviAreaNode }).inject( this.scrollNode );
+	load: function () {
+		this.scrollNode = new Element("div.naviScrollNode", { "styles": this.css.naviScrollNode }).inject(this.node);
+		this.areaNode = new Element("div.naviAreaNode", { "styles": this.css.naviAreaNode }).inject(this.scrollNode);
 
 		this.setNodeScroll();
 
-		var naviUrl = this.app.path+"navi.json";
-		MWF.getJSON(naviUrl, function(json){
-			json.each(function(navi){
-				if( navi.access && navi.access == "admin" ){
-					if( this.app.isAdmin() )this.createNaviNode(navi);
-				}else if( navi.access && navi.access == "admin_dept" ){
-					if( this.app.isUnitManager() || this.app.isAdmin() )this.createNaviNode(navi);
-				}else{
+		var naviUrl = this.app.path + "navi.json";
+		MWF.getJSON(naviUrl, function (json) {
+			json.each(function (navi) {
+				if (navi.access && navi.access == "admin") {
+					if (this.app.isAdmin()) this.createNaviNode(navi);
+				} else if (navi.access && navi.access == "admin_dept") {
+					if (this.app.isUnitManager() || this.app.isAdmin()) this.createNaviNode(navi);
+				} else if (navi.access && navi.access == "dingding") { //启用钉钉考勤同步后
+					debugger;
+					if ((this.app.isUnitManager() || this.app.isAdmin()) && (this.app.enableType == "dingding")) this.createNaviNode(navi);
+				} else {
 					this.createNaviNode(navi);
 				}
 			}.bind(this));
-			if( this.options.id == "" )this.elements[0].click();
+			if (this.options.id == "") this.elements[0].click();
 
 			this.setContentSize();
 
 			this.app.addEvent("resize", this.setContentSize.bind(this));
 		}.bind(this));
 	},
-	setNodeScroll: function(){
-		MWF.require("MWF.widget.DragScroll", function(){
+	setNodeScroll: function () {
+		MWF.require("MWF.widget.DragScroll", function () {
 			new MWF.widget.DragScroll(this.scrollNode);
 		}.bind(this));
-		MWF.require("MWF.widget.ScrollBar", function(){
-			new MWF.widget.ScrollBar(this.scrollNode, {"indent": false});
+		MWF.require("MWF.widget.ScrollBar", function () {
+			new MWF.widget.ScrollBar(this.scrollNode, { "indent": false });
 		}.bind(this));
 	},
-	createNaviNode :function(data){
-		if( data.type == "sep" ){
+	createNaviNode: function (data) {
+		if (data.type == "sep") {
 			var flag = true;
-			if( data.access == "admin" ){
-				if( !this.app.isAdmin() )flag = false;
-			}else if( data.access && data.access == "admin_dept" ){
-				if( !this.app.isUnitManager() && !this.app.isAdmin() )flag = false;
+			if (data.access == "admin") {
+				if (!this.app.isAdmin()) flag = false;
+			} else if (data.access && data.access == "admin_dept") {
+				if (!this.app.isUnitManager() && !this.app.isAdmin()) flag = false;
 			}
-			if( flag ){
+			if (flag) {
 				new Element("div", { "styles": this.css.viewNaviSepartorNode }).inject(this.areaNode);
 			}
-		}else if( data.sub && data.sub.length > 0 ){
+		} else if (data.sub && data.sub.length > 0) {
 			this.createNaviMenuNode(data);
-		}else{
+		} else {
 			this.menus[data.id] = {};
 			this.createNaviItemNode(data, data.id);
 		}
 	},
-	createNaviMenuNode :function(data){
-		if( data.access == "admin" ){
-			if( !this.app.isAdmin() )return;
-		}else if(data.access == "admin_dept"){
-			if( !this.app.isUnitManager() && !this.app.isAdmin() )return;
+	createNaviMenuNode: function (data) {
+		if (data.access == "admin") {
+			if (!this.app.isAdmin()) return;
+		} else if (data.access == "admin_dept") {
+			if (!this.app.isUnitManager() && !this.app.isAdmin()) return;
 		}
 		var _self = this;
 		var menuNode = new Element("div", {
@@ -387,7 +425,7 @@ MWF.xApplication.Attendance.Navi = new Class({
 		menuNode.store("data", data);
 		menuNode.store("type", "menu");
 
-		var textNode =  new Element("div", {
+		var textNode = new Element("div", {
 			"styles": this.css.naviMenuTextNode,
 			"text": data.title
 		});
@@ -399,54 +437,54 @@ MWF.xApplication.Attendance.Navi = new Class({
 		this.elements.push(menuNode);
 
 		menuNode.addEvents({
-			"mouseover": function(){ if (_self.currentMenu!=this) this.setStyles(_self.app.css.naviMenuNode_over);},
-			"mouseout": function(){if (_self.currentMenu!=this) this.setStyles(_self.app.css.naviMenuNode);},
-			"mousedown": function(){if (_self.currentMenu!=this) this.setStyles(_self.app.css.naviMenuNode_down);},
-			"mouseup": function(){if (_self.currentMenu!=this) this.setStyles(_self.app.css.naviMenuNode_over);},
-			"click": function(){
+			"mouseover": function () { if (_self.currentMenu != this) this.setStyles(_self.app.css.naviMenuNode_over); },
+			"mouseout": function () { if (_self.currentMenu != this) this.setStyles(_self.app.css.naviMenuNode); },
+			"mousedown": function () { if (_self.currentMenu != this) this.setStyles(_self.app.css.naviMenuNode_down); },
+			"mouseup": function () { if (_self.currentMenu != this) this.setStyles(_self.app.css.naviMenuNode_over); },
+			"click": function () {
 				//if (_self.currentNavi!=this) _self.doAction.apply(_self, [this]);
 				_self.clickMenu.apply(_self, [this]);
 			}
 		});
 
-		data.sub.each(function( d ){
-			this.createNaviItemNode( d, data.id, menuNode  )
+		data.sub.each(function (d) {
+			this.createNaviItemNode(d, data.id, menuNode)
 		}.bind(this))
 	},
-	clickMenu: function(naviNode) {
+	clickMenu: function (naviNode) {
 		var navi = naviNode.retrieve("data");
 		var action = navi.action;
 
 		this.closeCurrentMenu();
-		if( this.menus[navi.id].itemNodes ) {
-			this.menus[navi.id].itemNodes.each( function(itemNode){
-				itemNode.setStyle("display","block");
+		if (this.menus[navi.id].itemNodes) {
+			this.menus[navi.id].itemNodes.each(function (itemNode) {
+				itemNode.setStyle("display", "block");
 			})
 		}
 
 		var type = naviNode.retrieve("type");
 		if (!navi.target || navi.target != "_blank") {
-			naviNode.setStyles( this.css.naviMenuNode_current );
+			naviNode.setStyles(this.css.naviMenuNode_current);
 			this.currentMenu = naviNode;
 		}
 	},
-	closeCurrentMenu:function(){
-		if( this.currentMenu ) {
+	closeCurrentMenu: function () {
+		if (this.currentMenu) {
 			var data = this.currentMenu.retrieve("data");
 			if (this.menus[data.id].itemNodes) {
 				this.menus[data.id].itemNodes.each(function (itemNode) {
 					itemNode.setStyle("display", "none");
 				})
 			}
-			this.currentMenu.setStyles( this.css.naviMenuNode);
+			this.currentMenu.setStyles(this.css.naviMenuNode);
 		}
 	},
-	createNaviItemNode : function( data,menuId ){
+	createNaviItemNode: function (data, menuId) {
 
-		if( data.access == "admin" ){
-			if( !this.app.isAdmin() )return;
-		}else if( data.access && data.access == "admin_dept" ){
-			if( !this.app.isUnitManager() && !this.app.isAdmin() )return;
+		if (data.access == "admin") {
+			if (!this.app.isAdmin()) return;
+		} else if (data.access && data.access == "admin_dept") {
+			if (!this.app.isUnitManager() && !this.app.isAdmin()) return;
 		}
 
 		var _self = this;
@@ -456,13 +494,13 @@ MWF.xApplication.Attendance.Navi = new Class({
 		var itemNode = new Element("div", {
 			"styles": this.css.naviItemNode
 		});
-		itemNode.setStyle("display","block");
+		itemNode.setStyle("display", "block");
 
 		items.push(itemNode);
 		itemNode.store("data", data);
 		itemNode.store("type", "item");
 
-		var textNode =  new Element("div", {
+		var textNode = new Element("div", {
 			"styles": this.css.naviItemTextNode,
 			"text": data.title
 		});
@@ -474,20 +512,20 @@ MWF.xApplication.Attendance.Navi = new Class({
 		this.items[data.id] = itemNode;
 
 		itemNode.addEvents({
-			"mouseover": function(){ if (_self.currentItem!=this) this.setStyles(_self.app.css.naviItemNode_over);},
-			"mouseout": function(){if (_self.currentItem!=this) this.setStyles(_self.app.css.naviItemNode);},
-			"mousedown": function(){if (_self.currentItem!=this) this.setStyles(_self.app.css.naviItemNode_down);},
-			"mouseup": function(){if (_self.currentItem!=this) this.setStyles(_self.app.css.naviItemNode_over);},
-			"click": function(){
+			"mouseover": function () { if (_self.currentItem != this) this.setStyles(_self.app.css.naviItemNode_over); },
+			"mouseout": function () { if (_self.currentItem != this) this.setStyles(_self.app.css.naviItemNode); },
+			"mousedown": function () { if (_self.currentItem != this) this.setStyles(_self.app.css.naviItemNode_down); },
+			"mouseup": function () { if (_self.currentItem != this) this.setStyles(_self.app.css.naviItemNode_over); },
+			"click": function () {
 				_self.clickItem.apply(_self, [this]);
 			}
 		});
 
-		if( data.id == this.options.id ){
+		if (data.id == this.options.id) {
 			itemNode.click();
 		}
 	},
-	clickItem : function(naviNode) {
+	clickItem: function (naviNode) {
 		var navi = naviNode.retrieve("data");
 		var action = navi.action;
 
@@ -502,9 +540,9 @@ MWF.xApplication.Attendance.Navi = new Class({
 			this.app[navi.action].call(this.app, navi);
 		}
 	},
-	setContentSize : function(){
+	setContentSize: function () {
 		var size = this.app.content.getSize();
-		this.scrollNode.setStyle("height", size.y - 5 );
+		this.scrollNode.setStyle("height", size.y - 5);
 	}
 	//loadCalendar: function () {
 	//	var calendarArea = new Element("div#calendarArea",{

+ 455 - 0
o2web/source/x_component_Attendance/PeopleDingdingDetail.js

@@ -0,0 +1,455 @@
+MWF.xDesktop.requireApp("Attendance", "Explorer", null, false);
+MWF.xDesktop.requireApp("Selector", "package", null, false);
+
+MWF.xApplication.Attendance.PeopleDingdingDetail = new Class({
+    Extends: MWF.widget.Common,
+    Implements: [Options, Events],
+    options: {
+        "style": "default"
+    },
+    initialize: function (node, app, actions, options) {
+        this.setOptions(options);
+        this.app = app;
+        this.path = "/x_component_Attendance/$PeopleDetail/";
+        this.cssPath = "/x_component_Attendance/$PeopleDetail/" + this.options.style + "/css.wcss";
+        this._loadCss();
+
+        this.actions = actions;
+        this.node = $(node);
+    },
+    load: function () {
+        this.loadTab();
+    },
+    loadTab: function () {
+
+        this.tabNode = new Element("div", { "styles": this.css.tabNode }).inject(this.node);
+        this.detailArea = new Element("div", { "styles": this.css.tabPageContainer }).inject(this.tabNode);
+        //this.selfHolidayArea = new Element("div",{"styles" : this.css.tabPageContainer }).inject(this.tabNode)
+        this.detailStaticArea = new Element("div", { "styles": this.css.tabPageContainer }).inject(this.tabNode);
+        //this.selfHolidayStaticArea = new Element("div",{"styles" : this.css.tabPageContainer }).inject(this.tabNode)
+
+        MWF.require("MWF.widget.Tab", function () {
+
+            this.tabs = new MWF.widget.Tab(this.tabNode, { "style": "attendance" });
+            this.tabs.load();
+
+            this.detailPage = this.tabs.addTab(this.detailArea, "个人打卡明细", false);
+            this.detailPage.contentNodeArea.set("class", "detailPage");
+            this.detailPage.addEvent("show", function () {
+                if (!this.detailExplorer) {
+                    this.detailExplorer = new MWF.xApplication.Attendance.PeopleDingdingDetail.Explorer(this.detailArea, this);
+                    this.detailExplorer.load();
+                }
+            }.bind(this));
+
+
+            this.detailStaticPage = this.tabs.addTab(this.detailStaticArea, "个人打卡率统计", false);
+            this.detailStaticPage.contentNodeArea.set("class", "detailStaticPage");
+            this.detailStaticPage.addEvent("show", function () {
+                if (!this.detailStaticExplorer) {
+                    this.detailStaticExplorer = new MWF.xApplication.Attendance.PeopleDingdingDetail.DetailStaticExplorer(this.detailStaticArea, this);
+                    this.detailStaticExplorer.load();
+                }
+            }.bind(this));
+
+
+            this.tabs.pages[0].showTab();
+        }.bind(this));
+    }
+});
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.Explorer = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer,
+    Implements: [Options, Events],
+
+    initialize: function (node, parent, options) {
+        this.setOptions(options);
+        this.parent = parent;
+        this.app = parent.app;
+        this.css = parent.css;
+        this.path = parent.path;
+
+        this.actions = parent.actions;
+        this.node = $(node);
+
+
+        this.initData();
+        if (!this.peopleActions) this.peopleActions = new MWF.xAction.org.express.RestActions();
+    },
+    initData: function () {
+        this.toolItemNodes = [];
+    },
+    reload: function () {
+        this.node.empty();
+        this.load();
+    },
+    load: function () {
+        this.loadFilter();
+        this.loadContentNode();
+        this.setNodeScroll();
+    },
+    loadFilter: function () {
+        this.fileterNode = new Element("div.fileterNode", {
+            "styles": this.css.fileterNode
+        }).inject(this.node);
+
+        var html = "<table width='100%' bordr='0' cellpadding='5' cellspacing='0' styles='filterTable'>" +
+            "<tr>" +
+            "    <td styles='filterTableValue' lable='person'></td>" +
+            "    <td styles='filterTableTitle' item='person'></td>" +
+            "    <td styles='filterTableTitle' lable='year'></td>" +
+            "    <td styles='filterTableValue' item='year'></td>" +
+            "    <td styles='filterTableTitle' lable='month'></td>" +
+            "    <td styles='filterTableValue' item='month'></td>" +
+            "    <td styles='filterTableTitle' lable='day'></td>" +
+            "    <td styles='filterTableValue' item='day'></td>" +
+            "    <td styles='filterTableTitle' lable='checkType'></td>" +
+            "    <td styles='filterTableValue' item='checkType'></td>" +
+            "    <td styles='filterTableTitle' lable='timeResult'></td>" +
+            "    <td styles='filterTableValue' item='timeResult'></td>" +
+            "    <td styles='filterTableValue' item='action'></td>" +
+            "</tr>" +
+            "</table>";
+        this.fileterNode.set("html", html);
+
+        MWF.xDesktop.requireApp("Template", "MForm", function () {
+            this.form = new MForm(this.fileterNode, {}, {
+                isEdited: true,
+                itemTemplate: {
+                    person: { text: "人员", type: "org", orgType: "person", notEmpty: true, style: { "min-width": "100px" } },
+                    year: {
+                        text: "年度",
+                        "type": "select",
+                        "selectValue": function () {
+                            var years = [];
+                            var year = new Date().getFullYear();
+                            for (var i = 0; i < 6; i++) {
+                                years.push(year--);
+                            }
+                            return years;
+                        },
+                        "event": {
+                            "change": function (item, ev) {
+                                var values = this.getDateSelectValue();
+                                item.form.getItem("day").resetItemOptions(values, values)
+                            }.bind(this)
+                        }
+                    },
+                    month: {
+                        text: "月份",
+                        "type": "select",
+                        "defaultValue": function () {
+                            var month = (new Date().getMonth() + 1).toString();
+                            return month.length == 1 ? "0" + month : month;
+                        },
+                        "selectValue": ["", "01", "02", "03", "04", "05", "06", "07", "08", "09", "10", "11", "12"],
+                        "event": {
+                            "change": function (item, ev) {
+                                var values = this.getDateSelectValue();
+                                item.form.getItem("day").resetItemOptions(values, values)
+                            }.bind(this)
+                        }
+                    },
+                    day: { text: "日期", "type": "select", "selectValue": this.getDateSelectValue.bind(this) },
+                    checkType: { text: "打卡类型", "type": "select", "selectValue": ["", "OnDuty", "OffDuty"], "selectText": ["", "上班打卡", "下班打卡"] },
+                    timeResult: { text: "打卡结果", "type": "select", "selectValue": ["", "Normal", "Early", "Late", "SeriousLate", "Absenteeism", "NotSigned"], "selectText": ["", "正常", "早退", "迟到", "严重迟到", "旷工迟到", "未打卡"] },
+                    action: {
+                        "value": "查询", type: "button", className: "filterButton", event: {
+                            click: function () {
+                                var result = this.form.getResult(true, ",", true, true, false);
+                                if (!result) return;
+                                if (result.day && result.day != "") {
+                                    result.q_date = result.year + "-" + result.month + "-" + result.day;
+                                }
+                                this.loadView(result);
+                            }.bind(this)
+                        }
+                    }
+                }
+            }, this.app, this.css);
+            this.form.load();
+        }.bind(this), true);
+    },
+    getDateSelectValue: function () {
+        if (this.form) {
+            var year = parseInt(this.form.getItem("year").getValue());
+            var month = parseInt(this.form.getItem("month").getValue()) - 1;
+        } else {
+            var year = (new Date()).getFullYear();
+            var month = (new Date()).getMonth();
+        }
+        var date = new Date(year, month, 1);
+        var days = [];
+        days.push("");
+        while (date.getMonth() === month) {
+            var d = date.getDate().toString();
+            if (d.length == 1) d = "0" + d;
+            days.push(d);
+            date.setDate(date.getDate() + 1);
+        }
+        return days;
+    },
+
+    loadContentNode: function () {
+        this.elementContentNode = new Element("div", {
+            "styles": this.css.elementContentNode
+        }).inject(this.node);
+        this.app.addEvent("resize", function () { this.setContentSize(); }.bind(this));
+
+    },
+    loadView: function (filterData) {
+        this.elementContentNode.empty();
+        if (this.view) delete this.view;
+        this.view = new MWF.xApplication.Attendance.PeopleDingdingDetail.View(this.elementContentNode, this.app, this);
+        this.view.filterData = filterData;
+        this.view.listItemUrl = this.path + "listItem_dingding.json";
+        this.view.load();
+        this.setContentSize();
+    },
+    setContentSize: function () {
+        var tabNodeSize = this.parent.tabs ? this.parent.tabs.tabNodeContainer.getSize() : { "x": 0, "y": 0 };
+        var fileterNodeSize = this.fileterNode ? this.fileterNode.getSize() : { "x": 0, "y": 0 };
+        var nodeSize = this.parent.node.getSize();
+
+        var pt = this.elementContentNode.getStyle("padding-top").toFloat();
+        var pb = this.elementContentNode.getStyle("padding-bottom").toFloat();
+        //var filterSize = this.filterNode.getSize();
+
+        var height = nodeSize.y - tabNodeSize.y - pt - pb - fileterNodeSize.y - 20;
+        this.elementContentNode.setStyle("height", "" + height + "px");
+
+        this.pageCount = (height / 40).toInt() + 5;
+
+        if (this.view && this.view.items.length < this.pageCount) {
+            this.view.loadElementList(this.pageCount - this.view.items.length);
+        }
+    }
+});
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHoliday = new Class({
+    Extends: MWF.xApplication.Attendance.PeopleDingdingDetail.Explorer,
+
+    loadView: function (filterData) {
+        this.elementContentNode.empty();
+        if (this.view) delete this.view;
+        this.view = new MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHolidayView(this.elementContentNode, this.app, this);
+        this.view.filterData = filterData;
+        this.view.load();
+        this.setContentSize();
+    }
+});
+
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.DetailStaticExplorer = new Class({
+    Extends: MWF.xApplication.Attendance.PeopleDingdingDetail.Explorer,
+    loadFilter: function () {
+        this.fileterNode = new Element("div.fileterNode", {
+            "styles": this.css.fileterNode
+        }).inject(this.node);
+
+        var html = "<table width='100%' bordr='0' cellpadding='5' cellspacing='0' style='width: 460px;font-size: 14px;color:#666'>" +
+            "<tr>" +
+            "    <td styles='filterTableValue' lable='q_empName'></td>" +
+            "    <td styles='filterTableTitle' item='q_empName'></td>" +
+            "    <td styles='filterTableTitle' lable='cycleYear'></td>" +
+            "    <td styles='filterTableValue' item='cycleYear'></td>" +
+            "    <td styles='filterTableTitle' lable='cycleMonth'></td>" +
+            "    <td styles='filterTableValue' item='cycleMonth'></td>" +
+            "    <td styles='filterTableValue' item='action'></td>" +
+            "</tr>" +
+            "</table>";
+        this.fileterNode.set("html", html);
+
+        MWF.xDesktop.requireApp("Template", "MForm", function () {
+            this.form = new MForm(this.fileterNode, {}, {
+                isEdited: true,
+                itemTemplate: {
+                    q_empName: { text: "人员", type: "org", orgType: "person", notEmpty: true, style: { "min-width": "100px" } },
+                    cycleYear: {
+                        text: "年度",
+                        "type": "select",
+                        "selectValue": function () {
+                            var years = [];
+                            var year = new Date().getFullYear();
+                            for (var i = 0; i < 6; i++) {
+                                years.push(year--);
+                            }
+                            return years;
+                        }
+                    },
+                    cycleMonth: {
+                        text: "月份",
+                        "type": "select",
+                        "defaultValue": function () {
+                            var month = (new Date().getMonth() + 1).toString();
+                            return month.length == 1 ? "0" + month : month;
+                        },
+                        "selectValue": ["", "01", "02", "03", "04", "05", "06", "07", "08", "09", "10", "11", "12"]
+                    },
+                    action: {
+                        "value": "查询", type: "button", className: "filterButton", event: {
+                            click: function () {
+                                var result = this.form.getResult(true, ",", true, true, false);
+                                if (!result) return;
+                                this.loadView(result);
+                            }.bind(this)
+                        }
+                    }
+                }
+            }, this.app, this.css);
+            this.form.load();
+        }.bind(this), true);
+    },
+
+    loadView: function (filterData) {
+        this.elementContentNode.empty();
+        if (this.view) delete this.view;
+        this.view = new MWF.xApplication.Attendance.PeopleDingdingDetail.DetailStaticView(this.elementContentNode, this.app, this);
+        this.view.filterData = filterData;
+        this.view.listItemUrl = this.path + "listItem_detailStatic.json";
+        this.view.load();
+        this.setContentSize();
+    }
+});
+
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHolidayStaticExplorer = new Class({
+    Extends: MWF.xApplication.Attendance.PeopleDingdingDetail.Explorer,
+
+    loadView: function (filterData) {
+        this.elementContentNode.empty();
+        if (this.view) delete this.view;
+        this.view = new MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHolidayStaticView(this.elementContentNode, this.app, this);
+        this.view.filterData = filterData;
+        this.view.load();
+        this.setContentSize();
+    }
+});
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.View = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.View,
+    _createItem: function (data) {
+        return new MWF.xApplication.Attendance.PeopleDingdingDetail.Document(this.table, data, this.explorer, this);
+    },
+
+    _getCurrentPageData: function (callback, count) {
+        if (!count) count = 20;
+        var id = (this.items.length) ? this.items[this.items.length - 1].data.id : "(0)";
+        var filter = this.filterData || {};
+        
+        var action = o2.Actions.load("x_attendance_assemble_control");
+        action.DingdingAttendanceAction.listNextDingdingAttendance(id, count, filter, function (json) {
+            if (callback) callback(json);
+        }.bind(this));
+    },
+    _removeDocument: function (documentData, all) {
+
+    },
+    _createDocument: function () {
+
+    },
+    _openDocument: function (documentData) {
+
+    }
+
+});
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHolidayView = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.View,
+    _createItem: function (data) {
+        return new MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHolidayDocument(this.table, data, this.explorer, this);
+    },
+
+    _getCurrentPageData: function (callback, count) {
+        var filter = this.filterData || {};
+        this.actions.listDetailFilter(filter, function (json) {
+            if (callback) callback(json);
+        }.bind(this))
+    },
+    _removeDocument: function (documentData, all) {
+
+    },
+    _createDocument: function () {
+
+    },
+    _openDocument: function (documentData) {
+
+    }
+
+});
+
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.DetailStaticView = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.View,
+    _createItem: function (data) {
+        return new MWF.xApplication.Attendance.PeopleDingdingDetail.DetailStaticDocument(this.table, data, this.explorer, this);
+    },
+
+    _getCurrentPageData: function (callback, count) {
+        var filter = this.filterData || {};
+        if (filter.cycleMonth == "") filter.cycleMonth = "(0)";
+        this.actions.listStaticMonthPerson(filter.q_empName, filter.cycleYear, filter.cycleMonth, function (json) {
+            var data = json.data;
+            data.sort(function (a, b) {
+                return parseInt(b.statisticYear + b.statisticMonth) - parseInt(a.statisticYear + a.statisticMonth)
+            });
+            json.data = data;
+            if (callback) callback(json);
+        }.bind(this))
+    },
+    _removeDocument: function (documentData, all) {
+
+    },
+    _createDocument: function () {
+
+    },
+    _openDocument: function (documentData) {
+
+    }
+
+});
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHolidayStaticView = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.View,
+    _createItem: function (data) {
+        return new MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHolidayStaticDocument(this.table, data, this.explorer, this);
+    },
+
+    _getCurrentPageData: function (callback, count) {
+        var filter = this.filterData || {};
+        this.actions.listDetailFilter(filter, function (json) {
+            if (callback) callback(json);
+        }.bind(this))
+    },
+    _removeDocument: function (documentData, all) {
+
+    },
+    _createDocument: function () {
+
+    },
+    _openDocument: function (documentData) {
+
+    }
+
+});
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.Document = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.Document
+
+});
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHolidayDocument = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.Document
+
+});
+
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.DetailStaticDocument = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.Document
+
+});
+
+MWF.xApplication.Attendance.PeopleDingdingDetail.SelfHolidayStaticDocument = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.Document
+
+});

+ 375 - 0
o2web/source/x_component_Attendance/UnitDingdingDetail.js

@@ -0,0 +1,375 @@
+MWF.xDesktop.requireApp("Attendance", "Explorer", null, false);
+MWF.xDesktop.requireApp("Selector", "package", null, false);
+
+MWF.xApplication.Attendance.UnitDingdingDetail = new Class({
+    Extends: MWF.widget.Common,
+    Implements: [Options, Events],
+    options: {
+        "style": "default"
+    },
+    initialize: function (node, app, actions, options) {
+        this.setOptions(options);
+        this.app = app;
+        this.path = "/x_component_Attendance/$UnitDetail/";
+        this.cssPath = "/x_component_Attendance/$UnitDetail/" + this.options.style + "/css.wcss";
+        this._loadCss();
+
+        this.actions = actions;
+        this.node = $(node);
+    },
+    load: function () {
+        this.loadTab();
+    },
+    loadTab: function () {
+
+        this.tabNode = new Element("div", { "styles": this.css.tabNode }).inject(this.node);
+        this.detailArea = new Element("div", { "styles": this.css.tabPageContainer }).inject(this.tabNode);
+        //this.selfHolidayArea = new Element("div",{"styles" : this.css.tabPageContainer }).inject(this.tabNode)
+        this.detailStaticArea = new Element("div", { "styles": this.css.tabPageContainer }).inject(this.tabNode);
+        //this.selfHolidayStaticArea = new Element("div",{"styles" : this.css.tabPageContainer }).inject(this.tabNode)
+
+        MWF.require("MWF.widget.Tab", function () {
+
+            this.tabs = new MWF.widget.Tab(this.tabNode, { "style": "attendance" });
+            this.tabs.load();
+
+            this.detailPage = this.tabs.addTab(this.detailArea, "部门出勤明细", false);
+            this.detailPage.contentNodeArea.set("class", "detailPage");
+            this.detailPage.addEvent("show", function () {
+                if (!this.detailExplorer) {
+                    this.detailExplorer = new MWF.xApplication.Attendance.UnitDingdingDetail.Explorer(this.detailArea, this);
+                    this.detailExplorer.load();
+                }
+            }.bind(this));
+
+
+            this.detailStaticPage = this.tabs.addTab(this.detailStaticArea, "部门出勤率统计", false);
+            this.detailStaticPage.contentNodeArea.set("class", "detailStaticPage");
+            this.detailStaticPage.addEvent("show", function () {
+                if (!this.detailStaticExplorer) {
+                    this.detailStaticExplorer = new MWF.xApplication.Attendance.UnitDingdingDetail.DetailStaticExplorer(this.detailStaticArea, this);
+                    this.detailStaticExplorer.load();
+                }
+            }.bind(this));
+
+            this.tabs.pages[0].showTab();
+        }.bind(this));
+    }
+});
+
+MWF.xApplication.Attendance.UnitDingdingDetail.Explorer = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer,
+    Implements: [Options, Events],
+
+    initialize: function (node, parent, options) {
+        this.setOptions(options);
+        this.parent = parent;
+        this.app = parent.app;
+        this.lp = this.app.lp;
+        this.css = parent.css;
+        this.path = parent.path;
+
+        this.actions = parent.actions;
+        this.node = $(node);
+
+        this.initData();
+        if (!this.peopleActions) this.peopleActions = new MWF.xAction.org.express.RestActions();
+    },
+    initData: function () {
+        this.toolItemNodes = [];
+    },
+    reload: function () {
+        this.node.empty();
+        this.load();
+    },
+    load: function () {
+        this.loadFilter();
+        this.loadContentNode();
+        this.setNodeScroll();
+    },
+    loadFilter: function () {
+        this.fileterNode = new Element("div.fileterNode", {
+            "styles": this.css.fileterNode
+        }).inject(this.node);
+
+        var html = "<table width='100%' bordr='0' cellpadding='5' cellspacing='0' styles='filterTable'>" +
+            "<tr>" +
+            "    <td styles='filterTableValue' lable='unit'></td>" +
+            "    <td styles='filterTableTitle' item='unit'></td>" +
+            "    <td styles='filterTableTitle' lable='year'></td>" +
+            "    <td styles='filterTableValue' item='year'></td>" +
+            "    <td styles='filterTableTitle' lable='month'></td>" +
+            "    <td styles='filterTableValue' item='month'></td>" +
+            "    <td styles='filterTableTitle' lable='day'></td>" +
+            "    <td styles='filterTableValue' item='day'></td>" +
+            "    <td styles='filterTableTitle' lable='checkType'></td>" +
+            "    <td styles='filterTableValue' item='checkType'></td>" +
+            "    <td styles='filterTableTitle' lable='timeResult'></td>" +
+            "    <td styles='filterTableValue' item='timeResult'></td>" +
+            "    <td styles='filterTableValue' item='action'></td>" +
+            "</tr>" +
+            "</table>";
+        this.fileterNode.set("html", html);
+
+        MWF.xDesktop.requireApp("Template", "MForm", function () {
+            this.form = new MForm(this.fileterNode, {}, {
+                isEdited: true,
+                itemTemplate: {
+                    unit: { text: "部门", type: "org", orgType: "unit", notEmpty: true, style: { "min-width": "200px" } },
+                    year: {
+                        text: "年度",
+                        "type": "select",
+                        "selectValue": function () {
+                            var years = [];
+                            var year = new Date().getFullYear();
+                            for (var i = 0; i < 6; i++) {
+                                years.push(year--);
+                            }
+                            return years;
+                        },
+                        "event": {
+                            "change": function (item, ev) {
+                                var values = this.getDateSelectValue();
+                                item.form.getItem("day").resetItemOptions(values, values)
+                            }.bind(this)
+                        }
+                    },
+                    month: {
+                        text: "月份",
+                        "type": "select",
+                        "defaultValue": function () {
+                            var month = (new Date().getMonth() + 1).toString();
+                            return month.length == 1 ? "0" + month : month;
+                        },
+                        "selectValue": ["", "01", "02", "03", "04", "05", "06", "07", "08", "09", "10", "11", "12"],
+                        "event": {
+                            "change": function (item, ev) {
+                                var values = this.getDateSelectValue();
+                                item.form.getItem("day").resetItemOptions(values, values)
+                            }.bind(this)
+                        }
+                    },
+                    day: { text: "日期", "type": "select", "selectValue": this.getDateSelectValue.bind(this) },
+                    checkType: { text: "打卡类型", "type": "select", "selectValue": ["", "OnDuty", "OffDuty"], "selectText": ["", "上班打卡", "下班打卡"] },
+                    timeResult: { text: "打卡结果", "type": "select", "selectValue": ["", "Normal", "Early", "Late", "SeriousLate", "Absenteeism", "NotSigned"], "selectText": ["", "正常", "早退", "迟到", "严重迟到", "旷工迟到", "未打卡"] },
+                    action: {
+                        "value": "查询", type: "button", className: "filterButton", event: {
+                            click: function () {
+                                var result = this.form.getResult(true, ",", true, true, false);
+                                if (!result) return;
+                                if (result.day && result.day != "") {
+                                    result.q_date = result.year + "-" + result.month + "-" + result.day;
+                                }
+                                this.loadView(result);
+                            }.bind(this)
+                        }
+                    }
+                }
+            }, this.app, this.css);
+            this.form.load();
+        }.bind(this), true);
+    },
+    getDateSelectValue: function () {
+        if (this.form) {
+            var year = parseInt(this.form.getItem("year").getValue());
+            var month = parseInt(this.form.getItem("month").getValue()) - 1;
+        } else {
+            var year = (new Date()).getFullYear();
+            var month = (new Date()).getMonth();
+        }
+        var date = new Date(year, month, 1);
+        var days = [];
+        days.push("");
+        while (date.getMonth() === month) {
+            var d = date.getDate().toString();
+            if (d.length == 1) d = "0" + d;
+            days.push(d);
+            date.setDate(date.getDate() + 1);
+        }
+        return days;
+    },
+    loadContentNode: function () {
+        this.elementContentNode = new Element("div", {
+            "styles": this.css.elementContentNode
+        }).inject(this.node);
+        this.app.addEvent("resize", function () { this.setContentSize(); }.bind(this));
+
+    },
+    loadView: function (filterData) {
+        this.elementContentNode.empty();
+        if (this.view) delete this.view;
+        this.view = new MWF.xApplication.Attendance.UnitDingdingDetail.View(this.elementContentNode, this.app, this);
+        this.view.filterData = filterData;
+        this.view.listItemUrl = this.path + "listItem_dingding.json";
+        this.view.load();
+        this.setContentSize();
+    },
+    setContentSize: function () {
+        var tabNodeSize = this.parent.tabs ? this.parent.tabs.tabNodeContainer.getSize() : { "x": 0, "y": 0 };
+        var fileterNodeSize = this.fileterNode ? this.fileterNode.getSize() : { "x": 0, "y": 0 };
+        var nodeSize = this.parent.node.getSize();
+
+        var pt = this.elementContentNode.getStyle("padding-top").toFloat();
+        var pb = this.elementContentNode.getStyle("padding-bottom").toFloat();
+        //var filterSize = this.filterNode.getSize();
+
+        var height = nodeSize.y - tabNodeSize.y - pt - pb - fileterNodeSize.y - 20;
+        this.elementContentNode.setStyle("height", "" + height + "px");
+
+        this.pageCount = (height / 40).toInt() + 5;
+
+        if (this.view && this.view.items.length < this.pageCount) {
+            this.view.loadElementList(this.pageCount - this.view.items.length);
+        }
+    }
+});
+
+
+
+MWF.xApplication.Attendance.UnitDingdingDetail.DetailStaticExplorer = new Class({
+    Extends: MWF.xApplication.Attendance.UnitDingdingDetail.Explorer,
+
+    loadFilter: function () {
+        this.fileterNode = new Element("div.fileterNode", {
+            "styles": this.css.fileterNode
+        }).inject(this.node);
+
+        var html = "<table width='100%' bordr='0' cellpadding='5' cellspacing='0' style='width: 660px;font-size: 14px;color:#666'>" +
+            "<tr>" +
+            "    <td styles='filterTableValue' lable='q_unitName'></td>" +
+            "    <td styles='filterTableTitle' item='q_unitName'></td>" +
+            "    <td styles='filterTableTitle' lable='cycleYear'></td>" +
+            "    <td styles='filterTableValue' item='cycleYear'></td>" +
+            "    <td styles='filterTableTitle' lable='cycleMonth'></td>" +
+            "    <td styles='filterTableValue' item='cycleMonth'></td>" +
+            "    <td styles='filterTableValue' item='action'></td>" +
+            "</tr>" +
+            "</table>";
+        this.fileterNode.set("html", html);
+
+        MWF.xDesktop.requireApp("Template", "MForm", function () {
+            this.form = new MForm(this.fileterNode, {}, {
+                isEdited: true,
+                itemTemplate: {
+                    q_unitName: { text: "部门", type: "org", orgType: "unit", notEmpty: true, style: { "min-width": "200px" } },
+                    cycleYear: {
+                        text: "年度",
+                        "type": "select",
+                        "selectValue": function () {
+                            var years = [];
+                            var year = new Date().getFullYear();
+                            for (var i = 0; i < 6; i++) {
+                                years.push(year--);
+                            }
+                            return years;
+                        }
+                    },
+                    cycleMonth: {
+                        text: "月份", notEmpty: true,
+                        "type": "select",
+                        "defaultValue": function () {
+                            var month = (new Date().getMonth() + 1).toString();
+                            return month.length == 1 ? "0" + month : month;
+                        },
+                        "selectValue": ["", "01", "02", "03", "04", "05", "06", "07", "08", "09", "10", "11", "12"]
+                    },
+                    action: {
+                        "value": "查询", type: "button", className: "filterButton", event: {
+                            click: function () {
+                                var result = this.form.getResult(true, ",", true, true, false);
+                                if (!result) return;
+                                this.loadView(result);
+                            }.bind(this)
+                        }
+                    }
+                }
+            }, this.app, this.css);
+            this.form.load();
+        }.bind(this), true);
+    },
+
+    loadView: function (filterData) {
+        this.elementContentNode.empty();
+        if (this.view) delete this.view;
+        this.view = new MWF.xApplication.Attendance.UnitDingdingDetail.DetailStaticView(this.elementContentNode, this.app, this);
+        this.view.filterData = filterData;
+        this.view.listItemUrl = this.path + "listItem_detailStatic.json";
+        this.view.load();
+        this.setContentSize();
+    }
+});
+
+
+
+MWF.xApplication.Attendance.UnitDingdingDetail.View = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.View,
+    _createItem: function (data) {
+        return new MWF.xApplication.Attendance.UnitDingdingDetail.Document(this.table, data, this.explorer, this);
+    },
+
+    _getCurrentPageData: function (callback, count) {
+        if (!count) count = 20;
+        var id = (this.items.length) ? this.items[this.items.length - 1].data.id : "(0)";
+        var filter = this.filterData || {};
+
+        var action = o2.Actions.load("x_attendance_assemble_control");
+        action.DingdingAttendanceAction.listNextDingdingAttendance(id, count, filter, function (json) {
+            if (callback) callback(json);
+        }.bind(this));
+    },
+    _removeDocument: function (documentData, all) {
+
+    },
+    _createDocument: function () {
+
+    },
+    _openDocument: function (documentData) {
+
+    }
+
+});
+
+
+
+
+MWF.xApplication.Attendance.UnitDingdingDetail.DetailStaticView = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.View,
+    _createItem: function (data) {
+        return new MWF.xApplication.Attendance.UnitDingdingDetail.DetailStaticDocument(this.table, data, this.explorer, this);
+    },
+
+    _getCurrentPageData: function (callback, count) {
+        var filter = this.filterData || {};
+        //if( !filter.cycleMonth || filter.cycleMonth == "" )filter.cycleMonth = "(0)";
+        this.actions.listPersonMonthStaticByUnit(filter.q_unitName, filter.cycleYear, filter.cycleMonth, function (json) {
+
+            if (callback) callback(json);
+        }.bind(this));
+
+
+    },
+    _removeDocument: function (documentData, all) {
+
+    },
+    _createDocument: function () {
+
+    },
+    _openDocument: function (documentData) {
+
+    }
+
+});
+
+
+
+MWF.xApplication.Attendance.UnitDingdingDetail.Document = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.Document
+
+});
+
+
+MWF.xApplication.Attendance.UnitDingdingDetail.DetailStaticDocument = new Class({
+    Extends: MWF.xApplication.Attendance.Explorer.Document
+
+});
+