public Task <MessageEvent <TData> > postMessageAsync <TData>(TData message) { // Z:\jsc.svn\examples\javascript\chrome\hybrid\ChromeHybridCapture\ChromeHybridCapture\Application.cs var x = new TaskCompletionSource <MessageEvent <TData> >(); var c = new MessageChannel(); c.port1.onmessage += e => { // bypass type safety x.SetResult((MessageEvent <TData>)(object) e); }; c.port1.start(); c.port2.start(); this.postMessage(message, targetOrigin: "*", transfer: c.port2 ); return(x.Task); }
public Task <MessageEvent> postMessageAsync(object message, string targetOrigin = "*") { var x = new TaskCompletionSource <MessageEvent>(); var c = new MessageChannel(); c.port1.onmessage += e => { x.SetResult(e); }; c.port1.start(); c.port2.start(); this.postMessage(message, targetOrigin, c.port2 ); return(x.Task); }
public Task <MessageEvent <TData> > postMessageAsync <TData>() { var x = new TaskCompletionSource <MessageEvent <TData> >(); var c = new MessageChannel(); c.port1.onmessage += e => { // bypass type safety x.SetResult((MessageEvent <TData>)(object) e); }; c.port1.start(); c.port2.start(); this.postMessage(null, targetOrigin: "*", transfer: c.port2 ); return(x.Task); }
/// <summary> /// This is a javascript application. /// </summary> /// <param name="page">HTML document rendered by the web server which can now be enhanced.</param> public Application(IApp page) { new { }.With( async delegate { #region magic var isroot = Native.window.parent == Native.window.self; new IHTMLPre { new { isroot } }.AttachToDocument(); if (!isroot) { #region HopToParent HopToParent.VirtualOnCompleted = async (that, continuation) => { // https://sites.google.com/a/jsc-solutions.net/backlog/knowledge-base/2015/201511/20151102/hoptoui // the state is in a member variable? var r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // should not be a zero state // or do we have statemachine name clash? new IHTMLPre { "iframe about to jump to parent " + new { r.shadowstate.state } }.AttachToDocument(); Native.window.parent.postMessage(r.shadowstate); // we actually wont use the response yet.. }; #endregion // start the handshake // we gain intellisense, but the type is partal, likely not respawned, acivated, initialized new IHTMLPre { "inside iframe awaiting state" }.AttachToDocument(); var c = new MessageChannel(); c.port1.onmessage += m => { var that = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)m.data; new IHTMLPre { "inside iframe got state " + new { that.state } }.AttachToDocument(); // about to invoke #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( item => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(item); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return item.FullName == that.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, that.state ); } var xStringField = that.StringFields.AsEnumerable().FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion new IHTMLPre { "inside iframe invoke state" }.AttachToDocument(); NewStateMachineI.MoveNext(); // we can now send one hop back? }; c.port1.start(); c.port2.start(); Native.window.parent.postMessage(null, "*", c.port2 ); return; } var lookup = new Dictionary<IHTMLIFrame, MessageEvent> { }; #region HopToIFrame HopToIFrame.VirtualOnCompleted = async (that, continuation) => { var m = default(MessageEvent); var r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); if (lookup.ContainsKey(that.frame)) { new IHTMLPre { "parent already nows the iframe..." }.AttachToDocument(); m = lookup[that.frame]; } else { new IHTMLPre { "parent is awaiting handshake of the newly loaded iframe..." }.AttachToDocument(); // X:\jsc.svn\examples\javascript\Test\TestSwitchToIFrame\TestSwitchToIFrame\Application.cs //var m = await that.frame.contentWindow.async.onmessage; m = await that.frame.async.onmessage; lookup[that.frame] = m; #region onmessage that.frame.ownerDocument.defaultView.onmessage += e => { if (e.source != that.frame.contentWindow) return; var shadowstate = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)e.data; // are we jumping into a new statemachine? new IHTMLPre { "parent saw iframe instructions to jump back " + new { shadowstate.state } }.AttachToDocument(); // about to invoke #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( item => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(item); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return item.FullName == shadowstate.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, shadowstate.state ); } var xStringField = shadowstate.StringFields.AsEnumerable().FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion new IHTMLPre { "parent saw iframe instructions to jump back. invoking... " }.AttachToDocument(); NewStateMachineI.MoveNext(); }; #endregion } new IHTMLPre { "parent is sending state after handshake..." }.AttachToDocument(); m.postMessage(r.shadowstate); }; #endregion #endregion var hostname = Native.document.location.host.TakeUntilIfAny(":"); var hostport = Native.document.location.host.SkipUntilOrEmpty(":"); //var hostport1 = Convert.ToInt32(hostport) + 1; var hostport1 = Convert.ToInt32(hostport); var host1 = hostname + ":" + hostport1; var baseURI1 = "https://" + host1; new IHTMLButton { "Identity " + new { baseURI1 } }.AttachToDocument().onclick += async e => { #region statemachine fixup? await Task.CompletedTask; #endregion new IHTMLPre { "will jump into the iframe to do io and then jump back here" }.AttachToDocument(); //var iframe = new IHTMLIFrame { src = baseURI1 }.AttachToDocument(); iframe = new IHTMLIFrame { src = baseURI1 }.AttachToDocument(); // if the iframe is on another port, ssl client certificate may be prompted //await (HopTo)iframe; await (HopToIFrame)iframe; new IHTMLPre { "did we make it into iframe yet?" }.AttachToDocument(); // yes await new IHTMLButton { "lets jump back " }.AttachToDocument().async.onclick; new IHTMLPre { "lets jump back to parent..." }.AttachToDocument(); //await (HopTo)Native.window.parent; await default(HopToParent); new IHTMLPre { "did we make it into parent yet?" }.AttachToDocument(); // do we have iframe ref or are we a new statemachine? await new IHTMLButton { "lets jump back to iframe " + new { iframe } }.AttachToDocument().async.onclick; await (HopToIFrame)iframe; Native.document.body.Clear(); new IHTMLPre { "did we make it into iframe this time?" }.AttachToDocument(); // yes // TypeError: Cannot read property '__4__this' of null //var color = await base.Color(); var color = await new ApplicationWebService { }.Color(); Native.body.style.backgroundColor = color; await default(HopToParent); new IHTMLPre { "did we make it into parent yet? " + new { color } }.AttachToDocument(); Native.body.style.backgroundColor = color; }; } ); }
// who is calling? // triggered by InternalInvoke static void __worker_onfirstmessage( MessageEvent e, int InternalThreadCounter, object data___string, bool[] MethodTargetObjectDataIsProgress, object[] MethodTargetObjectData, // https://sites.google.com/a/jsc-solutions.net/backlog/knowledge-base/2014/201411/20141112 object[] MethodTargetObjectDataTypes, object MethodTargetTypeIndex, // set by ? string MethodToken, string MethodType, object state_ObjectData, object stateTypeHandleIndex, object state, bool IsIProgress, //bool IsTuple2_Item1_IsIProgress, __Task <object>[] TaskArray ) { // https://sites.google.com/a/jsc-solutions.net/backlog/knowledge-base/2015/201501/20150111 #region ConsoleFormWriter var w = new InternalInlineWorkerTextWriter(); var o = Console.Out; Console.SetOut(w); w.AtWrite = AtWrite => { // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs //dynamic zdata = new object(); //zdata.AtWrite = x; // working with multiple threads, keep the id in the log! // () means we are setting the thread up... [] is the thread AtWrite = "[" + Thread.CurrentThread.ManagedThreadId + "] " + AtWrite; var zdata = new { AtWrite }; foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } }; #endregion __Thread.InternalCurrentThread.ManagedThreadId = InternalThreadCounter; __Thread.InternalCurrentThread.IsBackground = true; // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic self = Native.self; var stateType = default(Type); if (stateTypeHandleIndex != null) { stateType = Type.GetTypeFromHandle(new __RuntimeTypeHandle((IntPtr)self[stateTypeHandleIndex])); } // X:\jsc.svn\examples\javascript\async\AsyncNonStaticHandler\AsyncNonStaticHandler\Application.cs var MethodTargetType = default(Type); if (MethodTargetTypeIndex != null) { MethodTargetType = Type.GetTypeFromHandle(new __RuntimeTypeHandle((IntPtr)self[MethodTargetTypeIndex])); } // stateType = <Namespace>.xFoo, // MethodTargetTypeIndex = type$GV0nCx_bM8z6My5NDh7GXlQ, Console.WriteLine( "__worker_onfirstmessage: " + new { Thread.CurrentThread.ManagedThreadId, Native.worker.location.href, MethodTargetTypeIndex, MethodTargetType, MethodToken, MethodType, //IsTuple2_Item1_IsIProgress, // X:\jsc.svn\examples\javascript\test\TestTypeHandle\TestTypeHandle\Application.cs stateTypeHandleIndex, stateType, state, IsIProgress, //MethodTokenReference } ); #region MethodTokenReference var MethodTokenReference = default(IFunction); var MethodTarget = default(object); if (MethodTargetType == null) { MethodTokenReference = IFunction.Of(MethodToken); } else { MethodTarget = FormatterServices.GetUninitializedObject(MethodTargetType); var MethodTargetTypeSerializableMembers = FormatterServices.GetSerializableMembers(MethodTargetType); // X:\jsc.svn\examples\javascript\async\test\TestWorkerScopeProgress\TestWorkerScopeProgress\Application.cs for (int i = 0; i < MethodTargetTypeSerializableMembers.Length; i++) { var xMember = MethodTargetTypeSerializableMembers[i] as FieldInfo; var xObjectData = MethodTargetObjectData[i]; var xMethodTargetObjectDataTypeIndex = MethodTargetObjectDataTypes[i]; var xIsProgress = MethodTargetObjectDataIsProgress[i]; // X:\jsc.svn\examples\javascript\chrome\apps\ChromeTCPServer\ChromeTCPServer\Application.cs // does our chrome tcp server get the damn path? Console.WriteLine(new { xMember, xMethodTargetObjectDataTypeIndex, xObjectData, xIsProgress }); // need to resurrect the semaphores! // X:\jsc.svn\examples\javascript\async\Test\TestSemaphoreSlim\TestSemaphoreSlim\ApplicationControl.cs #region MethodTargetObjectDataIsProgress // cant we use xMethodTargetObjectDataType instead? if (xIsProgress) { var ii = i; MethodTargetObjectData[ii] = new __Progress <object>( ProgressEvent => { // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic zdata = new object(); zdata.MethodTargetObjectDataProgressReport = new { ProgressEvent, ii }; foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } //Console.WriteLine(new { MethodTargetTypeSerializableMember, MethodTargetTypeSerializableMemberIsProgress, ProgressEvent }); } ); } #endregion else { var xMethodTargetObjectDataType = default(Type); if (xMethodTargetObjectDataTypeIndex != null) { xMethodTargetObjectDataType = Type.GetTypeFromHandle(new __RuntimeTypeHandle((IntPtr)self[xMethodTargetObjectDataTypeIndex])); } // now we know the type. should we review it? if (xMethodTargetObjectDataType != null) { var scope2copy = FormatterServices.GetUninitializedObject(xMethodTargetObjectDataType); //shall we copy the members too? //FormatterServices.PopulateObjectMembers(scope2copy, scope2TypeSerializableMembers, scope2ObjectData); MethodTargetObjectData[i] = scope2copy; #region __SemaphoreSlim // X:\jsc.svn\examples\javascript\async\Test\TestSemaphoreSlim\TestSemaphoreSlim\ApplicationControl.cs var xSemaphoreSlim = scope2copy as __SemaphoreSlim; if (xSemaphoreSlim != null) { // we now have to complete the entanglement. we have the caller on the UI. Action <string> WriteLine0 = text => { Console.WriteLine("(" + xMember.Name + ") " + text); }; //xSemaphoreSlim.InternalIsEntangled = true; #region InternalVirtualWaitAsync var xInternalVirtualWaitAsync = default(TaskCompletionSource <object>); xSemaphoreSlim.InternalVirtualWaitAsync += continuation => { WriteLine0("enter xSemaphoreSlim.InternalVirtualWaitAsync, worker is now awaiting for signal"); xInternalVirtualWaitAsync = continuation; }; // at this point lets call the UI to set up a new signal channel.. //new MessageChannel(); var c = new MessageChannel(); c.port1.onmessage += ce => { // ui has released? if (xInternalVirtualWaitAsync == null) { // what if the thread is not yet awaiting? WriteLine0("ui has sent a release signal, yet nobody awaiting"); return; } WriteLine0("ui has sent a release signal, resync"); // we should have byte fields now. // next strings as in thread hopping... dynamic data = ce.data; #region read xSemaphoreSlim_ByteArrayFields { __Task.xByteArrayField[] xSemaphoreSlim_ByteArrayFields = data.xSemaphoreSlim_ByteArrayFields; // X:\jsc.svn\examples\javascript\async\test\TestBytesToSemaphore\TestBytesToSemaphore\Application.cs if (xSemaphoreSlim_ByteArrayFields != null) { foreach (var item in xSemaphoreSlim_ByteArrayFields) { var xFieldInfo = (FieldInfo)MethodTargetTypeSerializableMembers[item.index]; // can we set the value? WriteLine0("worker resync " + new { item.index, //item.Name, xFieldInfo = xFieldInfo.Name, item.value }); xFieldInfo.SetValue( MethodTarget, // null? item.value ); } } } #endregion xInternalVirtualWaitAsync.SetResult(null); }; c.port1.start(); c.port2.start(); WriteLine0("will set up the signal channel"); foreach (var p in e.ports) { p.postMessage( new { xSemaphoreSlim = xMember.Name }, transfer: new[] { c.port2 } ); } #endregion #region InternalVirtualRelease xSemaphoreSlim.InternalVirtualRelease += delegate { WriteLine0("enter xSemaphoreSlim.InternalVirtualRelease, will send a signal to ui..."); // worker needs sync data about now. // the ui would be happy to have the latest version of the data. // this is tricky. we would really need to know which data fields have changed by now // and what will happen if the data was also changed on the ui. // technically we are doing a merge conflict resolver... // this is somewhat the same situation, we alrady have // when entering a worker // when exiting a worker // when hoping to or from a worker. // what data fields do we have to upload yo ui? // how much IL analysis is available for us to know what to sync // we should not sync fields that wont be used on the ui // the thread hop looks at strings only right now, as they are immputable yet primitive // what about bytewarrays? // X:\jsc.svn\examples\javascript\async\test\TestBytesFromSemaphore\TestBytesFromSemaphore\Application.cs #region xSemaphoreSlim_ByteArrayFields var xSemaphoreSlim_ByteArrayFields = new List <__Task.xByteArrayField>(); var MethodTargetTypeSerializableMembers_index = 0; foreach (FieldInfo item in MethodTargetTypeSerializableMembers) { // how would we know if the array is a byte array? // FieldType is not exactly available yet //Console.WriteLine("worker resync candidate " + new { item.Name, item.FieldType, item.FieldType.IsArray }); var item_value = item.GetValue(MethodTarget); if (item_value != null) { var item_value_constructor = Expando.Of(item_value).constructor; var item_value_IsByteArray = Native.self_Uint8ClampedArray == item_value_constructor; if (item_value_IsByteArray) { var value = (byte[])item_value; xSemaphoreSlim_ByteArrayFields.Add( new __Task.xByteArrayField { index = MethodTargetTypeSerializableMembers_index, // keep name for diagnostics Name = item.Name, value = value } ); WriteLine0("worker resync xByteArrayField candidate " + new { item.Name, value.Length }); } } MethodTargetTypeSerializableMembers_index++; } #endregion foreach (var p in e.ports) { p.postMessage( new { xSemaphoreSlim = xMember.Name, xSemaphoreSlim_ByteArrayFields = xSemaphoreSlim_ByteArrayFields.ToArray() } ); } }; #endregion } #endregion } } } FormatterServices.PopulateObjectMembers( MethodTarget, MethodTargetTypeSerializableMembers, MethodTargetObjectData ); // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs MethodTokenReference = (MethodTarget as dynamic)[MethodToken]; } // what if we are being called from within a secondary app? // stateTypeHandleIndex = type$XjKww8iSKT_aFTpY_bSs5vBQ, if (MethodTokenReference == null) { // tested at // X:\jsc.svn\examples\javascript\WorkerInsideSecondaryApplication\WorkerInsideSecondaryApplication\Application.cs // X:\jsc.svn\examples\javascript\Test\TestHopToThreadPoolAwaitable\TestHopToThreadPoolAwaitable\Application.cs // why? throw new InvalidOperationException( new { MethodToken } +" function is not available at " + new { Native.worker.location.href } ); } #endregion //Console.WriteLine( // new // { // MethodTokenReference, // Thread.CurrentThread.ManagedThreadId // } // ); // whats the type? #region xstate var xstate = default(object); if (stateType != null) { xstate = FormatterServices.GetUninitializedObject(stateType); var xstate_SerializableMembers = FormatterServices.GetSerializableMembers(stateType); FormatterServices.PopulateObjectMembers( xstate, xstate_SerializableMembers, (object[])state_ObjectData ); // MethodType = FuncOfObjectToObject //Console.WriteLine("as FuncOfObjectToObject"); } #endregion #region CreateProgress Func <__Progress <object> > CreateProgress = () => new __Progress <object>( value => { //Console.WriteLine("__IProgress_Report " + new { value }); // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic zdata = new object(); zdata.__IProgress_Report = new { value }; foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } } ); // X:\jsc.svn\examples\javascript\async\Test\TestWorkerProgress\TestWorkerProgress\Application.cs if (IsIProgress) { xstate = CreateProgress(); } #endregion #region __string // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic target = __string; var m = Expando.Of(data___string).GetMembers(); // https://sites.google.com/a/jsc-solutions.net/backlog/knowledge-base/2013/201308/20130826-domainmemory foreach (ExpandoMember nn in m) { target[nn.Name] = nn.Value; var trigger = "set_" + nn.Name; var trigger_default = IFunction.Of(trigger); (Native.self as dynamic)[trigger] = IFunction.OfDelegate( new Action <string>( Value => { if (nn.Value == Value) { return; } trigger_default.apply(null, Value); #region sync one field only { dynamic zdata = new object(); dynamic zdata___string = new object(); zdata.__string = zdata___string; zdata___string[nn.Name] = Value; // prevent sync via diff nn.Value = Value; foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } } #endregion } ) ); } #endregion { // https://sites.google.com/a/jsc-solutions.net/backlog/knowledge-base/2013/201308/20130828-thread-run // for now we only support static calls // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic zdata = new object(); if (MethodType == typeof(ActionOfDedicatedWorkerGlobalScope).Name) { MethodTokenReference.apply(null, Native.worker); } else if (MethodType == typeof(FuncOfObjectToObject).Name) { //Console.WriteLine("worker Task Run function call"); #region FuncOfObjectToObject // X:\jsc.svn\examples\javascript\test\TestTaskStartToString\TestTaskStartToString\Application.cs // X:\jsc.svn\examples\javascript\async\test\TestTaskRun\TestTaskRun\Application.cs // X:\jsc.svn\examples\javascript\Test\TestGetUninitializedObject\TestGetUninitializedObject\Application.cs var value = MethodTokenReference.apply(MethodTarget, xstate); // X:\jsc.svn\examples\javascript\async\test\TaskAsyncTaskRun\TaskAsyncTaskRun\Application.cs // whatif its an Action not a Func? //enter HopToThreadPoolAwaitable yield HopToUIAwaitable //worker Task Run function has returned {{ value_Task = null, value_TaskOfT = null }} //__Task.InternalStart inner complete {{ yield = {{ value = null }} }} var value_Task = value as __Task; var value_TaskOfT = value as __Task <object>; // if we are in a hop. allow the return task to be overriden. if (InternalOverrideTaskOfT != null) { value_TaskOfT = InternalOverrideTaskOfT; } // 0:25611ms Task Run function has returned { value_Task = [object Object], value_TaskOfT = [object Object] } //Console.WriteLine("worker Task Run function has returned " + new { value_Task, value_TaskOfT, InternalOverrideTaskOfT }); // 0:4284ms Task Run function has returned { value_Task = { IsCompleted = 1, Result = }, value_TaskOfT = { IsCompleted = 1, Result = } } // 0:5523ms Task Run function has returned { value_Task = { IsCompleted = false, Result = }, value_TaskOfT = { IsCompleted = false, Result = } } if (value_TaskOfT != null) { // special situation // if IsCompleted, called twice? or heard twice? value_TaskOfT.ContinueWith( t => { //Console.WriteLine("worker Task Run ContinueWith " + new { t }); // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic zzdata = new object(); // null? if (t.Result == null) { zzdata.ContinueWithResult = new { t.Result }; foreach (MessagePort port in e.ports) { port.postMessage((object)zzdata, new MessagePort[0]); } return; } var ResultType = t.Result.GetType(); var ResultTypeIndex = __Type.GetTypeIndex("workerResult", ResultType); var ResultTypeSerializableMembers = FormatterServices.GetSerializableMembers(ResultType); var ResultObjectData = FormatterServices.GetObjectData(t.Result, ResultTypeSerializableMembers); var ContinueWithResult = new { ResultTypeIndex, ResultObjectData, t.Result }; zzdata.ContinueWithResult = ContinueWithResult; foreach (MessagePort port in e.ports) { port.postMessage((object)zzdata, new MessagePort[0]); } } ); } else { if (value_Task != null) { // X:\jsc.svn\examples\javascript\async\test\TestWorkerScopeProgress\TestWorkerScopeProgress\Application.cs throw new NotImplementedException(); } else { var yield = new { value }; //Console.WriteLine(new { yield }); zdata.yield = yield; } } #endregion // now what? } else if (MethodType == typeof(FuncOfTaskToObject).Name) { // tested by? #region FuncOfTaskToObject // need to reconstruct the caller task? var value = MethodTokenReference.apply(null, TaskArray.Single()); var yield = new { value }; //Console.WriteLine(new { yield }); zdata.yield = yield; #endregion // now what? } else if (MethodType == typeof(FuncOfTaskOfObjectArrayToObject).Name) { // tested by? #region FuncOfTaskOfObjectArrayToObject // need to reconstruct the caller task? Console.WriteLine("__worker_onfirstmessage: " + new { TaskArray = TaskArray.Length }); //Debugger.Break(); var args = new object[] { TaskArray }; var value = MethodTokenReference.apply( o: null, // watch out args: args ); var yield = new { value }; //Console.WriteLine(new { yield }); zdata.yield = yield; #endregion // now what? } #region [sync] diff and upload changes to DOM context, the latest now { dynamic zdata___string = new object(); zdata.__string = zdata___string; foreach (ExpandoMember nn in m) { string Value = (string)Expando.InternalGetMember((object)target, nn.Name); // this is preferred: //string Value = target[nn.Name]; if (Value != nn.Value) { zdata___string[nn.Name] = Value; } } } #endregion //e.post foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } } }
// https://developer.chrome.com/apps/tags/webview // or what if we were to runn as chrome appwindow and webview // would they be in separate gpu procsses, leeping parent responsive while gpu is buzy? public Application(IApp page) { #if FCHROME #region += Launched chrome.app.window // X:\jsc.svn\examples\javascript\chrome\apps\ChromeTCPServerAppWindow\ChromeTCPServerAppWindow\Application.cs dynamic self = Native.self; dynamic self_chrome = self.chrome; object self_chrome_socket = self_chrome.socket; if (self_chrome_socket != null) { if (!(Native.window.opener == null && Native.window.parent == Native.window.self)) { // should implement hop here instead tho //new IHTMLPre { "empty window " }.AttachToDocument(); new IHTMLPre { () => "appwindow: " + new { DateTime.Now.Millisecond } }.AttachToDocument(); } else { //ChromeTCPServer.TheServerWithAppWindow.Invoke(AppSource.Text); ChromeTCPServer.TheServer.Invoke(AppSource.Text, // null means we get a new tab, which we could control as an extension? open: async uri => { // app to appwindow var xappwindow = await chrome.app.window.create(Native.document.location.pathname, options: null); // do we have an empty window? await xappwindow.contentWindow.async.onload; var webview = xappwindow.contentWindow.document.createElement("webview"); // You do not have permission to use <webview> tag. Be sure to declare 'webview' permission in your manifest. webview.setAttribute("partition", "p1"); webview.setAttribute("src", uri); webview.style.SetLocation(100, 80); webview.style.width = "400px"; webview.style.height = "400px"; webview.AttachTo(xappwindow.contentWindow.document.body); } ); } return; } #endregion #endif Native.body.Clear(); // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150824/webgliframebuffer // until we have webgl2 up and running, // iframes could work as well. // what we need is a set of iframes that allow // 360deg multishader rendering // to run it as a hybrid chrome app, either we need aawppwindow tcp webview or tabs window // each shader iframe can prep their frames ahead of time in their own pace.. // will three.planegeometry use atlas? #region setup var isroot = Native.window.parent == Native.window; if (isroot) Native.body.style.backgroundColor = "yellow"; else Native.body.style.backgroundColor = "cyan"; // called by? 619 app:HopToChromeAppWindow #region window: Native.window.onmessage Native.window.onmessage += e => { Console.WriteLine("iframe: Native.window.onmessage"); // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow var message = e.data; if (message is string) { Console.WriteLine("iframe: Native.window.onmessage: " + message); if (e.ports != null) foreach (var port in e.ports) { Console.WriteLine("iframe: Native.window.onmessage " + new { port }); //appwindow_to_app = port; } return; } // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp // casting from anonymous object. var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)message; // or constructor id? Console.WriteLine("iframe: Native.window.onmessage " + new { xShadowIAsyncStateMachine.state, xShadowIAsyncStateMachine.TypeName }); // 12468ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }}, expando_isstring = true, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.729 view-source:53670 12471ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} }} //2015-08-22 15:49:45.733 view-source:53670 12475ms extension port.onMessage {{ message = [object Object], expando_isstring = false, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.737 view-source:53670 12479ms extension port.onMessage {{ state = 0, TypeName = <Namespace>.___ctor_b__4_9_d }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); //var xisIAsyncStateMachine = typeof(mscorlib::System.Runtime.CompilerServices.IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); var xisIAsyncStateMachine = typeof(global::System.Runtime.CompilerServices.IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion var NewStateMachine = global::System.Runtime.Serialization.FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is global::System.Runtime.CompilerServices.IAsyncStateMachine; var NewStateMachineI = (global::System.Runtime.CompilerServices.IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // X:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); }; #endregion //Action<ScriptCoreLib.JavaScript.DOM.IWindow, Action> invokeWhenReady = (contentWindow, yield) => #region invokeWhenReady, roslyn ctp needs it. rc does not? Action<IHTMLIFrame, Action> invokeWhenReady = (that, yield) => { that.onload += delegate { if (yield == null) { Console.WriteLine("window: HopToIFrame that.that.contentWindow.onload dismissed"); return; } Console.WriteLine("window: HopToIFrame IHTMLIFrame.onload"); if (yield != null) { yield(); yield = null; } }; }; #endregion #region window:HopToChromeAppWindow // bugcheck: roslyn RC generates byref struct statemachine? //HopToIFrame.VirtualOnCompleted = async (that, continuation) => HopToIFrame.VirtualOnCompleted = (that, continuation) => { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150824/webgliframebuffer // state 0 ? or state -1 ? Console.WriteLine("window: HopToIFrame VirtualOnCompleted enter "); #region yield Action yield = delegate { // z:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} // Z:\jsc.svn\core\ScriptCoreLib\JavaScript\DOM\IWindow.postMessage.cs // how do we use this thing? var c = new MessageChannel(); c.port1.onmessage += e => { Console.WriteLine("window: HopToChromeAppWindow MessageChannel onmessage " + new { e.data }); //appwindow_to_app(e.data); }; c.port1.start(); c.port2.start(); Console.WriteLine("window to iframe postMessage"); // 15ms appwindow Native.window.onmessage: {{ ports = [object MessagePort] }} //2015-08-22 20:50:18.019 view-source:53702 17ms appwindow Native.window.onmessage: {{ port = [object MessagePort] }} that.that.contentWindow.postMessage("do HopToIFrame " + new { r.shadowstate.TypeName, r.shadowstate.state }, transfer: c.port2); // now send the jump instruction... will it make it? that.that.contentWindow.postMessage(r.shadowstate); }; #endregion #region outputWindow if (that.that == null) { // TypeError: Cannot read property 'document' of null // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or should we predownload our source as we do for Worker? that.that = new IHTMLIFrame { src = Native.document.location.href }; // bugcheck: roslyn RC generates byref struct statemachine? //await that.that.contentWindow.async.onload; // listener ready? // Error: InvalidOperationException: inline scope sharing not yet implemented //invokeWhenReady(that.that.contentWindow, yield); invokeWhenReady(that.that, yield); //that.that.contentWindow.async.onload.ContinueWith( // async task => // { // await Native.window.async.onframe; // yield(); // } //); that.that.AttachToDocument(); return; } #endregion yield(); }; #endregion if (!isroot) { // bail as we are making the jump.. return; } #endregion // multishader variant here. // singleshader variant here. new { }.With( async delegate { //Error CS7069 Reference to type 'TaskAwaiter<>' claims it is defined in 'mscorlib', but it could not be found WebGLIFrameBuffer Z:\jsc.svn\examples\javascript\WebGL\WebGLIFrameBuffer\Application.cs 48 // cna we now have HopToChromeWebview? new IHTMLButton { "window: lets do some slow thing and see if parent stays responsive.. " }.AttachToDocument().onclick += delegate { // simulate gpu timeout Thread.Sleep(10000); // are we a webview or appview? // works as appwindow and webview are in different processes? // until iframes start living in another frame, // we can use chrome and tcp webview to get dual ui it seems. }; await new IHTMLButton { () => "window: ready " + new { DateTime.Now.Millisecond } }.AttachToDocument().async.onclick; // red cmd start. example.com // to open chrome // should actually fork to do multiple shaders at the same time... new IHTMLPre { () => "window: hopping to iframe to prep shader... " + new { DateTime.Now.Millisecond } }.AttachToDocument(); new IStyle(Native.body.css[IHTMLElement.HTMLElementEnum.iframe].style) { border = "1px dashed red", width = "800px", height = "400px" }; await default(HopToIFrame); // in the camera tracker we have semaphores after making the jump. new IHTMLPre { () => "iframe: we made it..." + new { DateTime.Now.Millisecond } }.AttachToDocument(); // need intellisense to do some meaningful tests.. // lets switch from red to asus.. // now, can we try to lock up the ui? new IHTMLButton { "iframe: lets do some slow thing and see if parent stays responsive.. " }.AttachToDocument().onclick += delegate { // simulate gpu timeout Thread.Sleep(10000); // are we a webview or appview? // works as appwindow and webview are in different processes? }; //// Cross-site iframes are currently hosted in the same process as their parent document, because we don't yet have support for hosting them in a different process. //// https://www.chromium.org/developers/design-documents/site-isolation //// ? --site-per-process in chrome://flags //// https://code.google.com/p/chromium/issues/detail?id=99379 //// http://stackoverflow.com/questions/11510483/will-a-browser-give-an-iframe-a-separate-thread-for-javascript //// https://www.chromium.org/developers/design-documents/oop-iframes //// this will block parent UI .. //Thread.Sleep(2000); //// js thread seems to block the parent iframe too... //// would it mean blockin for webgl also blocks parent? //// this would make this approach rather useless? //new IHTMLButton { "iframe: done. " }.AttachToDocument(); await new IHTMLButton { "iframe: doprograms " }.AttachToDocument().async.onclick; // only multiple gpu cards seem to fix slow fps shaders // or webgl2 will allow async program calls... doprograms(); } ); }
public Application(IApp page) { // per iframe there is one only. // we should be respawning async state this pointer while jmping into iframe. __base = this; #region magic var isroot = Native.window.parent == Native.window.self; //new IHTMLPre { new { isroot } }.AttachToDocument(); if (!isroot) { #region HopToParent HopToParent.VirtualOnCompleted = async (that, continuation) => { // the state is in a member variable? var r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // should not be a zero state // or do we have statemachine name clash? //new IHTMLPre { // "iframe about to jump to parent " + new { r.shadowstate.state } //}.AttachToDocument(); Native.window.parent.postMessage(r.shadowstate); // we actually wont use the response yet.. }; #endregion // start the handshake // we gain intellisense, but the type is partal, likely not respawned, acivated, initialized // new IHTMLPre { // "inside iframe awaiting state" //}.AttachToDocument(); var c = new MessageChannel(); c.port1.onmessage += m => { var that = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)m.data; //new IHTMLPre { // "inside iframe got state " + // new { that.state } // }.AttachToDocument(); // about to invoke #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( item => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(item); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return item.FullName == that.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, that.state ); } var xStringField = that.StringFields.AsEnumerable().FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion //new IHTMLPre { // "inside iframe invoke state" // }.AttachToDocument(); NewStateMachineI.MoveNext(); // we can now send one hop back? }; c.port1.start(); c.port2.start(); Native.window.parent.postMessage(null, "*", c.port2 ); return; } var lookup = new Dictionary<IHTMLIFrame, MessageEvent> { }; #region HopToIFrame HopToIFrame.VirtualOnCompleted = async (that, continuation) => { var m = default(MessageEvent); var r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); if (lookup.ContainsKey(that.frame)) { // new IHTMLPre { // "parent already nows the iframe..." //}.AttachToDocument(); m = lookup[that.frame]; } else { // new IHTMLPre { // "parent is awaiting handshake of the newly loaded iframe..." //}.AttachToDocument(); // X:\jsc.svn\examples\javascript\Test\TestSwitchToIFrame\TestSwitchToIFrame\Application.cs //var m = await that.frame.contentWindow.async.onmessage; m = await that.frame.async.onmessage; lookup[that.frame] = m; #region onmessage that.frame.ownerDocument.defaultView.onmessage += e => { if (e.source != that.frame.contentWindow) return; var shadowstate = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)e.data; // are we jumping into a new statemachine? // new IHTMLPre { // "parent saw iframe instructions to jump back " + new { shadowstate.state } //}.AttachToDocument(); // about to invoke #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( item => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(item); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return item.FullName == shadowstate.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, shadowstate.state ); } var xStringField = shadowstate.StringFields.AsEnumerable().FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion // new IHTMLPre { // "parent saw iframe instructions to jump back. invoking... " //}.AttachToDocument(); NewStateMachineI.MoveNext(); }; #endregion } //new IHTMLPre { // "parent is sending state after handshake..." //}.AttachToDocument(); m.postMessage(r.shadowstate); }; #endregion #endregion // can we log in via MID? // where is the last test? // Z:\jsc.svn\examples\javascript\crypto\VerifyIdentityAffinity\VerifyIdentityAffinity\Application.cs // can we modify roslyn to compile comments into IL? new IHTMLPre { "guest, EID, MID. which are we?" }.AttachToDocument(); new IHTMLPre { new { Native.document.location.protocol, Native.document.location.host } }.AttachToDocument(); // NFC ? new IHTMLPre { new { Native.window.navigator.userAgent } }.AttachToDocument(); var hostname = Native.document.location.host.TakeUntilIfAny(":"); var hostport = Native.document.location.host.SkipUntilOrEmpty(":"); if (string.IsNullOrEmpty(hostport)) hostport = "443"; new IHTMLPre { new { base.identity, hostname, hostport } }.AttachToDocument(); // { identity = { value = guest, signature = 70d1638ccb1627209f7d5751b989dd5cc399ff17c72aff075f2e05ff1b3c9a1f474cf5813c6470b8e9ee77b5911316acee62c6bf3534b2bc4942bc9de4344fc9 } } // doesnt jsc assetslibary do public key? // should we want to validate the identity on client? // can we? if we run on http we cant. #region EID new IHTMLButton { "EID" }.AttachToDocument().With( async e => { #region statemachine fixup? await Task.CompletedTask; #endregion // are we running nfc web browser? if (Native.window.navigator.userAgent.Contains("NFCDID")) e.innerText = "NFC DID"; // NFC ? await e.async.onclick; Native.document.body.Clear(); // https://technet.microsoft.com/en-us/library/dd979547(v=ws.10).aspx new IHTMLPre { e.innerText + " - Please insert smart card..." }.AttachToDocument(); // need hopping support. var hostport1 = Convert.ToInt32(hostport) + 1; var host1 = hostname + ":" + hostport1; var baseURI1 = "https://" + host1; iframe = new IHTMLIFrame { src = baseURI1, frameBorder = "0" }.AttachToDocument(); // if the iframe is on another port, ssl client certificate may be prompted //await (HopTo)iframe; await (HopToIFrame)iframe; // ding ding ding. //new IHTMLPre { "hello __base?" }.AttachToDocument(); //var xidenity_value = base.identity.value; //var xidenity_signature = base.identity.signature; var xidenity_value = __base.identity.value; //var xidenity_signature = __base.identity.signature; // jsc wont do byte array jumps yet? var xidenity_signature = Convert.ToBase64String(__base.identity.signature); await default(HopToParent); //new IHTMLPre { new { xidenity_value, xidenity_signature, base.identity } }.AttachToDocument(); //new IHTMLPre { new { xidenity_value, xidenity_signature, __base.identity } }.AttachToDocument(); __base.identity = new VerifiableString { value = xidenity_value, signature = Convert.FromBase64String(xidenity_signature) }; __base.foo = "bar"; Native.document.body.Clear(); new IHTMLPre { new { __base.identity, __base.foo } }.AttachToDocument(); // IE cant verify? // verify our new identity. await new IHTMLButton { "Verify" }.AttachToDocument().async.onclick; Native.document.body.style.backgroundColor = "yellow"; if (await __base.Verify()) Native.document.body.style.backgroundColor = "cyan"; else Native.document.body.style.backgroundColor = "red"; //await new IHTMLButton { "close" }.AttachToDocument().async.onclick; //// cant close? //Native.window.close(); } ); #endregion new IHTMLButton { "MID" }.AttachToDocument().With( async e => { await e.async.onclick; Native.document.body.Clear(); new IHTMLPre { "MID login..." }.AttachToDocument(); var state = await base.MobileAuthenticateAsync15(); if (state == null) { new IHTMLPre { "fault" }.AttachToDocument(); return; } new IHTMLPre { new { state.MobileAuthenticateAsync15_UserIDCode } }.AttachToDocument(); new IHTMLPre { new { state.MobileAuthenticateAsync15_Sesscode } }.AttachToDocument(); new IHTMLPre { new { state.MobileAuthenticateAsync15_ChallengeID } }.AttachToDocument(); new IHTMLCenter { state.MobileAuthenticateAsync15_ChallengeID.value }.AttachToDocument(); var sw = Stopwatch.StartNew(); //new IHTMLPre { base.MobileAuthenticateAsync15_ChallengeID, () => new { sw.ElapsedMilliseconds } }.AttachToDocument(); //using (new IHTMLPre { () => new { sw.ElapsedMilliseconds } }.AttachToDocument()) var u = (new IHTMLPre { () => new { sw.ElapsedMilliseconds } }.AttachToDocument()); { await Task.Delay(15000); sw.Stop(); } u.Dispose(); Native.document.documentElement.style.borderLeft = "2px solid yellow"; await base.MobileAuthenticateAsync15Continue(state); // { identity = { value = 14212128025, signature = 818a158d2497c54e9bde7cc7ee498b264282b709a87394be7037c09a7e38d57d515d34fa3cd7a93e8487bd477e4bd20d3f6bfbdce3c07926a1ede5935b6e5d3e } } Native.document.body.Clear(); new IHTMLPre { new { base.identity } }.AttachToDocument(); await new IHTMLButton { "Verify" }.AttachToDocument().async.onclick; Native.document.body.style.backgroundColor = "yellow"; if (await __base.Verify()) Native.document.body.style.backgroundColor = "cyan"; else Native.document.body.style.backgroundColor = "red"; } ); }
public Application(IApp page) { // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeTabsExperiment\ChromeTabsExperiment\Application.cs Console.WriteLine("enter HybridHopToUDPChromeApp Application"); dynamic self = Native.self; dynamic self_chrome = self.chrome; #region self_chrome_socket app object self_chrome_socket = self_chrome.socket; if (self_chrome_socket != null) { if (!(Native.window.opener == null && Native.window.parent == Native.window.self)) { Console.WriteLine("appwindow chrome.app.window.create, is that you?"); MessagePort appwindow_to_app = null; // called by? 619 app:HopToChromeAppWindow #region appwindow Native.window.onmessage Native.window.onmessage += e => { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // appwindow Native.window.onmessage {{ data = app to appwindow! }} var message = e.data; //Console.WriteLine("appwindow Native.window.onmessage " + new { e.data }); // extension port.onMessage {{ message = from app hello to extension }} //var expando_isstring = ScriptCoreLib.JavaScript.Runtime.Expando.Of(message).IsString; // look app sent a message to extension //Console.WriteLine("app port.onMessage " + new { message }); if (message is string) { Console.WriteLine("appwindow Native.window.onmessage: " + message); //Console.WriteLine("appwindow Native.window.onmessage: " + new { e.ports }); if (e.ports != null) foreach (var port in e.ports) { Console.WriteLine("appwindow Native.window.onmessage " + new { port }); appwindow_to_app = port; } //e.po return; } // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp // casting from anonymous object. // defined at? // "Z:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync.csproj" // clean and rebuild // 2>C:\Program Files (x86)\MSBuild\14.0\bin\Microsoft.Common.CurrentVersion.targets(1612,5): warning : The referenced project '..\..\..\..\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync.csproj' does not exist. var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)message; // or constructor id? Console.WriteLine("appwindow Native.window.onmessage " + new { xShadowIAsyncStateMachine.state, xShadowIAsyncStateMachine.TypeName }); // 12468ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }}, expando_isstring = true, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.729 view-source:53670 12471ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} }} //2015-08-22 15:49:45.733 view-source:53670 12475ms extension port.onMessage {{ message = [object Object], expando_isstring = false, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.737 view-source:53670 12479ms extension port.onMessage {{ state = 0, TypeName = <Namespace>.___ctor_b__4_9_d }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // X:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); }; #endregion #region appwindow:HopToChromeApp HopToChromeApp.VirtualOnCompleted = async (that, continuation) => { // do we have the port to send back our portal warp? // state 0 ? or state -1 ? Console.WriteLine("appwindow HopToChromeApp VirtualOnCompleted enter " + new { appwindow_to_app }); //// https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow //// async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} appwindow_to_app.postMessage("do HopToChromeAppWindow " + new { r.shadowstate.TypeName, r.shadowstate.state }); // now send the jump instruction... will it make it? appwindow_to_app.postMessage(r.shadowstate); }; #endregion } else { //Console.WriteLine("running as app"); // running as app {{ FullName = HybridHopToUDPChromeApp.Application, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null }} //Console.WriteLine("running as app " + new { typeof(Application).Assembly.FullName }); // running as app {{ Name = HybridHopToUDPChromeApp.Application }} Console.WriteLine("running as app " + new { typeof(Application).Assembly.GetName().Name } + " now reenable extension.."); // called by? #region app:appwindow_to_app Action<object> appwindow_to_app = data => { // what if its a string not a dictinary? var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)data; Console.WriteLine("app:appwindow_to_app " + new { xShadowIAsyncStateMachine.TypeName }); // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150905/hoptoudpchromeapp //13882ms app HopToChromeAppWindow MessageChannel onmessage {{ data = do HopToChromeAppWindow {{ TypeName = <Namespace>.___ctor_b__5_19_d, state = 2 }} }} //view-source:54032 13883ms app appwindow_to_app {{ TypeName = null }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { Console.WriteLine(new { xAsyncStateMachineTypeCandidate.FullName, xisIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion Console.WriteLine("app:appwindow_to_app " + new { xAsyncStateMachineType }); if (xAsyncStateMachineType == null) Debugger.Break(); var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // X:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); }; #endregion #region app:HopToChromeAppWindow HopToChromeAppWindow.VirtualOnCompleted = async (that, continuation) => { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150824/webgliframebuffer // state 0 ? or state -1 ? Console.WriteLine("app HopToChromeAppWindow VirtualOnCompleted enter "); #region outputWindow if (that.window == null) { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow if (outputWindow == null) { // https://developer.chrome.com/apps/app_window#type-CreateWindowOptions outputWindow = await chrome.app.window.create( Native.document.location.pathname, // https://developer.chrome.com/apps/app_window#type-CreateWindowOptions // this ctually works. but we wont see console on app log.. options: new { hidden = true, alwaysOnTop = true } ); ////xappwindow.setAlwaysOnTop // or can we stay hidden? //that.window.show(); await outputWindow.contentWindow.async.onload; } // reuse the window... that.window = outputWindow; } #endregion // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} // Z:\jsc.svn\core\ScriptCoreLib\JavaScript\DOM\IWindow.postMessage.cs // how do we use this thing? var c = new MessageChannel(); c.port1.onmessage += e => { //10818ms app HopToChromeAppWindow MessageChannel onmessage {{ data = do HopToChromeAppWindow {{ TypeName = <Namespace>.___ctor_b__5_19_d, state = 2 }} }} //view-source:54032 10820ms app:appwindow_to_app {{ TypeName = null }} if (e.data is string) { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150905/hoptoudpchromeapp Console.WriteLine("app c.port1.onmessage: " + e.data); return; } Console.WriteLine("app HopToChromeAppWindow MessageChannel onmessage " + new { e.data }); appwindow_to_app(e.data); }; c.port1.start(); c.port2.start(); // 15ms appwindow Native.window.onmessage: {{ ports = [object MessagePort] }} //2015-08-22 20:50:18.019 view-source:53702 17ms appwindow Native.window.onmessage: {{ port = [object MessagePort] }} that.window.contentWindow.postMessage("do HopToChromeAppWindow " + new { r.shadowstate.TypeName, r.shadowstate.state }, transfer: c.port2); // now send the jump instruction... will it make it? that.window.contentWindow.postMessage(r.shadowstate); }; #endregion // called by? #region app:ConnectExternal chrome.runtime.ConnectExternal += port => { // app chrome.runtime.ConnectExternal {{ name = , id = jadmeogmbokffpkdfeiemjplohfgkidd }} //Console.WriteLine("app chrome.runtime.ConnectExternal " + new { port.name, port.sender.id }); Console.WriteLine("app chrome.runtime.ConnectExternal " + new { port.sender.id } + " now click launch!"); new chrome.Notification(title: "HybridHopToUDPChromeApp", message: "service connected. click launch").Clicked += delegate { // https://developer.chrome.com/apps/app_runtime // management_api }; // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hybrid // should we now be able to hop to our tab? // what about if we are in an app window? // called by? port.onMessage.addListener( new Action<object>( (message) => { // extension port.onMessage {{ message = from app hello to extension }} //var expando_isstring = ScriptCoreLib.JavaScript.Runtime.Expando.Of(message).IsString; // look app sent a message to extension //Console.WriteLine("app port.onMessage " + new { message }); // did we not fix jsc? if (message is string) { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150905/hoptoudpchromeapp Console.WriteLine("app port.onMessage: " + message); return; } // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp // casting from anonymous object. var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)message; // or constructor id? Console.WriteLine("app port.onMessage " + new { xShadowIAsyncStateMachine.state, xShadowIAsyncStateMachine.TypeName }); // 12468ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }}, expando_isstring = true, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.729 view-source:53670 12471ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} }} //2015-08-22 15:49:45.733 view-source:53670 12475ms extension port.onMessage {{ message = [object Object], expando_isstring = false, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.737 view-source:53670 12479ms extension port.onMessage {{ state = 0, TypeName = <Namespace>.___ctor_b__4_9_d }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // z:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); } ) ); //port.postMessage( // new // { // text = "from app hello to extension" // } //); port.postMessage("from app hello to extension, click launch?"); // enable //await default(HopToChromeExtension); #region HopToChromeExtension HopToChromeExtension.VirtualOnCompleted = async (that, continuation) => { // state 0 ? or state -1 ? Console.WriteLine("app HopToChromeExtension VirtualOnCompleted enter "); // where is it defined? // z:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\ShadowIAsyncStateMachine.cs // async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} port.postMessage("do HopToChromeExtension " + new { r.shadowstate.TypeName, r.shadowstate.state }); // now send the jump instruction... will it make it? port.postMessage(r.shadowstate); // how would we know to continue from current continuation? // or are we fine to rebuild the scope if we jump back? }; #endregion }; #endregion chrome.runtime.MessageExternal += (message, sender, sendResponse) => { // was the extension able to pass us a message? //Console.WriteLine("chrome.runtime.MessageExternal " + new { message, sender, sendResponse }); Console.WriteLine("app: chrome.runtime.MessageExternal " + new { message }); // app chrome.runtime.MessageExternal {{ message = extension to app! }} // remember the connection to enable hop to extension? }; //Action AtLaunch = delegate { }; // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150905/hoptoudpchromeapp // jsc servicing compiler does it already let the apps know they need to reload? #region Launched // can the extension launch us too? // either the user launches by a click or we launch from extension? chrome.app.runtime.Launched += async delegate { // state 0 ? or state -1 ? Console.WriteLine("app: chrome.app.runtime.Launched before delay"); await Task.Delay(1); Console.WriteLine("app: before HopToChromeAppWindow"); //// https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // defined at? await default(HopToChromeAppWindow); // cant select ffs (Native.body.style as dynamic).webkitUserSelect = "text"; Native.body.style.overflow = IStyle.OverflowEnum.auto; Native.body.Clear(); chrome.app.window.current().show(); new IHTMLPre { "appwindow: chrome.app.window.current().show();" }.AttachToDocument(); var NetworkList = await chrome.socket.getNetworkList(); //appwindow: chrome.app.window.current().show(); //appwindow: {{ prefixLength = 64, name = {5AE7FDA4-3FE5-42B2-905A-90962F983884}, address = 2001:7d0:8424:1f01:18fb:7bdf:54a7:e32 }} //appwindow: {{ prefixLength = 64, name = {5AE7FDA4-3FE5-42B2-905A-90962F983884}, address = fe80::18fb:7bdf:54a7:e32 }} //appwindow: {{ prefixLength = 24, name = {5AE7FDA4-3FE5-42B2-905A-90962F983884}, address = 192.168.1.13 }} //appwindow: {{ prefixLength = 64, name = {7F261BE1-E637-4E3E-B766-BD56F87515A5}, address = fe80::9cb1:846a:f8c0:ae4d }} //appwindow: {{ prefixLength = 16, name = {7F261BE1-E637-4E3E-B766-BD56F87515A5}, address = 169.254.174.77 }} //appwindow: {{ prefixLength = 64, name = {296E36A9-A4D6-4994-9496-69CCFD248303}, address = fe80::742a:74b2:f2a0:d632 }} //appwindow: {{ prefixLength = 16, name = {296E36A9-A4D6-4994-9496-69CCFD248303}, address = 169.254.214.50 }} //appwindow: {{ prefixLength = 64, name = {A588C792-795A-49EA-B7B7-FF2791BD0DDA}, address = fe80::b102:9f72:e61b:59b6 }} //appwindow: {{ prefixLength = 24, name = {A588C792-795A-49EA-B7B7-FF2791BD0DDA}, address = 192.168.81.1 }} // should figure out which nics to broadcast to by default? foreach (var item in NetworkList) { new IHTMLPre { "appwindow: " + new { item.prefixLength, item.name, item.address } }.AttachToDocument(); // if we have multiple NICs broadcast em all? // Z:\jsc.svn\examples\javascript\chrome\apps\ChromeAppWindowUDPPointerLock\ChromeAppWindowUDPPointerLock\Application.cs } Console.WriteLine("appwindow: appwindow to app"); await default(HopToChromeApp); Console.WriteLine("app: appwindow to app"); // send intent over udp? }; #endregion chrome.runtime.Startup += async delegate { Console.WriteLine(@"app: chrome.runtime.Startup // lets start listening for udp. as the other device may want to click launch and jump into us. "); // Z:\jsc.svn\examples\javascript\chrome\apps\ChromeUDPReceiveAsync\ChromeUDPReceiveAsync\Application.cs // Z:\jsc.svn\examples\javascript\chrome\apps\ChromeUDPFloats\ChromeUDPFloats\Application.cs // can we run this on CLR too? var socket = new UdpClient(40014); //socket.Client.Bind( // //new IPEndPoint(IPAddress.Any, port: 40000) // new IPEndPoint(IPAddress.Any, port) //); // no port? socket.JoinMulticastGroup( IPAddress.Parse("239.1.2.3") ); while (true) { Console.WriteLine(@"app: chrome.runtime.Startup await socket.ReceiveAsync"); // Z:\jsc.svn\examples\javascript\chrome\hybrid\HybridHopToUDPChromeApp\Application.cs // X:\jsc.svn\examples\javascript\chrome\apps\ChromeUDPNotification\ChromeUDPNotification\Application.cs // X:\jsc.svn\examples\javascript\chrome\apps\ChromeUDPNotification\ChromeUDPNotification\Application.cs var s = await socket.ReceiveAsync(); Console.WriteLine($"app: recvFrom: {s.Buffer.Length}"); } }; return; } } #endregion // running as regular web page? Console.WriteLine("running as content?"); // were we loaded into chrome.app.window? //new IHTMLButton { "openDirectory" }.AttachToDocument().onclick += async delegate // { // var dir = (DirectoryEntry)await chrome.fileSystem.chooseEntry(new { type = "openDirectory" }); // }; }
public Application(IApp page) { // https://www.ssllabs.com/ssltest/analyze.html // https://sslanalyzer.comodoca.com/ // https://support.comodo.com/index.php?/Default/Knowledgebase/Article/View/683/17/firefox-error-code-sec_error_unknown_issuer // z:\jsc.svn\core\ScriptCoreLib.Ultra.Library\ScriptCoreLib.Ultra.Library\Extensions\TcpListenerExtensions.cs new { }.With( async delegate { #region magic var isroot = Native.window.parent == Native.window.self; //new IHTMLPre { new { isroot } }.AttachToDocument(); if (!isroot) { #region HopToParent HopToParent.VirtualOnCompleted = async (that, continuation) => { // the state is in a member variable? var r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // should not be a zero state // or do we have statemachine name clash? //new IHTMLPre { // "iframe about to jump to parent " + new { r.shadowstate.state } //}.AttachToDocument(); Native.window.parent.postMessage(r.shadowstate); // we actually wont use the response yet.. }; #endregion // start the handshake // we gain intellisense, but the type is partal, likely not respawned, acivated, initialized // new IHTMLPre { // "inside iframe awaiting state" //}.AttachToDocument(); var c = new MessageChannel(); c.port1.onmessage += m => { var that = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)m.data; //new IHTMLPre { // "inside iframe got state " + // new { that.state } // }.AttachToDocument(); // about to invoke #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( item => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(item); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return item.FullName == that.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, that.state ); } var xStringField = that.StringFields.AsEnumerable().FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion //new IHTMLPre { // "inside iframe invoke state" // }.AttachToDocument(); NewStateMachineI.MoveNext(); // we can now send one hop back? }; c.port1.start(); c.port2.start(); Native.window.parent.postMessage(null, "*", c.port2 ); return; } var lookup = new Dictionary<IHTMLIFrame, MessageEvent> { }; #region HopToIFrame HopToIFrame.VirtualOnCompleted = async (that, continuation) => { var m = default(MessageEvent); var r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); if (lookup.ContainsKey(that.frame)) { // new IHTMLPre { // "parent already nows the iframe..." //}.AttachToDocument(); m = lookup[that.frame]; } else { // new IHTMLPre { // "parent is awaiting handshake of the newly loaded iframe..." //}.AttachToDocument(); // X:\jsc.svn\examples\javascript\Test\TestSwitchToIFrame\TestSwitchToIFrame\Application.cs //var m = await that.frame.contentWindow.async.onmessage; m = await that.frame.async.onmessage; lookup[that.frame] = m; #region onmessage that.frame.ownerDocument.defaultView.onmessage += e => { if (e.source != that.frame.contentWindow) return; var shadowstate = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)e.data; // are we jumping into a new statemachine? // new IHTMLPre { // "parent saw iframe instructions to jump back " + new { shadowstate.state } //}.AttachToDocument(); // about to invoke #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( item => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(item); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return item.FullName == shadowstate.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, shadowstate.state ); } var xStringField = shadowstate.StringFields.AsEnumerable().FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion // new IHTMLPre { // "parent saw iframe instructions to jump back. invoking... " //}.AttachToDocument(); NewStateMachineI.MoveNext(); }; #endregion } //new IHTMLPre { // "parent is sending state after handshake..." //}.AttachToDocument(); m.postMessage(r.shadowstate); }; #endregion #endregion var hostname = Native.document.location.host.TakeUntilIfAny(":"); var hostport = Native.document.location.host.SkipUntilOrEmpty(":"); await new IHTMLButton { "login " + new{ Native.document.location.protocol, Native.document.location.host, Native.document.baseURI } }.AttachToDocument().async.onclick; // port + 1 iframe? Native.document.body.style.backgroundColor = "cyan"; var hostport1 = Convert.ToInt32(hostport) + 1; var host1 = hostname + ":" + hostport1; var baseURI1 = "https://" + host1; new IHTMLPre { new { host1 } }.AttachToDocument(); iframe = new IHTMLIFrame { src = baseURI1, frameBorder = "0" }.AttachToDocument(); // if the iframe is on another port, ssl client certificate may be prompted //await (HopTo)iframe; await (HopToIFrame)iframe; //new IHTMLPre { "did we make it into iframe yet?" }.AttachToDocument(); // yes //12031 ERROR_INTERNET_CONNECTION_RESET // The connection with the server has been reset. var id = await new ApplicationWebService { }.Identity(); //await new IHTMLButton { "lets jump back " }.AttachToDocument().async.onclick; //new IHTMLPre { "lets jump back to parent... " + new { id } }.AttachToDocument(); //await (HopTo)Native.window.parent; await default(HopToParent); //new IHTMLPre { "did we make it into parent yet? " + new { id } }.AttachToDocument(); Native.document.body.style.backgroundColor = "yellow"; new IHTMLButton { "GetSpecialData " + new { id } }.AttachToDocument().onclick += async delegate { #region statemachine fixup? await Task.CompletedTask; #endregion //new IHTMLPre { "ready to call GetSpecialData" }.AttachToDocument(); Native.document.body.style.backgroundColor = "white"; var foo = "foo1"; await (HopToIFrame)iframe; Native.document.body.style.backgroundColor = "cyan"; var data = await new ApplicationWebService { Foo = foo }.GetSpecialData(); Native.document.body.style.backgroundColor = "white"; await default(HopToParent); // forks for chrome // ie gives 404 // firefox bails new IHTMLPre { new { data } }.AttachToDocument(); Native.document.body.style.backgroundColor = "cyan"; }; } ); }
public Application(IApp page) { // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeTabsExperiment\ChromeTabsExperiment\Application.cs Console.WriteLine("enter ChromeHybridCapture Application"); dynamic self = Native.self; dynamic self_chrome = self.chrome; #region self_chrome_tabs extension object self_chrome_tabs = self_chrome.tabs; if (self_chrome_tabs != null) { // running as extension {{ FullName = <Namespace>.Application }} //Console.WriteLine("running as extension " + new { typeof(Application).FullName }); //Console.WriteLine("running as extension " + new { typeof(Application).Assembly.FullName }); // can we find and connect to app? Console.WriteLine("running as extension " + new { typeof(Application).Assembly.GetName().Name }); //70ms chrome.management.getAll //2015-08-22 13:41:33.591 view-source:53670 98ms chrome.management.getAll {{ Length = 28 }} //2015-08-22 13:41:33.594 view-source:53670 101ms ExtensionInfo {{ id = aemlnmcokphbneegoefdckonejmknohh, name = ChromeHybridCapture }} //2015-08-22 13:41:33.597 view-source:53670 104ms ExtensionInfo {{ id = apdfllckaahabafndbhieahigkjlhalf, name = Google Drive }} //2015-08-22 13:41:33.599 view-source:53670 106ms ExtensionInfo {{ id = blpcfgokakmgnkcojhhkbfbldkacnbeo, name = YouTube }} //2015-08-22 13:41:33.602 view-source:53670 109ms ExtensionInfo {{ id = cgnjcccfcjhdnbfgjgllglbhfcgndmea, name = WebGLHZBlendCharacter }} //2015-08-22 13:41:33.604 view-source:53670 111ms ExtensionInfo {{ id = coobgpohoikkiipiblmjeljniedjpjpf, name = Google Search }} //2015-08-22 13:41:33.608 view-source:53670 114ms ExtensionInfo {{ id = fkgibadjpabiongmgoeomdbcefhabmah, name = ChromeCaptureToFile.Application.exe }} //2015-08-22 13:41:33.610 view-source:53670 117ms ExtensionInfo {{ id = ghbmnnjooekpmoecnnnilnnbdlolhkhi, name = Google Docs Offline }} //2015-08-22 13:41:33.612 view-source:53670 119ms ExtensionInfo {{ id = haebnnbpedcbhciplfhjjkbafijpncjl, name = TinEye Reverse Image Search }} //2015-08-22 13:41:33.614 view-source:53670 121ms ExtensionInfo {{ id = lchcahaldakdnjlkchkgncecgpcnabgo, name = Heat Zeeker }} //2015-08-22 13:41:33.616 view-source:53670 123ms ExtensionInfo {{ id = nhkcfbkpodjkallcfebgihcoglfaniep, name = freenode irc }} //2015-08-22 13:41:33.619 view-source:53670 126ms ExtensionInfo {{ id = ogmpedngmnolclkmlpcdgmfonlagkejp, name = Private Joe: Urban Warfare }} //2015-08-22 13:41:33.621 view-source:53670 128ms ExtensionInfo {{ id = pcklgpcdddecpmkiinpkhehanbijjepn, name = idea-remixer }} //2015-08-22 13:41:33.624 view-source:53670 131ms ExtensionInfo {{ id = pjkljhegncpnkpknbcohdijeoejaedia, name = Gmail }} //2015-08-22 13:41:33.626 view-source:53670 133ms ExtensionInfo {{ id = plgmlhohecdddhbmmkncjdmlhcmaachm, name = draw.io (Legacy) }} //2015-08-22 13:41:33.629 view-source:53670 136ms ExtensionInfo {{ id = aapbdbdomjkkjkaonfhkkikfgjllcleb, name = Google Translate }} //2015-08-22 13:41:33.631 view-source:53670 138ms ExtensionInfo {{ id = bcfddoencoiedfjgepnlhcpfikgaogdg, name = QR-Code Tag Extension }} //2015-08-22 13:41:33.633 view-source:53670 139ms ExtensionInfo {{ id = coblegoildgpecccijneplifmeghcgip, name = Web Cache }} //2015-08-22 13:41:33.635 view-source:53670 142ms ExtensionInfo {{ id = ganlifbpkcplnldliibcbegplfmcfigp, name = Collusion for Chrome }} //2015-08-22 13:41:33.638 view-source:53670 145ms ExtensionInfo {{ id = gighmmpiobklfepjocnamgkkbiglidom, name = AdBlock }} //2015-08-22 13:41:33.640 view-source:53670 147ms ExtensionInfo {{ id = iiabebggdceojiejhopnopmbkgandhha, name = Operation Heat Zeeker }} //2015-08-22 13:41:33.642 view-source:53670 149ms ExtensionInfo {{ id = jkgfnfnagdnjicmonpfhhdnkdjgjdamo, name = Avalon Spider Solitaire }} //2015-08-22 13:41:33.644 view-source:53670 151ms ExtensionInfo {{ id = kdifgkljkjhpflhalpkhehlldfakggdi, name = my.jsc-solutions.net }} //2015-08-22 13:41:33.646 view-source:53670 153ms ExtensionInfo {{ id = lmjegmlicamnimmfhcmpkclmigmmcbeh, name = Application Launcher for Drive (by Google) }} //2015-08-22 13:41:33.648 view-source:53670 155ms ExtensionInfo {{ id = mmfbcljfglbokpmkimbfghdkjmjhdgbg, name = Text }} //2015-08-22 13:41:33.650 view-source:53670 157ms ExtensionInfo {{ id = molncoemjfmpgdkbdlbjmhlcgniigdnf, name = Project Naptha }} //2015-08-22 13:41:33.652 view-source:53670 159ms ExtensionInfo {{ id = ogkcjmbhnfmlnielkjhedpcjomeaghda, name = WebGL Inspector }} //2015-08-22 13:41:33.653 view-source:53670 160ms ExtensionInfo {{ id = pkngagjebplcgimojegcakmnlggmcjlc, name = LBA Redux }} //2015-08-22 13:41:33.657 view-source:53670 164ms ExtensionInfo {{ id = ppmibgfeefcglejjlpeihfdimbkfbbnm, name = Change HTTP Request Header }} Action<string> __ChromeCaptureToFile_Application_sendMessage = delegate { }; new { }.With( async delegate { // TypeError: chrome.management.getAll is not a function Console.WriteLine("chrome.management.getAll"); var extensions = await chrome.management.getAll(); Console.WriteLine("chrome.management.getAll " + new { extensions.Length }); // https://developer.chrome.com/extensions/management#type-ExtensionInfo // view - source:53670 69ms chrome.management.getAll //2015 - 08 - 22 13:34:13.514 view - source:53670 89ms chrome.management.getAll { { Length = 28 } } // 2015 - 08 - 22 13:34:13.518 view - source:53670 93ms ExtensionInfo { { item = [object Object] } } foreach (var item in extensions) { //Console.WriteLine("ExtensionInfo " + new { item }); //Console.WriteLine("ExtensionInfo " + new { item.id, item.name }); //2015-08-22 13:41:33.608 view-source:53670 114ms ExtensionInfo {{ id = fkgibadjpabiongmgoeomdbcefhabmah, name = ChromeCaptureToFile.Application.exe }} // typeof(self) ? if (item.name.StartsWith(typeof(Application).Assembly.GetName().Name)) { var __item = item; // we will also know when it reloads? we have to reconnect then? __ChromeCaptureToFile_Application_sendMessage = message => { Console.WriteLine("extension chrome.runtime.sendMessage " + new { message, __item.id, __item.name }); chrome.runtime.sendMessage(item.id, message, null); }; chrome.runtime.sendMessage(item.id, "extension to app!", null); // extension chrome.runtime.connect done {{ name = , sender = null }} chrome.runtime.connect(item.id).With( port => { //Console.WriteLine("extension chrome.runtime.connect done " + new { port.name, port.sender.id }); //Console.WriteLine("extension chrome.runtime.connect done " + new { port.name, port.sender }); Console.WriteLine("extension chrome.runtime.connect done"); #region extension: HopToChromeApp.VirtualOnCompleted // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp HopToChromeApp.VirtualOnCompleted = async (that, continuation) => { // state 0 ? or state -1 ? Console.WriteLine("extension HopToChromeApp VirtualOnCompleted enter "); TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} port.postMessage("do HopToChromeApp " + new { r.shadowstate.TypeName, r.shadowstate.state }); // now send the jump instruction... will it make it? port.postMessage(r.shadowstate); }; #endregion // is the app now able to send extension messages? port.onMessage.addListener( new Action<object>( (message) => { // 4847ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} // extension port.onMessage {{ message = from app hello to extension }} // extension port.onMessage {{ message = [object Object] }} // look app sent a message to extension // 191ms extension port.onMessage {{ message = from app hello to extension, is_string = false, equals_typeofstring = false }} // 219ms extension port.onMessage {{ message = from app hello to extension, expando_isstring = true, is_string = false, equals_typeofstring = false }} //var expando_isstring = ScriptCoreLib.JavaScript.Runtime.Expando.Of(message).IsString; // roslyn? wtf //var is_string = message is string; //var equals_typeofstring = message.GetType() == typeof(string); //Console.WriteLine("extension port.onMessage " + new { expando_isstring, is_string, equals_typeofstring }); // extension port.onMessage {{ state = null, TypeName = null }} if (message is string) { Console.WriteLine("extension port.onMessage: " + message); // Z:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\ShadowIAsyncStateMachine.cs return; } #region IAsyncStateMachine // casting from anonymous object. var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)message; // or constructor id? Console.WriteLine("extension port.onMessage " + new { xShadowIAsyncStateMachine.state, xShadowIAsyncStateMachine.TypeName }); // 12468ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }}, expando_isstring = true, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.729 view-source:53670 12471ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} }} //2015-08-22 15:49:45.733 view-source:53670 12475ms extension port.onMessage {{ message = [object Object], expando_isstring = false, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.737 view-source:53670 12479ms extension port.onMessage {{ state = 0, TypeName = <Namespace>.___ctor_b__4_9_d }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } } ); #endregion NewStateMachineI.MoveNext(); #endregion } ) ); //chrome.tabs.Created += async tab => //{ // port.postMessage("chrome.tabs.Created " + new { tab }); //}; //chrome.tabs.Updated += async (tabId, x, tab) => //{ // // Updated {{ i = 0, x = null, tab = null }} // port.postMessage("chrome.tabs.Updated " + new { tabId, x, tab }); //}; } ); } } } ); //chrome.tabs.Created += async tab => //{ // Console.WriteLine("chrome.tabs.Created " + new { tab }); //}; //chrome.tabs.Updated += async (tabId, x, tab) => //{ // // Updated {{ i = 0, x = null, tab = null }} // Console.WriteLine("chrome.tabs.Updated " + new { tabId, x, tab }); //}; return; } #endregion #region self_chrome_socket app object self_chrome_socket = self_chrome.socket; if (self_chrome_socket != null) { if (!(Native.window.opener == null && Native.window.parent == Native.window.self)) { Console.WriteLine("appwindow chrome.app.window.create, is that you?"); MessagePort appwindow_to_app = null; // called by? 619 app:HopToChromeAppWindow #region appwindow Native.window.onmessage Native.window.onmessage += e => { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // appwindow Native.window.onmessage {{ data = app to appwindow! }} var message = e.data; //Console.WriteLine("appwindow Native.window.onmessage " + new { e.data }); // extension port.onMessage {{ message = from app hello to extension }} //var expando_isstring = ScriptCoreLib.JavaScript.Runtime.Expando.Of(message).IsString; // look app sent a message to extension //Console.WriteLine("app port.onMessage " + new { message }); if (message is string) { Console.WriteLine("appwindow Native.window.onmessage: " + message); //Console.WriteLine("appwindow Native.window.onmessage: " + new { e.ports }); if (e.ports != null) foreach (var port in e.ports) { Console.WriteLine("appwindow Native.window.onmessage " + new { port }); appwindow_to_app = port; } //e.po return; } // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp // casting from anonymous object. var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)message; // or constructor id? Console.WriteLine("appwindow Native.window.onmessage " + new { xShadowIAsyncStateMachine.state, xShadowIAsyncStateMachine.TypeName }); // 12468ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }}, expando_isstring = true, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.729 view-source:53670 12471ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} }} //2015-08-22 15:49:45.733 view-source:53670 12475ms extension port.onMessage {{ message = [object Object], expando_isstring = false, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.737 view-source:53670 12479ms extension port.onMessage {{ state = 0, TypeName = <Namespace>.___ctor_b__4_9_d }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // X:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); }; #endregion #region appwindow:HopToChromeApp HopToChromeApp.VirtualOnCompleted = async (that, continuation) => { // do we have the port to send back our portal warp? // state 0 ? or state -1 ? Console.WriteLine("appwindow HopToChromeApp VirtualOnCompleted enter " + new { appwindow_to_app }); //// https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow //// async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} appwindow_to_app.postMessage("do HopToChromeAppWindow " + new { r.shadowstate.TypeName, r.shadowstate.state }); // now send the jump instruction... will it make it? appwindow_to_app.postMessage(r.shadowstate); }; #endregion } else { //Console.WriteLine("running as app"); // running as app {{ FullName = ChromeHybridCapture.Application, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null }} //Console.WriteLine("running as app " + new { typeof(Application).Assembly.FullName }); // running as app {{ Name = ChromeHybridCapture.Application }} Console.WriteLine("running as app " + new { typeof(Application).Assembly.GetName().Name } + " now reenable extension.."); #region app:appwindow_to_app Action<object> appwindow_to_app = data => { var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)data; Console.WriteLine("app appwindow_to_app " + new { xShadowIAsyncStateMachine.TypeName }); #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion Console.WriteLine("app appwindow_to_app " + new { xAsyncStateMachineType }); var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // X:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); }; #endregion #region app:HopToChromeAppWindow HopToChromeAppWindow.VirtualOnCompleted = async (that, continuation) => { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150824/webgliframebuffer // state 0 ? or state -1 ? Console.WriteLine("app HopToChromeAppWindow VirtualOnCompleted enter "); #region outputWindow if (that.window == null) { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow if (outputWindow == null) { // https://developer.chrome.com/apps/app_window#type-CreateWindowOptions outputWindow = await chrome.app.window.create( Native.document.location.pathname, // https://developer.chrome.com/apps/app_window#type-CreateWindowOptions // this ctually works. but we wont see console on app log.. options: new { hidden = true, alwaysOnTop = true } ); ////xappwindow.setAlwaysOnTop // or can we stay hidden? //that.window.show(); await outputWindow.contentWindow.async.onload; } // reuse the window... that.window = outputWindow; } #endregion // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} // Z:\jsc.svn\core\ScriptCoreLib\JavaScript\DOM\IWindow.postMessage.cs // how do we use this thing? var c = new MessageChannel(); c.port1.onmessage += e => { Console.WriteLine("app HopToChromeAppWindow MessageChannel onmessage " + new { e.data }); appwindow_to_app(e.data); }; c.port1.start(); c.port2.start(); // 15ms appwindow Native.window.onmessage: {{ ports = [object MessagePort] }} //2015-08-22 20:50:18.019 view-source:53702 17ms appwindow Native.window.onmessage: {{ port = [object MessagePort] }} that.window.contentWindow.postMessage("do HopToChromeAppWindow " + new { r.shadowstate.TypeName, r.shadowstate.state }, transfer: c.port2); // now send the jump instruction... will it make it? that.window.contentWindow.postMessage(r.shadowstate); }; #endregion #region app:ConnectExternal chrome.runtime.ConnectExternal += port => { // app chrome.runtime.ConnectExternal {{ name = , id = jadmeogmbokffpkdfeiemjplohfgkidd }} //Console.WriteLine("app chrome.runtime.ConnectExternal " + new { port.name, port.sender.id }); Console.WriteLine("app chrome.runtime.ConnectExternal " + new { port.sender.id } + " now click launch!"); new chrome.Notification(title: "ChromeHybridCapture", message: "service connected. click launch").Clicked += delegate { // https://developer.chrome.com/apps/app_runtime // management_api }; // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hybrid // should we now be able to hop to our tab? // what about if we are in an app window? port.onMessage.addListener( new Action<object>( (message) => { // extension port.onMessage {{ message = from app hello to extension }} var expando_isstring = ScriptCoreLib.JavaScript.Runtime.Expando.Of(message).IsString; // look app sent a message to extension //Console.WriteLine("app port.onMessage " + new { message }); if (expando_isstring) { Console.WriteLine("app port.onMessage: " + message); return; } #region IAsyncStateMachine // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp // casting from anonymous object. var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)message; // or constructor id? Console.WriteLine("app port.onMessage " + new { xShadowIAsyncStateMachine.state, xShadowIAsyncStateMachine.TypeName }); // 12468ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }}, expando_isstring = true, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.729 view-source:53670 12471ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} }} //2015-08-22 15:49:45.733 view-source:53670 12475ms extension port.onMessage {{ message = [object Object], expando_isstring = false, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.737 view-source:53670 12479ms extension port.onMessage {{ state = 0, TypeName = <Namespace>.___ctor_b__4_9_d }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // z:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); #endregion } ) ); //port.postMessage( // new // { // text = "from app hello to extension" // } //); port.postMessage("from app hello to extension, click launch?"); // enable //await default(HopToChromeExtension); #region HopToChromeExtension HopToChromeExtension.VirtualOnCompleted = async (that, continuation) => { // state 0 ? or state -1 ? Console.WriteLine("app HopToChromeExtension VirtualOnCompleted enter "); // where is it defined? // z:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\ShadowIAsyncStateMachine.cs // async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} port.postMessage("do HopToChromeExtension " + new { r.shadowstate.TypeName, r.shadowstate.state }); // now send the jump instruction... will it make it? port.postMessage(r.shadowstate); // how would we know to continue from current continuation? // or are we fine to rebuild the scope if we jump back? }; #endregion }; #endregion chrome.runtime.MessageExternal += (message, sender, sendResponse) => { // was the extension able to pass us a message? //Console.WriteLine("chrome.runtime.MessageExternal " + new { message, sender, sendResponse }); Console.WriteLine("app chrome.runtime.MessageExternal " + new { message }); // app chrome.runtime.MessageExternal {{ message = extension to app! }} // remember the connection to enable hop to extension? }; //Action AtLaunch = delegate { }; #region Launched // can the extension launch us too? // either the user launches by a click or we launch from extension? chrome.app.runtime.Launched += async delegate { // state 0 ? or state -1 ? Console.WriteLine("app chrome.app.runtime.Launched before delay"); await Task.Delay(1); nexttake: //Console.WriteLine("nexttake " + new { index }); Console.WriteLine("nexttake"); // using IDisposable ? await default(HopToChromeExtension); #region HopToChromeExtension // now this would be cool if it worked? Console.WriteLine("app to extension chrome.app.runtime.Launched, only state was sent over?"); // can we do our thing and jump back with the capture now? // lets create a tab for us to jump into.. //var tab = await chrome.tabs.create(new { url = "http://example.com" }); // https://developer.chrome.com/extensions/activeTab // implict/auto context hop? var tabsw = Stopwatch.StartNew(); // which window station? var tabwindow = await chrome.windows.create(new { state = "fullscreen", url = "http://www.flightradar24.com/59.15,23.86/9" }); //var tabwindow = await chrome.windows.create(new { state = "fullscreen", url = "http://example.com" }); //var tab = await chrome.tabs.create(new { url = "http://www.flightradar24.com/59.05,24.14/8" }); // would we need to hop into the tab to inspec data? Console.WriteLine("extension chrome.tabs.create done. about to capture... " + new { tabsw.ElapsedMilliseconds }); // how do we know a tab is loaded? // content takes a while to load doesnt it... await Task.Delay(7000); // Error: Invocation of form tabs.captureVisibleTab(object, null, function) doesn't match definition tabs.captureVisibleTab(optional integer windowId, optional object options, function callback) //var captureVisibleTab = await tab.windowId.captureVisibleTab(null); // Unchecked runtime.lastError while running tabs.captureVisibleTab: Failed to capture tab: unknown error retry_captureVisibleTab: var captureVisibleTab = await tabwindow.id.captureVisibleTab(options: new { format = "png" }); if (captureVisibleTab == null) { await Task.Delay(500); Console.WriteLine("extension chrome.tabs.create done. about to capture... error"); goto retry_captureVisibleTab; } // extension captureVisibleTab {{ Length = 47743 }} Console.WriteLine("extension captureVisibleTab " + new { captureVisibleTab.Length }); await Task.Delay(500); // or just unload the window? //await tab.id.remove(); await tabwindow.id.remove(); Console.WriteLine("extension to app chrome.tabs.create removed, jump back?"); #endregion await default(HopToChromeApp); // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp Console.WriteLine("extension to app chrome.tabs.create removed, jump back done! did the strings make it?"); if (captureVisibleTab == null) Console.WriteLine("app chrome.tabs.create removed, jump back done! did the strings make it? no"); else Console.WriteLine("app chrome.tabs.create removed, jump back done! did the strings make it? yes " + new { captureVisibleTab.Length }); Console.WriteLine("app chrome.fileSystem.chooseEntry"); // not available in background? // TypeError: Cannot read property 'chooseEntry' of undefined // Unchecked runtime.lastError while running fileSystem.chooseEntry: Invalid calling page. This function can't be called from a background page. //var dir = (DirectoryEntry)await chrome.fileSystem.chooseEntry(new { type = "openDirectory" }); // can we jump to extension to open our tab? //// https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // defined at? await default(HopToChromeAppWindow); #region HopToChromeAppWindow if (captureVisibleTab == null) Console.WriteLine("appwindow chrome.tabs.create removed, jump back done! did the strings make it? no"); else Console.WriteLine("appwindow chrome.tabs.create removed, jump back done! did the strings make it? yes " + new { captureVisibleTab.Length }); // 182ms appwindow chrome.fileSystem.chooseEntry Console.WriteLine("appwindow chrome.fileSystem.chooseEntry"); // Unchecked runtime.lastError while running fileSystem.chooseEntry: User cancelled Native.body.style.overflow = IStyle.OverflowEnum.auto; Native.body.Clear(); chrome.app.window.current().show(); var icaptureVisibleTabFull = await new IHTMLImage { src = captureVisibleTab }.async.oncomplete; ; // 200, 80 // 1600, 880 // 1920x1080 var focusw = icaptureVisibleTabFull.width - 320; var focush = icaptureVisibleTabFull.height - 200; new IHTMLPre { new { focusw, focush } }.AttachToDocument(); var focus = new CanvasRenderingContext2D(focusw, focush); focus.drawImage(icaptureVisibleTabFull, 200, 80, focusw, focush, 0, 0, focusw, focush); // this is a thumbnail var icaptureVisibleTab = new IHTMLImage { src = captureVisibleTab }.AttachToDocument(); new IStyle(icaptureVisibleTab) { width = "120px", border = "1px dashed blue" }; Native.document.documentElement.style.overflow = IStyle.OverflowEnum.auto; if (dir == null) { await new IHTMLButton { "openDirectory" }.AttachToDocument().async.onclick; dir = (DirectoryEntry)await chrome.fileSystem.chooseEntry(new { type = "openDirectory" }); } var file = index.ToString().PadLeft(5, '0') + ".png"; new IHTMLPre { "WriteAllBytes... " + new { file } }.AttachToDocument(); //await dir.WriteAllBytes("0001.png", icaptureVisibleTabFull); // chrome://blob-internals/ // those blobs wont go away... // GC kicks in at 36 it seems. await dir.WriteAllBytes(file, focus); focus = null; // [Window Title] //Location is not available //[Content] //R:\ is not accessible. //Logon failure: unknown user name or bad password. //[OK] // --------------------------- // Restoring Network Connections //--------------------------- //An error occurred while reconnecting R: // to //\\192.168.1.12\x$ //Microsoft Windows Network: The local device name is already in use. //This connection has not been restored. //--------------------------- //OK //-------------------------- - new IHTMLPre { "WriteAllBytes... done " + new { file } }.AttachToDocument(); index++; #endregion //Console.WriteLine("app chrome.app.window content loaded!"); //Console.WriteLine("app chrome.app.runtime.Launched ready to exit"); //await Task.Delay(3000); //// wont work? //w.close(); ////1343ms app chrome.runtime.MessageExternal {{ message = extension to app! }} ////2015-08-22 15:18:44.738 view-source:53670 1357ms app chrome.runtime.ConnectExternal {{ id = jadmeogmbokffpkdfeiemjplohfgkidd }} ////2015-08-22 15:18:52.314 view-source:53670 8933ms app chrome.app.runtime.Launched ////2015-08-22 15:18:52.342 view-source:53670 8961ms app chrome.app.runtime.Launched exit ////2015-08-22 15:18:52.348 view-source:53670 8967ms app port.onMessage {{ message = chrome.tabs.Created {{ tab = [object Object] }} }} ////2015-08-22 15:18:52.652 view-source:53670 9271ms app port.onMessage {{ message = chrome.tabs.Updated {{ tabId = 419, x = [object Object], tab = [object Object] }} }} ////2015-08-22 15:18:52.690 view-source:53670 9308ms app port.onMessage {{ message = chrome.tabs.Updated {{ tabId = 419, x = [object Object], tab = [object Object] }} }} //Console.WriteLine("app chrome.app.runtime.Launched exit"); // or tcp? //await new IHTMLButton { "next take" }.AttachToDocument().async.onclick; // var countdown = Stopwatch.StartNew(); //Error CS1929 'int' does not contain a definition for 'GetAwaiter' and the best extension method overload 'IXMLHttpRequestAsyncExtensions.GetAwaiter(IXMLHttpRequest)' requires a receiver of type 'IXMLHttpRequest' ChromeHybridCapture Z:\jsc.svn\examples\javascript\chrome\hybrid\ChromeHybridCapture\ChromeHybridCapture\Application.cs 1141 IntelliSense // script: error JSC1000: No implementation found for this native method, please implement [static System.TimeSpan.op_Subtraction(System.TimeSpan, System.TimeSpan)] // TypeError: Cannot set property 'countdown' of null // Cannot set property 'sw' of null countdown = Stopwatch.StartNew(); new IHTMLPre { () => "close to abort... " + countdown.ElapsedMilliseconds }.AttachToDocument(); // GC? await Task.Delay(2000); //await Task.WhenAny( // new IHTMLButton { // "click next take or wait " // }.AttachToDocument().async.onclick, // Task.Delay(1000) // ); //await // new IHTMLButton { // "click next take " // }.AttachToDocument().async.onclick; new IHTMLPre { "preparing..." }.AttachToDocument(); Console.WriteLine("appwindow: appwindow to app"); await default(HopToChromeApp); Console.WriteLine("app: appwindow to app"); goto nexttake; }; #endregion return; } } #endregion // running as regular web page? Console.WriteLine("running as content?"); // were we loaded into chrome.app.window? //new IHTMLButton { "openDirectory" }.AttachToDocument().onclick += async delegate // { // var dir = (DirectoryEntry)await chrome.fileSystem.chooseEntry(new { type = "openDirectory" }); // }; }
/// <summary> /// This is a javascript application. /// </summary> /// <param name="page">HTML document rendered by the web server which can now be enhanced.</param> public Application(IApp page) { // { self = [object Window] } //var self = new IFunction("return this;").apply(null); // { self = [object Window], window = [object Window], screen = [object Screen], document = [object HTMLDocument], page = [object Object] } Console.WriteLine(new { Native.self, Native.window, Native.screen, Native.document, page }); Native.worker.With( worker => { worker.onmessage += e => { // onmessage: { data = mirror: { data = hey you, ports = 1 } } worker.postMessage( "mirror: " + new { e.data, ports = e.ports.Length } ); e.ports.WithEach( port => { port.postMessage( "port mirror: " + new { e.data, ports = e.ports.Length } ); } ); }; worker.postMessage( "hello from worker? " + new { Native.self, Native.window, Native.screen, Native.document, page } ); } ); Native.document.With( document => { // what if we are in web worker? // Uncaught ReferenceError: document is not defined new IHTMLButton { innerText = "worker" }.AttachToDocument().WhenClicked( delegate { Console.WriteLine("before Worker"); //var tt = new Thread(); // Error 1 'ScriptCoreLib.JavaScript.DOM.Worker.Worker(System.Action<ScriptCoreLib.JavaScript.DOM.DedicatedWorkerGlobalScope>)' is obsolete: 'not implemented yet' x:\jsc.svn\examples\javascript\OmniWebWorkerExperiment\OmniWebWorkerExperiment\Application.cs 87 38 OmniWebWorkerExperiment var ww = new Worker( (DedicatedWorkerGlobalScope worker) => { // running in worker context. cannot talk to outer scope yet. worker.postMessage("xxx"); } ); ww.onmessage += e => { Console.WriteLine("ww.onmessage: " + new { e.data }); }; var w = new Worker(); w.onmessage += e => { Console.WriteLine("onmessage: " + new { e.data }); // onmessage: { data = hello from worker? 1 } }; var c = new MessageChannel(); c.port1.onmessage += e => { Console.WriteLine("port1.onmessage: " + new { e.data }); // onmessage: { data = hello from worker? 1 } }; c.port1.start(); c.port2.start(); // Transferable should be an interface? w.postMessage("hey you", new[] { c.port2 }); //w.postMessage("hey you", new[] { (Transferable)(object)c.port2 }); Console.WriteLine("after Worker"); //onmessage: { data = hello from worker? { self = [object global], window = , screen = , document = , page = } } //onmessage: { data = mirror: { data = hey you } } } ); } ); }
public Application(IApp page) { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20151101 // first lets do some chrome extension magic. dynamic self = Native.self; dynamic self_chrome = self.chrome; #region self_chrome_tabs extension object self_chrome_tabs = self_chrome.tabs; if (self_chrome_tabs != null) { Console.WriteLine("running as extension " + new { typeof(Application).Assembly.GetName().Name }); // verified. // running as extension {{ Name = ChromeHybridCaptureAE.Application }} new { }.With( async delegate { app = (await chrome.management.getAll()).FirstOrDefault(item => item.name.StartsWith(typeof(Application).Assembly.GetName().Name)); if (app == null) { Console.WriteLine("running as extension. app not found."); return; } // running as extension {{ shortName = ChromeHybridCaptureAE.Application.exe, launchType = OPEN_AS_WINDOW }} Console.WriteLine("running as extension " + new { app.shortName, app.launchType }); chrome.runtime.connect(app.id).With( async (chrome.Port port) => { //Console.WriteLine("extension chrome.runtime.connect done " + new { port.name, port.sender.id }); //Console.WriteLine("extension chrome.runtime.connect done " + new { port.name, port.sender }); Console.WriteLine("extension chrome.runtime.connect done, click launch"); #region extension: HopToChromeApp.VirtualOnCompleted // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp HopToChromeApp.VirtualOnCompleted = async (that, continuation) => { // state 0 ? or state -1 ? Console.WriteLine("extension HopToChromeApp enter "); TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // now send the jump instruction... will it make it? port.postMessage(r.shadowstate); }; #endregion // is async better than event += here? var m = default(chrome.PortMessageEvent); while (m = await port.async.onmessage) { var message = m.data; // verified. #region IAsyncStateMachine // casting from anonymous object. var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)message; // 12961ms extension port.onMessage {{ state = null, TypeName = null }} // or constructor id? Console.WriteLine("extension port.onMessage " + new { xShadowIAsyncStateMachine.state, xShadowIAsyncStateMachine.TypeName }); // 12468ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }}, expando_isstring = true, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.729 view-source:53670 12471ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} }} //2015-08-22 15:49:45.733 view-source:53670 12475ms extension port.onMessage {{ message = [object Object], expando_isstring = false, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.737 view-source:53670 12479ms extension port.onMessage {{ state = 0, TypeName = <Namespace>.___ctor_b__4_9_d }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion Console.WriteLine(new { xAsyncStateMachineType }); var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); #endregion } } ); } ); return; } #endregion object self_chrome_socket = self_chrome.socket; if (self_chrome_socket != null) { #region running as appwindow if (!(Native.window.opener == null && Native.window.parent == Native.window.self)) { Console.WriteLine("running as appwindow"); MessagePort appwindow_to_app2 = null; // called by? 619 app:HopToChromeAppWindow #region appwindow Native.window.onmessage Native.window.onmessage += e => { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // appwindow Native.window.onmessage {{ data = app to appwindow! }} var message = e.data; //Console.WriteLine("appwindow Native.window.onmessage " + new { e.data }); // extension port.onMessage {{ message = from app hello to extension }} //var expando_isstring = ScriptCoreLib.JavaScript.Runtime.Expando.Of(message).IsString; // look app sent a message to extension //Console.WriteLine("app port.onMessage " + new { message }); { // DataCloneError: Failed to execute 'postMessage' on 'Window': Port at index 0 is already neutered. if (e.ports != null) foreach (var port in e.ports) { Console.WriteLine("appwindow Native.window.onmessage " + new { port }); appwindow_to_app2 = port; } } // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp // casting from anonymous object. var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)message; // or constructor id? Console.WriteLine("appwindow Native.window.onmessage " + new { xShadowIAsyncStateMachine.state, xShadowIAsyncStateMachine.TypeName }); // 12468ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }}, expando_isstring = true, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.729 view-source:53670 12471ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} }} //2015-08-22 15:49:45.733 view-source:53670 12475ms extension port.onMessage {{ message = [object Object], expando_isstring = false, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.737 view-source:53670 12479ms extension port.onMessage {{ state = 0, TypeName = <Namespace>.___ctor_b__4_9_d }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // X:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); }; #endregion #region appwindow:HopToChromeApp HopToChromeApp.VirtualOnCompleted = async (that, continuation) => { // do we have the port to send back our portal warp? // state 0 ? or state -1 ? Console.WriteLine("appwindow HopToChromeApp enter " + new { appwindow_to_app2 }); // appwindow HopToChromeApp enter {{ appwindow_to_app2 = null }} //// https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow //// async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} //appwindow_to_app.postMessage("do HopToChromeAppWindow " + new { r.shadowstate.TypeName, r.shadowstate.state }); // now send the jump instruction... will it make it? appwindow_to_app2.postMessage(r.shadowstate); }; #endregion return; } #endregion // running as app {{ Name = ChromeHybridCaptureAE.Application }} now reenable extension.. Console.WriteLine("running as app " + new { typeof(Application).Assembly.GetName().Name } + " now reenable extension.."); #region app:appwindow_to_app Action<object> appwindow_to_app = data => { var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)data; Console.WriteLine("app appwindow_to_app " + new { xShadowIAsyncStateMachine.TypeName }); #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion Console.WriteLine("app appwindow_to_app " + new { xAsyncStateMachineType }); var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // X:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); }; #endregion var c = new MessageChannel(); var cneutered = c; c.port1.onmessage += e => { Console.WriteLine("app HopToChromeAppWindow MessageChannel onmessage " + new { e.data }); appwindow_to_app(e.data); }; c.port1.start(); c.port2.start(); #region app:HopToChromeAppWindow HopToChromeAppWindow.VirtualOnCompleted = async (that, continuation) => { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150824/webgliframebuffer // state 0 ? or state -1 ? Console.WriteLine("app HopToChromeAppWindow enter "); #region outputWindow if (that.window == null) { // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow if (outputWindow == null) { // https://developer.chrome.com/apps/app_window#type-CreateWindowOptions outputWindow = await chrome.app.window.create( Native.document.location.pathname, // https://developer.chrome.com/apps/app_window#type-CreateWindowOptions // this ctually works. but we wont see console on app log.. options: new { hidden = true, alwaysOnTop = true } ); ////xappwindow.setAlwaysOnTop // or can we stay hidden? //that.window.show(); await outputWindow.contentWindow.async.onload; } // reuse the window... that.window = outputWindow; } #endregion // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // 29035ms extension port.onMessage {{ message = do HopToChromeExtension }} // Z:\jsc.svn\core\ScriptCoreLib\JavaScript\DOM\IWindow.postMessage.cs // how do we use this thing? // 15ms appwindow Native.window.onmessage: {{ ports = [object MessagePort] }} //2015-08-22 20:50:18.019 view-source:53702 17ms appwindow Native.window.onmessage: {{ port = [object MessagePort] }} //that.window.contentWindow.postMessage("do HopToChromeAppWindow " + new { r.shadowstate.TypeName, r.shadowstate.state }, transfer: c.port2); // now send the jump instruction... will it make it? if (cneutered != null) { that.window.contentWindow.postMessage(r.shadowstate, transfer: cneutered.port2); cneutered = null; } else { that.window.contentWindow.postMessage(r.shadowstate); } }; #endregion #region ConnectExternal chrome.runtime.ConnectExternal += async port => { // app chrome.runtime.ConnectExternal {{ id = jadmeogmbokffpkdfeiemjplohfgkidd }} now click launch! Console.WriteLine("app chrome.runtime.ConnectExternal " + new { port.sender.id } + " now click launch!"); new chrome.Notification( title: typeof(Application).Assembly.GetName().Name, message: "ready. click launch" ).Clicked += delegate { // https://developer.chrome.com/apps/app_runtime // management_api }; // can we have async thing here? #region HopToChromeExtension HopToChromeExtension.VirtualOnCompleted = async (that, continuation) => { // state 0 ? or state -1 ? Console.WriteLine("app HopToChromeExtension enter "); // where is it defined? // z:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\ShadowIAsyncStateMachine.cs // async dont like ref? TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableContinuation r = TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine.ResumeableFromContinuation(continuation); // now send the jump instruction... will it make it? port.postMessage(r.shadowstate); // how would we know to continue from current continuation? // or are we fine to rebuild the scope if we jump back? }; #endregion var m = default(chrome.PortMessageEvent); while (m = await port.async.onmessage) { //var m = await port.async.onmessage; var message = m.data; #region IAsyncStateMachine // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeapp // casting from anonymous object. var xShadowIAsyncStateMachine = (TestSwitchToServiceContextAsync.ShadowIAsyncStateMachine)message; // or constructor id? Console.WriteLine("app port.onMessage " + new { xShadowIAsyncStateMachine.state, xShadowIAsyncStateMachine.TypeName }); // 12468ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }}, expando_isstring = true, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.729 view-source:53670 12471ms extension port.onMessage {{ message = do HopToChromeExtension {{ TypeName = <Namespace>.___ctor_b__4_9_d, state = 0 }} }} //2015-08-22 15:49:45.733 view-source:53670 12475ms extension port.onMessage {{ message = [object Object], expando_isstring = false, is_string = false, equals_typeofstring = false }} //2015-08-22 15:49:45.737 view-source:53670 12479ms extension port.onMessage {{ state = 0, TypeName = <Namespace>.___ctor_b__4_9_d }} #region xAsyncStateMachineType var xAsyncStateMachineType = typeof(Application).Assembly.GetTypes().FirstOrDefault( xAsyncStateMachineTypeCandidate => { // safety check 1 //Console.WriteLine(new { sw.ElapsedMilliseconds, item.FullName }); var xisIAsyncStateMachine = typeof(IAsyncStateMachine).IsAssignableFrom(xAsyncStateMachineTypeCandidate); if (xisIAsyncStateMachine) { //Console.WriteLine(new { item.FullName, isIAsyncStateMachine }); return xAsyncStateMachineTypeCandidate.FullName == xShadowIAsyncStateMachine.TypeName; } return false; } ); #endregion var NewStateMachine = FormatterServices.GetUninitializedObject(xAsyncStateMachineType); var isIAsyncStateMachine = NewStateMachine is IAsyncStateMachine; var NewStateMachineI = (IAsyncStateMachine)NewStateMachine; #region 1__state xAsyncStateMachineType.GetFields( System.Reflection.BindingFlags.Public | System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance ).WithEach( AsyncStateMachineSourceField => { //Console.WriteLine(new { AsyncStateMachineSourceField }); if (AsyncStateMachineSourceField.Name.EndsWith("1__state")) { AsyncStateMachineSourceField.SetValue( NewStateMachineI, xShadowIAsyncStateMachine.state ); } // z:\jsc.svn\examples\javascript\async\Test\TestSwitchToServiceContextAsync\TestSwitchToServiceContextAsync\CLRWebServiceInvoke.cs // field names/ tokens need to be encrypted like typeinfo. // some do manual restore // X:\jsc.svn\examples\javascript\chrome\extensions\ChromeExtensionHopToTabThenIFrame\ChromeExtensionHopToTabThenIFrame\Application.cs // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow // or, are we supposed to initialize a string value here? var xStringField = TestSwitchToServiceContextAsync.ArrayListExtensions.AsEnumerable(xShadowIAsyncStateMachine.StringFields).FirstOrDefault( f => DecoratedString(f.FieldName) == DecoratedString(AsyncStateMachineSourceField.Name) ); if (xStringField != null) { // once we are to go back to client. we need to reverse it? AsyncStateMachineSourceField.SetValue( NewStateMachineI, xStringField.value ); // next xml? // before lets send our strings back with the new state! // what about exceptions? } } ); #endregion NewStateMachineI.MoveNext(); #endregion } }; #endregion // nuget chrome chrome.app.runtime.Launched += async delegate { { fixup: await Task.CompletedTask; } Console.WriteLine("app Launched, will hop to extension"); // verified. await default(HopToChromeExtension); // https://developer.chrome.com/extensions/management // as an extension we now can inspect our app ? Console.WriteLine("hop from app to extension " + new { app.name }); // hop from app to extension {{ name = ChromeHybridCaptureAE.Application.exe }} // what else can we do as an extension? // lets hop back? await default(HopToChromeApp); Console.WriteLine("hop from extension to app "); // ok hopping works. lets do some ui now. //// https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150822/hoptochromeappwindow await default(HopToChromeAppWindow); Native.document.documentElement.style.overflow = IStyle.OverflowEnum.auto; //Native.body.style.overflow = IStyle.OverflowEnum.auto; Native.body.Clear(); (Native.body.style as dynamic).webkitUserSelect = "text"; chrome.app.window.current().show(); // now what? new IHTMLPre { "now what?" }.AttachToDocument(); // lets have some ui to do a fullsceen tab capture? // http://earth.nullschool.net/#2015/10/31/1500Z/wind/surface/level/anim=off/overlay=temp/azimuthal_equidistant=24.64,98.15,169 // http://earth.nullschool.net/#2015/10/31/2100Z/wind/surface/level/anim=off/overlay=temp/azimuthal_equidistant=24.64,98.15,169 // TypeError: Cannot set property 'uri' of null // jsc statemachine hop doesnt like scopes yet. staic it is. uri = new IHTMLInput { value = "http://earth.nullschool.net/#2015/10/31/2100Z/wind/surface/level/anim=off/overlay=temp/azimuthal_equidistant=24.64,98.15,169" }.AttachToDocument(); uri.style.width = "100%"; Console.WriteLine("appwindow: " + new { uri }); new IHTMLPre { () => new { index } }.AttachToDocument(); frameID = new IHTMLInput { type = ScriptCoreLib.Shared.HTMLInputTypeEnum.range, min = 0, //max = 3600, max = 240, valueAsNumber = 0 }.AttachToDocument().With( async i => { do { // http://earth.nullschool.net/#2015/10/01/0000Z/wind/surface/level/anim=off/overlay=temp/azimuthal_equidistant=24.64,98.15,169 index = (int)i.valueAsNumber; var hh = 3 * index; var dd = 1 + Math.Floor(hh / 24.0); uri.value = "http://earth.nullschool.net/#2015/10/" + dd.ToString().PadLeft(2, '0') + "/" + (hh % 24).ToString().PadLeft(2, '0') + "00Z/wind/surface/level/anim=off/overlay=temp/azimuthal_equidistant=24.64,98.15,169"; } while (await i.async.onchange); } ); go = new IHTMLButton { "go" }.AttachToDocument(); Console.WriteLine("appwindow: " + new { go }); go.onclick += async delegate { //Error CS0158 The label 'fixup' shadows another label by the same name in a contained scope ChromeHybridCaptureAE Z:\jsc.svn\examples\javascript\chrome\hybrid\ChromeHybridCaptureAE\Application.cs 791 { fixup: await Task.CompletedTask; } Native.body.style.backgroundColor = "yellow"; var scope_uri = uri.value; #region await default(HopToChromeExtension) await default(HopToChromeApp); Console.WriteLine("hop from appwindow to app! " + new { scope_uri }); // verify await default(HopToChromeExtension); #endregion Console.WriteLine("hop from app to extension! " + new { scope_uri }); // hop from app to extension! {{ scope_uri = http://earth.nullschool.net/#2015/10/31/2100Z/wind/surface/level/anim=off/overlay=temp/azimuthal_equidistant=24.64,98.15,169 }} var tabwindow = await chrome.windows.create(new { state = "fullscreen", url = scope_uri }); // um. unless we hop into it we wont know when its ready? //await Task.Delay(7000); await Task.Delay(5000); // Error: Invalid value for argument 2. Property 'format': Value must be one of: [jpeg, png]. at validate var captureVisibleTab = await tabwindow.id.captureVisibleTab(options: new { format = "jpeg" }); Console.WriteLine("extension captureVisibleTab " + new { captureVisibleTab.Length }); await tabwindow.id.remove(); #region await default(HopToChromeAppWindow) await default(HopToChromeApp); Console.WriteLine("app " + new { captureVisibleTab.Length }); await default(HopToChromeAppWindow); Console.WriteLine("appwindow " + new { captureVisibleTab.Length }); #endregion // appwindow {{ Length = 272711 }} var icaptureVisibleTabFull = await new IHTMLImage { src = captureVisibleTab }.async.oncomplete; // {{ width = 1920, height = 1080 }} new IHTMLPre { new { icaptureVisibleTabFull.width, icaptureVisibleTabFull.height } } ; // .AttachToDocument(); var focus = new CanvasRenderingContext2D(icaptureVisibleTabFull.height, icaptureVisibleTabFull.height); focus.drawImage(icaptureVisibleTabFull, (icaptureVisibleTabFull.width - icaptureVisibleTabFull.height) / 2, 0, icaptureVisibleTabFull.height, icaptureVisibleTabFull.height, 0, 0, icaptureVisibleTabFull.height, icaptureVisibleTabFull.height); var icaptureVisibleTab = new IHTMLImage { src = focus.canvas.toDataURL() }.AttachToDocument(); icaptureVisibleTab.style.width = "100%"; icaptureVisibleTab.AttachToDocument(); await new IHTMLButton { "save " }.AttachToDocument().async.onclick; if (dir == null) dir = (DirectoryEntry)await chrome.fileSystem.chooseEntry(new { type = "openDirectory" }); var file = index.ToString().PadLeft(5, '0') + ".jpg"; await dir.WriteAllBytes(file, focus); //frameID.valueAsNumber++; await new IHTMLButton { "automate " + new { frameID = frameID.valueAsNumber } }.AttachToDocument().async.onclick; //new IHTMLPre { uri.value }.AttachToDocument(); next: frameID.valueAsNumber++; await Native.window.async.onframe; await Native.window.async.onframe; //new IHTMLPre { uri.value }.AttachToDocument(); // go? // TypeError: Cannot read property 'id' of null scope_uri = uri.value; #region await default(HopToChromeExtension) await default(HopToChromeApp); Console.WriteLine("hop from appwindow to app! " + new { scope_uri }); // verify await default(HopToChromeExtension); #endregion var tabwindow2 = await chrome.windows.create(new { state = "fullscreen", url = scope_uri }); await Task.Delay(5000); var captureVisibleTab2 = await tabwindow2.id.captureVisibleTab(options: new { format = "jpeg" }); await tabwindow2.id.remove(); #region await default(HopToChromeAppWindow) await default(HopToChromeApp); Console.WriteLine("app " + new { captureVisibleTab.Length }); await default(HopToChromeAppWindow); Console.WriteLine("appwindow " + new { captureVisibleTab.Length }); #endregion var icaptureVisibleTabFull2 = await new IHTMLImage { src = captureVisibleTab2 }.async.oncomplete; var focus2 = new CanvasRenderingContext2D(icaptureVisibleTabFull2.height, icaptureVisibleTabFull2.height); focus2.drawImage(icaptureVisibleTabFull2, (icaptureVisibleTabFull2.width - icaptureVisibleTabFull2.height) / 2, 0, icaptureVisibleTabFull2.height, icaptureVisibleTabFull2.height, 0, 0, icaptureVisibleTabFull2.height, icaptureVisibleTabFull2.height); var icaptureVisibleTab2 = new IHTMLImage { src = focus2.canvas.toDataURL() }; var file2 = index.ToString().PadLeft(5, '0') + ".jpg"; await dir.WriteAllBytes(file2, focus2); // done? goto next; }; await default(HopToChromeApp); Console.WriteLine("hop from appwindow to app!"); }; return; } Console.WriteLine("running as content?"); }
// who is calling? // triggered by InternalInvoke static void __worker_onfirstmessage( MessageEvent e, int InternalThreadCounter, object data___string, bool[] MethodTargetObjectDataIsProgress, object[] MethodTargetObjectData, // https://sites.google.com/a/jsc-solutions.net/backlog/knowledge-base/2014/201411/20141112 object[] MethodTargetObjectDataTypes, object MethodTargetTypeIndex, // set by ? string MethodToken, string MethodType, object state_ObjectData, object stateTypeHandleIndex, object state, bool IsIProgress, //bool IsTuple2_Item1_IsIProgress, __Task<object>[] TaskArray ) { // https://sites.google.com/a/jsc-solutions.net/backlog/knowledge-base/2015/201501/20150111 #region ConsoleFormWriter var w = new InternalInlineWorkerTextWriter(); var o = Console.Out; Console.SetOut(w); w.AtWrite = AtWrite => { // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs //dynamic zdata = new object(); //zdata.AtWrite = x; // working with multiple threads, keep the id in the log! // () means we are setting the thread up... [] is the thread AtWrite = "W[" + Thread.CurrentThread.ManagedThreadId + "] " + AtWrite; var zdata = new { AtWrite }; foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } }; #endregion __Thread.InternalCurrentThread.ManagedThreadId = InternalThreadCounter; __Thread.InternalCurrentThread.IsBackground = true; // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic self = Native.self; var stateType = default(Type); if (stateTypeHandleIndex != null) stateType = Type.GetTypeFromHandle(new __RuntimeTypeHandle((IntPtr)self[stateTypeHandleIndex])); // X:\jsc.svn\examples\javascript\async\AsyncNonStaticHandler\AsyncNonStaticHandler\Application.cs var MethodTargetType = default(Type); if (MethodTargetTypeIndex != null) MethodTargetType = Type.GetTypeFromHandle(new __RuntimeTypeHandle((IntPtr)self[MethodTargetTypeIndex])); // stateType = <Namespace>.xFoo, // MethodTargetTypeIndex = type$GV0nCx_bM8z6My5NDh7GXlQ, Console.WriteLine( "__worker_onfirstmessage: " + new { Thread.CurrentThread.ManagedThreadId, Native.worker.location.href, MethodTargetTypeIndex, MethodTargetType, MethodToken, MethodType, //IsTuple2_Item1_IsIProgress, // X:\jsc.svn\examples\javascript\test\TestTypeHandle\TestTypeHandle\Application.cs stateTypeHandleIndex, stateType, state, IsIProgress, //MethodTokenReference } ); #region MethodTokenReference var MethodTokenReference = default(IFunction); var MethodTarget = default(object); if (MethodTargetType == null) { MethodTokenReference = IFunction.Of(MethodToken); } else { MethodTarget = FormatterServices.GetUninitializedObject(MethodTargetType); var MethodTargetTypeSerializableMembers = FormatterServices.GetSerializableMembers(MethodTargetType); // X:\jsc.svn\examples\javascript\async\test\TestWorkerScopeProgress\TestWorkerScopeProgress\Application.cs for (int i = 0; i < MethodTargetTypeSerializableMembers.Length; i++) { var xMember = MethodTargetTypeSerializableMembers[i] as FieldInfo; var xObjectData = MethodTargetObjectData[i]; var xMethodTargetObjectDataTypeIndex = MethodTargetObjectDataTypes[i]; var xIsProgress = MethodTargetObjectDataIsProgress[i]; // X:\jsc.svn\examples\javascript\chrome\apps\ChromeTCPServer\ChromeTCPServer\Application.cs // does our chrome tcp server get the damn path? // https://sites.google.com/a/jsc-solutions.net/work/knowledge-base/15-dualvr/20150428 //Console.WriteLine(new { xMember, xMethodTargetObjectDataTypeIndex, xObjectData, xIsProgress }); Console.WriteLine(new { xMember, xMethodTargetObjectDataTypeIndex, xIsProgress }); // need to resurrect the semaphores! // X:\jsc.svn\examples\javascript\async\Test\TestSemaphoreSlim\TestSemaphoreSlim\ApplicationControl.cs #region MethodTargetObjectDataIsProgress // cant we use xMethodTargetObjectDataType instead? if (xIsProgress) { var ii = i; MethodTargetObjectData[ii] = new __Progress<object>( ProgressEvent => { // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic zdata = new object(); zdata.MethodTargetObjectDataProgressReport = new { ProgressEvent, ii }; foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } //Console.WriteLine(new { MethodTargetTypeSerializableMember, MethodTargetTypeSerializableMemberIsProgress, ProgressEvent }); } ); } #endregion else { var xMethodTargetObjectDataType = default(Type); if (xMethodTargetObjectDataTypeIndex != null) xMethodTargetObjectDataType = Type.GetTypeFromHandle(new __RuntimeTypeHandle((IntPtr)self[xMethodTargetObjectDataTypeIndex])); // now we know the type. should we review it? if (xMethodTargetObjectDataType != null) { var scope2copy = FormatterServices.GetUninitializedObject(xMethodTargetObjectDataType); //shall we copy the members too? //FormatterServices.PopulateObjectMembers(scope2copy, scope2TypeSerializableMembers, scope2ObjectData); MethodTargetObjectData[i] = scope2copy; #region __SemaphoreSlim // X:\jsc.svn\examples\javascript\async\Test\TestSemaphoreSlim\TestSemaphoreSlim\ApplicationControl.cs var xSemaphoreSlim = scope2copy as __SemaphoreSlim; if (xSemaphoreSlim != null) { // we now have to complete the entanglement. we have the caller on the UI. Action<string> UIWriteLine0 = text => { // mimick roslyn syntax Console.WriteLine("$" + xMember.Name + " " + text); }; //xSemaphoreSlim.InternalIsEntangled = true; #region InternalVirtualWaitAsync var xInternalVirtualWaitAsync = default(TaskCompletionSource<object>); xSemaphoreSlim.InternalVirtualWaitAsync += continuation => { UIWriteLine0("enter xSemaphoreSlim.InternalVirtualWaitAsync, worker is now awaiting for signal " + new { xSemaphoreSlim.Name }); xInternalVirtualWaitAsync = continuation; }; // at this point lets call the UI to set up a new signal channel.. //new MessageChannel(); var c = new MessageChannel(); c.port1.onmessage += ce => { // ui has released? if (xInternalVirtualWaitAsync == null) { // what if the thread is not yet awaiting? UIWriteLine0("ui has sent a release signal, yet nobody awaiting"); return; } UIWriteLine0("ui has sent a release signal, resync"); // we should have byte fields now. // next strings as in thread hopping... dynamic data = ce.data; #region read xSemaphoreSlim_ByteArrayFields { __Task.xByteArrayField[] xSemaphoreSlim_ByteArrayFields = data.xSemaphoreSlim_ByteArrayFields; // X:\jsc.svn\examples\javascript\async\test\TestBytesToSemaphore\TestBytesToSemaphore\Application.cs if (xSemaphoreSlim_ByteArrayFields != null) foreach (var item in xSemaphoreSlim_ByteArrayFields) { var xFieldInfo = (FieldInfo)MethodTargetTypeSerializableMembers[item.index]; // X:\jsc.svn\examples\javascript\chrome\apps\ChromeThreadedCameraTracker\ChromeThreadedCameraTracker\Application.cs // can we set the value? UIWriteLine0("worker resync " + new { item.index, //item.Name, xFieldInfo = xFieldInfo.Name, //item.value }); xFieldInfo.SetValue( MethodTarget, // null? item.value ); } } #endregion xInternalVirtualWaitAsync.SetResult(null); }; c.port1.start(); c.port2.start(); UIWriteLine0("will set up the signal channel"); foreach (var p in e.ports) { p.postMessage( new { xSemaphoreSlim = xMember.Name }, transfer: new[] { c.port2 } ); } #endregion #region InternalVirtualRelease xSemaphoreSlim.InternalVirtualRelease += delegate { UIWriteLine0("enter xSemaphoreSlim.InternalVirtualRelease, will send a signal to ui..."); // worker needs sync data about now. // the ui would be happy to have the latest version of the data. // this is tricky. we would really need to know which data fields have changed by now // and what will happen if the data was also changed on the ui. // technically we are doing a merge conflict resolver... // this is somewhat the same situation, we alrady have // when entering a worker // when exiting a worker // when hoping to or from a worker. // what data fields do we have to upload yo ui? // how much IL analysis is available for us to know what to sync // we should not sync fields that wont be used on the ui // the thread hop looks at strings only right now, as they are immputable yet primitive // what about bytewarrays? // X:\jsc.svn\examples\javascript\async\test\TestBytesFromSemaphore\TestBytesFromSemaphore\Application.cs #region xSemaphoreSlim_ByteArrayFields var xSemaphoreSlim_ByteArrayFields = new List<__Task.xByteArrayField>(); var MethodTargetTypeSerializableMembers_index = 0; foreach (FieldInfo item in MethodTargetTypeSerializableMembers) { // how would we know if the array is a byte array? // FieldType is not exactly available yet //Console.WriteLine("worker resync candidate " + new { item.Name, item.FieldType, item.FieldType.IsArray }); var item_value = item.GetValue(MethodTarget); if (item_value != null) { var item_value_constructor = Expando.Of(item_value).constructor; var item_value_IsByteArray = Native.self_Uint8ClampedArray == item_value_constructor; if (item_value_IsByteArray) { var value = (byte[])item_value; xSemaphoreSlim_ByteArrayFields.Add( new __Task.xByteArrayField { index = MethodTargetTypeSerializableMembers_index, // keep name for diagnostics Name = item.Name, value = value } ); UIWriteLine0("worker resync xByteArrayField candidate " + new { item.Name, value.Length }); } } MethodTargetTypeSerializableMembers_index++; } #endregion foreach (var p in e.ports) { p.postMessage( new { xSemaphoreSlim = xMember.Name, xSemaphoreSlim_ByteArrayFields = xSemaphoreSlim_ByteArrayFields.ToArray() } ); } }; #endregion } #endregion } } } FormatterServices.PopulateObjectMembers( MethodTarget, MethodTargetTypeSerializableMembers, MethodTargetObjectData ); // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs MethodTokenReference = (MethodTarget as dynamic)[MethodToken]; } // what if we are being called from within a secondary app? // stateTypeHandleIndex = type$XjKww8iSKT_aFTpY_bSs5vBQ, if (MethodTokenReference == null) { // tested at // X:\jsc.svn\examples\javascript\WorkerInsideSecondaryApplication\WorkerInsideSecondaryApplication\Application.cs // X:\jsc.svn\examples\javascript\Test\TestHopToThreadPoolAwaitable\TestHopToThreadPoolAwaitable\Application.cs // why? throw new InvalidOperationException( new { MethodToken } + " function is not available at " + new { Native.worker.location.href } ); } #endregion //Console.WriteLine( // new // { // MethodTokenReference, // Thread.CurrentThread.ManagedThreadId // } // ); // whats the type? #region xstate var xstate = default(object); if (stateType != null) { xstate = FormatterServices.GetUninitializedObject(stateType); var xstate_SerializableMembers = FormatterServices.GetSerializableMembers(stateType); FormatterServices.PopulateObjectMembers( xstate, xstate_SerializableMembers, (object[])state_ObjectData ); // MethodType = FuncOfObjectToObject //Console.WriteLine("as FuncOfObjectToObject"); } #endregion #region CreateProgress Func<__Progress<object>> CreateProgress = () => new __Progress<object>( value => { //Console.WriteLine("__IProgress_Report " + new { value }); // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic zdata = new object(); zdata.__IProgress_Report = new { value }; foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } } ); // X:\jsc.svn\examples\javascript\async\Test\TestWorkerProgress\TestWorkerProgress\Application.cs if (IsIProgress) xstate = CreateProgress(); #endregion #region __string // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic target = __string; var m = Expando.Of(data___string).GetMembers(); // https://sites.google.com/a/jsc-solutions.net/backlog/knowledge-base/2013/201308/20130826-domainmemory foreach (ExpandoMember nn in m) { target[nn.Name] = nn.Value; var trigger = "set_" + nn.Name; var trigger_default = IFunction.Of(trigger); (Native.self as dynamic)[trigger] = IFunction.OfDelegate( new Action<string>( Value => { if (nn.Value == Value) return; trigger_default.apply(null, Value); #region sync one field only { dynamic zdata = new object(); dynamic zdata___string = new object(); zdata.__string = zdata___string; zdata___string[nn.Name] = Value; // prevent sync via diff nn.Value = Value; foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } } #endregion } ) ); } #endregion { // https://sites.google.com/a/jsc-solutions.net/backlog/knowledge-base/2013/201308/20130828-thread-run // for now we only support static calls // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic zdata = new object(); if (MethodType == typeof(ActionOfDedicatedWorkerGlobalScope).Name) { MethodTokenReference.apply(null, Native.worker); } else if (MethodType == typeof(FuncOfObjectToObject).Name) { Console.WriteLine("worker Task Run function call, FuncOfObjectToObject, will invoke MethodTokenReference"); #region FuncOfObjectToObject // X:\jsc.svn\examples\javascript\test\TestTaskStartToString\TestTaskStartToString\Application.cs // X:\jsc.svn\examples\javascript\async\test\TestTaskRun\TestTaskRun\Application.cs // X:\jsc.svn\examples\javascript\Test\TestGetUninitializedObject\TestGetUninitializedObject\Application.cs var value = MethodTokenReference.apply(MethodTarget, xstate); Console.WriteLine("worker Task Run function call, FuncOfObjectToObject, will invoke MethodTokenReference " + new { value }); // X:\jsc.svn\examples\javascript\async\test\TaskAsyncTaskRun\TaskAsyncTaskRun\Application.cs // whatif its an Action not a Func? //enter HopToThreadPoolAwaitable yield HopToUIAwaitable //worker Task Run function has returned {{ value_Task = null, value_TaskOfT = null }} //__Task.InternalStart inner complete {{ yield = {{ value = null }} }} var value_Task = value as __Task; var value_TaskOfT = value as __Task<object>; // if we are in a hop. allow the return task to be overriden. if (InternalOverrideTaskOfT != null) value_TaskOfT = InternalOverrideTaskOfT; // 0:25611ms Task Run function has returned { value_Task = [object Object], value_TaskOfT = [object Object] } //Console.WriteLine("worker Task Run function has returned " + new { value_Task, value_TaskOfT, InternalOverrideTaskOfT }); // 0:4284ms Task Run function has returned { value_Task = { IsCompleted = 1, Result = }, value_TaskOfT = { IsCompleted = 1, Result = } } // 0:5523ms Task Run function has returned { value_Task = { IsCompleted = false, Result = }, value_TaskOfT = { IsCompleted = false, Result = } } if (value_TaskOfT != null) { // special situation // if IsCompleted, called twice? or heard twice? value_TaskOfT.ContinueWith( t => { //Console.WriteLine("worker Task Run ContinueWith " + new { t }); // X:\jsc.svn\examples\javascript\Test\Test435CoreDynamic\Test435CoreDynamic\Class1.cs dynamic zzdata = new object(); // null? if (t.Result == null) { zzdata.ContinueWithResult = new { t.Result }; foreach (MessagePort port in e.ports) { port.postMessage((object)zzdata, new MessagePort[0]); } return; } var ResultType = t.Result.GetType(); var ResultTypeIndex = __Type.GetTypeIndex("workerResult", ResultType); var ResultTypeSerializableMembers = FormatterServices.GetSerializableMembers(ResultType); var ResultObjectData = FormatterServices.GetObjectData(t.Result, ResultTypeSerializableMembers); var ContinueWithResult = new { ResultTypeIndex, ResultObjectData, t.Result }; zzdata.ContinueWithResult = ContinueWithResult; foreach (MessagePort port in e.ports) { port.postMessage((object)zzdata, new MessagePort[0]); } } ); } else { if (value_Task != null) { // X:\jsc.svn\examples\javascript\async\test\TestWorkerScopeProgress\TestWorkerScopeProgress\Application.cs throw new NotImplementedException(); } else { var yield = new { value }; //Console.WriteLine(new { yield }); Console.WriteLine("worker Task Run function call, FuncOfObjectToObject, will yield? " + new { value_Task, value_TaskOfT }); zdata.yield = yield; } } #endregion // now what? } else if (MethodType == typeof(FuncOfTaskToObject).Name) { Console.WriteLine("bugcheck FuncOfTaskToObject ?"); // tested by? #region FuncOfTaskToObject // need to reconstruct the caller task? var value = MethodTokenReference.apply(null, TaskArray.Single()); var yield = new { value }; //Console.WriteLine(new { yield }); zdata.yield = yield; #endregion // now what? } else if (MethodType == typeof(FuncOfTaskOfObjectArrayToObject).Name) { // tested by? #region FuncOfTaskOfObjectArrayToObject // need to reconstruct the caller task? Console.WriteLine("__worker_onfirstmessage: " + new { TaskArray = TaskArray.Length }); //Debugger.Break(); var args = new object[] { TaskArray }; var value = MethodTokenReference.apply( o: null, // watch out args: args ); var yield = new { value }; //Console.WriteLine(new { yield }); zdata.yield = yield; #endregion // now what? } #region [sync] diff and upload changes to DOM context, the latest now { dynamic zdata___string = new object(); zdata.__string = zdata___string; foreach (ExpandoMember nn in m) { string Value = (string)Expando.InternalGetMember((object)target, nn.Name); // this is preferred: //string Value = target[nn.Name]; if (Value != nn.Value) { zdata___string[nn.Name] = Value; } } } #endregion //e.post foreach (MessagePort port in e.ports) { port.postMessage((object)zdata, new MessagePort[0]); } } }