2022年4月20日 星期三

iTEXT QRCODE備忘

最近BarCode128 不夠用了,隨著硬體設備(掃描器)跟標籤機增購所以QRCode也上了時程,做個JAVA iTextPDF產製QRCODE的備忘文章。

import java.util.HashMap;
import java.util.Map;
import com.itextpdf.text.pdf.qrcode.EncodeHintType;
import com.itextpdf.text.pdf.qrcode.ErrorCorrectionLevel;
import com.itextpdf.text.pdf.BarcodeQRCode;

//QRCODE  
StringBuffer sb = new StringBuffer ();    
sb.append ("QRCODE內容");  
Map<EncodeHintType, Object> qrParam = new HashMap<EncodeHintType, Object> ();
qrParam.put ( EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.M );
qrParam.put ( EncodeHintType.CHARACTER_SET, "UTF-8" );
//size_x, size_y 為QRCODE寬跟高
BarcodeQRCode qrcode = new BarcodeQRCode ( sb.toString (), size_x, size_y, qrParam );  
Image qrcode_img = qrcode.getImage();

InputStream input =  new FileInputStream("source.pdf");
OutputStream output= new FileOutputStream(new File("target.pdf"));

PdfReader reader = new PdfReader(input);           
PdfStamper stamper = new PdfStamper(reader, output);
PdfContentByte cb = stamper.getOverContent(1);

//x,y 放置在PDF內的座標位置
qrcode_img.setAbsolutePosition(x, y); 
cb.addImage(qrcode_img);

stamper.setFormFlattening(true);           
stamper.close();           
reader.close();

2021年11月16日 星期二

iTEXT罕字處理

 

中文字博大精深尤其是姓名的使用,為了命好而擇用特殊的文字組合或筆劃值也不算罕見,不過系統列印要處理這類就狀況百出。幾個步驟備忘來留念下
1. 編碼:不管是大五碼還是簡字總之先轉碼成UNICODE為先。
2.字型:大概率要找免費的比較好,全字庫是可以考慮的範圍,底下是拿細明體+細明體ExtB來做範例,因為全字庫的罕字分三層,感覺卡麻煩。

部分罕字/特殊字的字碼會在65535使用4byte來儲存,故判斷上就不能只取3Byte不然會對不上字元,另外罕字不可能單純出現在最前或最後也可能藏在中間或單字以上,故處理上得一字字處理,底下的Method送入inStr 原始Unicode字串回傳Paragraph餵給iText來顯示....

private Paragraph getExtName(String inStr) {
Paragraph simplePara = new Paragraph();
BaseFont bf_name = null;
int i_char = 0;
try {
bf_name = BaseFont.createFont("c:\\windows\\fonts\\mingliu.ttc,1", "Identity-H", BaseFont.NOT_EMBEDDED);

int getCode;
int start=0;
int end=0;
String getstr = "";
for(int j=0;j<inStr.length();j++) 
{
getCode = inStr.codePointAt(j);
start=j;
end=start+1;
if(getCode > 65535) {
   j++;
   end=start+2;
}
getstr = inStr.substring(start, end);
boolean tmpc  = bf_name.charExists(getCode);
if(tmpc) {
Chunk Chunkid0 = new Chunk(getstr, font12_name);
simplePara.add(Chunkid0);
i_char++;
} else {
tmpc  = bf_name_ext.charExists(getCode);
if(tmpc) {
Chunk Chunkid1 = new Chunk(getstr, font12_name_ext);
simplePara.add(Chunkid1);
i_char++;
}
}
}
        } catch (Exception ex) {
        i_char = 0;
        log.error(ex.toString());
        }

if (i_char == 0) {
Phrase simplePhr1 = new Phrase(inStr, font12_name);
simplePara.add(simplePhr1);
}
return simplePara;
}

2021年11月4日 星期四

EDC2POS communication

 電子商務的軟體服務,經常需要有與週邊構聯的需求,今天就EDC裝置來做個備忘,可能若干年後會改變但近幾年碰到都還是如此吧!!


首先從規格書上會告知這個裝置的連線設定與通訊電文(文法),得符合這些規則那裝置就會依照命令(Command)作相對應的反應。


STX, ETX, ACK均為ASCII表所規範之字碼,這部分處理需已Byte array方式來塞值傳遞,Encode 是ASCII


LRC碼是將欲傳送之電文位元組(Bytes)各Byte做XOR後的結果用於檢核用。


LRC Method Sample Code:


刷1元回傳的電文範本,依照規格書上的來去一項項對應,取需要的即可!!





2021年9月30日 星期四

COBOL & DB2 中文字的處理

 古時候的DB2儲存中文字會在前後用0E跟0F框起來,但後人在改寫存取時沒處理好COBOL讀取時就會變成亂碼0E0F湊起來就佔了2 BYTES,也會讓欄位要塞好塞滿時得先扣掉2bytes才行,這部分要記好別踩坑。


直接更新下指令如果兩個TABLE長度不一樣,如TABLEA.CNNAME(14)而TABLEB.CNNAME2(20),就可以透過下列語法來塞值。

UPDATE TABLEA SET CNNAME=(SELECT CONCAT(LEFT(CNNAME2,13), X'''0F''') FROM TABLEB WHERE KEY=?) WHERE KEY2=?;

decodeURIComponent後把+號改空白顯示

前後端資料拋接要避開依些特殊符號的異常或資安檢核可透過URLEncoder來轉碼,不過特殊符號在decode後會變+號造成解譯上的困擾,這時候加上.replace(/\+/g, ' ') 即可。

JAVA端

rtnval.setDatas(URLEncoder.encode(gson.toJson(tablelist), "UTF-8" ));

JS端

call_ajax($('#QueryForm').attr('action'), $('#QueryForm').serialize(), e)

.done(function(data){

$('#rtn_tbody').html(decodeURIComponent(data.datas).replace(/\+/g, ' '));

})

.fail(function(){

alert('ajax call fail.');

});

}