2012-11-27 21 views
9

Trong trang web của chúng tôi, một số người dùng Mac gặp khó khăn khi họ sao chép-dán văn bản từ tệp PDF vào TextArea (do TinyMCE xử lý). Tất cả các chữ nổi bật bị hỏng, và trở thành ví dụ e? cho một é, i? cho một î, v.v. Tôi không thể tạo lại vấn đề này với máy tính Windows.PHP: Unicode nhấn mạnh char và dấu phụ

Khi tôi đã viết nội dung của TextArea trên một tệp (trước khi chèn nó vào cơ sở dữ liệu), tôi chỉ phát hiện ra rằng ban đầu là khác nhau về mặt truyền thống é (trên Vim, xem bên dưới).

Visual example of the problem

Thật vậy:

// the corrupted é - first line of the screenshot 
echo bin2hex($char); // display 65cc81 

// traditionnal é 
echo bin2hex('é'); // display c3a9 

Sau khi tìm kiếm rất nhiều, ở đây tôi: Dường như Mac OS bản Unicode nhấn mạnh chars như một sự kết hợp của hai ký tự: trong ví dụ của chúng tôi, e + ́. Cho đến nay, tôi đã không tìm thấy bất kỳ giải pháp nào để thay thế số é bị hỏng bằng thực tế, để tránh e? trong cơ sở dữ liệu.

Và tôi hơi tuyệt vọng.

+4

http://unicode.org/reports/tr15/ – hakre

Trả lời

8

Quá trình normalizing the representation to one form or the other được gọi là, tốt, chuẩn hóa. Trong PHP có các Normalizer class cho rằng, gửi tất cả các đầu vào thông qua nó là một ý tưởng tốt:

$input = Normalizer::normalize($input); 

Bạn có muốn bình thường hóa để tạo thành C, Canonical phân hủy tiếp theo Composition Canonical.

Lớp học đó không có sẵn trên hệ thống của bạn, có Patchwork UTF-8 library.

+0

Hmm, thật thú vị. Vẫn giữ cho tôi ngạc nhiên bởi câu trả lời của bạn ... – shadyyx

+1

Cần lưu ý rằng không có tham nhũng thực sự. Các ký tự bị phân tách hoàn toàn hợp lệ. –

+0

@Tino Thật vậy. Nó nên được điều tra lý do tại sao cơ sở dữ liệu hoặc một số quá trình dẫn đến nó * là tham nhũng * các ký tự bị phân hủy. – deceze

0

Có một tham số cấu hình TinyMCE cho phép bạn xác định một chức năng để xử lý các nội dung được dán trước khi chèn trong trình soạn thảo: paste_preprocessing

Sử dụng chức năng mà bạn có thể thay thế các specialchars với hình thức mong muốn

tinyMCE.init({ 
     ... 
     paste_preprocess : function(pl, o) { 
      // Content string containing the HTML from the clipboard 
      o.content = o.content.replace(/\u2020/, 'x'); // example 
     }, 
     paste_postprocess : function(pl, o) { 
      ... 
     }, 
     ... 
}); 
+1

Biểu mẫu mong muốn sẽ là * Singleton * thay vì * Kết hợp chuỗi * Bạn có một thư viện javascript trong tay mà đề với điều đó? – hakre

+0

có, nó là API tinymce: http://tinymce.moxiecode.com/js/tinymce/docs/api/index.html nhưng chuyển đổi ký tự javascript cần được quản trị viên trang web xác định trong hàm paste_preprocess – Thariama

+0

Thú vị, nhưng wha t là tên của lớp Normalizer? Tôi không thể tìm thấy nó. – hakre

4

Đây chỉ là bổ sung cho những gì @deceze đã được trả lời. Có nhiều cách trong Unicode để chỉ định cùng một ký tự (theo nghĩa tương đương).

Bạn có một ví dụ phổ biến ở đây:

65cc81 

Đó là hai codepoints Unicode trong mã UTF-8. 65eLATIN THƯ NHỎ E (U + 0065) và cc81́kết hợp CẤP TÍNH ACCENT (U + 0301) (nó không thể được hiển thị độc lập bởi trình duyệt của bạn, vì vậy tôi đã thực thể HTML).

Trong Unicode, đây được gọi là Kết hợp chuỗi. Tuy nhiên, vì lý do nào đó, cơ sở dữ liệu của bạn không hỗ trợ nó. Có lẽ vì mã hóa của cột không phải là UTF-8 hoặc kết nối cơ sở dữ liệu có vấn đề với nó.

Đó là theo giáo luật tương đương với

c3a9 

Đó là một Unicode điểm mã duy nhất trong mã UTF-8. c3a9éLATIN SMALL LETTER E VỚI ACUTE (U + 00E9). Có vẻ như cơ sở dữ liệu của bạn không có vấn đề gì để xử lý nó, có thể bởi vì nó được mã hóa lại thành Latin-1/ISO-8859-1 bởi kết nối cơ sở dữ liệu thành công.

Vì vậy, hai cách xử lý dữ liệu đến với tâm trí. Đó là một vấn đề trong việc mã hóa lại dữ liệu hoặc một vấn đề lưu trữ dữ liệu.

Miễn là bạn quan tâm đến việc tạo thành các trình tự mã hóa unicode được tạo thành, bạn nên dùng trình bình thường được nêu trong Deceze's answer.

Bạn cũng có thể cho phép UTF-8 được lưu trữ vào cơ sở dữ liệu và sau đó bạn không nên có một vấn đề, quá.

Ngoài ra bạn có lẽ nên bình thường nào để phân loại và so sánh dữ liệu trong cơ sở dữ liệu hoặc chương trình của bạn hoạt động tốt hơn. Như bạn có thể thấy, các chuỗi nhị phân khác nhau có thể gây ra các vấn đề cho mọi thứ so sánh ở mức nhị phân.

Và chắc chắn, bạn tiết kiệm một số lưu lượng truy cập :)

+0

Thnak bạn cho câu trả lời của bạn. Trình bày rất hữu ích, tôi học được rất nhiều nhờ bạn! :) –

+1

Điều đó rất hay để đọc. Ngoài ra tôi thấy bài đăng trên blog này thú vị trong mắt tôi: [Unicode Normalization] (http://annevankesteren.nl/2009/02/unicode-normalization) - nó có một số liên kết khác, một số vẫn hoạt động nếu bạn muốn đào thậm chí sâu hơn cho phần unicode. – hakre

+0

Cảm ơn bạn đã liên kết. Tôi chỉ Poket-ed nó, và tôi sẽ đọc nó sau này (trên tàu điện ngầm :)) –