Anonymous
Как обеспечить правильное отображение смайлов в именах PDF-файлов и их содержимом?
Сообщение
Anonymous » 02 окт 2024, 12:56
Я использую iText для обработки различных шрифтов и смайлов, но смайлы не отображаются должным образом. Вместо этого они полностью удаляются.
Это мои зависимости
Код: Выделить всё
11
false
2.17.2
1.5.3.Final
8.0.5
com.itextpdf
kernel
${itext.version}
com.itextpdf
io
${itext.version}
com.itextpdf
layout
${itext.version}
com.itextpdf
forms
${itext.version}
com.itextpdf
pdfa
${itext.version}
com.itextpdf
sign
${itext.version}
com.itextpdf
barcodes
${itext.version}
com.itextpdf
font-asian
${itext.version}
com.itextpdf
hyph
${itext.version}
Код: Выделить всё
private static final float MARGIN_X = 50;
private static final float MARGIN_Y = 50;
private static final float FONT_SIZE = 12;
private static final float LINE_HEIGHT = 1.5f * FONT_SIZE;
private static final String EMOJI_FONT_PATH = "static/NotoColorEmoji-Regular.ttf";
private BaseFont emojiBaseFont;
private Font emojiFont;
private Font normalFont;
private Font boldFont;
private Font italicFont;
private Font monospaceFont;
private List messages;
private String ticketNumber;
private String issuedTime;
private String closedTime;
private String clientWhatsAppNumber;
private String customerWhatsAppNumber;
private String agentName;
private String customerName;
private String lastOutgoingMessageTime;
private String fileName;
private Font fallbackFont;
public ChatTranscriptServiceImpl(ChatParticipantClient chatParticipantClient) {
this.chatParticipantClient = chatParticipantClient;
}
@Override
public ChatTranscriptResponse downloadChatTranscript(String chatParticipantId) {
this.messages = chatParticipantClient.getMessagesByChatParticipant(chatParticipantId);
byte[] pdfBytes = processMessages();
ChatTranscriptResponse response = new ChatTranscriptResponse();
response.setPdfBytes(pdfBytes);
response.setFilename(fileName);
return response;
}
private byte[] processMessages() {
Pattern ticketNumberPattern = Pattern.compile("Your (?:previous )?ticket number is (.*?) please retain the ticket number to reference this chat.", Pattern.DOTALL);
Pattern ratingMessagePattern = Pattern.compile("Please rate our service.");
for (Message message : this.messages) {
processTicketNumber(ticketNumberPattern, message);
processOutgoingMessage(message);
processRatingMessage(ratingMessagePattern, message);
extractWhatsAppNumbers(message);
}
return finalizeTranscript();
}
private void processTicketNumber(Pattern pattern, Message message) {
String text = message.getText();
if (text != null) {
Matcher matcher = pattern.matcher(text);
if (matcher.find()) {
ticketNumber = matcher.group(1).trim();
issuedTime = formatDateTime(message.getCreatedTime());
} else if (issuedTime == null) {
issuedTime = formatDateTime(message.getCreatedTime());
}
} else if (issuedTime == null) {
issuedTime = formatDateTime(message.getCreatedTime());
}
}
private void processOutgoingMessage(Message message) {
if (Pl4ChatMessageDirection.OUTGOING.equals(message.getDirection())) {
lastOutgoingMessageTime = formatDateTime(message.getCreatedTime());
if (message.getAgent() != null) {
agentName = getAgentName(message.getAgent());
} else {
agentName = "Bot";
}
if (message.getChatParticipant() != null) {
customerName = getCustomerName(message.getChatParticipant());
}
}
}
private void processRatingMessage(Pattern pattern, Message message) {
Matcher matcher = pattern.matcher(message.getText());
if (matcher.find()) {
closedTime = formatDateTime(message.getCreatedTime());
} else if (message.getChatParticipant() != null && message.getChatParticipant().isConversationClosed()) {
closedTime = lastOutgoingMessageTime != null ? lastOutgoingMessageTime : "Open";
} else {
closedTime = "Open";
}
}
private void extractWhatsAppNumbers(Message message) {
if (clientWhatsAppNumber == null && message.getChatParticipant() != null && message.getChatParticipant().getWhatsAppClientNumber() != null) {
clientWhatsAppNumber = message.getChatParticipant().getWhatsAppClientNumber();
}
if (customerWhatsAppNumber == null && message.getChatParticipant() != null && message.getChatParticipant().getPhoneNumber() != null) {
customerWhatsAppNumber = message.getChatParticipant().getPhoneNumber();
}
}
private String getAgentName(SystemUser agent) {
if (agent.getFirstName() != null && agent.getLastName() != null) {
return agent.getFirstName() + " " + agent.getLastName();
} else if (agent.getFirstName() != null) {
return agent.getFirstName();
} else if (agent.getLastName() != null) {
return agent.getLastName();
}
return "Bot";
}
private String getCustomerName(ChatParticipant participant) {
if (participant.getFullName() != null) {
return participant.getFullName();
} else if (participant.getFirstName() != null && participant.getLastName() != null) {
return participant.getFirstName() + " " + participant.getLastName();
} else if (participant.getFirstName() != null) {
return participant.getFirstName();
} else if (participant.getLastName() != null) {
return participant.getLastName();
}
return "Unknown";
}
private byte[] finalizeTranscript() {
try {
return this.generatePdfTranscript();
} catch (IOException | DocumentException e) {
log.error("Error generating file: {}", e.getMessage());
throw CustomParameterizedException.singleParameterProblem(
String.format("Error generating transcript... %n%s", e.getMessage()),
Status.BAD_REQUEST
);
}
}
private byte[] generatePdfTranscript() throws IOException, DocumentException {
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
Document document = new Document(PageSize.A4, MARGIN_X, MARGIN_X, MARGIN_Y, MARGIN_Y);
PdfWriter writer = PdfWriter.getInstance(document, byteArrayOutputStream);
document.open();
initializeFonts();
setupPdfHeader(document);
addTranscriptTitle(document);
for (Message message : messages) {
addMessage(document, writer, message);
}
document.close();
fileName = sanitizeFilename("chat_transcript_" + ticketNumber + ".pdf");
return byteArrayOutputStream.toByteArray();
}
private void setupPdfHeader(Document document) throws DocumentException {
Font headerFont = new Font(Font.FontFamily.HELVETICA, FONT_SIZE, Font.BOLD);
Paragraph header = new Paragraph();
header.setAlignment(Element.ALIGN_LEFT);
if (ticketNumber != null) {
header.add(new Chunk("Ticket Number: " + ticketNumber + "\n", headerFont));
header.add(new Chunk("Date & Time Ticket Issued: " + issuedTime + "\n", headerFont));
header.add(new Chunk("Date & Time Ticket Closed: " + closedTime + "\n", headerFont));
} else {
header.add(new Chunk("No ticket issued\n", headerFont));
}
if (clientWhatsAppNumber != null) {
header.add(new Chunk("Service's WhatsApp number: " + clientWhatsAppNumber + "\n", headerFont));
}
if (customerWhatsAppNumber != null) {
header.add(new Chunk("Customer's WhatsApp number: " + customerWhatsAppNumber + "\n", headerFont));
}
header.add(new Chunk("Agent's Name & Surname: " + agentName + "\n", headerFont));
header.add(new Chunk("Customer's Name & Surname: " + customerName + "\n", headerFont));
PdfPTable table = new PdfPTable(1);
table.setWidthPercentage(100);
PdfPCell cell = new PdfPCell(header);
cell.setBorder(Rectangle.BOX);
cell.setPadding(10);
table.addCell(cell);
document.add(table);
document.add(Chunk.NEWLINE);
}
private void addTranscriptTitle(Document document) throws DocumentException {
Font titleFont = new Font(Font.FontFamily.HELVETICA, FONT_SIZE + 2, Font.BOLD);
Paragraph title = new Paragraph("Ticket Transcript:", titleFont);
title.setAlignment(Element.ALIGN_LEFT);
document.add(title);
document.add(Chunk.NEWLINE);
}
private Font getFontForPart(ProcessedPart part) {
switch (part.style) {
case "bold":
return boldFont;
case "italic":
return italicFont;
case "monospace":
return monospaceFont;
default:
return normalFont;
}
}
private boolean isEmoji(int codePoint) {
return (codePoint >= 0x1F300 && codePoint = 0x2600 && codePoint = 0x2700 && codePoint = 0xFE00 && codePoint = 0x1F900 && codePoint 0) {
paragraph.add(Chunk.NEWLINE);
}
}
}
Я пробовал отображать смайлы в том виде, в каком они есть в PDF-документе, но он возвращает пустые места там, где должны быть смайлы: «Esphi N» вместо «
Esphi N
'. Однако когда я копирую и вставляю текст с пустыми местами в Google, смайлы отображаются правильно
Подробнее здесь:
https://stackoverflow.com/questions/790 ... and-its-co
1727862994
Anonymous
Я использую iText для обработки различных шрифтов и смайлов, но смайлы не отображаются должным образом. Вместо этого они полностью удаляются. Это мои зависимости [code] 11 false 2.17.2 1.5.3.Final 8.0.5 com.itextpdf kernel ${itext.version} com.itextpdf io ${itext.version} com.itextpdf layout ${itext.version} com.itextpdf forms ${itext.version} com.itextpdf pdfa ${itext.version} com.itextpdf sign ${itext.version} com.itextpdf barcodes ${itext.version} com.itextpdf font-asian ${itext.version} com.itextpdf hyph ${itext.version} [/code] [code] private static final float MARGIN_X = 50; private static final float MARGIN_Y = 50; private static final float FONT_SIZE = 12; private static final float LINE_HEIGHT = 1.5f * FONT_SIZE; private static final String EMOJI_FONT_PATH = "static/NotoColorEmoji-Regular.ttf"; private BaseFont emojiBaseFont; private Font emojiFont; private Font normalFont; private Font boldFont; private Font italicFont; private Font monospaceFont; private List messages; private String ticketNumber; private String issuedTime; private String closedTime; private String clientWhatsAppNumber; private String customerWhatsAppNumber; private String agentName; private String customerName; private String lastOutgoingMessageTime; private String fileName; private Font fallbackFont; public ChatTranscriptServiceImpl(ChatParticipantClient chatParticipantClient) { this.chatParticipantClient = chatParticipantClient; } @Override public ChatTranscriptResponse downloadChatTranscript(String chatParticipantId) { this.messages = chatParticipantClient.getMessagesByChatParticipant(chatParticipantId); byte[] pdfBytes = processMessages(); ChatTranscriptResponse response = new ChatTranscriptResponse(); response.setPdfBytes(pdfBytes); response.setFilename(fileName); return response; } private byte[] processMessages() { Pattern ticketNumberPattern = Pattern.compile("Your (?:previous )?ticket number is (.*?) please retain the ticket number to reference this chat.", Pattern.DOTALL); Pattern ratingMessagePattern = Pattern.compile("Please rate our service."); for (Message message : this.messages) { processTicketNumber(ticketNumberPattern, message); processOutgoingMessage(message); processRatingMessage(ratingMessagePattern, message); extractWhatsAppNumbers(message); } return finalizeTranscript(); } private void processTicketNumber(Pattern pattern, Message message) { String text = message.getText(); if (text != null) { Matcher matcher = pattern.matcher(text); if (matcher.find()) { ticketNumber = matcher.group(1).trim(); issuedTime = formatDateTime(message.getCreatedTime()); } else if (issuedTime == null) { issuedTime = formatDateTime(message.getCreatedTime()); } } else if (issuedTime == null) { issuedTime = formatDateTime(message.getCreatedTime()); } } private void processOutgoingMessage(Message message) { if (Pl4ChatMessageDirection.OUTGOING.equals(message.getDirection())) { lastOutgoingMessageTime = formatDateTime(message.getCreatedTime()); if (message.getAgent() != null) { agentName = getAgentName(message.getAgent()); } else { agentName = "Bot"; } if (message.getChatParticipant() != null) { customerName = getCustomerName(message.getChatParticipant()); } } } private void processRatingMessage(Pattern pattern, Message message) { Matcher matcher = pattern.matcher(message.getText()); if (matcher.find()) { closedTime = formatDateTime(message.getCreatedTime()); } else if (message.getChatParticipant() != null && message.getChatParticipant().isConversationClosed()) { closedTime = lastOutgoingMessageTime != null ? lastOutgoingMessageTime : "Open"; } else { closedTime = "Open"; } } private void extractWhatsAppNumbers(Message message) { if (clientWhatsAppNumber == null && message.getChatParticipant() != null && message.getChatParticipant().getWhatsAppClientNumber() != null) { clientWhatsAppNumber = message.getChatParticipant().getWhatsAppClientNumber(); } if (customerWhatsAppNumber == null && message.getChatParticipant() != null && message.getChatParticipant().getPhoneNumber() != null) { customerWhatsAppNumber = message.getChatParticipant().getPhoneNumber(); } } private String getAgentName(SystemUser agent) { if (agent.getFirstName() != null && agent.getLastName() != null) { return agent.getFirstName() + " " + agent.getLastName(); } else if (agent.getFirstName() != null) { return agent.getFirstName(); } else if (agent.getLastName() != null) { return agent.getLastName(); } return "Bot"; } private String getCustomerName(ChatParticipant participant) { if (participant.getFullName() != null) { return participant.getFullName(); } else if (participant.getFirstName() != null && participant.getLastName() != null) { return participant.getFirstName() + " " + participant.getLastName(); } else if (participant.getFirstName() != null) { return participant.getFirstName(); } else if (participant.getLastName() != null) { return participant.getLastName(); } return "Unknown"; } private byte[] finalizeTranscript() { try { return this.generatePdfTranscript(); } catch (IOException | DocumentException e) { log.error("Error generating file: {}", e.getMessage()); throw CustomParameterizedException.singleParameterProblem( String.format("Error generating transcript... %n%s", e.getMessage()), Status.BAD_REQUEST ); } } private byte[] generatePdfTranscript() throws IOException, DocumentException { ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); Document document = new Document(PageSize.A4, MARGIN_X, MARGIN_X, MARGIN_Y, MARGIN_Y); PdfWriter writer = PdfWriter.getInstance(document, byteArrayOutputStream); document.open(); initializeFonts(); setupPdfHeader(document); addTranscriptTitle(document); for (Message message : messages) { addMessage(document, writer, message); } document.close(); fileName = sanitizeFilename("chat_transcript_" + ticketNumber + ".pdf"); return byteArrayOutputStream.toByteArray(); } private void setupPdfHeader(Document document) throws DocumentException { Font headerFont = new Font(Font.FontFamily.HELVETICA, FONT_SIZE, Font.BOLD); Paragraph header = new Paragraph(); header.setAlignment(Element.ALIGN_LEFT); if (ticketNumber != null) { header.add(new Chunk("Ticket Number: " + ticketNumber + "\n", headerFont)); header.add(new Chunk("Date & Time Ticket Issued: " + issuedTime + "\n", headerFont)); header.add(new Chunk("Date & Time Ticket Closed: " + closedTime + "\n", headerFont)); } else { header.add(new Chunk("No ticket issued\n", headerFont)); } if (clientWhatsAppNumber != null) { header.add(new Chunk("Service's WhatsApp number: " + clientWhatsAppNumber + "\n", headerFont)); } if (customerWhatsAppNumber != null) { header.add(new Chunk("Customer's WhatsApp number: " + customerWhatsAppNumber + "\n", headerFont)); } header.add(new Chunk("Agent's Name & Surname: " + agentName + "\n", headerFont)); header.add(new Chunk("Customer's Name & Surname: " + customerName + "\n", headerFont)); PdfPTable table = new PdfPTable(1); table.setWidthPercentage(100); PdfPCell cell = new PdfPCell(header); cell.setBorder(Rectangle.BOX); cell.setPadding(10); table.addCell(cell); document.add(table); document.add(Chunk.NEWLINE); } private void addTranscriptTitle(Document document) throws DocumentException { Font titleFont = new Font(Font.FontFamily.HELVETICA, FONT_SIZE + 2, Font.BOLD); Paragraph title = new Paragraph("Ticket Transcript:", titleFont); title.setAlignment(Element.ALIGN_LEFT); document.add(title); document.add(Chunk.NEWLINE); } private Font getFontForPart(ProcessedPart part) { switch (part.style) { case "bold": return boldFont; case "italic": return italicFont; case "monospace": return monospaceFont; default: return normalFont; } } private boolean isEmoji(int codePoint) { return (codePoint >= 0x1F300 && codePoint = 0x2600 && codePoint = 0x2700 && codePoint = 0xFE00 && codePoint = 0x1F900 && codePoint 0) { paragraph.add(Chunk.NEWLINE); } } } [/code] Я пробовал отображать смайлы в том виде, в каком они есть в PDF-документе, но он возвращает пустые места там, где должны быть смайлы: «Esphi N» вместо «🌹🦬🪶🐓Esphi N🤣😂 '. Однако когда я копирую и вставляю текст с пустыми местами в Google, смайлы отображаются правильно Подробнее здесь: [url]https://stackoverflow.com/questions/79040757/how-can-i-ensure-that-emojis-are-displayed-correctly-in-pdf-filenames-and-its-co[/url]