桦山涧

桦山涧
Asp.net ---->知识改变命运!
  博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

 先上效果图如下:

1、本公式自定义配置计算器的实现基于DataTable.Compute()的用法,该函数用法详细参考文档;本示例支持条件公式、计算公式的配置

2、界面样式

 1 <style type="text/css">
 2         .p {
 3             width: 40px;
 4             height: 40px;
 5             background-color: green;
 6             border: 1px solid #0e0808;
 7             float: left;
 8             text-align: center;
 9             line-height: 40px;
10             color: white;
11             font-weight: bold;
12             cursor: pointer;
13         }
14         .pblack {
15             width: 100px;
16         }
17         .param {
18             width: 90%;
19             height: 40px;
20             background-color: green;
21             border: 1px solid #0e0808;
22             float: left;
23             text-align: center;
24             line-height: 40px;
25             color: white;
26             font-weight: bold;
27             cursor: pointer;
28         }
29     </style>

3、界面脚本

  1 <script type="text/javascript">
  2 
  3         var KeyList = new Array();//公式对外文本
  4         var KeyValueList = new Array();//公司的对内编码
  5 
  6         jQuery(document).ready(function () {
  7 
  8             //选公式
  9             jQuery(".p").click(function () {
 10 
 11                 jQuery("#TextAreaFormula").focus();//
 12                 
 13                 var inputText = jQuery(this).text();//
 14                 var inputValue = jQuery(this).data("value");//
 15 
 16                 //1、空格键
 17                 if (inputText.length == 0 || inputText == "") {
 18                     inputText = " ";
 19                     inputValue = " ";
 20                 }
 21 
 22                 //非数字键
 23                 if ("0123456789".indexOf(String(inputText)) < 0) {
 24                     if ("C←".indexOf(String(inputText)) >= 0) {
 25                         switch (String(inputText)) {
 26                             case "C"://清空键
 27                                 KeyList = [];
 28                                 KeyValueList = [];
 29 
 30                                 jQuery("#TextAreaFormula").val("");
 31                                 jQuery("#TextAreaFormulaCode").val("");
 32 
 33                                 jQuery("#TextAreaFormula").focus();
 34                                 return;
 35                                 break;
 36                             case ""://退格键
 37                                 //
 38                                 KeyList.pop();
 39                                 var strChanged = "";
 40                                 for (var i = 0; i < KeyList.length; i++) {
 41                                     strChanged += String(KeyList[i]);
 42                                 }
 43                                 jQuery("#TextAreaFormula").val(strChanged.trimEnd());
 44                                 jQuery("#TextAreaFormula").focus();
 45 
 46                                 //
 47                                 KeyValueList.pop();
 48                                 var strvalueCharged = "";
 49                                 for (var i = 0; i < KeyValueList.length; i++) {
 50                                     strvalueCharged += String(KeyValueList[i]);
 51                                 }
 52                                 jQuery("#TextAreaFormulaCode").val(strvalueCharged.trimEnd());
 53                                 return;
 54                                 break;
 55                             //case "And":
 56                             //    inputText = " " + "&&" + " ";
 57                             //    inputValue = " " + "&&" + " ";
 58                             //    break;
 59                             //case "Or":
 60                             //    inputText = " " + "||" + " ";
 61                             //    inputValue = " " + "||" + " ";
 62                             //    break;
 63                             default:
 64                                 break;
 65                         }
 66                     }
 67                     else if ("." == String(inputText)) {
 68 
 69                     }
 70                     else { //非清空\退格\小数点键的其他键
 71                         inputText = " " + inputText + " ";
 72                         inputValue = " " + inputValue + " ";
 73                     }
 74                 }
 75 
 76                 //数字和小数点-键
 77                 var HaveExistStr = jQuery("#TextAreaFormula").val();
 78                 jQuery("#TextAreaFormula").val(HaveExistStr + inputText);
 79                 KeyList.push(inputText);
 80                 jQuery("#TextAreaFormula").focus();
 81 
 82                 //数字和小数点-值
 83                 var HaveExistStrValue = jQuery("#TextAreaFormulaCode").val();
 84                 jQuery("#TextAreaFormulaCode").val(HaveExistStrValue + inputValue);
 85                 KeyValueList.push(inputValue);
 86 
 87             });
 88 
 89             //选参数
 90             jQuery(".param").click(function () {
 91                 jQuery("#TextAreaFormula").focus();
 92 
 93                 var inputText = jQuery(this).text();
 94                 var inputValue = jQuery(this).data("value");
 95                 inputText = " [" + inputText + "] ";
 96                 inputValue = " [" + inputValue + "] ";
 97 
 98                 var HaveExistStr = jQuery("#TextAreaFormula").val();
 99                 jQuery("#TextAreaFormula").val(HaveExistStr.trimEnd() + inputText);
100                 KeyList.push(inputText);
101                 jQuery("#TextAreaFormula").focus();
102 
103                 var HaveExistStrValue = jQuery("#TextAreaFormulaCode").val();
104                 jQuery("#TextAreaFormulaCode").val(HaveExistStrValue.trimEnd() + inputValue);
105                 KeyValueList.push(inputValue);
106 
107             });
108 
109         });
110 
111         //去除字符串尾部空格或指定字符   
112         String.prototype.trimEnd = function (s) {
113             s = (s ? s : "\\s");
114             s = ("(" + s + ")");
115             var reg_trimEnd = new RegExp(s + "*$", "g");
116             return this.replace(reg_trimEnd, "");
117         };
118 
119 
120     </script>

