convert/normalize 使用jspdf时的特殊字符
convert/normalize special characters when using jspdf
尝试使用 jspdf lib @1.4.1 将文本转换为 pdf,输出有时变得非常难看和不可读,因为文本包含一些特殊字符,例如:
左单引号U+2018
,或右单引号U+2019
,或→
,或Kadıköy
中的ı
。 .
我怎么能sanitize/normalize这样的文字?或者我可以使用 jspdf 来解决这个问题吗?
更新:
要重现问题,只需使用此字符串:'→Kadıköy'
在本例中 https://parall.ax/products/jspdf,第 9 行,您会看到箭头已转换到 !’
并且 ı
转换为 1
(仅供参考,Kadıköy 是一个城市的名称 https://en.wikipedia.org/wiki/Kad%C4%B1k%C3%B6y)
您可以通过导入支持您的特殊字符的字体来实现。
从 basic.js on examples 你可以看到如何应用它的参考。
(示例带有西里尔字母)。
function demoUsingTTFFont() {
//https://fonts.google.com/specimen/PT+Sans
var PTSans = “...... “); // place long string of text here
var doc = new jsPDF();
doc.addFileToVFS("PTSans.ttf", PTSans);
doc.addFont('PTSans.ttf', 'PTSans', 'normal');
doc.setFont('PTSans'); // set font
doc.setFontSize(10);
doc.text("А ну чики брики и в дамки!", 10, 10);
doc.save('test.pdf');
}
作为fontfamily,请看看Google的Noto。
来源:
恕我直言,mico answer OK,只需将字体 PTSans 替换为您使用的字体(base64 编码)。
参见 jsfiddle:https://jsfiddle.net/o0m9pzyv/12/
var PTSans = ...
我们可以阅读here:
jsPDF supports finally UTF-8 by having the ability to use custom fonts.
您遇到的问题是您没有真正了解 PDF 的工作原理。它必须有一些可以显示正确字母的字体。它必须是一种系统字体(对于 PDF reader)或嵌入字体。对于每一个字母,PDF 都必须有一种正确的字体。 在这种情况下,对于同一 PDF 中新语言的每个单词,您必须设置正确的字体。
一些TTF fonts was created for some specific letters, but not all TTFs was correctly created because behind this is one standard technology。 此外,并非所有为某些特定字母创建的 TTF 字体都可以在 PDF 中显示它们。例如我在网上找到的字体 "Devanagari" 应该支持所有印地语字母,但它完全失败了。
我们还必须找到正确的 TTF 字体。我找到了它们 - 在您的情况下,对于字符串“‘→Kadıköy’”,您可以使用 "Courier New" 或 "Arial Unicode MS".
我已经搜索了您任务中的每封信,并找到了以下列表:
→ – Font support for "Rightwards arrow" (u+2192)
ı – Font support for "Latin small letter dotless I" (u+0131)
‘ – Font support for "Left single quotation mark" (u+2018)
' – Font support for "Right single quotation mark" (u+2019)
ö – Font support for "Latin small letter o with diaeresis'" (u+00F6)
世界上大多数语言的解决方案
我已经创建了可以为世界上大多数语言创建 PDF 的应用程序。
使用方法:
- 首先下载并解压免费的TTF字体“Arial Unicode MS”
- 启动下面的代码片段并从您的文件夹中选择提取的免费 TTF 字体 "Arial Unicode MS"。
- 用您的语言编写文本,然后单击 "Create PDF" 按钮。
- 将下载 PDF,您可以打开它。
在某些情况下,TTF 字体可能不支持您的语言 "Arial Unicode MS"。您可以找到支持语言的完整列表 here。在这种情况下,您必须从正确的 TTF 字体中找到一个。 但请注意: 如果字体小于 100 kb。我有不适用于 jsPDF 的经验(请参阅我的 post 的开头)。
申请
var fontInBase64 = '',
fileName = '',
message = document.querySelector('div'),
txtForPdf = document.querySelector('textarea'),
errorStr = '<b style="color:red">Please select a font file!</b>';
function readFile()
{
var file = document.querySelector('input[type=file]').files[0],
reader = new FileReader();
if(file && file.name.split('.')[1].toLowerCase() != 'ttf')
{
message.innerHTML = errorStr;
return;
}
if(txtForPdf.value.replace(/\s+/g, '').length < 1)
{
message.innerHTML = '<b style="color:red">Please write some Text!</b>';;
return;
}
reader.onloadend = function()
{
fontInBase64 = reader.result.split(',')[1];
fileName = file.name.replace(/\s+/g, '-');
createPDF(fileName, fontInBase64);
}
if(file) reader.readAsDataURL(file);
else message.innerHTML = errorStr;
}
function createPDF(fileName, fontInBase64)
{
var doc = new jsPDF('p','mm','a4');
fileNameWithoutExtension = fileName.split('.')[0],
lMargin = 15, // left margin in mm
rMargin = 15, // right margin in mm
pdfInMM = 210; // width of A4 in mm
doc.addFileToVFS(fileName, fontInBase64);
doc.addFont(fileName, fileNameWithoutExtension, 'normal');
doc.setFont(fileNameWithoutExtension);
doc.setFontSize(14);
var splitParts = doc.splitTextToSize(txtForPdf.value, (pdfInMM - lMargin - rMargin));
doc.text(15, 15, splitParts);
doc.save('test.pdf');
}
function setHindiToTextArea()
{
txtForPdf.value =
"हिन्दी विश्व की एक प्रमुख भाषा है एवं भारत की राजभाषा है। केंद्रीय स्तर पर भारत में दूसरी आधिकारिक भाषा अंग्रेजी है। यह हिन्दुस्तानी भाषा की एक मानकीकृत रूप है जिसमें संस्कृत के तत्सम तथा तद्भव शब्द का प्रयोग अधिक हैं और अरबी-फ़ारसी शब्द कम हैं। हिन्दी संवैधानिक रूप से भारत की प्रथम राजभाषा और भारत की सबसे अधिक बोली और समझी जाने वाली भाषा है। हालांकि, हिन्दी भारत की राष्ट्रभाषा नहीं है क्योंकि भारत का संविधान में कोई भी भाषा को ऐसा दर्जा नहीं दिया गया था। चीनी के बाद यह विश्व में सबसे अधिक बोली जाने वाली भाषा भी है। विश्व आर्थिक मंच की गणना के अनुसार यह विश्व की दस शक्तिशाली भाषाओं में से एक है। हिन्दी और इसकी बोलियाँ सम्पूर्ण भारत के विविध राज्यों में बोली जाती हैं। भारत और अन्य देशों में भी लोग हिन्दी बोलते, पढ़ते और लिखते हैं। फ़िजी, मॉरिशस, गयाना, सूरीनाम की और नेपाल की जनता भी हिन्दी बोलती है। 2001 की भारतीय जनगणना में भारत में ४२ करोड़ २० लाख लोगों ने हिन्दी को अपनी मूल भाषा बताया। भारत के बाहर, हिन्दी बोलने वाले संयुक्त राज्य अमेरिका में 648,983; मॉरीशस में ६,८५,१७०; दक्षिण अफ्रीका में ८,९०,२९२; यमन में २,३२,७६०; युगांडा में १,४७,०००; सिंगापुर में ५,०००; नेपाल में ८ लाख; जर्मनी में ३०,००० हैं। न्यूजीलैंड में हिन्दी चौथी सर्वाधिक बोली जाने वाली भाषा है";
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/1.4.1/jspdf.min.js" crossorigin="anonymous"></script>
<input type="file" onchange="message.innerHTML=' '"><br><br>
<textarea rows="4" cols="75">‘→Kadıköy’</textarea>
<div> </div>
<input type="button" value="Create PDF with UTF support" onclick="readFile()">
<br>
<i>For example</i>:<br><a href="#" onclick="setHindiToTextArea()"><b>Click on this line if you wont to set hindi text to the textarea.</b></a>
尝试使用 jspdf lib @1.4.1 将文本转换为 pdf,输出有时变得非常难看和不可读,因为文本包含一些特殊字符,例如:
左单引号U+2018
,或右单引号U+2019
,或→
,或Kadıköy
中的ı
。 .
我怎么能sanitize/normalize这样的文字?或者我可以使用 jspdf 来解决这个问题吗?
更新:
要重现问题,只需使用此字符串:'→Kadıköy'
在本例中 https://parall.ax/products/jspdf,第 9 行,您会看到箭头已转换到 !’
并且 ı
转换为 1
(仅供参考,Kadıköy 是一个城市的名称 https://en.wikipedia.org/wiki/Kad%C4%B1k%C3%B6y)
您可以通过导入支持您的特殊字符的字体来实现。
从 basic.js on examples 你可以看到如何应用它的参考。
(示例带有西里尔字母)。
function demoUsingTTFFont() {
//https://fonts.google.com/specimen/PT+Sans
var PTSans = “...... “); // place long string of text here
var doc = new jsPDF();
doc.addFileToVFS("PTSans.ttf", PTSans);
doc.addFont('PTSans.ttf', 'PTSans', 'normal');
doc.setFont('PTSans'); // set font
doc.setFontSize(10);
doc.text("А ну чики брики и в дамки!", 10, 10);
doc.save('test.pdf');
}
作为fontfamily,请看看Google的Noto。
来源:
恕我直言,mico answer OK,只需将字体 PTSans 替换为您使用的字体(base64 编码)。 参见 jsfiddle:https://jsfiddle.net/o0m9pzyv/12/
var PTSans = ...
我们可以阅读here:
jsPDF supports finally UTF-8 by having the ability to use custom fonts.
您遇到的问题是您没有真正了解 PDF 的工作原理。它必须有一些可以显示正确字母的字体。它必须是一种系统字体(对于 PDF reader)或嵌入字体。对于每一个字母,PDF 都必须有一种正确的字体。 在这种情况下,对于同一 PDF 中新语言的每个单词,您必须设置正确的字体。
一些TTF fonts was created for some specific letters, but not all TTFs was correctly created because behind this is one standard technology。 此外,并非所有为某些特定字母创建的 TTF 字体都可以在 PDF 中显示它们。例如我在网上找到的字体 "Devanagari" 应该支持所有印地语字母,但它完全失败了。
我们还必须找到正确的 TTF 字体。我找到了它们 - 在您的情况下,对于字符串“‘→Kadıköy’”,您可以使用 "Courier New" 或 "Arial Unicode MS".
我已经搜索了您任务中的每封信,并找到了以下列表:
→ – Font support for "Rightwards arrow" (u+2192)
ı – Font support for "Latin small letter dotless I" (u+0131)
‘ – Font support for "Left single quotation mark" (u+2018)
' – Font support for "Right single quotation mark" (u+2019)
ö – Font support for "Latin small letter o with diaeresis'" (u+00F6)
世界上大多数语言的解决方案
我已经创建了可以为世界上大多数语言创建 PDF 的应用程序。
使用方法:
- 首先下载并解压免费的TTF字体“Arial Unicode MS”
- 启动下面的代码片段并从您的文件夹中选择提取的免费 TTF 字体 "Arial Unicode MS"。
- 用您的语言编写文本,然后单击 "Create PDF" 按钮。
- 将下载 PDF,您可以打开它。
在某些情况下,TTF 字体可能不支持您的语言 "Arial Unicode MS"。您可以找到支持语言的完整列表 here。在这种情况下,您必须从正确的 TTF 字体中找到一个。 但请注意: 如果字体小于 100 kb。我有不适用于 jsPDF 的经验(请参阅我的 post 的开头)。
申请
var fontInBase64 = '',
fileName = '',
message = document.querySelector('div'),
txtForPdf = document.querySelector('textarea'),
errorStr = '<b style="color:red">Please select a font file!</b>';
function readFile()
{
var file = document.querySelector('input[type=file]').files[0],
reader = new FileReader();
if(file && file.name.split('.')[1].toLowerCase() != 'ttf')
{
message.innerHTML = errorStr;
return;
}
if(txtForPdf.value.replace(/\s+/g, '').length < 1)
{
message.innerHTML = '<b style="color:red">Please write some Text!</b>';;
return;
}
reader.onloadend = function()
{
fontInBase64 = reader.result.split(',')[1];
fileName = file.name.replace(/\s+/g, '-');
createPDF(fileName, fontInBase64);
}
if(file) reader.readAsDataURL(file);
else message.innerHTML = errorStr;
}
function createPDF(fileName, fontInBase64)
{
var doc = new jsPDF('p','mm','a4');
fileNameWithoutExtension = fileName.split('.')[0],
lMargin = 15, // left margin in mm
rMargin = 15, // right margin in mm
pdfInMM = 210; // width of A4 in mm
doc.addFileToVFS(fileName, fontInBase64);
doc.addFont(fileName, fileNameWithoutExtension, 'normal');
doc.setFont(fileNameWithoutExtension);
doc.setFontSize(14);
var splitParts = doc.splitTextToSize(txtForPdf.value, (pdfInMM - lMargin - rMargin));
doc.text(15, 15, splitParts);
doc.save('test.pdf');
}
function setHindiToTextArea()
{
txtForPdf.value =
"हिन्दी विश्व की एक प्रमुख भाषा है एवं भारत की राजभाषा है। केंद्रीय स्तर पर भारत में दूसरी आधिकारिक भाषा अंग्रेजी है। यह हिन्दुस्तानी भाषा की एक मानकीकृत रूप है जिसमें संस्कृत के तत्सम तथा तद्भव शब्द का प्रयोग अधिक हैं और अरबी-फ़ारसी शब्द कम हैं। हिन्दी संवैधानिक रूप से भारत की प्रथम राजभाषा और भारत की सबसे अधिक बोली और समझी जाने वाली भाषा है। हालांकि, हिन्दी भारत की राष्ट्रभाषा नहीं है क्योंकि भारत का संविधान में कोई भी भाषा को ऐसा दर्जा नहीं दिया गया था। चीनी के बाद यह विश्व में सबसे अधिक बोली जाने वाली भाषा भी है। विश्व आर्थिक मंच की गणना के अनुसार यह विश्व की दस शक्तिशाली भाषाओं में से एक है। हिन्दी और इसकी बोलियाँ सम्पूर्ण भारत के विविध राज्यों में बोली जाती हैं। भारत और अन्य देशों में भी लोग हिन्दी बोलते, पढ़ते और लिखते हैं। फ़िजी, मॉरिशस, गयाना, सूरीनाम की और नेपाल की जनता भी हिन्दी बोलती है। 2001 की भारतीय जनगणना में भारत में ४२ करोड़ २० लाख लोगों ने हिन्दी को अपनी मूल भाषा बताया। भारत के बाहर, हिन्दी बोलने वाले संयुक्त राज्य अमेरिका में 648,983; मॉरीशस में ६,८५,१७०; दक्षिण अफ्रीका में ८,९०,२९२; यमन में २,३२,७६०; युगांडा में १,४७,०००; सिंगापुर में ५,०००; नेपाल में ८ लाख; जर्मनी में ३०,००० हैं। न्यूजीलैंड में हिन्दी चौथी सर्वाधिक बोली जाने वाली भाषा है";
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/1.4.1/jspdf.min.js" crossorigin="anonymous"></script>
<input type="file" onchange="message.innerHTML=' '"><br><br>
<textarea rows="4" cols="75">‘→Kadıköy’</textarea>
<div> </div>
<input type="button" value="Create PDF with UTF support" onclick="readFile()">
<br>
<i>For example</i>:<br><a href="#" onclick="setHindiToTextArea()"><b>Click on this line if you wont to set hindi text to the textarea.</b></a>