예제 #1
0
        public static void RegisterProxyConverter <T>(this IJSValueConverterService service, Action <JSValueBinding, T, IServiceNode> createBinding) where T : class
        {
            toJSValueDelegate <T> tojs = (IServiceNode node, T value) =>
            {
                return(node.GetService <IContextSwitchService>().With(() =>
                {
                    var result = JavaScriptValue.CreateExternalObject(IntPtr.Zero, null);
                    JSValueBinding binding = new JSValueBinding(node, result);
                    var handle = node.GetService <IGCSyncService>().SyncWithJsValue(value, result);
                    result.ExternalData = GCHandle.ToIntPtr(handle);//save the object reference to javascript values's external data
                    createBinding?.Invoke(binding, value, node);
                    return result;
                }));
            };
            fromJSValueDelegate <T> fromjs = (IServiceNode node, JavaScriptValue value) =>
            {
                if (value.HasExternalData)
                {
                    GCHandle handle = GCHandle.FromIntPtr(value.ExternalData);
                    return(handle.Target as T);
                }
                else
                {
                    throw new ArgumentOutOfRangeException("Convert from jsValue to proxy object failed, jsValue does not have a linked CLR object");
                }
            };

            service.RegisterConverter <T>(tojs, fromjs);
        }
예제 #2
0
        public static void RegisterTask(this IJSValueConverterService target)
        {
            if (target.CanConvert <Task>())
            {
                return;
            }
            //register internal call back types
            target.RegisterMethodConverter <string>();
            target.RegisterFunctionConverter <JSValue>();
            target.RegisterMethodConverter <JavaScriptValue>();


            target.RegisterConverter <Task>(
                (node, value) =>
            {
                var jsValueService = node.GetService <IJSValueService>();
                var globalObject   = jsValueService.JSGlobalObject;
                var converter      = node.GetService <IJSValueConverterService>();
                var tmp            = node.WithContext(() =>
                {
                    JavaScriptValue.CreatePromise(out var result, out var resolve, out var reject);
                    return(Tuple.Create(result, resolve, reject));
                });
                //start the task on new thread
                Task.Factory.StartNew(async() =>
                {
                    try
                    {
                        await value;
                        jsValueService.CallFunction(tmp.Item2, globalObject);
                    }
                    catch (PromiseRejectedException ex)
                    {
                        var message = converter.ToJSValue(ex.ToString());
                        jsValueService.CallFunction(tmp.Item3, globalObject, message);
                    }
                    catch (Exception)
                    {
                        throw;
                    }
                });
                //return the promise without wait task complete
                return(tmp.Item1);
            },

                (node, value) =>
            {
                //from a promise
                return(Task.Factory.FromAsync(

                           (callback, state) =>
                {
                    return BeginMethod(value, node, callback, state);
                }
                           , EndMethod, null
                           ));
            }, false
                );
        }
예제 #3
0
 private void registerTTexture(IJSValueConverterService converter)
 {
     converter.RegisterProxyConverter <TTexture>(
         (binding, obj, node) =>
     {
         binding.SetFunction <SizeF>(nameof(obj.GetSize), () => obj.GetSize);
     });
 }
예제 #4
0
 private void registerTDrawingSurface(IJSValueConverterService converter)
 {
     converter.RegisterProxyConverter <TDrawingSurface>(
         (binding, obj, node) =>
     {
         binding.SetFunction(nameof(obj.CreateSpritBatch), obj.CreateSpritBatch);
     });
 }
예제 #5
0
 public static void RegisterMethodConverter <T1, T2, T3, T4>(this IJSValueConverterService service)
 {
     if (service.CanConvert <Action <T1, T2, T3, T4> >())
     {
         return;
     }
     service.RegisterConverter <Action <T1, T2, T3, T4> >(toJSMethod <T1, T2, T3, T4>, fromJSMethod <T1, T2, T3, T4>, false);
 }
