on master help sign in
Add support for using JavaScriptFFI. Make JMacro support optional. Use new Gtk3 packages when building with webkit support.
commit3538e29f5ca3ee6ccbea67ffd9f1e29bd761f95f authorHamish Mackenzie <Hamish.K.Mackenzie@googlemail.com> dateMon 22 Jul 2013, 10:03 (13 years ago) parentf0c963a
13 files changed+451−58
jsc.cabal+56−14 src/Language/Javascript/JSC.hs+5 src/Language/Javascript/JSC/Classes.hs+1−1 src/Language/Javascript/JSC/Evaluate.hs+25−4 src/Language/Javascript/JSC/Exception.hs+1−1 src/Language/Javascript/JSC/Monad.hs+39−7 src/Language/Javascript/JSC/Object.hs+113−12 src/Language/Javascript/JSC/PropRef.hs+4−4 src/Language/Javascript/JSC/Properties.hs+49−5 src/Language/Javascript/JSC/String.hs+16−3 src/Language/Javascript/JSC/Types.hs+53 src/Language/Javascript/JSC/Value.hs+86−5 tests/TestJSC.hs+3−2
jsc.cabal+56−14
@@ -15,20 +15,46 @@ flag gtk3
1515 Description: Use GTK3 rather than GTK2
1616 Default: True
1717
18+flag jsffi
19+ description: Use JavaScriptFFI extension for GHCJS JavaScript output
20+ default: True
21+
22+flag webkit
23+ description: Use WebKitGtk and JavaScriptCore for GHCJS output
24+ default: False
25+
26+flag jmacro
27+ description: Include some JMacro support
28+ default: False
29+
1830library
19− if flag(gtk3)
20− build-depends: webkit3-javascriptcore >=0.0.0.999 && <0.1, webkit3 -any
21− else
22− build-depends: webkit-javascriptcore >=0.0.0.999 && <0.1, webkit -any
31+ if impl(ghcjs) && flag(jsffi)
32+ cpp-options: -DUSE_JAVASCRIPTFFI
33+ build-depends: ghcjs-base
34+
35+ if !impl(ghcjs) || flag(webkit)
36+ cpp-options: -DUSE_WEBKIT
37+ if flag(gtk3)
38+ build-depends: webkit3 >=0.12.5 && <0.13,
39+ webkit3-javascriptcore >=0.0.0.999 && <0.1
40+ else
41+ build-depends: webkit >=0.12.5 && <0.13,
42+ webkit-javascriptcore >=0.0.0.999 && <0.1
43+
44+ if flag(jmacro)
45+ exposed-modules: Language.Javascript.JSC.JMacro
46+ build-depends: jmacro >=0.6.3 && <0.7
47+
2348 build-depends: template-haskell -any, base -any, lens >=3.8.5 && <3.11,
24− text >=0.11.2.3 && <0.12, transformers >=0.3.0.0 && <0.4,
25− jmacro >=0.6.3 && <0.7
49+ text >=0.11.2.3 && <0.12, transformers >=0.3.0.0 && <0.4
50+
2651 exposed-modules: Language.Javascript.JSC
2752 Language.Javascript.JSC.Arguments Language.Javascript.JSC.Classes
2853 Language.Javascript.JSC.Evaluate Language.Javascript.JSC.Exception
29− Language.Javascript.JSC.JMacro Language.Javascript.JSC.Monad
54+ Language.Javascript.JSC.Monad
3055 Language.Javascript.JSC.Object Language.Javascript.JSC.Properties
3156 Language.Javascript.JSC.String Language.Javascript.JSC.Value
57+ Language.Javascript.JSC.Types
3258 exposed: True
3359 buildable: True
3460 default-language: Haskell2010
@@ -36,16 +62,32 @@ library
3662 other-modules: Language.Javascript.JSC.PropRef
3763
3864test-suite test-tool
39− if flag(gtk3)
40− build-depends: webkit3-javascriptcore >=0.0.0.999 && <0.1, webkit3 -any
41− else
42− build-depends: webkit-javascriptcore >=0.0.0.999 && <0.1, webkit -any
65+ if flag(jsffi)
66+ buildable: False
67+
68+ if impl(ghcjs) && flag(jsffi)
69+ cpp-options: -DUSE_JAVASCRIPTFFI
70+ build-depends: ghcjs-base
71+
72+ if !impl(ghcjs) || flag(webkit)
73+ cpp-options: -DUSE_WEBKIT
74+ build-depends: glib >=0.12.3.1 && <0.13
75+ if flag(gtk3)
76+ build-depends: gtk3 >= 0.12.4.1 && <0.13,
77+ webkit3 >=0.12.5 && <0.13,
78+ webkit3-javascriptcore >=0.0.0.999 && <0.1
79+ else
80+ build-depends: gtk >= 0.12.4.1 && <0.13,
81+ webkit >=0.12.5 && <0.13,
82+ webkit-javascriptcore >=0.0.0.999 && <0.1
83+
84+ if flag(jmacro)
85+ build-depends: jmacro >=0.6.3 && <0.7
86+
4387 build-depends: template-haskell -any, base -any, lens >=3.8.5 && <3.11,
4488 text >=0.11.2.3 && <0.12, transformers >=0.3.0.0 && <0.4,
45− jmacro >=0.6.3 && <0.7,
46− hslogger -any, glib -any, gtk -any, jsc ==0.1.1.0
89+ hslogger -any, jsc ==0.1.1.0
4790 type: exitcode-stdio-1.0
4891 main-is: TestJSC.hs
49− buildable: True
5092 default-language: Haskell2010
5193 hs-source-dirs: tests
src/Language/Javascript/JSC.hs+5
@@ -1,3 +1,4 @@
1+{-# LANGUAGE CPP #-}
12-----------------------------------------------------------------------------
23--
34-- Module : Language.Javascript.JSC
@@ -61,7 +62,9 @@ module Language.Javascript.JSC (
6162 , module Language.Javascript.JSC.Properties
6263 , module Language.Javascript.JSC.Object
6364 , module Language.Javascript.JSC.Evaluate
65+#ifdef MIN_VERSION_jmacro
6466 , module Language.Javascript.JSC.JMacro
67+#endif
6568 , module Language.Javascript.JSC.String
6669) where
6770
@@ -72,5 +75,7 @@ import Language.Javascript.JSC.Arguments
7275import Language.Javascript.JSC.Properties
7376import Language.Javascript.JSC.Object
7477import Language.Javascript.JSC.Evaluate
78+#ifdef MIN_VERSION_jmacro
7579import Language.Javascript.JSC.JMacro
80+#endif
7681import Language.Javascript.JSC.String
src/Language/Javascript/JSC/Classes.hs+1−1
@@ -22,7 +22,7 @@ module Language.Javascript.JSC.Classes (
2222) where
2323
2424import Control.Monad.IO.Class (MonadIO)
25−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
25+import Language.Javascript.JSC.Types
2626 (JSObjectRef, JSStringRef, JSValueRef)
2727import Language.Javascript.JSC.Monad (JSC)
2828import Language.Javascript.JSC.PropRef (JSPropRef)
src/Language/Javascript/JSC/Evaluate.hs+25−4
@@ -1,3 +1,7 @@
1+{-# LANGUAGE CPP #-}
2+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
3+{-# LANGUAGE ForeignFunctionInterface, JavaScriptFFI #-}
4+#endif
15-----------------------------------------------------------------------------
26--
37-- Module : Language.Javascript.JSC.Evaluate
@@ -18,10 +22,16 @@ module Language.Javascript.JSC.Evaluate (
1822
1923import Control.Monad.Trans.Reader (ask)
2024import Control.Monad.IO.Class (MonadIO(..))
21−import Foreign (nullPtr)
22−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
23− (JSStringRef, JSValueRef, JSObjectRef, jsevaluatescript,
25+import Language.Javascript.JSC.Types
26+ (JSStringRef, JSValueRef, JSObjectRef,
2427 JSValueRefRef)
28+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
29+import GHCJS.Types (nullRef)
30+#else
31+import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
32+ (jsevaluatescript)
33+import Foreign (nullPtr)
34+#endif
2535import Language.Javascript.JSC.Exception (rethrow)
2636import Language.Javascript.JSC.Value ()
2737import Language.Javascript.JSC.Object ()
@@ -41,10 +51,18 @@ evaluateScript :: (MakeStringRef script, MakeObjectRef this, MakeStringRef url)
4151 -> url
4252 -> Int -- ^ The Line number of the first line of the script
4353 -> JSC JSValueRef
54+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
55+evaluateScript script this url line = liftIO $ js_eval (makeStringRef script)
56+foreign import javascript unsafe "$r = eval(s);"
57+ js_eval :: JSStringRef -> IO JSValueRef
58+#elif defined(USE_WEBKIT)
4459evaluateScript script this url line = do
4560 gctxt <- ask
4661 thisr <- makeObjectRef this
4762 rethrow $ liftIO . jsevaluatescript gctxt (makeStringRef script) thisr (makeStringRef url) line
63+#else
64+evaluateScript = undefined
65+#endif
4866
4967-- | Evaluates a script (like eval in java script)
5068--
@@ -53,6 +71,9 @@ evaluateScript script this url line = do
5371eval :: MakeStringRef script
5472 => script -- ^ JavaScript to evaluate
5573 -> JSC JSValueRef
74+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
75+eval script = evaluateScript script (nullRef::JSObjectRef) (nullRef::JSStringRef) 1
76+#else
5677eval script = evaluateScript script (nullPtr::JSObjectRef) (nullPtr::JSStringRef) 1
57−
78+#endif
5879
src/Language/Javascript/JSC/Exception.hs+1−1
@@ -17,7 +17,7 @@ module Language.Javascript.JSC.Exception (
1717) where
1818
1919import qualified Control.Exception as E (throwIO, Exception)
20−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
20+import Language.Javascript.JSC.Types
2121 (JSValueRefRef, JSValueRef)
2222import Data.Typeable (Typeable)
2323import Language.Javascript.JSC.Monad (catchval, JSC)
src/Language/Javascript/JSC/Monad.hs+39−7
@@ -1,3 +1,4 @@
1+{-# LANGUAGE CPP #-}
12-----------------------------------------------------------------------------
23--
34-- Module : Language.Javascript.JSC.Monad
@@ -15,6 +16,9 @@ module Language.Javascript.JSC.Monad (
1516 JSC(..)
1617 , JSContextRef
1718
19+ -- * Running JSC given a DOM Window
20+ , runJSC
21+
1822 -- * Exception Handling
1923 , catchval
2024 , catch
@@ -22,11 +26,22 @@ module Language.Javascript.JSC.Monad (
2226
2327import Prelude hiding (catch)
2428import Control.Monad.Trans.Reader (runReaderT, ask, ReaderT(..))
25−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
29+import Language.Javascript.JSC.Types
2630 (JSValueRefRef, JSValueRef, JSContextRef)
2731import Control.Monad.IO.Class (MonadIO(..))
32+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
33+import GHCJS.Types (isUndefined, isNull)
34+import GHCJS.Foreign (newArray, indexArray)
35+#else
2836import Foreign (nullPtr, alloca)
2937import Foreign.Storable (Storable(..))
38+import Graphics.UI.Gtk.WebKit.Types
39+ (WebView(..))
40+import Graphics.UI.Gtk.WebKit.WebView
41+ (webViewGetMainFrame)
42+import Graphics.UI.Gtk.WebKit.JavaScriptCore.WebFrame
43+ (webFrameGetGlobalContext)
44+#endif
3045import qualified Control.Exception as E (Exception, catch)
3146
3247-- | The @JSC@ monad keeps track of the JavaScript context.
@@ -53,13 +68,30 @@ t `catch` c = do
5368-- to throw exceptions.
5469catchval :: (JSValueRefRef -> JSC a) -> (JSValueRef -> JSC a) -> JSC a
5570catchval f catcher = do
56− gctxt <- ask
57− liftIO . alloca $ \pexc -> flip runReaderT gctxt $ do
58− liftIO $ poke pexc nullPtr
71+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
72+ pexc <- liftIO $ newArray
5973 result <- f pexc
60− exc <- liftIO $ peek pexc
61− if exc == nullPtr
74+ exc <- liftIO $ indexArray 0 pexc
75+ if isUndefined exc || isNull exc
6276 then return result
6377 else catcher exc
78+#else
79+ gctxt <- ask
80+ liftIO . alloca $ \pexc -> flip runReaderT gctxt $ do
81+ liftIO $ poke pexc nullPtr
82+ result <- f pexc
83+ exc <- liftIO $ peek pexc
84+ if exc == nullPtr
85+ then return result
86+ else catcher exc
87+#endif
6488
65−
89+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
90+runJSC :: w -> JSC a -> IO a
91+runJSC _ f = runReaderT f ()
92+#else
93+runJSC :: WebView -> JSC a -> IO a
94+runJSC webView f = do
95+ gctxt <- webViewGetMainFrame webView >>= webFrameGetGlobalContext
96+ runReaderT f gctxt
97+#endif
src/Language/Javascript/JSC/Object.hs+113−12
@@ -1,8 +1,12 @@
1−{-# LANGUAGE ForeignFunctionInterface #-}
1+{-# LANGUAGE CPP #-}
22{-# LANGUAGE FlexibleInstances #-}
33{-# LANGUAGE TypeSynonymInstances #-}
44{-# LANGUAGE ScopedTypeVariables #-}
55{-# LANGUAGE Rank2Types #-}
6+{-# LANGUAGE ForeignFunctionInterface #-}
7+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
8+{-# LANGUAGE JavaScriptFFI #-}
9+#endif
610-----------------------------------------------------------------------------
711--
812-- Module : Language.Javascript.JSC.Object
@@ -63,7 +67,6 @@ module Language.Javascript.JSC.Object (
6367 , global
6468
6569 -- * Enumerating Properties
66− , copyPropertyNames
6770 , propertyNames
6871
6972 -- * Low level
@@ -72,10 +75,16 @@ module Language.Javascript.JSC.Object (
7275) where
7376
7477import Prelude hiding ((!!))
75−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
78+import Language.Javascript.JSC.Types
7679 (JSPropertyNameArrayRef, JSStringRef, JSObjectRef, JSValueRefRef,
77− JSValueRef, JSContextRef)
78−import Foreign.C (CSize(..), CUInt(..), CULong(..))
80+ JSValueRef, JSContextRef, Index)
81+import Foreign.C (CSize(..), CUInt(..))
82+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
83+import GHCJS.Types (nullRef, castRef, JSArray, JSFun)
84+import GHCJS.Foreign (newObj, toArray, fromArray, syncCallback2)
85+import Control.Monad (liftM)
86+import Control.Applicative ((<$>))
87+#else
7988import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSObjectRef
8089 (jsobjectmake, jspropertynamearraygetnameatindex,
8190 jspropertynamearraygetcount, jsobjectcopypropertynames,
@@ -84,6 +93,12 @@ import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSObjectRef
8493 jsobjectcallasfunction, jsobjectgetproperty, jsobjectsetproperty,
8594 JSPropertyAttributes, JSObjectCallAsFunctionCallback,
8695 jsobjectmakefunctionwithcallback)
96+import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSValueRef
97+ (jsvaluemakeundefined)
98+import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSContextRef
99+ (jscontextgetglobalobject)
100+import Foreign (peekArray, nullPtr, withArrayLen)
101+#endif
87102import Language.Javascript.JSC.Exception (rethrow)
88103import Language.Javascript.JSC.Value
89104 (JSUndefined, valMakeUndefined, valToObject)
@@ -95,15 +110,10 @@ import Language.Javascript.JSC.Monad
95110 (JSC)
96111import Control.Monad.Trans.Reader (runReaderT, ask)
97112import Control.Monad.IO.Class (MonadIO(..))
98−import Foreign (peekArray, nullPtr, withArrayLen)
99113import qualified Control.Exception as E (catch)
100114import Control.Exception (SomeException)
101115import qualified Data.Text as T (pack)
102116import Foreign.Storable (Storable(..))
103−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSValueRef
104− (jsvaluemakeundefined)
105−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSContextRef
106− (jscontextgetglobalobject)
107117import Language.Javascript.JSC.Properties
108118import Control.Lens
109119 (IndexPreservingGetter, to, (^.))
@@ -144,7 +154,7 @@ this ! name = do
144154-- W
145155(!!) :: (MakeObjectRef this)
146156 => this -- ^ Object to look on
147− -> CUInt -- ^ Index of the property to lookup
157+ -> Index -- ^ Index of the property to lookup
148158 -> JSC JSPropRef -- ^ Property reference
149159this !! index = do
150160 rthis <- makeObjectRef this
@@ -282,15 +292,19 @@ call function this args = do
282292-- >>> testJSC $ do { a <- obj; a ^. js "x" <# "Hello"; a ^. js "x" }
283293-- Hello
284294obj :: JSC JSObjectRef
295+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
296+obj = liftIO $ newObj
297+#else
285298obj = do
286299 gctxt <- ask
287300 liftIO $ jsobjectmake gctxt nullPtr nullPtr
301+#endif
288302
289303type JSObjectCallAsFunctionCallback' =
290304 JSContextRef
291305 -> JSValueRef
292306 -> JSValueRef
293− -> CULong
307+ -> CUInt
294308 -> JSValueRefRef
295309 -> JSValueRefRef
296310 -> IO JSValueRef
@@ -315,8 +329,10 @@ type JSCallAsFunction = JSValueRef -- ^ Function object
315329fun :: JSCallAsFunction -> JSCallAsFunction
316330fun = id
317331
332+#if (!defined(__GHCJS__) || !defined(USE_JAVASCRIPTFFI)) && defined(USE_WEBKIT)
318333foreign import ccall "wrapper"
319334 mkJSObjectCallAsFunctionCallback :: JSObjectCallAsFunctionCallback' -> IO JSObjectCallAsFunctionCallback
335+#endif
320336
321337-- ^ Make a JavaScript function object that wraps a Haskell function.
322338function :: MakeStringRef name
@@ -324,6 +340,15 @@ function :: MakeStringRef name
324340 -> JSCallAsFunction -- ^ Haskell function to call
325341 -> JSC JSObjectRef -- ^ Returns a JavaScript function object that will
326342 -- call the Haskell one when it is called
343+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
344+function name f = liftIO $ do
345+ callback <- syncCallback2 False True $ \this args -> do
346+ rargs <- fromArray args
347+ runReaderT (f this this rargs) () -- TODO pass function object through
348+ makeFunctionWithCallback (makeStringRef name) callback
349+foreign import javascript unsafe "$r = function () { $2(this, arguments); }"
350+ makeFunctionWithCallback :: JSStringRef -> JSFun (JSValueRef -> JSValueRefRef -> IO ()) -> IO JSObjectRef
351+#elif defined(USE_WEBKIT)
327352function name f = do
328353 gctxt <- ask
329354 callback <- liftIO $ mkJSObjectCallAsFunctionCallback wrap
@@ -337,24 +362,39 @@ function name f = do
337362 str <- runReaderT (makeValueRef . T.pack $ show e) ctx
338363 poke exception str
339364 jsvaluemakeundefined ctx
365+#else
366+function = undefined
367+#endif
340368
341369-- | A callback to Haskell can be used as a JavaScript value. This will create
342370-- an anonymous JavaScript function object. Use 'function' to create one with
343371-- a name.
344372instance MakeValueRef JSCallAsFunction where
373+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
374+ makeValueRef = function (nullRef::JSStringRef)
375+#else
345376 makeValueRef = function (nullPtr::JSStringRef)
377+#endif
346378
347379instance MakeArgRefs JSCallAsFunction where
348380 makeArgRefs f = do
381+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
382+ rarg <- function (nullRef::JSStringRef) f
383+#else
349384 rarg <- function (nullPtr::JSStringRef) f
385+#endif
350386 return [rarg]
351387
352388makeArray :: MakeArgRefs args => args -> JSValueRefRef -> JSC JSObjectRef
389+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
390+makeArray args exceptions = makeArgRefs args >>= liftM castRef . liftIO . toArray
391+#else
353392makeArray args exceptions = do
354393 gctxt <- ask
355394 rargs <- makeArgRefs args
356395 liftIO $ withArrayLen rargs $ \ len ptr ->
357396 jsobjectmakearray gctxt (fromIntegral len) ptr exceptions
397+#endif
358398
359399-- | Make an JavaScript array from a list of values
360400--
@@ -369,9 +409,18 @@ array = rethrow . makeArray
369409
370410-- | JavaScript's global object
371411global :: JSC JSObjectRef
412+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
413+global = liftIO js_window
414+foreign import javascript unsafe "$r = window"
415+ js_window :: IO JSObjectRef
416+#elif defined(USE_WEBKIT)
372417global = ask >>= (liftIO . jscontextgetglobalobject)
418+#else
419+global = undefined
420+#endif
373421
374422-- | Get an array containing the property names present on a given object
423+#if (!defined(__GHCJS__) || !defined(USE_JAVASCRIPTFFI)) && defined(USE_WEBKIT)
375424copyPropertyNames :: MakeObjectRef this => this -> JSC JSPropertyNameArrayRef
376425copyPropertyNames this = do
377426 gctxt <- ask
@@ -391,10 +440,19 @@ propertyNamesList :: MonadIO m => JSPropertyNameArrayRef -> m [JSStringRef]
391440propertyNamesList names = do
392441 count <- propertyNamesCount names
393442 mapM (propertyNamesAt names) $ enumFromTo 0 (count - 1)
443+#endif
394444
395445-- | Get a list containing the property names present on a given object
396446propertyNames :: MakeObjectRef this => this -> JSC [JSStringRef]
447+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
448+propertyNames this = makeObjectRef this >>= liftIO . js_propertyNames >>= liftIO . fromArray
449+foreign import javascript unsafe "$r = []; h$forIn($1, function(n){$r.push(n);})"
450+ js_propertyNames :: JSObjectRef -> IO (JSArray a)
451+#elif defined(USE_WEBKIT)
397452propertyNames this = copyPropertyNames this >>= propertyNamesList
453+#else
454+propertyNames = undefined
455+#endif
398456
399457-- | Get a list containing references to all the properties present on a given object
400458properties :: MakeObjectRef this => this -> JSC [JSPropRef]
@@ -407,11 +465,21 @@ objCallAsFunction :: MakeArgRefs args
407465 -> args
408466 -> JSValueRefRef
409467 -> JSC JSValueRef
468+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
469+objCallAsFunction function this args exceptions = do
470+ rargs <- makeArgRefs args >>= liftIO . toArray
471+ liftIO $ js_apply function this rargs exceptions
472+foreign import javascript unsafe "try { $r = $1.apply($2, $3) } catch(e) { $4[0] = e }"
473+ js_apply :: JSObjectRef -> JSObjectRef -> JSValueRefRef -> JSValueRefRef -> IO JSValueRef
474+#elif defined(USE_WEBKIT)
410475objCallAsFunction function this args exceptions = do
411476 gctxt <- ask
412477 rargs <- makeArgRefs args
413478 liftIO $ withArrayLen rargs $ \ largs pargs ->
414479 jsobjectcallasfunction gctxt function this (fromIntegral largs) pargs exceptions
480+#else
481+objCallAsFunction = undefined
482+#endif
415483
416484-- | Call a JavaScript object as a constructor. Consider using 'new'.
417485objCallAsConstructor :: MakeArgRefs args
@@ -419,11 +487,44 @@ objCallAsConstructor :: MakeArgRefs args
419487 -> args
420488 -> JSValueRefRef
421489 -> JSC JSValueRef
490+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
491+objCallAsConstructor function args exceptions = do
492+ rargs <- makeArgRefs args >>= liftIO . toArray
493+ liftIO $ js_new function rargs exceptions
494+foreign import javascript unsafe "\
495+ try {\
496+ switch($2.length) {\
497+ case 0 : $r = new $1();\
498+ case 1 : $r = new $1($2[0]);\
499+ case 2 : $r = new $1($2[0],$2[1]);\
500+ case 3 : $r = new $1($2[0],$2[1],$2[2]);\
501+ case 4 : $r = new $1($2[0],$2[1],$2[2],$2[3]);\
502+ case 5 : $r = new $1($2[0],$2[1],$2[2],$2[3],$2[4]);\
503+ case 6 : $r = new $1($2[0],$2[1],$2[2],$2[3],$2[4],$2[5]);\
504+ case 6 : $r = new $1($2[0],$2[1],$2[2],$2[3],$2[4],$2[5],$2[6]);\
505+ default:\
506+ var ret;\
507+ var temp = function() {\
508+ ret = $1.apply(this, $2);\
509+ };\
510+ temp.prototype = f.prototype;\
511+ var i = new temp();\
512+ $r = ret instanceof Object ? ret : i;\
513+ }\
514+ }\
515+ catch(e) {\
516+ $3[0] = e;\
517+ }"
518+ js_new :: JSObjectRef -> JSValueRefRef -> JSValueRefRef -> IO JSValueRef
519+#elif defined(USE_WEBKIT)
422520objCallAsConstructor function args exceptions = do
423521 gctxt <- ask
424522 rargs <- makeArgRefs args
425523 liftIO $ withArrayLen rargs $ \ largs pargs ->
426524 jsobjectcallasconstructor gctxt function (fromIntegral largs) pargs exceptions
525+#else
526+objCallAsConstructor = undefined
527+#endif
427528
428529
429530
src/Language/Javascript/JSC/PropRef.hs+4−4
@@ -13,13 +13,13 @@
1313module Language.Javascript.JSC.PropRef (
1414 JSPropRef(..)
1515) where
16−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
17− (JSStringRef, JSObjectRef)
18−import Foreign.C (CUInt)
16+
17+import Language.Javascript.JSC.Types
18+ (JSStringRef, JSObjectRef, Index)
1919
2020-- | A reference to a property.
2121-- Implemented as a reference to an object and something to find the property.
2222data JSPropRef = JSPropRef JSObjectRef JSStringRef -- ^ Object and property name.
23− | JSPropIndexRef JSObjectRef CUInt -- ^ Object and property index.
23+ | JSPropIndexRef JSObjectRef Index -- ^ Object and property index.
2424
2525
src/Language/Javascript/JSC/Properties.hs+49−5
@@ -1,5 +1,9 @@
1+{-# LANGUAGE CPP #-}
12{-# LANGUAGE FlexibleInstances #-}
23{-# LANGUAGE TypeSynonymInstances #-}
4+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
5+{-# LANGUAGE ForeignFunctionInterface, JavaScriptFFI #-}
6+#endif
37-----------------------------------------------------------------------------
48--
59-- Module : Language.Javascript.JSC.Properties
@@ -32,20 +36,24 @@ module Language.Javascript.JSC.Properties (
3236 , objSetProperty
3337) where
3438
39+import Control.Applicative ((<$>))
3540import Language.Javascript.JSC.PropRef (JSPropRef(..))
3641import Language.Javascript.JSC.Classes
3742 (MakePropRef(..), MakeObjectRef(..), MakeValueRef(..),
3843 MakeArgRefs(..), MakeStringRef(..))
3944import Language.Javascript.JSC.Monad (JSC)
40−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
41− (JSValueRefRef, JSObjectRef)
45+import Language.Javascript.JSC.Types
46+ (JSValueRefRef, JSObjectRef, JSPropertyAttributes,
47+ Index(..), JSStringRef)
48+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
49+#else
4250import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSObjectRef
4351 (jsobjectgetpropertyatindex, jsobjectgetproperty,
4452 jsobjectsetpropertyatindex, jsobjectsetproperty,
4553 JSPropertyAttributes)
54+#endif
4655import Control.Monad.Trans.Reader (ask)
4756import Control.Monad.IO.Class (MonadIO(..))
48−import Foreign.C (CUInt)
4957import Language.Javascript.JSC.Exception (rethrow)
5058import Language.Javascript.JSC.Value (JSValueRef)
5159import Language.Javascript.JSC.Arguments ()
@@ -80,18 +88,34 @@ objGetPropertyByName :: MakeStringRef name
8088 -> name -- ^ name of the property.
8189 -> JSValueRefRef -- ^ exception if one is raised.
8290 -> JSC JSValueRef -- ^ returns the property value.
91+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
92+objGetPropertyByName this name = liftIO . js_tryGetProp (makeStringRef name) this
93+foreign import javascript unsafe "try { $r=$2[$1] } catch(e) { $3[0] = e }"
94+ js_tryGetProp :: JSStringRef -> JSObjectRef -> JSValueRefRef -> IO JSValueRef
95+#elif defined(USE_WEBKIT)
8396objGetPropertyByName this name exceptions = do
8497 gctxt <- ask
8598 liftIO $ jsobjectgetproperty gctxt this (makeStringRef name) exceptions
99+#else
100+objGetPropertyByName = undefined
101+#endif
86102
87103-- | Get a property value given the object and the index of the property.
88104objGetPropertyAtIndex :: JSObjectRef -- ^ object to find the property on.
89− -> CUInt -- ^ index of the property.
105+ -> Index -- ^ index of the property.
90106 -> JSValueRefRef -- ^ exception if one is raised.
91107 -> JSC JSValueRef -- ^ returns the property value.
108+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
109+objGetPropertyAtIndex this index = liftIO . js_tryIndex index this
110+foreign import javascript unsafe "try { $r=$2[$1] } catch(e) { $3[0] = e }"
111+ js_tryIndex :: Index -> JSObjectRef -> JSValueRefRef -> IO JSValueRef
112+#elif defined(USE_WEBKIT)
92113objGetPropertyAtIndex this index exceptions = do
93114 gctxt <- ask
94115 liftIO $ jsobjectgetpropertyatindex gctxt this index exceptions
116+#else
117+objGetPropertyAtIndex = undefined
118+#endif
95119
96120-- | Gets the value of a property given a 'JSPropRef'.
97121objGetProperty :: JSPropRef -- ^ property reference.
@@ -121,22 +145,42 @@ objSetPropertyByName :: (MakeStringRef name, MakeValueRef val)
121145 -> JSPropertyAttributes -- ^ property attributes to give the property.
122146 -> JSValueRefRef -- ^ exception if one is raised.
123147 -> JSC ()
148+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
149+objSetPropertyByName this name val attributes exceptions = do
150+ vref <- makeValueRef val
151+ liftIO $ js_trySetProp (makeStringRef name) this vref exceptions
152+foreign import javascript unsafe "try { $2[$1]=$3 } catch(e) { $4[0] = e }"
153+ js_trySetProp :: JSStringRef -> JSObjectRef -> JSValueRef -> JSValueRefRef -> IO ()
154+#elif defined(USE_WEBKIT)
124155objSetPropertyByName this name val attributes exceptions = do
125156 gctxt <- ask
126157 vref <- makeValueRef val
127158 liftIO $ jsobjectsetproperty gctxt this (makeStringRef name) vref attributes exceptions
159+#else
160+objSetPropertyByName = undefined
161+#endif
128162
129163-- | Set a property value given the object and the index of the property.
130164objSetPropertyAtIndex :: (MakeValueRef val)
131165 => JSObjectRef -- ^ object to find property on.
132− -> CUInt -- ^ index of the property.
166+ -> Index -- ^ index of the property.
133167 -> val -- ^ new value to set the property to.
134168 -> JSValueRefRef -- ^ exception if one is raised.
135169 -> JSC ()
170+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
171+objSetPropertyAtIndex this index val exceptions = do
172+ vref <- makeValueRef val
173+ liftIO $ js_trySetAtIndex index this vref exceptions
174+foreign import javascript unsafe "try { $2[$1]=$3 } catch(e) { $4[0] = e }"
175+ js_trySetAtIndex :: Index -> JSObjectRef -> JSValueRef -> JSValueRefRef -> IO ()
176+#elif defined(USE_WEBKIT)
136177objSetPropertyAtIndex this index val exceptions = do
137178 gctxt <- ask
138179 vref <- makeValueRef val
139180 liftIO $ jsobjectsetpropertyatindex gctxt this index vref exceptions
181+#else
182+objSetPropertyAtIndex = undefined
183+#endif
140184
141185-- | Sets the value of a property given a 'JSPropRef'.
142186objSetProperty :: (MakeValueRef val)
src/Language/Javascript/JSC/String.hs+16−3
@@ -1,3 +1,4 @@
1+{-# LANGUAGE CPP #-}
12{-# LANGUAGE FlexibleInstances #-}
23{-# LANGUAGE TypeSynonymInstances #-}
34-----------------------------------------------------------------------------
@@ -24,13 +25,17 @@ module Language.Javascript.JSC.String (
2425import Data.Text (Text)
2526import qualified Data.Text as T (pack)
2627import Control.Monad.IO.Class (MonadIO(..))
28+import Language.Javascript.JSC.Types (JSStringRef)
29+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
30+import GHCJS.Foreign (fromJSString, toJSString)
31+#else
2732import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSStringRef
2833 (jsstringcreatewithcharacters, jsstringgetcharactersptr,
2934 jsstringgetlength)
35+#endif
3036import qualified Data.Text.Foreign as T (fromPtr)
3137import Foreign (castPtr)
3238import Data.Text.Foreign (useAsPtr)
33−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase (JSStringRef)
3439import Language.Javascript.JSC.Classes (MakeStringRef(..))
3540import System.IO.Unsafe (unsafePerformIO)
3641
@@ -46,16 +51,24 @@ instance MakeStringRef String where
4651
4752-- | Convert a JavaScript string to a Haskell 'Text'
4853strToText :: MonadIO m => JSStringRef -> m Text
54+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
55+strToText = return . fromJSString
56+#else
4957strToText jsstring = liftIO $ do
5058 l <- jsstringgetlength jsstring
5159 p <- jsstringgetcharactersptr jsstring
5260 T.fromPtr (castPtr p) (fromIntegral l)
61+#endif
5362
5463-- | Convert a Haskell 'Text' to a JavaScript string
5564textToStr :: Text -> JSStringRef
56−textToStr text =
57− unsafePerformIO $ useAsPtr text $ \p l ->
65+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
66+textToStr = toJSString
67+#else
68+textToStr text = unsafePerformIO $
69+ useAsPtr text $ \p l ->
5870 jsstringcreatewithcharacters (castPtr p) (fromIntegral l)
71+#endif
5972
6073
6174
src/Language/Javascript/JSC/Types.hsnew file+53
@@ -0,0 +1,53 @@
1+{-# LANGUAGE CPP, FlexibleInstances #-}
2+-----------------------------------------------------------------------------
3+--
4+-- Module : Language.Javascript.JSC.Properties
5+-- Copyright : (c) Hamish Mackenzie
6+-- License : MIT
7+--
8+-- Maintainer : Hamish Mackenzie <Hamish.K.Mackenzie@googlemail.com>
9+--
10+-- |
11+--
12+-----------------------------------------------------------------------------
13+
14+module Language.Javascript.JSC.Types (
15+ JSValueRef(..)
16+ , JSValueRefRef(..)
17+ , JSObjectRef(..)
18+ , JSPropertyNameArrayRef(..)
19+ , JSPropertyAttributes(..)
20+ , JSContextRef(..)
21+ , JSStringRef(..)
22+ , Index(..)
23+) where
24+
25+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
26+import GHCJS.Types
27+import Data.Word (Word(..))
28+#else
29+import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
30+ (JSValueRef, JSValueRefRef, JSObjectRef, JSStringRef,
31+ JSContextRef, JSPropertyNameArrayRef)
32+import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSObjectRef (JSPropertyAttributes)
33+import Foreign.C (CUInt(..))
34+#endif
35+
36+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
37+data ValueOrObject
38+data Object
39+data PropertyNameArray
40+type JSValueRef = JSRef ValueOrObject
41+type JSValueRefRef = JSArray ValueOrObject
42+type JSObjectRef = JSRef ValueOrObject
43+type JSPropertyNameArrayRef = JSRef PropertyNameArray
44+type JSPropertyAttributes = Word
45+type JSContextRef = ()
46+type JSStringRef = JSString
47+type Index = Int
48+
49+instance Show (JSRef ValueOrObject)
50+instance Eq (JSRef ValueOrObject)
51+#else
52+type Index = CUInt
53+#endif
src/Language/Javascript/JSC/Value.hs+86−5
@@ -1,5 +1,10 @@
1+{-# LANGUAGE CPP #-}
2+{-# LANGUAGE ScopedTypeVariables #-}
13{-# LANGUAGE FlexibleInstances #-}
24{-# LANGUAGE TypeSynonymInstances #-}
5+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
6+{-# LANGUAGE ForeignFunctionInterface, JavaScriptFFI #-}
7+#endif
38-----------------------------------------------------------------------------
49--
510-- Module : Language.Javascript.JSC.Value
@@ -59,12 +64,13 @@ module Language.Javascript.JSC.Value (
5964) where
6065
6166import Prelude hiding (catch)
62−import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSBase
67+import Language.Javascript.JSC.Types
6368 (JSValueRefRef, JSObjectRef, JSStringRef, JSValueRef)
64−import Language.Javascript.JSC.Monad (JSC, catchval)
65−import Language.Javascript.JSC.Exception (rethrow)
66−import Control.Monad.Trans.Reader (ask)
67−import Control.Monad.IO.Class (MonadIO, MonadIO(..))
69+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
70+import GHCJS.Types (castRef, JSRef(..))
71+import GHCJS.Foreign (toJSBool, fromJSBool', jsNull, jsUndefined, toJSString)
72+import GHCJS.Marshal (toJSRef)
73+#else
6874import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSValueRef
6975 (jsvaluecreatejsonstring, JSType(..), jsvaluegettype,
7076 jsvaluemakestring, jsvaluemakenumber, jsvaluemakeboolean,
@@ -73,6 +79,11 @@ import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSValueRef
7379import Graphics.UI.Gtk.WebKit.JavaScriptCore.JSStringRef
7480 (jsstringcreatewithcharacters, jsstringgetcharactersptr,
7581 jsstringgetlength)
82+#endif
83+import Language.Javascript.JSC.Monad (JSC, catchval)
84+import Language.Javascript.JSC.Exception (rethrow)
85+import Control.Monad.Trans.Reader (ask)
86+import Control.Monad.IO.Class (MonadIO, MonadIO(..))
7687import qualified Data.Text.Foreign as T (fromPtr)
7788import Foreign (castPtr)
7889import Data.Text.Foreign (useAsPtr)
@@ -125,10 +136,14 @@ data JSValue = ValNull -- ^ null
125136-- >>> testJSC $ valToBool "1"
126137-- true
127138valToBool :: MakeValueRef val => val -> JSC JSBool
139+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
140+valToBool val = fromJSBool' <$> makeValueRef val
141+#else
128142valToBool val = do
129143 gctxt <- ask
130144 rval <- makeValueRef val
131145 liftIO $ jsvaluetoboolean gctxt rval
146+#endif
132147
133148-- | Given a JavaScript value get its numeric value.
134149-- May throw JSException.
@@ -150,10 +165,17 @@ valToBool val = do
150165-- >>> testJSC $ show <$> valToNumber "1"
151166-- 1.0
152167valToNumber :: MakeValueRef val => val -> JSC JSNumber
168+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
169+valToNumber val = jsrefToNumber <$> makeValueRef val
170+foreign import javascript unsafe "$r = Number($1);" jsrefToNumber :: JSRef a -> Double
171+#elif defined(USE_WEBKIT)
153172valToNumber val = do
154173 gctxt <- ask
155174 rval <- makeValueRef val
156175 rethrow $ liftIO . jsvaluetonumber gctxt rval
176+#else
177+valToNumber = undefined
178+#endif
157179
158180-- | Given a JavaScript value get its string value (as a JavaScript string).
159181-- May throw JSException.
@@ -175,10 +197,17 @@ valToNumber val = do
175197-- >>> testJSC $ valToStr "1" >>= strToText
176198-- 1
177199valToStr :: MakeValueRef val => val -> JSC JSStringRef
200+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
201+valToStr val = jsrefToString <$> makeValueRef val
202+foreign import javascript unsafe "$r = $1.toString();" jsrefToString :: JSRef a -> JSStringRef
203+#elif defined(USE_WEBKIT)
178204valToStr val = do
179205 gctxt <- ask
180206 rval <- makeValueRef val
181207 rethrow $ liftIO . jsvaluetostringcopy gctxt rval
208+#else
209+valToStr = undefined
210+#endif
182211
183212-- | Given a JavaScript value get its string value (as a Haskell 'Text').
184213-- May throw JSException.
@@ -224,10 +253,17 @@ valToText jsvar = valToStr jsvar >>= strToText
224253-- >>> testJSC $ obj >>= valToJSON 0 >>= strToText
225254-- {}
226255valToJSON :: MakeValueRef val => Word -> val -> JSC JSStringRef
256+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
257+valToJSON indent val = jsrefToJSON <$> makeValueRef val
258+foreign import javascript unsafe "$r = JSON.stringify($1);" jsrefToJSON :: JSRef a -> JSStringRef
259+#elif defined(USE_WEBKIT)
227260valToJSON indent val = do
228261 gctxt <- ask
229262 rval <- makeValueRef val
230263 rethrow $ liftIO . jsvaluecreatejsonstring gctxt rval (fromIntegral indent)
264+#else
265+valToJSON = undefined
266+#endif
231267
232268-- | Given a JavaScript value get its object value.
233269-- May throw JSException.
@@ -249,10 +285,14 @@ valToJSON indent val = do
249285-- >>> testJSC $ valToObject "1"
250286-- 1
251287valToObject :: MakeValueRef val => val -> JSC JSObjectRef
288+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
289+valToObject val = castRef <$> makeValueRef val
290+#else
252291valToObject val = do
253292 gctxt <- ask
254293 rval <- makeValueRef val
255294 rethrow $ liftIO . jsvaluetoobject gctxt rval
295+#endif
256296
257297-- | Convert to a JavaScript value (just an alias for 'makeValueRef')
258298val :: MakeValueRef value
@@ -276,7 +316,11 @@ instance MakeValueRef v => MakeValueRef (JSC v) where
276316----------- null ---------------
277317-- | Make a @null@ JavaScript value
278318valMakeNull :: JSC JSValueRef
319+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
320+valMakeNull = return jsNull
321+#else
279322valMakeNull = ask >>= (liftIO . jsvaluemakenull)
323+#endif
280324
281325-- | Makes a @null@ JavaScript value
282326instance MakeValueRef JSNull where
@@ -289,7 +333,11 @@ instance MakeArgRefs JSNull where
289333----------- undefined ---------------
290334-- | Make an @undefined@ JavaScript value
291335valMakeUndefined :: JSC JSValueRef
336+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
337+valMakeUndefined = return jsUndefined
338+#else
292339valMakeUndefined = ask >>= (liftIO . jsvaluemakeundefined)
340+#endif
293341
294342-- | Makes an @undefined@ JavaScript value
295343instance MakeValueRef JSUndefined where
@@ -307,9 +355,13 @@ instance MakeArgRefs () where
307355----------- booleans ---------------
308356-- | Make a JavaScript boolean value
309357valMakeBool :: JSBool -> JSC JSValueRef
358+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
359+valMakeBool b = return . castRef $ toJSBool b
360+#else
310361valMakeBool b = do
311362 gctxt <- ask
312363 liftIO $ jsvaluemakeboolean gctxt b
364+#endif
313365
314366-- | Make a JavaScript boolean value
315367instance MakeValueRef Bool where
@@ -322,9 +374,13 @@ instance MakeArgRefs Bool where
322374----------- numbers ---------------
323375-- | Make a JavaScript number
324376valMakeNumber :: JSNumber -> JSC JSValueRef
377+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
378+valMakeNumber n = liftIO $ castRef <$> toJSRef n
379+#else
325380valMakeNumber n = do
326381 gctxt <- ask
327382 liftIO $ jsvaluemakenumber gctxt n
383+#endif
328384
329385-- | Makes a JavaScript number
330386instance MakeValueRef Double where
@@ -337,9 +393,13 @@ instance MakeArgRefs Double where
337393----------- numbers ---------------
338394-- | Make a JavaScript string
339395valMakeString :: Text -> JSC JSValueRef
396+#if (defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)) || !defined(USE_WEBKIT)
397+valMakeString = return . castRef . toJSString
398+#else
340399valMakeString text = do
341400 gctxt <- ask
342401 liftIO $ jsvaluemakestring gctxt (textToStr text)
402+#endif
343403
344404-- | Makes a JavaScript string
345405instance MakeValueRef Text where
@@ -374,6 +434,24 @@ instance MakeValueRef String where
374434-- >>> testJSC $ show <$> valToObject True >>= deRefVal
375435-- ValObject 0x...
376436deRefVal :: MakeValueRef val => val -> JSC JSValue
437+#if defined(__GHCJS__) && defined(USE_JAVASCRIPTFFI)
438+deRefVal val = do
439+ gctxt <- ask
440+ valref <- makeValueRef val
441+ case (jsrefGetType valref :: Int) of
442+ 0 -> return ValUndefined
443+ 1 -> return ValNull
444+ 2 -> ValBool <$> valToBool valref
445+ 3 -> ValNumber <$> valToNumber valref
446+ 4 -> ValString <$> (valToStr valref >>= strToText)
447+ 5 -> ValObject <$> valToObject valref
448+foreign import javascript unsafe "$r = ($1 === undefined)?0:\
449+ ($1===null)?1:\
450+ (typeof $1===\"boolean\")?2:\
451+ (typeof $1===\"number\")?3:\
452+ (typeof $1===\"string\")?4:\
453+ (typeof $1===\"object\")?5:-1;" jsrefGetType :: JSValueRef -> Int
454+#elif defined(USE_WEBKIT)
377455deRefVal val = do
378456 gctxt <- ask
379457 valref <- makeValueRef val
@@ -385,6 +463,9 @@ deRefVal val = do
385463 Kjstypenumber -> ValNumber <$> valToNumber valref
386464 Kjstypestring -> ValString <$> (valToStr valref >>= strToText)
387465 Kjstypeobject -> ValObject <$> valToObject valref
466+#else
467+deRefVal = undefined
468+#endif
388469
389470-- | Make a JavaScript value out of a 'JSValue' ADT.
390471--
tests/TestJSC.hs+3−2
@@ -18,7 +18,7 @@ module Main (
1818import Prelude hiding((!!), catch)
1919import Graphics.UI.Gtk
2020 (Window, widgetDestroy, postGUIAsync, postGUISync, widgetShowAll,
21− mainGUI, mainQuit, onDestroy, containerAdd, scrolledWindowNew,
21+ mainGUI, mainQuit, on, destroyEvent, containerAdd, scrolledWindowNew,
2222 windowSetPosition, windowSetDefaultSize, timeoutAddFull, windowNew,
2323 initGUI)
2424import Control.Concurrent
@@ -82,7 +82,7 @@ testJSC' showWindow f = do
8282 webView <- webViewNew
8383 window `containerAdd` scrollWin
8484 scrollWin `containerAdd` webView
85− window `onDestroy` do
85+ on window destroyEvent . liftIO $ do
8686 debugLog "onDestroy"
8787 tryTakeMVar state
8888 debugLog "put state"
@@ -91,6 +91,7 @@ testJSC' showWindow f = do
9191 mainQuit
9292 debugLog "put done"
9393 putMVar done ()
94+ return True
9495 debugLog "get context"
9596 jsContext <- webViewGetMainFrame webView >>= webFrameGetGlobalContext
9697 debugLog "put initial state"