You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
279 lines
9.0 KiB
279 lines
9.0 KiB
/********************************************************************************************************* |
|
* 프로그램명 : CalculationForm.java 프로그램설명 : 엑셀변환시 엑셀에 적용되는 수식을 처리하는곳 작성자 : 강원중 작성일 : 2004-12-02 변경일 : 2005-02-04 |
|
**********************************************************************************************************/ |
|
|
|
package kr.co.kihyun.text.excel; |
|
|
|
import java.util.ArrayList; |
|
import java.util.List; |
|
|
|
import kr.co.kihyun.lang.MInteger; |
|
import kr.co.kihyun.lang.MString; |
|
import kr.co.kihyun.moumi.doc.table.item.MItem; |
|
|
|
public class CalculationForm { |
|
|
|
public static String getCalculationForm(String expr, int rowNum, String type) { |
|
|
|
// 필요없는 EXPR ^ |
|
if (MString.isNull(expr) || expr.indexOf("^") > -1 || expr.indexOf("~") > -1) |
|
return expr; |
|
|
|
// "SUM", "(", ")", ":", ",", "+", "-", "*", "/" |
|
// SUM(B9:F99) |
|
char[] charList = expr.toCharArray(); // 수식을 char array로 변환 |
|
int[] charInfoList = null; |
|
int[] numList = null; |
|
int charCount = 0; |
|
|
|
charCount = charList.length; |
|
|
|
// char infomation array, num value array create |
|
if (charList.length > 0) { |
|
charInfoList = new int[charCount]; |
|
numList = new int[charCount]; |
|
} else { |
|
return expr; |
|
} |
|
|
|
// char array analysis |
|
for (int i = 0; i < charCount; i++) { |
|
|
|
if (48 <= (int) charList[i] && (int) charList[i] <= 57) { |
|
numList[i] = Integer.parseInt(Character.toString(charList[i])); |
|
charInfoList[i] = MItem.INT; |
|
} else if ((65 <= (int) charList[i] && (int) charList[i] <= 90) |
|
|| (97 <= (int) charList[i] && (int) charList[i] <= 122)) { |
|
// a: 97, z: 122, A: 65, Z: 90 |
|
charInfoList[i] = MItem.CHAR; |
|
} else { |
|
charInfoList[i] = MItem.SPCHAR; // 수식 == 기타 문자 |
|
} |
|
} |
|
|
|
// item name에 포함되어있는 숫자의 값을 행(rowNum)만큼 증가 시키거나 감소 시킴 |
|
StringBuffer exprbuf = new StringBuffer(); // 분리된 수식을 StringBuffer에 하나씩 변환하여 추가 |
|
String tmpNum = ""; // item name에 속한 숫자를 문자로 표시 |
|
boolean isItemNum = false; // item name에 속한 숫자들 이라면 append해라 "1"+"2".... |
|
|
|
for (int i = 0; i < charCount; i++) { |
|
if (charInfoList[i] == MItem.CHAR) { // 문자이고 |
|
if (charInfoList[i] == 's' || charInfoList[i] == 'S') { |
|
isItemNum = true; |
|
} else if (i > 0 && (charInfoList[i] == 'u' || charInfoList[i] == 'U')) { |
|
isItemNum = true; |
|
} else if (i > 1 && (charInfoList[i] == 'm' || charInfoList[i] == 'M')) { // SUM으로 이건 Item name이 아니다 |
|
isItemNum = false; |
|
} else { // sum을 뺀 나머지는 다 Item name이다 |
|
isItemNum = true; |
|
} |
|
exprbuf.append(charList[i]); |
|
} else if (charInfoList[i] == MItem.INT) { // 숫자이고 |
|
if (i > 0 && MItem.CHAR == charInfoList[i - 1] && isItemNum) { // Item name이며 첫번째 숫자임 |
|
tmpNum = Integer.toString(numList[i]); |
|
isItemNum = true; |
|
} else if (i > 0 && MItem.INT == charInfoList[i - 1] && isItemNum) { // Item name이며 두번째 숫자임 |
|
tmpNum += Integer.toString(numList[i]); |
|
isItemNum = true; |
|
} else { // Item name이 아닌 그냥 숫자라면 |
|
exprbuf.append(charList[i]); |
|
isItemNum = false; |
|
} |
|
|
|
if ((i == (charCount - 1) || MItem.INT != charInfoList[i + 1]) && isItemNum) { |
|
if (type != null && type.equals("add")) { // 동적표에서 보고자료 보기시 보고한 행에 따라 수식을 변경해줌 |
|
exprbuf.append((MInteger.parseInt(tmpNum) + rowNum)); |
|
} else if (type != null && type.equals("sub")) { // 두개의 표를 등록할때 Form에 적용되는 수식사용 |
|
exprbuf.append((MInteger.parseInt(tmpNum) - rowNum)); |
|
} |
|
} |
|
} else { |
|
exprbuf.append(charList[i]); |
|
isItemNum = false; |
|
} |
|
} |
|
|
|
return exprbuf.toString(); |
|
} |
|
|
|
// 보고자가 보고한 하나의 동적표의 total을 작성할때 사용하는 수식 |
|
public static String getDynaReportTotCalculationForm(String itemName, int titleRowCount, int rowCount) { |
|
if (MString.isNull(itemName)) |
|
return ""; |
|
itemName = Character.toString((itemName.toCharArray())[0]); |
|
|
|
StringBuffer strbuf = new StringBuffer(); |
|
strbuf.append("SUM("); |
|
strbuf.append(itemName); |
|
strbuf.append((titleRowCount + 1)); |
|
strbuf.append(":"); |
|
strbuf.append(itemName); |
|
strbuf.append((rowCount + titleRowCount)); |
|
strbuf.append(")"); |
|
|
|
return getCalculationForm(strbuf.toString()); |
|
} |
|
|
|
// 엑셀에서 사용하는 수식 테그 |
|
public static String getCalculationForm(String sumStr) { |
|
|
|
if (MString.isNull(sumStr)) |
|
return ""; |
|
|
|
StringBuffer strbuf = new StringBuffer(); |
|
strbuf.append(" x:num=\"0\" x:fmla=\"="); |
|
strbuf.append(sumStr); |
|
strbuf.append("\""); |
|
|
|
return strbuf.toString(); |
|
} |
|
|
|
// FIXME : remove me. |
|
public static String getCalculationForms(String arrayName, String propName, String sData) { |
|
|
|
int stTDIndex = 0; |
|
int edTDIndex = 0; |
|
int stExIndex = 0; |
|
int edExIndex = 0; |
|
int exHeadIndex = 0; |
|
int index = -1; |
|
|
|
String headEx = "x:fmla="; |
|
String stEx = "="; |
|
String edEx = "\""; |
|
String tdContext = null; |
|
String endResult = null; |
|
StringBuffer exprbuf = new StringBuffer(); |
|
|
|
while (true) { |
|
stTDIndex = sData.indexOf("<td", stTDIndex + 1); |
|
if (stTDIndex == -1) |
|
break; |
|
index++; |
|
|
|
edTDIndex = sData.indexOf(">", stTDIndex); |
|
if (stTDIndex == -1) |
|
break; |
|
|
|
tdContext = sData.substring(stTDIndex, edTDIndex + 1); // TD의 옵션 내용 |
|
exHeadIndex = tdContext.indexOf(headEx); |
|
// 예) <td nowrap x:num x:fmla="=sum(c2:c5)" > |
|
|
|
if (exHeadIndex != -1) { |
|
stExIndex = tdContext.indexOf(stEx, exHeadIndex + headEx.length()); // x:fmla="=sum(c2:c5)" 에서 첫번째 `=` 를 |
|
// 검색 |
|
edExIndex = tdContext.indexOf(edEx, stExIndex + stEx.length()); // x:fmla="=sum(c2:c5)" 에서 마지막 `"`를 검색 |
|
endResult = tdContext.substring(stExIndex + stEx.length(), edExIndex); |
|
endResult = endResult.toUpperCase(); |
|
exprbuf.append(arrayName); |
|
exprbuf.append("["); |
|
exprbuf.append(index); |
|
exprbuf.append("]."); |
|
exprbuf.append(propName); |
|
exprbuf.append(" = '"); |
|
exprbuf.append(endResult); |
|
exprbuf.append("';\n"); |
|
} |
|
} |
|
return exprbuf.toString(); |
|
} |
|
|
|
// 엑셀 sum수식을 javascript itemExprList로 추출 |
|
public static String getCalculationForms(String sData) { |
|
|
|
int stTDIndex = 0; |
|
int edTDIndex = 0; |
|
int stExIndex = 0; |
|
int edExIndex = 0; |
|
int exHeadIndex = 0; |
|
int index = -1; |
|
|
|
String headEx = "x:fmla="; |
|
String stEx = "="; |
|
String edEx = "\""; |
|
String tdContext = null; |
|
String endResult = null; |
|
StringBuffer exprbuf = new StringBuffer(); |
|
|
|
while (true) { |
|
stTDIndex = sData.indexOf("<td", stTDIndex + 1); |
|
if (stTDIndex == -1) |
|
break; |
|
index++; |
|
|
|
edTDIndex = sData.indexOf(">", stTDIndex); |
|
if (stTDIndex == -1) |
|
break; |
|
|
|
tdContext = sData.substring(stTDIndex, edTDIndex + 1); // TD의 옵션 내용 |
|
exHeadIndex = tdContext.indexOf(headEx); |
|
// 예) <td nowrap x:num x:fmla="=sum(c2:c5)" > |
|
|
|
if (exHeadIndex != -1) { |
|
stExIndex = tdContext.indexOf(stEx, exHeadIndex + headEx.length()); // x:fmla="=sum(c2:c5)" 에서 첫번째 `=` 를 |
|
// 검색 |
|
edExIndex = tdContext.indexOf(edEx, stExIndex + stEx.length()); // x:fmla="=sum(c2:c5)" 에서 마지막 `"`를 검색 |
|
endResult = tdContext.substring(stExIndex + stEx.length(), edExIndex); |
|
endResult = endResult.toUpperCase(); |
|
exprbuf.append("itemExprList["); |
|
exprbuf.append(index); |
|
exprbuf.append("] = '"); |
|
exprbuf.append(endResult); |
|
exprbuf.append("';\n"); |
|
} |
|
} |
|
return exprbuf.toString(); |
|
} |
|
|
|
// 엑셀 sum수식을 javascript itemExprList로 추출 |
|
// TODO refactoring, duplicated code with getCalculationForms(String) |
|
public static List<String> getExprList(String sData) { |
|
List<String> exprList = new ArrayList<String>(); |
|
|
|
int stTDIndex = 0; |
|
int edTDIndex = 0; |
|
int stExIndex = 0; |
|
int edExIndex = 0; |
|
int exHeadIndex = 0; |
|
int index = -1; |
|
|
|
String headEx = "x:fmla="; |
|
String stEx = "="; |
|
String edEx = "\""; |
|
String tdContext = null; |
|
String endResult; |
|
; |
|
StringBuffer exprbuf = new StringBuffer(); |
|
|
|
while (true) { |
|
endResult = null; |
|
stTDIndex = sData.indexOf("<td", stTDIndex + 1); |
|
if (stTDIndex == -1) |
|
break; |
|
index++; |
|
|
|
edTDIndex = sData.indexOf(">", stTDIndex); |
|
if (stTDIndex == -1) |
|
break; |
|
|
|
tdContext = sData.substring(stTDIndex, edTDIndex + 1); // TD의 옵션 내용 |
|
exHeadIndex = tdContext.indexOf(headEx); |
|
// 예) <td nowrap x:num x:fmla="=sum(c2:c5)" > |
|
|
|
if (exHeadIndex != -1) { |
|
stExIndex = tdContext.indexOf(stEx, exHeadIndex + headEx.length()); // x:fmla="=sum(c2:c5)" 에서 첫번째 `=` 를 |
|
// 검색 |
|
edExIndex = tdContext.indexOf(edEx, stExIndex + stEx.length()); // x:fmla="=sum(c2:c5)" 에서 마지막 `"`를 검색 |
|
endResult = tdContext.substring(stExIndex + stEx.length(), edExIndex); |
|
endResult = endResult.toUpperCase(); |
|
exprbuf.append("itemExprList["); |
|
exprbuf.append(index); |
|
exprbuf.append("] = '"); |
|
exprbuf.append(endResult); |
|
exprbuf.append("';\n"); |
|
} |
|
exprList.add(endResult); |
|
} |
|
return exprList; |
|
} |
|
}
|
|
|