예제 #6
0
 public virtual void TestInitialize()
 {
     runtime = ChakraRuntime.Create();
     LogAndPush("Runtime Created");
     context = runtime.CreateContext(true);
     LogAndPush("Context created");
     converter = context.ServiceNode.GetService <IJSValueConverterService>();
     SetupContext();
     Log("Context setup complete");
 }
예제 #7
0
 private static void registerProxy(IJSValueConverterService converter)
 {
     converter.RegisterProxyConverter <HostingProxy>(
         (binding, obj, node) =>
     {
         binding.SetFunction <string, string, Task <string> >("Dispatch", obj.Dispatch);
     }
         );
     converter.RegisterTask <HostingProxy>();
     converter.RegisterTask <string>();
 }
예제 #8
0
 //register direct call delegate and callback delegate
 public static void RegisterFunctionConverter <T1, T2, T3, TResult>(this IJSValueConverterService service)
 {
     if (!service.CanConvert <Func <bool, T1, T2, T3, TResult> >())
     {
         service.RegisterConverter <Func <bool, T1, T2, T3, TResult> >(toJSFunction <T1, T2, T3, TResult>, fromJSFunction <T1, T2, T3, TResult>, false);
     }
     if (!service.CanConvert <Func <T1, T2, T3, TResult> >())
     {
         service.RegisterConverter <Func <T1, T2, T3, TResult> >(toJSCallbackFunction <T1, T2, T3, TResult>, fromJSCallbackFunction <T1, T2, T3, TResult>, false);
     }
 }
예제 #9
0
        public static void RegisterTask <TResult>(this IJSValueConverterService target)
        {
            if (target.CanConvert <Task <TResult> >())
            {
                return;
            }
            //register internal call back types
            target.RegisterFunctionConverter <TResult>();
            target.RegisterMethodConverter <TResult>();
            target.RegisterMethodConverter <string>();
            target.RegisterFunctionConverter <JSValue>();
            target.RegisterMethodConverter <JavaScriptValue>();
            target.RegisterMethodConverter <Action <TResult>, Action <JavaScriptValue> >();


            target.RegisterConverter <Task <TResult> >(
                (node, value) =>
            {
                //convert resolve, reject
                Action <Action <TResult>, Action <JavaScriptValue> > promiseBody = async(resolve, reject) =>
                {
                    try
                    {
                        var result = await value;
                        resolve(result);
                    }
                    catch (PromiseRejectedException ex)
                    {
                        reject(ex.Error);
                    }
                    catch (Exception)
                    {
                        throw;
                    }
                };
                var jsValueService = node.GetService <IJSValueService>();
                var globalObject   = jsValueService.JSGlobalObject;
                var jsGlobalObject = new JSValue(node, globalObject);
                return(jsGlobalObject.CallFunction <Action <Action <TResult>, Action <JavaScriptValue> >, JavaScriptValue>("Promise", promiseBody, true));
            },
                (node, value) =>
            {
                //from a promise
                return(Task.Factory.FromAsync(

                           (callback, state) =>
                {
                    return BeginMethod <TResult>(value, node, callback, state);
                }
                           , EndMethod <TResult>, null
                           ));
            }, false
                );
        }
예제 #10
0
        public static void RegisterProxyConverter <T>(this IJSValueConverterService service, Action <JSValueBinding, T, IServiceNode> createBinding) where T : class
        {
            toJSValueDelegate <T> tojs = (IServiceNode node, T value) =>
            {
                var mapService = node.GetService <IProxyMapService>();
                return(mapService.Map <T>(value, createBinding));
            };
            fromJSValueDelegate <T> fromjs = (IServiceNode node, JavaScriptValue value) =>
            {
                var mapService = node.GetService <IProxyMapService>();
                return(mapService.Get <T>(value));
            };

            service.RegisterConverter <T>(tojs, fromjs);
        }
