Checkbox.js 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443
  1. MWF.xDesktop.requireApp("process.Xform", "$Input", null, false);
  2. MWF.require("MWF.widget.UUID", null, false);
  3. /** @class Calendar 多选按钮组件。
  4. * @example
  5. * //可以在脚本中获取该组件
  6. * //方法1:
  7. * var field = this.form.get("fieldId"); //获取组件对象
  8. * //方法2
  9. * var field = this.target; //在组件本身的脚本中获取,比如事件脚本、默认值脚本、校验脚本等等
  10. * @extends MWF.xApplication.process.Xform.$Input
  11. * @o2category FormComponents
  12. * @o2range {Process|CMS|Portal}
  13. * @hideconstructor
  14. */
  15. MWF.xApplication.process.Xform.Checkbox = MWF.APPCheckbox = new Class(
  16. /** @lends MWF.xApplication.process.Xform.Checkbox# */
  17. {
  18. Implements: [Events],
  19. Extends: MWF.APP$Input,
  20. loadDescription: function(){},
  21. _loadNode: function(){
  22. if (this.readonly || this.json.isReadonly ){
  23. this._loadNodeRead();
  24. }else{
  25. this._loadNodeEdit();
  26. }
  27. },
  28. _loadNodeRead: function(){
  29. this.node.empty();
  30. this.node.set({
  31. "nodeId": this.json.id,
  32. "MWFType": this.json.type
  33. });
  34. var radioValues = this.getOptions();
  35. var value = this.getValue();
  36. if (value){
  37. var texts = [];
  38. radioValues.each(function(item){
  39. var tmps = item.split("|");
  40. var t = tmps[0];
  41. var v = tmps[1] || t;
  42. if (value.indexOf(v)!=-1){
  43. texts.push(t);
  44. }
  45. });
  46. this.node.set("text", texts.join(", "));
  47. }
  48. },
  49. _resetNodeEdit: function(){
  50. var div = new Element("div");
  51. div.set(this.json.properties);
  52. div.inject(this.node, "after");
  53. this.node.destroy();
  54. this.node = div;
  55. },
  56. _loadNodeEdit: function(){
  57. //this.container = new Element("select");
  58. if (!this.json.preprocessing) this._resetNodeEdit();
  59. this.node.set({
  60. "id": this.json.id,
  61. "MWFType": this.json.type,
  62. "styles": {
  63. "display": "inline"
  64. }
  65. });
  66. this.setOptions();
  67. },
  68. _loadDomEvents: function(){
  69. },
  70. _loadEvents: function(){
  71. Object.each(this.json.events, function(e, key){
  72. if (e.code){
  73. if (this.options.moduleEvents.indexOf(key)!=-1){
  74. this.addEvent(key, function(event){
  75. return this.form.Macro.fire(e.code, this, event);
  76. }.bind(this));
  77. }else{
  78. //this.node.addEvent(key, function(event){
  79. // return this.form.Macro.fire(e.code, this, event);
  80. //}.bind(this));
  81. }
  82. }
  83. }.bind(this));
  84. },
  85. addModuleEvent: function(key, fun){
  86. if (this.options.moduleEvents.indexOf(key)!==-1){
  87. this.addEvent(key, function(event){
  88. return (fun) ? fun(this, event) : null;
  89. }.bind(this));
  90. }else{
  91. var inputs = this.node.getElements("input");
  92. inputs.each(function(input){
  93. input.addEvent(key, function(event){
  94. return (fun) ? fun(this, event) : null;
  95. }.bind(this));
  96. }.bind(this));
  97. }
  98. },
  99. /**
  100. * @summary 重新计算下拉选项,该功能通常用在下拉选项为动态计算的情况.
  101. * @example
  102. * this.form.get('fieldId').resetOption();
  103. */
  104. resetOption: function(){
  105. this.node.empty();
  106. this.setOptions();
  107. },
  108. /**
  109. * @summary 获取选择项数组.
  110. * @example
  111. * var array = this.form.get('fieldId').getOptions();
  112. * @return {Array} 选择项数组,如果配置为脚本返回计算结果.
  113. */
  114. getOptions: function(){
  115. if (this.json.itemType == "values"){
  116. return this.json.itemValues;
  117. }else{
  118. return this.form.Macro.exec(((this.json.itemScript) ? this.json.itemScript.code : ""), this);
  119. }
  120. //return [];
  121. },
  122. setOptions: function(){
  123. var optionItems = this.getOptions();
  124. this._setOptions(optionItems);
  125. },
  126. _setOptions: function(optionItems){
  127. var p = o2.promiseAll(optionItems).then(function(radioValues){
  128. this.moduleSelectAG = null;
  129. if (!radioValues) radioValues = [];
  130. if (o2.typeOf(radioValues)==="array"){
  131. var flag = (new MWF.widget.UUID).toString();
  132. radioValues.each(function(item){
  133. var tmps = item.split("|");
  134. var text = tmps[0];
  135. var value = tmps[1] || text;
  136. var radio = new Element("input", {
  137. "type": "checkbox",
  138. "name": ((this.json.properties) ? this.json.properties.name : null) || flag+this.json.id,
  139. "value": value,
  140. "showText": text,
  141. "styles": this.json.buttonStyles
  142. }).inject(this.node);
  143. //radio.appendText(text, "after");
  144. var textNode = new Element( "span", {
  145. "text" : text,
  146. "styles" : { "cursor" : "default" }
  147. }).inject(this.node);
  148. textNode.addEvent("click", function( ev ){
  149. if( this.radio.get("disabled") === true || this.radio.get("disabled") === "true" )return;
  150. this.radio.checked = ! this.radio.checked;
  151. this.radio.fireEvent("change");
  152. this.radio.fireEvent("click");
  153. }.bind( {radio : radio} ) );
  154. radio.addEvent("click", function(){
  155. this.validationMode();
  156. if (this.validation()) this._setBusinessData(this.getInputData("change") || []);
  157. }.bind(this));
  158. Object.each(this.json.events, function(e, key){
  159. if (e.code){
  160. if (this.options.moduleEvents.indexOf(key)!=-1){
  161. }else{
  162. radio.addEvent(key, function(event){
  163. return this.form.Macro.fire(e.code, this, event);
  164. }.bind(this));
  165. }
  166. }
  167. }.bind(this));
  168. }.bind(this));
  169. }
  170. }.bind(this), function(){});
  171. this.moduleSelectAG = p;
  172. if (p) p.then(function(){
  173. this.moduleSelectAG = null;
  174. }.bind(this), function(){
  175. this.moduleSelectAG = null;
  176. }.bind(this));
  177. },
  178. _setValue: function(value, m){
  179. var mothed = m || "__setValue";
  180. if (!!value){
  181. var p = o2.promiseAll(value).then(function(v){
  182. //if (o2.typeOf(v)=="array") v = v[0];
  183. if (this.moduleSelectAG){
  184. this.moduleValueAG = this.moduleSelectAG;
  185. this.moduleSelectAG.then(function(){
  186. this[mothed](v);
  187. return v;
  188. }.bind(this), function(){});
  189. }else{
  190. this[mothed](v)
  191. }
  192. return v;
  193. }.bind(this), function(){});
  194. this.moduleValueAG = p;
  195. if (this.moduleValueAG) this.moduleValueAG.then(function(){
  196. this.moduleValueAG = null;
  197. }.bind(this), function(){
  198. this.moduleValueAG = null;
  199. }.bind(this));
  200. }else{
  201. this[mothed](value);
  202. }
  203. // this.moduleValueAG = o2.AG.all(value).then(function(v){
  204. // if (this.moduleSelectAG){
  205. // this.moduleValueAG = this.moduleSelectAG;
  206. // this.moduleSelectAG.then(function(){
  207. // this.moduleValueAG = null;
  208. // this.__setValue(v);
  209. // }.bind(this));
  210. // }else{
  211. // this.moduleValueAG = null;
  212. // this.__setValue(v);
  213. // }
  214. // return v;
  215. // }.bind(this));
  216. //
  217. // if (this.moduleValueAG) this.moduleValueAG.then(function(){
  218. // this.moduleValueAG = "";
  219. // }.bind(this));
  220. },
  221. __setValue: function(value){
  222. this._setBusinessData(value);
  223. var radios = this.node.getElements("input");
  224. for (var i=0; i<radios.length; i++){
  225. var radio = radios[i];
  226. radio.checked = value.indexOf(radio.value) != -1;
  227. }
  228. },
  229. /**
  230. * @summary 获取选中的值和文本.
  231. * @example
  232. * var array = this.form.get('fieldId').getTextData();
  233. * @return {Object} 返回选中项值和文本,格式为 { 'value' : value, 'text' : text }.
  234. */
  235. getTextData: function(){
  236. var inputs = this.node.getElements("input");
  237. var value = [];
  238. var text = [];
  239. if (inputs.length){
  240. inputs.each(function(input){
  241. if (input.checked){
  242. var v = input.get("value");
  243. var t = input.get("showText");
  244. value.push(v || "");
  245. text.push(t || v || "");
  246. }
  247. });
  248. }
  249. if (!value.length) value = [""];
  250. if (!text.length) text = [""];
  251. return {"value": value, "text": text};
  252. },
  253. //getData: function(){
  254. //var inputs = this.node.getElements("input");
  255. //var value = [];
  256. //if (inputs.length){
  257. // inputs.each(function(input){
  258. // if (input.checked){
  259. // var v = input.get("value");
  260. // if (v) value.push(v || "");
  261. // }
  262. // });
  263. //}
  264. //return (value.length==1) ? value[0] : value;
  265. //},
  266. isEmpty: function(){
  267. var data = this.getData();
  268. if( typeOf(data) !== "array" )return true;
  269. if( data.length === 0 )return true;
  270. return false;
  271. },
  272. getInputData: function(){
  273. if (this.readonly || this.json.isReadonly ){
  274. return this._getBusinessData();
  275. }else{
  276. var inputs = this.node.getElements("input");
  277. var value = [];
  278. if (inputs.length){
  279. inputs.each(function(input){
  280. if (input.checked){
  281. var v = input.get("value");
  282. if (v) value.push(v || "");
  283. }
  284. });
  285. }
  286. return (value.length) ? value : [];
  287. }
  288. },
  289. resetData: function(){
  290. this.setData(this.getValue());
  291. },
  292. /**当参数为Promise的时候,请查看文档: {@link https://www.yuque.com/o2oa/ixsnyt/ws07m0|使用Promise处理表单异步}
  293. * @summary 为字段赋值,并且使值对应的选项选中。
  294. * @param data{String|Promise} .
  295. * @example
  296. * this.form.get("fieldId").setData("test"); //赋文本值
  297. * @example
  298. * //使用Promise
  299. * var field = this.form.get("fieldId");
  300. * var dict = new this.Dict("test"); //test为数据字典名称
  301. * var promise = dict.get("tools", true); //异步使用数据字典的get方法时返回Promise,参数true表示异步
  302. * field.setData( promise );
  303. */
  304. setData: function(data){
  305. return this._setValue(data, "__setData");
  306. // if (data && data.isAG){
  307. // this.moduleValueAG = data;
  308. // data.addResolve(function(v){
  309. // this.setData(v);
  310. // }.bind(this));
  311. // }else{
  312. // this.__setData(data);
  313. // this.moduleValueAG = null;
  314. // }
  315. },
  316. __setData: function(data){
  317. this._setBusinessData(data);
  318. var inputs = this.node.getElements("input");
  319. if (inputs.length){
  320. inputs.each(function(input){
  321. if (typeOf(data)=="array"){
  322. if (data.indexOf(input.get("value"))!=-1){
  323. input.set("checked", true);
  324. }else{
  325. input.set("checked", false);
  326. }
  327. }else{
  328. if (data == input.get("value")){
  329. input.set("checked", true);
  330. }else{
  331. input.set("checked", false);
  332. }
  333. }
  334. });
  335. this.validationMode();
  336. }
  337. this.fireEvent("setData");
  338. },
  339. notValidationMode: function(text){
  340. if (!this.isNotValidationMode){
  341. this.isNotValidationMode = true;
  342. this.node.store("background", this.node.getStyles("background"));
  343. this.node.setStyle("background", "#ffdcdc");
  344. this.errNode = this.createErrorNode(text);
  345. if (this.iconNode){
  346. this.errNode.inject(this.iconNode, "after");
  347. }else{
  348. this.errNode.inject(this.node, "after");
  349. }
  350. this.showNotValidationMode(this.node);
  351. if (!this.node.isIntoView()) this.node.scrollIntoView();
  352. }
  353. },
  354. validationMode: function(){
  355. if (this.isNotValidationMode){
  356. this.isNotValidationMode = false;
  357. this.node.setStyles(this.node.retrieve("background"));
  358. if (this.errNode){
  359. this.errNode.destroy();
  360. this.errNode = null;
  361. }
  362. }
  363. },
  364. validationConfigItem: function(routeName, data){
  365. var flag = (data.status==="all") ? true: (routeName === data.decision);
  366. if (flag){
  367. var n = this.getInputData();
  368. if( typeOf(n)==="array" && n.length === 0 )n = "";
  369. var v = (data.valueType==="value") ? n : n.length;
  370. switch (data.operateor){
  371. case "isnull":
  372. if (!v){
  373. this.notValidationMode(data.prompt);
  374. return false;
  375. }
  376. break;
  377. case "notnull":
  378. if (v){
  379. this.notValidationMode(data.prompt);
  380. return false;
  381. }
  382. break;
  383. case "gt":
  384. if (v>data.value){
  385. this.notValidationMode(data.prompt);
  386. return false;
  387. }
  388. break;
  389. case "lt":
  390. if (v<data.value){
  391. this.notValidationMode(data.prompt);
  392. return false;
  393. }
  394. break;
  395. case "equal":
  396. if (v==data.value){
  397. this.notValidationMode(data.prompt);
  398. return false;
  399. }
  400. break;
  401. case "neq":
  402. if (v!=data.value){
  403. this.notValidationMode(data.prompt);
  404. return false;
  405. }
  406. break;
  407. case "contain":
  408. if (v.indexOf(data.value)!=-1){
  409. this.notValidationMode(data.prompt);
  410. return false;
  411. }
  412. break;
  413. case "notcontain":
  414. if (v.indexOf(data.value)==-1){
  415. this.notValidationMode(data.prompt);
  416. return false;
  417. }
  418. break;
  419. }
  420. }
  421. return true;
  422. }
  423. });