{"action":"created","issue":{"url":"https://api.github.com/repos/hoaproject/String/issues/18","labels_url":"https://api.github.com/repos/hoaproject/String/issues/18/labels{/name}","comments_url":"https://api.github.com/repos/hoaproject/String/issues/18/comments","events_url":"https://api.github.com/repos/hoaproject/String/issues/18/events","html_url":"https://github.com/hoaproject/String/pull/18","id":53473763,"number":18,"title":"Add the `getCharWidth` and `isCharPrintable` methods","user":{"login":"Hywan","id":946104,"avatar_url":"https://avatars.githubusercontent.com/u/946104?v=3","gravatar_id":"","url":"https://api.github.com/users/Hywan","html_url":"https://github.com/Hywan","followers_url":"https://api.github.com/users/Hywan/followers","following_url":"https://api.github.com/users/Hywan/following{/other_user}","gists_url":"https://api.github.com/users/Hywan/gists{/gist_id}","starred_url":"https://api.github.com/users/Hywan/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/Hywan/subscriptions","organizations_url":"https://api.github.com/users/Hywan/orgs","repos_url":"https://api.github.com/users/Hywan/repos","events_url":"https://api.github.com/users/Hywan/events{/privacy}","received_events_url":"https://api.github.com/users/Hywan/received_events","type":"User","site_admin":false},"labels":[{"url":"https://api.github.com/repos/hoaproject/String/labels/bug","name":"bug","color":"fc2929"},{"url":"https://api.github.com/repos/hoaproject/String/labels/enhancement","name":"enhancement","color":"84b6eb"}],"state":"open","locked":false,"assignee":null,"milestone":null,"comments":3,"created_at":"2015-01-06T02:27:44Z","updated_at":"2015-01-06T14:58:29Z","closed_at":null,"pull_request":{"url":"https://api.github.com/repos/hoaproject/String/pulls/18","html_url":"https://github.com/hoaproject/String/pull/18","diff_url":"https://github.com/hoaproject/String/pull/18.diff","patch_url":"https://github.com/hoaproject/String/pull/18.patch"},"body":"Fix #8.\r\nAddress https://github.com/hoaproject/Console/issues/17.\r\nAddress https://github.com/hoaproject/Console/issues/16.\r\n\r\n# `getCharWidth`\r\n\r\nSooo… it has been a long time before fixing this issue but it was not easy :-].\r\n[`mb_strwidth`](http://php.net/mb_strwidth) does not support C0/C1 control characters from the terminal and the PHP implementation is quite strange (apparently, it mainly supports Japanese, don't know why, the documentation is wrong… well, I didn't dig more).\r\n\r\nI propose to keep the `String::getWidth` method because it uses `mb_strwidth`. **However**, to test the width of a **specific character**, I propose to introduce the `String::getCharWidth`. This static method takes care of C0/C1 sequence character. The algorithm is based on http://www.cl.cam.ac.uk/~mgk25/ucs/wcwidth.c by @mgkuhn (thanks @nicolas-grekas for the link!). I forgot this link but a comment on Reddit reminds me it :-p.\r\n\r\nTesting this algorithm was not simple. I used a tool called Pex, by Nikolai Tillmann to help me. The resulting test data are small but relevant. Maybe we should add more data to test the `$combining` table?\r\n\r\n# `isCharPrintable`\r\n\r\nThen, I was able to easily introduce the `isCharPrintable` static method. In the case of https://github.com/hoaproject/Console/issues/17, the [`DELETE` character is `0x7f`](http://graphemica.com/007F). According to our tests, we can't print this character, which is correct. Finally :-].\r\n\r\nI am asking a review from @nicolas-grekas and @hoaproject/hoackers :-)."},"comment":{"url":"https://api.github.com/repos/hoaproject/String/issues/comments/68875236","html_url":"https://github.com/hoaproject/String/pull/18#issuecomment-68875236","issue_url":"https://api.github.com/repos/hoaproject/String/issues/18","id":68875236,"user":{"login":"mgkuhn","id":4479402,"avatar_url":"https://avatars.githubusercontent.com/u/4479402?v=3","gravatar_id":"","url":"https://api.github.com/users/mgkuhn","html_url":"https://github.com/mgkuhn","followers_url":"https://api.github.com/users/mgkuhn/followers","following_url":"https://api.github.com/users/mgkuhn/following{/other_user}","gists_url":"https://api.github.com/users/mgkuhn/gists{/gist_id}","starred_url":"https://api.github.com/users/mgkuhn/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/mgkuhn/subscriptions","organizations_url":"https://api.github.com/users/mgkuhn/orgs","repos_url":"https://api.github.com/users/mgkuhn/repos","events_url":"https://api.github.com/users/mgkuhn/events{/privacy}","received_events_url":"https://api.github.com/users/mgkuhn/received_events","type":"User","site_admin":false},"created_at":"2015-01-06T14:58:29Z","updated_at":"2015-01-06T14:58:29Z","body":"BTW, \"uniset\" refers to my Unicode set calculator in http://www.cl.cam.ac.uk/~mgk25/download/uniset.tar.gz which is the Perl script that generated that table. (Probably time for it to catch up with more recent versions of the Unicode tables.)"}}