예제 #11
0
        private static void InjectDictionaryConverter(IJSValueConverterService service)
        {
            service.RegisterArrayConverter <string>();

            service.RegisterProxyConverter <IDictionary <string, string> >(
                (binding, dict, node) =>
            {
                DictionaryWrapper wrapper = new DictionaryWrapper(dict);
                binding.SetFunction <IEnumerable <string> >("GetKeys", wrapper.GetKeys);
                binding.SetMethod <string, string>("SetItem", wrapper.SetItem);
                binding.SetFunction <string, string>("GetItem", wrapper.GetItem);
                binding.SetFunction <string, bool>("ContainsKey", wrapper.ContainsKey);
            }

                );
        }
예제 #12
0
 private void registerFont(IJSValueConverterService converter)
 {
     converter.RegisterStructConverter <Font>(
         (jsvalue, obj) =>
     {
         jsvalue.WriteProperty <string>(nameof(obj.Name), obj.Name);
         jsvalue.WriteProperty <float>(nameof(obj.Size), obj.Size);
     },
         (jsvalue) =>
     {
         return(new Font()
         {
             Name = jsvalue.ReadProperty <string>(nameof(Font.Name)),
             Size = jsvalue.ReadProperty <float>(nameof(Font.Size))
         });
     });
 }
예제 #13
0
 public static void RegisterStructConverter <T>(this IJSValueConverterService service, Action <JSValue, T> toJSValue, Func <JSValue, T> fromJSValue) //where T:struct
 {
     service.RegisterConverter <T>(
         (node, value) =>
     {
         JavaScriptValue jsObj = node.GetService <IJSValueService>().CreateObject();
         JSValue v             = new JSValue(node, jsObj);
         toJSValue(v, value);
         return(jsObj);
     },
         (node, value) =>
     {
         JSValue v = new JSValue(node, value);
         return(fromJSValue(v));
     }
         );
 }
예제 #14
0
        public static void RegisterArrayConverter <T>(this IJSValueConverterService service)
        {
            toJSValueDelegate <IEnumerable <T> > tojs = (node, value) =>
            {
                return(node.WithContext <JavaScriptValue>(() =>
                {
                    var result = node.GetService <IJSValueService>().CreateArray(Convert.ToUInt32(value.Count()));
                    int index = 0;
                    foreach (T item in value)
                    {
                        result.SetIndexedProperty(service.ToJSValue <int>(index++), service.ToJSValue <T>(item));
                    }
                    return result;
                }
                                                          ));
            };
            fromJSValueDelegate <IEnumerable <T> > fromjs = (node, value) =>
            {
                return(node.WithContext <IEnumerable <T> >(() =>
                {
                    var jsValueService = node.GetService <IJSValueService>();
                    var length = service.FromJSValue <int>(value.GetProperty(JavaScriptPropertyId.FromString("length")));
                    List <T> result = new List <T>(length);//copy the data to avoid context switch in user code
                    for (int i = 0; i < length; i++)
                    {
                        result.Add(
                            service.FromJSValue <T>(value.GetIndexedProperty(
                                                        service.ToJSValue <int>(i))
                                                    )
                            );
                    }
                    return result;
                }
                                                           ));
            };

            service.RegisterConverter <IEnumerable <T> >(tojs, fromjs, false);
        }
