/// <summary> /// Binds the current values of all binding variables to the specified <see cref="ScriptProxy"/>. /// </summary> /// <param name="proxy">The proxy to bind the variables to</param> private void BindProxyVars(ScriptProxy proxy) { foreach (Variable var in bindingVariables) { // Bind the value to the variable proxy.Fields[var.Name] = var.Value; } }
/// <summary> /// Unbinds the values from the specified <see cref="ScriptProxy"/>. /// </summary> /// <param name="proxy">The proxy to unbind the variables from</param> private void UnbindProxyVars(ScriptProxy proxy) { foreach (Variable var in bindingVariables) { // Unbind the value var.Update(proxy.Fields[var.Name]); } }
/// <summary> /// Binds the current delegate list of binding delegates to the specified <see cref="ScriptProxy"/>. /// </summary> /// <param name="proxy">The proxy to bind the delegates to</param> private void BindProxyDelegates(ScriptProxy proxy) { // Create a temp list of names List <string> names = new List <string>(bindingDelegates.Keys); foreach (string name in names) { // Get the delegate Delegate action = bindingDelegates[name]; // Assign the delegate proxy.Fields[name] = action; } }
/// <summary> /// Creates an instance of this type and returns the result as the specified generic type. /// A raw instance will return the actual instance of the type as opposed to a <see cref="ScriptProxy"/> which allows for more control. /// The type will be constructed using the appropriate method (AddComponent, CreateInstance, new). /// </summary> /// <typeparam name="T">The generic type to return the instance as</typeparam> /// <param name="parent">The <see cref="GameObject"/> to attach the instance to or null if the type is not a <see cref="MonoBehaviour"/></param> /// <param name="parameters">The parameter list for the desired constructor. only used when the type does not inherit from <see cref="UnityEngine.Object"/></param> /// <returns>A raw instance as the specified generic type</returns> public T CreateRawInstance <T>(GameObject parent = null, params object[] parameters) where T : class { // Call through ScriptProxy proxy = CreateInstance(parent); // Check the error if (proxy == null) { return(null); } // Get the instance return(proxy.GetInstanceAs <T>(false)); }
/// <summary> /// Creates a raw instance of this type. /// A raw instance will return the actual instance of the type as opposed to a <see cref="ScriptProxy"/> which allows for more control. /// The type will be constructed using the appropriate method (AddComponent, CreateInstance, new). /// </summary> /// <param name="parent">The <see cref="GameObject"/> to attach the instance to or null if the type is not a <see cref="MonoBehaviour"/></param> /// <param name="parameters">The parameter list for the desired constructor. only used when the type does not inherit from <see cref="UnityEngine.Object"/></param> /// <returns>A raw instance that can be cast to the desired type</returns> public object CreateRawInstance(GameObject parent = null, params object[] parameters) { // Call through ScriptProxy proxy = CreateInstance(parent, parameters); // Check for error if (proxy == null) { return(null); } // Get the instance return(proxy.Instance); }
/// <summary> /// Attempt to evaluate the specified source code. /// The provided source code will be compiled (unless cached) and then executed in <see cref="ScriptDomain"/> specified in the constructor. /// Any valid C# method body syntax is accepted. You may not define user types or methods in the provided source. Type declarations are allowed. /// </summary> /// <typeparam name="T">The generic type that the evaluated code should return</typeparam> /// <param name="sourceCode">The string source code to execute</param> /// <returns>A <see cref="Variable"/> representing the return value of the evaluated code. If the evaluated code does not return a value then the result will be a <see cref="Variable"/> representing 'default(T)'. If the code failed to run then the return value will be null</returns> public Variable <T> Eval <T>(string sourceCode) { ScriptProxy proxy = null; // Check whether this source is cached bool isCached = evalCache.ContainsKey(sourceCode); // Check if we have a cached version of this source code if (isCached == true) { // Get the cached type proxy = evalCache[sourceCode]; } else { // Get the full C# source code string source = BuildSourceAroundTemplate(sourceCode); #if UNITY_EDITOR && !UNITY_WEBPLAYER // Check if we should output the generated source if (outputGeneratedSourceIfDebug == true) { System.IO.File.WriteAllText("DynamicCSharp_Eval_GeneratedSource.cs", source); } #endif // Try to compile the code ScriptType type = domain.CompileAndLoadScriptSource(source); // Looks like we failed to compile or find a cached type if (type == null) { return(null); } // Create an instance proxy = type.CreateInstance(); // Check for error if (proxy == null) { return(null); } } // Check if we need to cache the type if (isCached == false) { // Make a cache entry evalCache.Add(sourceCode, proxy); } // Bind the delegates to the proxy BindProxyDelegates(proxy); // Bind the values to the proxy BindProxyVars(proxy); // Bind our return value object returnResult = new object(); proxy.Fields[returnObject] = returnResult; // Call the method object result = proxy.SafeCall(entryMethod); // Read the value back into evaluator memory space UnbindProxyVars(proxy); // Check if we returned a value if (returnResult == result) { return(new Variable <T>(returnObject, default(T))); } // Create a default error value that we can use if we fail to get the correct type T resolvedReturn = default(T); try { // Try to cast to type resolvedReturn = (T)result; } catch (InvalidCastException) { } // We successfully ran the code return(new Variable <T>(returnObject, resolvedReturn)); }
// Constructor internal FieldProxy(ScriptProxy owner) { this.owner = owner; }
// Constructor internal PropertyProxy(ScriptProxy owner) { this.owner = owner; }