See Also: JSContext Members
The MonoTouch.JavaScriptCore.JSContext is the central object of the JavaScriptCore namespace. The MonoTouch.JavaScriptCore.JSContext maintains a JavaScript environment (manipulated by the JSContext.Item property) and evaluates scripts with the JSContext.EvaluateScript method.
Application developers will often want to assign a delegate to the JSContext.ExceptionHandler property to gain access, in their Xamarin.iOS code, of exceptions raised in the JavaScript realm.
The following example shows the basic use of MonoTouch.JavaScriptCore.JSContext. The context is instantiated and a simple exception handler is assigned. One of the JSValue.From method overloads is used to assign values to the JavaScript variables arg1 and arg2. The JSContext.EvaluateScript method evaluates the JavaScript and returns the result, which is converted back into a .NET object with the JSResult.ToInt32 method.
C# Example
jsContext = new JSContext(); jsContext.ExceptionHandler = (context, exception) => { Console.WriteLine(exception); }; jsContext[new NSString("arg1")] = JSValue.From(2, jsContext); jsContext[new NSString("arg2")] = JSValue.From(2, jsContext); var jsResult = jsContext.EvaluateScript("arg1 + arg2;"); var four = jsResult.ToInt32();
The MonoTouch.JavaScriptCore.JSContext contains the global JavaScript context, including variables set by JavaScript calculations, as shown in the following example:
C# Example
jsContext.EvaluateScript("sum = 2 + 2;"); var four = jsContext[(NSString)"sum"].ToInt32();
Currently, C# methods cannot be exposed directly to JavaScript via JavaScript Core. The recommended technique for calling C# code from Xamarin.iOS is to use REST, as shown in the following:
In the JavaScript code, use XMLHttpRequest and standard JSON techniques to post and parse a query to a REST service running on the local device:
JavaScript Example
<html> <head> <title></title> <script type="text/javascript"> function callCSharp(msg) { var request = new XMLHttpRequest(); request.open('GET','http://127.0.0.1:1711/', false); request.send(); if(request.status == 200){ alert(JSON.parse(request.responseText)); }else{ alert("Error"); } } </script> </head> <body> <div onclick="callCSharp('this is a test')" class="button"> Click Me </div> </body> </html>
In the application, use System.Net.HttpListener to listen and respond to that request:
C# Example
//Wire up listener listener = new HttpListener(); listener.Prefixes.Add("http://*:1711/"); listener.Start(); listener.BeginGetContext(new AsyncCallback(Callback), listener); //....etc... void Callback(IAsyncResult result) { //Get the listener context var context = listener.EndGetContext(result); //Start listening for the next request listener.BeginGetContext(new AsyncCallback(Callback), listener); var response = CalculateResponse(); var responseBytes = System.Text.Encoding.UTF8.GetBytes(response); context.Response.ContentType = "text/json"; context.Response.StatusCode = HttpStatusCode.OK; context.Response.ContentLength64 = responseBytes.Length; context.Response.OutputStream.Write(responseBytes, 0, responseBytes.Length); context.Response.OutputStream.Close(); }
An alternative technique is to poll the MonoTouch.JavaScriptCore.JSContext for a flag set by a JavaScript calculation.