예제 #15
0
 private void registerTSprintBatch(IJSValueConverterService converter)
 {
     converter.RegisterProxyConverter <TSpritBatch>(
         (binding, obj, node) =>
     {
         binding.SetMethod <PointF, string, Font, string, int>(nameof(obj.DrawText), obj.DrawText);
         binding.SetMethod <IEnumerable <PointF>, string, int>(nameof(obj.DrawLines), obj.DrawLines);
         binding.SetMethod <PointF, SizeF, string, int, bool>(nameof(obj.DrawEclipse), obj.DrawEclipse);
         binding.SetMethod <PointF, SizeF, TTexture, float>(nameof(obj.DrawImage), obj.DrawImage);
         binding.SetMethod <string, RectangleF>(nameof(obj.Fill), obj.Fill);
         binding.SetMethod <RectangleF, string, int, bool>(nameof(obj.DrawRectangle), obj.DrawRectangle);
         binding.SetMethod <PointF, PointF, PointF, string, int, bool>(nameof(obj.DrawTriangle), obj.DrawTriangle);
         binding.SetMethod <PointF>(nameof(obj.Translate), obj.Translate);
         binding.SetMethod <PointF>(nameof(obj.Scale), obj.Scale);
         binding.SetMethod <float>(nameof(obj.Rotate), obj.Rotate);
         binding.SetFunction <int>(nameof(obj.PushMatrix), obj.PushMatrix);
         binding.SetFunction <int>(nameof(obj.PopMatrix), obj.PopMatrix);
         binding.SetMethod(nameof(obj.ResetMatrix), obj.ResetMatrix);
         binding.SetMethod <BlendModeEnum, Effect>(nameof(obj.Begin), obj.Begin);
         binding.SetMethod(nameof(obj.End), obj.End);
     }
         );
 }
예제 #16
0
 protected void RegisterCustomValueConverter(IJSValueConverterService converterService)
 {
 }
예제 #17
0
        private void registerBasicTypes(IJSValueConverterService converter)
        {
            converter.RegisterStructConverter <PointF>(
                (jsvalue, value) =>
            {
                jsvalue.WriteProperty("X", value.X);
                jsvalue.WriteProperty("Y", value.Y);
            },
                (jsvalue) =>
            {
                return(new PointF(
                           jsvalue.ReadProperty <float>("X")
                           , jsvalue.ReadProperty <float>("Y")));
            });

            converter.RegisterStructConverter <SizeF>(
                (jsvalue, value) =>
            {
                jsvalue.WriteProperty("Width", value.Width);
                jsvalue.WriteProperty("Height", value.Height);
            },
                (jsvalue) =>
            {
                return(new SizeF(
                           jsvalue.ReadProperty <float>("Width")
                           , jsvalue.ReadProperty <float>("Height")));
            });
            converter.RegisterStructConverter <RectangleF>(
                (jsvalue, value) =>
            {
                jsvalue.WriteProperty("X", value.X);
                jsvalue.WriteProperty("Y", value.Y);
                jsvalue.WriteProperty("Width", value.Width);
                jsvalue.WriteProperty("Height", value.Height);
            },
                (jsvalue) =>
            {
                return(new RectangleF(
                           jsvalue.ReadProperty <float>("X")
                           , jsvalue.ReadProperty <float>("Y")
                           , jsvalue.ReadProperty <float>("Width")
                           , jsvalue.ReadProperty <float>("Height")));
            });
            converter.RegisterArrayConverter <PointF>();

            converter.RegisterConverter <BlendModeEnum>(
                (node, value) =>
            {
                return(node.GetService <IContextSwitchService>().With(() =>
                {
                    return API.JavaScriptValue.FromInt32((int)value);
                }));
            },
                (node, jsvalue) =>
            {
                return(node.GetService <IContextSwitchService>().With(() =>
                {
                    return (BlendModeEnum)jsvalue.ToInt32();
                }));
            }


                );
            converter.RegisterStructConverter <Effect>(
                (jsvalue, value) =>
            {
                jsvalue.WriteProperty <string>(nameof(value.Name), value.Name);
                jsvalue.WriteProperty <string>(nameof(value.ConfigJson), value.ConfigJson);
            },
                (jsvalue) =>
            {
                return(new Effect()
                {
                    Name = jsvalue.ReadProperty <string>(nameof(Effect.Name)),
                    ConfigJson = jsvalue.ReadProperty <string>(nameof(Effect.ConfigJson))
                });
            }

                );
        }