4、界面HTML源码

 1     <form id="form1" runat="server">
 2         
 3         <div style="float:left;width:90%;border:1px solid #ff0000;margin:5px;padding:20px;">
 4             <table>
 5                 <tr>
 6                     <td colspan="2">
 7                         <textarea id="TextAreaFormula" cols="80" rows="2" style="float:left;width:680px;" readonly="readonly" runat="server"></textarea>
 8                         <input id="TextAreaFormulaCode" type="text" style="float:left;width:681px;" readonly="readonly" runat="server"/>
 9                     </td>
10                 </tr>
11                 <tr>
12                     <td style="width:100px;vertical-align:top;">
13                         <div class="param" data-value="BasicSalary">基本工资</div>
14                         <div class="param" data-value="OTDays">加班天数</div>
15                         <div class="param" data-value="LengthOfService">工龄</div>
16                     </td>
17                     <td style="width:280px;">
18                         <div class="p" data-value="(">(</div><div class="p" data-value=")">)</div>
19                         <div class="p" data-value="+">+</div><div class="p" data-value="-">-</div>
20                         <div class="p" data-value="*">*</div><div class="p" data-value="/">/</div>
21                         <div class="p" data-value="0">0</div><div class="p" data-value="1">1</div>
22                         <div class="p" data-value="2">2</div><div class="p" data-value="3">3</div>
23                         <div class="p" data-value="4">4</div><div class="p" data-value="5">5</div>
24                         <div class="p" data-value="6">6</div><div class="p" data-value="7">7</div>
25                         <div class="p" data-value="8">8</div><div class="p" data-value="9">9</div>
26                         <div class="p" data-value=">">></div><div class="p" data-value=">=">>=</div>
27                         <div class="p" data-value="=">=</div>
28                         <div class="p" data-value="<"><</div><div class="p" data-value="<="><=</div>
29                         <div class="p" data-value=".">.</div>
30                         <div class="p" data-value="And">And</div>
31                         <div class="p" data-value="Or">Or</div>
32                         <div class="p pblack" data-value=""></div>
33                         <div class="p" data-value="C">C</div>
34                         <div class="p" data-value="←"></div>
35                     </td>
36                 </tr>
37                 <tr>
38                     <td>
39                         
40                     </td>
41                     <td>
42                         <table>
43                             <tr>
44                                 <td>基本工资金额:</td>
45                                 <td>
46                                     <asp:TextBox ID="TextBoxBasicSalary" runat="server">2000</asp:TextBox>
47                                 </td>
48                             </tr>
49                             <tr>
50                                 <td>加班天数:</td>
51                                 <td><asp:TextBox ID="TextBoxOTDays" runat="server">20</asp:TextBox></td>
52                             </tr>
53                             <tr>
54                                 <td>工龄(年):</td>
55                                 <td><asp:TextBox ID="TextBoxLengthOfService" runat="server">10</asp:TextBox></td>
56                             </tr>
57                             <tr>
58                                 <td colspan="2">
59                                     <asp:Button ID="Button1" runat="server" Text="配置公式→输入参数值→计算公式的结果" OnClick="Button1_Click" />
60                                 </td>
61                             </tr>
62                         </table>
63                         
64                         <br/>
65                         
66                         <br/>
67                         
68                         <br/>
69                         
70                     </td>
71                 </tr>
72             </table>
73         </div>
74     </form>

 

