我正在编写一个应用程序,它从NADRA发布的NIC中读取条形码(http://www.nadra.gov.pk/index.php?option=com_content&view=article&id=6&Itemid=9)。 NADRA向巴基斯坦公民发放CNIC。我想阅读这些印在CNIC上的条形码。 NADRA编码了名称,父姓,地址,DOB等信息,但这些信息存储在乌尔都语中。我成功地阅读了这些条形码,但事实是,我无法将他们的角色转换为乌尔都语。我安装了urdu字体,比如Noori Nistalique,Aswad等等,但是这些字符只显示了一堆混乱的字符,而不是一个有意义的信息。当我用简单的英语解码这些条形码时,它会显示正确的数字信息,但不会显示urdu中的信息。
有没有人试过阅读这些条形码,并成功解码了?请帮助我,或指导我做我要做的事情......?
这是我读过的一个例子,这是简单的英文:
A0U1200708091232 13501722 T31 2602 -E'/
这是我读过的一个样本,这是在乌尔都语:
آڑم0287870180ء1200708091232 13501722ٹ31ص2602 -ففف-فڈف┴ف,ف9ف┴ف1ف-فف“ففف
正如您所看到的,数字信息是相同的,但是在乌尔都语中编码的信息是混乱的......
任何帮助???
答案 0 :(得分:6)
NADRA做了一个技巧,NADRA实际上是使用最后两个字符形成一个单词的十六进制值,例如如果\u0622
是Alif(假设),那么NADRA只使用最后两个字符进行编码,22
所以这只是技巧。我附加了一些代码,将十六进制转换为乌尔都语,读取条形码数据,将其转换为十六进制字符串,然后将此字符串传递给此函数,您将获得乌尔都语中的所有信息,只需将此字符串放入某些乌尔都语或阿拉伯语支持的视图中(Android),组件(Java)或者如果您使用的是C#,则将其放入标签中。
public class ConvertToUrdu {
public static String convertToUrdu(String text)
{
StringBuilder sb = new StringBuilder();
String[] characters = text.split(",");
for(String character : characters)
{
//if (ListDigits.Contains(ch))
//{
// continue;
//}
switch (character)
{
case "20":
sb.append(" ");
break;
case "22":
sb.append("\u0622");
break;
case "27":
sb.append("\u0627");
break;
case "13":
sb.append("\u0613");
break;
case "28":
sb.append("\u0628");
break;
case "2B":
sb.append("\u062b");
break;
case "86":
sb.append("\u0686");
break;
case "88":
sb.append("\u0688");
break;
case "2F":
sb.append("\u062f");
break;
case "10":
sb.append("\u0610");
break;
case "39":
sb.append("\u0639");
break;
case "41":
sb.append("\u0641");
break;
case "3A":
sb.append("\u063a");
break;
case "AF":
sb.append("\u06af");
break;
case "2D":
sb.append("\u062d");
break;
case "BE":
sb.append("\u06be");
break;
case "CC":
sb.append("\u06cc");
break;
case "36":
sb.append("\u0636");
break;
case "2C":
sb.append("\u062c");
break;
case "2E":
sb.append("\u062e");
break;
case "43":
sb.append("\u0643");
break;
case "12":
sb.append("\u0612");
break;
case "44":
sb.append("\u0644");
break;
case "45":
sb.append("\u0645");
break;
case "BA":
sb.append("\u06ba");
break;
case "46":
sb.append("\u0646");
break;
case "29":
sb.append("\u0629");
break;
case "A9":
sb.append("\u06a9");
break;
case "C1":
sb.append("\u06c1");
break;
//case "45":
// sb.Append("\u0645");
// break;
case "7E":
sb.append("\u067e");
break;
case "42":
sb.append("\u0642");
break;
case "91":
sb.append("\u0691");
break;
case "31":
sb.append("\u0631");
break;
case "35":
sb.append("\u0635");
break;
case "33":
sb.append("\u0633");
break;
case "79":
sb.append("\u0679");
break;
case "2A":
sb.append("\u062a");
break;
case "21":
sb.append("\u0621");
break;
case "38":
sb.append("\u0638");
break;
case "37":
sb.append("\u0637");
break;
//case "48":
// sb.Append("\\u0635\u0644\u0649\u0020\u0627\u0644\u0644\u0647\u0020\u0639\u0644\u064a\u0647\u0020\u0648\u0633\u0644\u0645");
// break;
case "48":
sb.append("\u0648");
break;
case "98":
sb.append("\u0698");
break;
case "34":
sb.append("\u0634");
break;
case "D2":
sb.append("\u06d2");
break;
case "30":
sb.append("\u0630");
break;
case "32":
sb.append("\u0632");
break;
case "60":
sb.append("\u0660");
break;
case "61":
sb.append("\u0661");
break;
case "62":
sb.append("\u0662");
break;
case "63":
sb.append("\u0663");
break;
case "64":
sb.append("\u0664");
break;
case "65":
sb.append("\u0665");
break;
case "66":
sb.append("\u0666");
break;
case "67":
sb.append("\u0667");
break;
case "68":
sb.append("\u0668");
break;
case "69":
sb.append("\u0669");
break;
case "0C":
sb.append(" \u200c");
break;
case "D4":
sb.append("\u06d4");
break;
//case "0C":
// sb.Append("\u060c");
// break;
case "1F":
sb.append("\u061f");
break;
case "02":
sb.append("\u0602");
break;
case "1B":
sb.append("\u061b");
break;
case "7b":
sb.append("\u007b");
break;
case "7D":
sb.append("\u007d");
break;
//default:
// sb.Append(ch);
// break;
}
}
return sb.toString();
}
}
我为Java编写了这段代码,您可以将其转换为任何其他语言。
希望最好: - )
注意
为了方便起见,我在原始字符串中的两个字符之后添加了“,”,例如A0U1200708091232
- > A0,U1,20,07,08,09,12,32
。只是为了调试,所以这个函数实际上将第二个字符串转换为Urdu。
修改的
从注释开始,这是我的函数,它将字符串转换为十六进制,我在C#
private string convertToHex(string text)
{
StringBuilder sb = new StringBuilder();
foreach (char c in text)
{
if (c == '\n')
{
sb.Append('\n');
sb.Append(',');
}
else
{
sb.Append(String.Format("{0:X}", (int)c));
sb.Append(',');
//sb.Append((int)c + " ");
}
}
return sb.ToString();
}
在JAVA中,您可以通过编写String hex = String.format("%04x", (int) c);
答案 1 :(得分:1)
除了以上@moonzai的答案之外,我想补充一些我迄今为止能够实现的细节(借助@ moonzai的帖子!)。
到目前为止,有三种类型的CNIC:
后两者(2&3)只有身份证号码和一些额外的数字细节(最可能是(2)和Nadra_DB_#(3)中的问题数量)
以下是PDF417格式条形码(1)中编码的信息:
通过省略HEX代码的公共部分来编码urdu,例如,如果是Java / C / C ++ / ...则为\ u06;对于Web或简称为0x06,则为“&#x6”。
例如“alif”的HEX代码是\ u0627或者它们只添加了27并省略了&#x6。
在单词“جاوید”的情况下,实际字符串应如下所示:&#x62C&#x627&#x648&#x6CC&#x62F
但NADRA仅添加:2C2748CC2F (省略所有&#x6)
下面附有一个VBA代码,有助于为CNIC卡的扫描输出生成一个WEB字符串。我将继续添加精炼代码,以及其他语言的代码;特别是在JS / Jquery和PHP中。
Public Function Convert2Urdu(vString As String) As String Dim vCharArray As Variant, vChar As String For i = 1 To Len(vString) vChar = Mid(vString, i, 1) vCharArray = vCharArray & GetUrduChar(Hex(AscW(vChar))) Next Convert2Urdu = vCharArray End Function Private Function GetUrduChar(vHex) As String Select Case vHex ' Alphabets Case "22", "27", "28", "7E", "2A", "79", "2B", "2C", "86", "2D", "2E", "2F", "88", "30", "31", "91", "32", "98", "33", "34", "35", "36", "37", "38", "39", "3A", "41", "42", "A9", "AF", "44", "45", "46", "BA", "48", "C1", "C3", "BE", "21", "CC", "D2" GetUrduChar = "" & vHex ' Numerics Case "F0", "F1", "F2", "F3", "F4", "F5", "F6", "F6", "F7", "F8", "F9" GetUrduChar = "" & vHex ' Eraabs Case "10", "11", "12", "13", "14", "15", "4B", "4C", "4D", "4E", "4F", "50", "51", "52", "53", "54", "56", "57", "58", "70" GetUrduChar = "" & vHex ' Punctuation Case "1B", "1F", "64", "6C", "D4", "6B" GetUrduChar = "" & vHex ' Space Case "20" GetUrduChar = "&#x" & "0" & vHex Case Else GetUrduChar = " " & Chr(vHex) & " " ' Ideally, it should be Chr(Asc(Hex)) [working on it] End Select End Function