/// <summary> /// For object constructed in JS, we need to create a C# representation and bind it to that /// object. For this, we'll use a <see cref="Dictionary{TKey,TValue}"/>. Possibly a later addition /// could use a custom serialization process and allow the user to control. /// </summary> private Dictionary <string, object> NewHostObject(JavaScriptValue arg) { // Create new Dictionary mapping to hold the properties, Create a new bindable JS object to replace // the existing one. Note: This could cause issues if these objects are used as keys. var d = new Dictionary <string, object>(); var replacement = _binder.BindObject(d); var propNames = (string[])ToHostArray(arg.GetOwnPropertyNames(), typeof(string[])); for (var i = 0; i < propNames.Length; ++i) { var propName = propNames[i]; var propId = JavaScriptPropertyId.FromString(propName); var jsProp = arg.GetProperty(propId); // Copy Properties into Replacement replacement.SetProperty(propId, jsProp, true); Type propType; if (!TryInferType(jsProp, out propType)) { throw new Exception($"Failed to create Host representation of JS object. Property: {propName}"); } d[propName] = ToHostObject(jsProp, propType); } return(d); }
/// <summary> /// Creates the <see cref="JsBinding"/> instance representing the new bound JavaScript object. /// </summary> public JsBinding Build() { return(_scope.Run(() => { // Create a host object binding or new JS Object binding var jsValue = null != _boundTo ? _binder.BindObject(_boundTo) : JavaScriptValue.CreateObject(); var binding = new JsBinding(_scope, _binder, _interop, jsValue); // Bind Host Object Methods, Properties, and Fields if bound to host object if (null != _boundTo && null != _hostType) { BindMethods(binding, _hostType, _boundTo); BindProperties(binding, _hostType, _boundTo); BindFields(binding, _hostType, _boundTo); } // Set custom binding values if (null != _values) { for (int i = 0; i < _values.Count; ++i) { var valueDescriptor = _values[i]; binding.SetValue(valueDescriptor.Name, valueDescriptor.Value, valueDescriptor.ValueType); } } return binding; })); }