5、后台代码

 1     /// <summary>
 2     /// 计算
 3     /// </summary>
 4     public class ParamModel {
 5 
 6         /// <summary>
 7         /// 基本工资
 8         /// </summary>
 9         public decimal BasicSalary { get; set; }
10 
11         /// <summary>
12         /// 加班天数
13         /// </summary>
14         public decimal OTDays { get; set; }
15 
16         /// <summary>
17         /// 工龄
18         /// </summary>
19         public decimal LengthOfService { get; set; }
20 
21         //还可继续扩充,也可以考虑使用动态类
22     }
 1         /// <summary>
 2         /// 实例源码
 3         /// </summary>
 4         /// <param name="sender"></param>
 5         /// <param name="e"></param>
 6         protected void Button1_Click(object sender, EventArgs e)
 7         {
 8             var ParamModel = new ParamModel();
 9             ParamModel.BasicSalary = Convert.ToDecimal(this.TextBoxBasicSalary.Text ?? "0");
10             ParamModel.OTDays = Convert.ToDecimal(this.TextBoxOTDays.Text ?? "0");
11             ParamModel.LengthOfService = Convert.ToDecimal(this.TextBoxLengthOfService.Text ?? "0");
12 
13 
14             DataTable eval = new DataTable();
15             var formulaText = this.TextAreaFormulaCode.Value;//公式
16             var Str = formulaText;
17             var StrParam = string.Empty;
18             foreach (var PropertyInfo in ParamModel.GetType().GetProperties())
19             {
20                 if (formulaText.IndexOf("[" + PropertyInfo.Name + "]") >= 0)
21                 {
22                     Str = Str.Replace(("[" + PropertyInfo.Name + "]"), "(" + PropertyInfo.GetValue(ParamModel, null).ToString() + ")");//将表达式中的参数Code替换为实际的值
23                     StrParam += string.Format("[{0}]={1},", PropertyInfo.Name, PropertyInfo.GetValue(ParamModel, null).ToString());//表达式中各参数的值
24                 }
25             }
26             object result = null;
27             try
28             {
29                 result = eval.Compute(Str, "");//文本表达式的运行结果
30             }
31             catch(Exception ex)
32             {
33                 Response.Write("公式配置有误,请重新配置!具体错误:" + ex.Message+"<br/>");
34                 return;
35             }
36             StrParam = StrParam.TrimEnd(',');//各参数的值
37             Response.Write(string.Format(
38                 "公式含义:{4}<br/>"
39                 + "公式编码:{0}<br/>"
40                 + "参数取值:<br/>"
41                 + "{3}<br/>"
42                 + "公式解析:{1} <br/>"
43                 + "计算结果:{2}<br/>",
44                 formulaText,
45                 Str,
46                 Convert.ToString(result),
47                 StrParam,
48                 this.TextAreaFormula.Value));
49 
50         }


6、扩展

在此基础上可以进一步发挥的空间很大

》结合存储设计如数据库等,参数可以动态加载参数;

》诸如参数自定义,自定义的参数再次被用作新参数的配置,参数嵌套使用,可以配置出强大而复杂的计算公式以及条件公式

》结合存储设计再结合C#的动态类,可以使得参数对应的类也动态化;

》当然简单级别的计算并不完全需要面向对象的类的设计,完全使用存储设计,所有参数可以完全依赖如数据库或其他存储方式如XML等来提供