protected virtual bool baseCanHandle <T>(T plugin, ref string ns, ref Dictionary <string, object> options) where T : class { if (ns == null) { var export = new NKScriptExportProxy <T>(plugin); ns = export.defaultNamespace; } if (options == null) { options = new Dictionary <string, object>(); } bool mainThread; if (options.ContainsKey("NKS.MainThread")) { mainThread = (bool)options["NKS.MainThread"]; } else { mainThread = false; options["NKS.MainThread"] = mainThread; } NKScriptExportType bridge; if (options.ContainsKey("NKS.PluginBridge")) { bridge = (NKScriptExportType)options["NKS.PluginBridge"]; } else if (plugin == null) { bridge = NKScriptExportType.WinRT; options["NKS.PluginBridge"] = bridge; } else { bridge = NKScriptExportType.NKScriptExport; options["NKS.PluginBridge"] = bridge; } switch (bridge) { case NKScriptExportType.NKScriptExport: return(true); default: return(false); } }
// Public methods public virtual async Task <NKScriptValue> bindPlugin <T>(T obj, string ns) where T : class { var context = this.context; context.setNKScriptChannel(this); if ((this.id != null) || (context == null)) { return(null); } this.id = (NKScriptChannel.sequenceNumber++).ToString(); context.NKaddScriptMessageHandler(this, id); string name; if (typeof(T) == typeof(Type)) { // Class, not instance, passed to bindPlugin -- to be used in Factory constructor/instance pattern in js isFactory = true; _typeInfo = new NKScriptTypeInfo <T>(obj); name = (obj as Type).Name; // Need to store the channel on the class itself so it can be found when native construct requests come in from other plugins obj.setNKScriptChannel(this); } else { name = (typeof(T)).Name; // Instance of Princpal passed to bindPlugin -- to be used in singleton/static pattern in js isFactory = false; _typeInfo = new NKScriptTypeInfo <T>(obj); } _principal = new NKScriptValueNative(ns, this, 0, obj); this._instances[0] = _principal; _channels[ns] = this; obj.setNKScriptValue(_principal); var export = new NKScriptExportProxy <T>(obj); var script = new NKScriptSource(_generateStubs(export, name), ns + "/plugin/" + name + ".js"); await context.NKinjectScript(script); await export.initializeForContext(context); return(_principal); }
private string _generateStubs <T>(NKScriptExportProxy <T> export, string name) where T : class { bool prebind = !typeInfo.ContainsConstructor(""); var stubs = ""; foreach (var member in typeInfo) { string stub; if ((member.isMethod()) && (member.name != "")) { var methodStr = _generateMethod(String.Format("{0}{1}", member.key, member.NKScriptingjsType), prebind ? "exports" : "this", prebind); if (member.isTask) { stub = string.Format("exports.{0} = {1}", member.name + "Sync", methodStr); stubs += export.rewriteGeneratedStub(stub, member.name + "Sync") + "\n"; stub = string.Format("exports.{0} = {1}", member.name + "Async", methodStr); stubs += export.rewriteGeneratedStub(stub, member.name + "Async") + "\n"; } else { stub = string.Format("exports.{0} = {1}", member.name, methodStr); stubs += export.rewriteGeneratedStub(stub, member.name) + "\n"; } } else if (member.isProperty()) { if (isFactory) { stub = string.Format("NKScripting.defineProperty(exports, '{0}', null, {1});", member.name, (member.setter != null).ToString().ToLower()); } else { var value = context.NKserialize(_principal.valueForPropertyNative(member.name)); stub = string.Format("NKScripting.defineProperty(exports, '{0}', {1}, {2});", member.name, value, (member.setter != null).ToString().ToLower()); } stubs += export.rewriteGeneratedStub(stub, member.name) + "\n"; } else { continue; } } string basestub; if (typeInfo.ContainsConstructor("")) { var constructor = typeInfo.DefaultConstructor(); // basestub = generateMethod("\(member.type)", this: "arguments.callee", prebind: false) basestub = export.rewriteGeneratedStub(string.Format("'{0}'", constructor.NKScriptingjsType), ".base"); } else { basestub = export.rewriteGeneratedStub("null", ".base"); } var localstub = export.rewriteGeneratedStub(stubs, ".local"); var globalstubber = "(function(exports) {\n" + localstub + "})(NKScripting.createPlugin('" + id + "', '" + ns + "', " + basestub + "));\n"; return(export.rewriteGeneratedStub(globalstubber, ".global")); }
public NKScriptTypeInfo(T plugin) : base() { T instance; _pluginType = typeof(T); if (_pluginType == typeof(Type)) { _pluginType = plugin as Type; instance = default(T); } else { instance = plugin; } enumerateExcluding(exclusion, (member) => { var key = member.key; var name = member.name; NKScriptExportProxy <T> cls = new NKScriptExportProxy <T>(plugin); switch (member.memberType) { case MemberType.Method: if (name.Substring(0, 1) == "_") { return(true); } if (cls.isExcludedFromScript(key)) { return(true); } member.name = cls.rewritescriptNameForKey(key, name); return(false); case MemberType.Property: if (name.Substring(0, 1) == "_") { return(true); } if (cls.isExcludedFromScript(key)) { return(true); } member.name = cls.rewritescriptNameForKey(key, name); return(false); case MemberType.Constructor: if (cls.isExcludedFromScript(key)) { return(true); } member.name = cls.rewritescriptNameForKey(key, name); return(false); default: return(false); } }); }