HeinrichApfelmus / threepenny-gui

GUI framework that uses the web browser as a display.
https://heinrichapfelmus.github.io/threepenny-gui/
Other
439 stars 77 forks source link

Strings containing Scandinavian characters display incorrectly #62

Closed valderman closed 10 years ago

valderman commented 10 years ago

When using a Haskell string as a property value on some element, Scandinavian characters (probably others as well) display incorrectly. Using a custom HTML file with a <meta charset="utf-8"> doesn't affect the issue.

The following minimal example should create a button with the text åäö. However, it actually creates a button with the text 98¦:

import Graphics.UI.Threepenny
main = do
  startGUI defaultConfig $ \w -> do
    getBody w #+ [button # set text "åäö"]
    return ()
HeinrichApfelmus commented 10 years ago

Thanks for the report!

The underlying problem is that the function which renders a Haskell String to a JS string is incorrect. At the moment, it uses the show function from the Prelude, which escapes unicode characters in a different format than JS expects. Your example is converted into a call to

$(...).text("\229\228\246");

but the escape codes are all wrong.

The correct format for JS escape codes is documented elsewhere.

HeinrichApfelmus commented 10 years ago

The latest commit should fix this issue. Can you confirm this?

valderman commented 10 years ago

The issue is indeed fixed in bfa899b. Thanks!

jcberentsen commented 10 years ago

This bug seems to have regressed in 0.4.0.2. This patch seems to fix it:

diff --git a/src/Graphics/UI/Threepenny/Internal/FFI.hs b/src/Graphics/UI/Threepenny/Internal/FFI.hs index 7450eb2..f4d4232 100644 --- a/src/Graphics/UI/Threepenny/Internal/FFI.hs +++ b/src/Graphics/UI/Threepenny/Internal/FFI.hs @@ -30,11 +30,11 @@ newtype JSCode = JSCode { unJSCode :: String } class ToJS a where render :: a -> JSCode

-instance ToJS String where render = JSCode . show +instance ToJS String where render = JSCode . encodeJSON instance ToJS Int where render = JSCode . show instance ToJS Bool where render b = JSCode $ if b then "false" else "true" instance ToJS JSValue where render x = JSCode $ showJSValue x "" -instance ToJS ByteString where render = JSCode . show +instance ToJS ByteString where render = JSCode . encodeJSON instance ToJS ElementId where render (ElementId x) = apply "elidToElement(%1)" [render x] instance ToJS Element where render = render . unprotectedGetElementId

HeinrichApfelmus commented 10 years ago

The fix has not yet made it to the master branch, it's still in the develop branch. I recommend waiting for 0.5 or using the development branch.