/// <see cref="WorkQueue.IResponseHandler.HandleResponse"/> ////[OgreVersion(1, 7, 2)] public void HandleResponse(WorkQueue.Response res, WorkQueue srcq) { if (res.Request.Aborted) { this.outstandingRequestSet.Remove(res.Request.ID); return; } if (res.Succeeded) { var resresp = (ResourceResponse)res.Data; // Complete full loading in main thread if semithreading ResourceRequest req = resresp.Request; #if AXIOM_THREAD_SUPPORT if (Configuration.Config.AxiomThreadLevel == 2) { // These load commands would have been downgraded to prepare() for the background if (req.Type == RequestType.LoadResource) { ResourceManager rm = ResourceGroupManager.Instance.ResourceManagers[req.ResourceType]; rm.Load(req.ResourceName, req.GroupName, req.IsManual, req.Loader, req.LoadParams, true); } else if (req.Type == RequestType.LoadGroup) { ResourceGroupManager.Instance.LoadResourceGroup(req.GroupName); } } #endif this.outstandingRequestSet.Remove(res.Request.ID); // Call resource listener if (resresp.Resource != null) { if (req.Type == RequestType.LoadResource) { resresp.Resource.FireLoadingComplete(true); } else { resresp.Resource.FirePreparingComplete(true); } } // Call queue listener if (req.Listener != null) { req.Listener.Invoke(res.Request.ID, req.Result); } } }
/// <summary> /// Process a request if possible. /// </summary> /// <returns>Valid response if processed, null otherwise</returns> ////[OgreVersion(1, 7, 2)] public Response HandleRequest(Request req, WorkQueue srcQ) { // Read mutex so that multiple requests can be processed by the // same handler in parallel if required Response response = null; lock (this._mutex) { if (this._handler != null) { if (this._handler.CanHandleRequest(req, srcQ)) { response = this._handler.HandleRequest(req, srcQ); } } } return(response); }
/// <see cref="WorkQueue.IRequestHandler.HandleRequest"/> //[OgreVersion(1, 7, 2)] public WorkQueue.Response HandleRequest(WorkQueue.Request req, WorkQueue srcQ) { var resreq = (ResourceRequest)req.Data; if (req.Aborted) { if (resreq.Type == RequestType.PrepareResource || resreq.Type == RequestType.LoadResource) { resreq.LoadParams.Clear(); resreq.LoadParams = null; } resreq.Result.Error = false; var resresp = new ResourceResponse(null, resreq); return(new WorkQueue.Response(req, true, resresp)); } ResourceManager rm = null; Resource resource = null; try { switch (resreq.Type) { case RequestType.InitializeGroup: ResourceGroupManager.Instance.InitializeResourceGroup(resreq.GroupName); break; case RequestType.InitializeAllGroups: ResourceGroupManager.Instance.InitializeAllResourceGroups(); break; case RequestType.PrepareGroup: ResourceGroupManager.Instance.PrepareResourceGroup(resreq.GroupName); break; case RequestType.LoadGroup: #if AXIOM_THREAD_SUPPORT if (Axiom.Configuration.Config.AxiomThreadLevel == 2) { ResourceGroupManager.Instance.PrepareResourceGroup(resreq.GroupName); } else { ResourceGroupManager.Instance.LoadResourceGroup(resreq.GroupName); } #endif break; case RequestType.UnloadGroup: ResourceGroupManager.Instance.UnloadResourceGroup(resreq.GroupName); break; case RequestType.PrepareResource: rm = ResourceGroupManager.Instance.ResourceManagers[resreq.ResourceType]; resource = rm.Prepare(resreq.ResourceName, resreq.GroupName, resreq.IsManual, resreq.Loader, resreq.LoadParams, true); break; case RequestType.LoadResource: #if AXIOM_THREAD_SUPPORT rm = ResourceGroupManager.Instance.ResourceManagers[resreq.ResourceType]; if (Axiom.Configuration.Config.AxiomThreadLevel == 2) { resource = rm.Prepare(resreq.ResourceName, resreq.GroupName, resreq.IsManual, resreq.Loader, resreq.LoadParams, true); } else { resource = rm.Load(resreq.ResourceName, resreq.GroupName, resreq.IsManual, resreq.Loader, resreq.LoadParams, true); } #endif break; case RequestType.UnloadResource: rm = ResourceGroupManager.Instance.ResourceManagers[resreq.ResourceType]; if (string.IsNullOrEmpty(resreq.ResourceName)) { rm.Unload(resreq.ResourceHandle); } else { rm.Unload(resreq.ResourceName); } break; } } catch (Exception e) { if (resreq.Type == RequestType.PrepareResource || resreq.Type == RequestType.LoadResource) { resreq.LoadParams.Clear(); resreq.LoadParams = null; } resreq.Result.Error = true; resreq.Result.Message = e.Message; //return error response var resresp = new ResourceResponse(resource, resreq); return(new WorkQueue.Response(req, false, resresp, e.Message)); } //success if (resreq.Type == RequestType.PrepareResource || resreq.Type == RequestType.LoadResource) { resreq.LoadParams.Clear(); resreq.LoadParams = null; } resreq.Result.Error = false; var resp = new ResourceResponse(resource, resreq); return(new WorkQueue.Response(req, true, resp)); }
/// <see cref="WorkQueue.IRequestHandler.CanHandleRequest"/> //[OgreVersion(1, 7, 2)] public bool CanHandleRequest(WorkQueue.Request req, WorkQueue srcQ) { return(true); }
/// <summary> /// Aborts background process. /// </summary> //[OgreVersion(1, 7, 2)] public void AbortRequest(RequestID ticket) { WorkQueue queue = Root_Instance_WorkQueue; queue.AbortRequest(ticket); }
public WorkQueue.Response HandleRequest( WorkQueue.Request req, WorkQueue srcQ ) { var lreq = (LoadRequest)req.Data; var def = lreq.Slot.Def; var t = lreq.Slot.Instance; System.Diagnostics.Debug.Assert( t != null, "Terrain instance should have been constructed in the main thread" ); WorkQueue.Response response; try { if ( !string.IsNullOrEmpty( def.FileName ) ) { t.Prepare( def.FileName ); } else { System.Diagnostics.Debug.Assert( def.ImportData != null, "No import data or file name" ); t.Prepare( def.ImportData ); // if this worked, we can destroy the input data to save space def.FreeImportData(); } response = new WorkQueue.Response( req, true, new object() ); } catch ( Exception e ) { // oops response = new WorkQueue.Response( req, false, new object(), e.Message ); } return response; }
/// <see cref="WorkQueue.RemoveResponseHandler"/> //[OgreVersion(1, 7, 2)] public override void RemoveResponseHandler(ushort channel, WorkQueue.IResponseHandler rh) { if (this.responseHandlers.ContainsKey(channel)) { if (this.responseHandlers[channel].Contains(rh)) { this.responseHandlers[channel].Remove(rh); } } }
/// <see cref="Axiom.Core.WorkQueue.RemoveRequestHandler"/> ////[OgreVersion(1, 7, 2)] public override void RemoveRequestHandler(ushort channel, WorkQueue.IRequestHandler rh) { lock (requestHandlerMutex) { if (this.requestHandlers.ContainsKey(channel)) { foreach (var j in this.requestHandlers[channel]) { if (j.Handler == rh) { // Disconnect - this will make it safe across copies of the list // this is threadsafe and will wait for existing processes to finish j.DisconnectHandler(); this.requestHandlers[channel].Remove(j); break; } } } } }
/// <summary> /// Called to shutdown the engine and dispose of all it's resources. /// </summary> public void Dispose() { // force the engine to shutdown Shutdown(); DDSCodec.Shutdown(); PVRTCCodec.Shutdown(); CompositorManager.Instance.SafeDispose(); OverlayManager.Instance.SafeDispose(); OverlayElementManager.Instance.SafeDispose(); FontManager.Instance.SafeDispose(); ArchiveManager.Instance.SafeDispose(); SkeletonManager.Instance.SafeDispose(); MeshManager.Instance.SafeDispose(); MaterialManager.Instance.SafeDispose(); ParticleSystemManager.Instance.SafeDispose(); ControllerManager.Instance.SafeDispose(); HighLevelGpuProgramManager.Instance.SafeDispose(); PluginManager.Instance.SafeDispose(); Pass.ProcessPendingUpdates(); ResourceGroupManager.Instance.SafeDispose(); // Note: The dispose method implementation of both ResourceBackgroundQueue and // DefaultWorkQueue internally calls Shutdown, so the direct call to Shutdown methods // isn't necessary in Root.Shutdown. ResourceBackgroundQueue.Instance.Dispose(); this._workQueue.Dispose(); this._workQueue = null; CodecManager.Instance.SafeDispose(); #if !XBOX360 PlatformManager.Instance.SafeDispose(); #endif this.activeRenderSystem = null; WindowEventMonitor.Instance.SafeDispose(); #if DEBUG ObjectManager.Instance.SafeDispose(); #endif LogManager.Instance.SafeDispose(); instance = null; }
/// <see cref="WorkQueue.IResponseHandler.HandleResponse"/> public void HandleResponse( WorkQueue.Response res, WorkQueue srcq ) { // Main thread var pres = (PageResponse)res.Data; var preq = (PageRequest)res.Request.Data; // only deal with own requests if ( preq.srcPage != this ) { return; } // final loading behaviour if ( res.Succeeded ) { Utility.Swap<List<PageContentCollection>>( ref this.mContentCollections, ref pres.pageData.collectionsToAdd ); LoadImpl(); } this.mDeferredProcessInProgress = false; }
/// <see cref="WorkQueue.IResponseHandler.CanHandleResponse"/> public bool CanHandleResponse( WorkQueue.Response res, WorkQueue srcq ) { var preq = (PageRequest)res.Request.Data; // only deal with own requests // we do this because if we delete a page we want any pending tasks to be discarded if ( preq.srcPage != this ) { return false; } else { return true; } }
/// <see cref="WorkQueue.IRequestHandler.HandleRequest"/> public WorkQueue.Response HandleRequest( WorkQueue.Request req, WorkQueue srcQ ) { // Background thread (maybe) var preq = (PageRequest)req.Data; // only deal with own requests; we shouldn't ever get here though if ( preq.srcPage != this ) { return null; } var res = new PageResponse(); res.pageData = new PageData(); WorkQueue.Response response; try { PrepareImpl( ref res.pageData ); response = new WorkQueue.Response( req, true, res ); } catch ( Exception e ) { // oops response = new WorkQueue.Response( req, false, res, e.Message ); } return response; }
/// <see cref="WorkQueue.IRequestHandler.CanHandleRequest"/> public bool CanHandleRequest( WorkQueue.Request req, WorkQueue srcQ ) { var preq = (PageRequest)req.Data; // only deal with own requests // we do this because if we delete a page we want any pending tasks to be discarded if ( preq.srcPage != this ) { return false; } else { return !req.Aborted; } }
public void HandleResponse( WorkQueue.Response res, WorkQueue srcq ) { // No response data, just request var lreq = (LoadRequest)res.Request.Data; if ( res.Succeeded ) { var slot = lreq.Slot; var terrain = slot.Instance; if ( terrain != null ) { // do final load now we've prepared in the background // we must set the position terrain.Position = GetTerrainSlotPosition( slot.X, slot.Y ); terrain.Load(); // hook up with neighbours for ( int i = -1; i <= 1; ++i ) { for ( int j = -1; j <= 1; ++j ) { if ( i != 0 || j != 0 ) { ConnectNeighbour( slot, i, j ); } } } } } else { // oh dear LogManager.Instance.Write( LogMessageLevel.Critical, false, "We failed to prepare the terrain at ({0}, {1}) with the error '{2}'", lreq.Slot.X, lreq.Slot.Y, res.Messages ); lreq.Slot.FreeInstance(); } }
public bool CanHandleResponse( WorkQueue.Response res, WorkQueue srcq ) { var lreq = (LoadRequest)res.Request.Data; // only deal with own requests if ( lreq.Origin != this ) { return false; } else { return true; } }
/// <see cref="WorkQueue.IResponseHandler.CanHandleResponse"/> ////[OgreVersion(1, 7, 2)] public bool CanHandleResponse(WorkQueue.Response res, WorkQueue srcq) { return(true); }
public bool CanHandleRequest( WorkQueue.Request req, WorkQueue srcQ ) { var ddr = (DerivedDataRequest)req.Data; // only deal with own requests // we do this because if we delete a terrain we want any pending tasks to be discarded if ( ddr.Terrain != this ) { return false; } else { return !req.Aborted; } }
public WorkQueue.Response HandleRequest( WorkQueue.Request req, WorkQueue srcQ ) { // Background thread (maybe) var ddr = (DerivedDataRequest)req.Data; // only deal with own requests; we shouldn't ever get here though if ( ddr.Terrain != this ) { return null; } var ddres = new DerivedDataResponse(); ddr.TypeMask = (byte)( ddr.TypeMask & DERIVED_DATA_ALL ); // Do only ONE type of task per background iteration, in order of priority // this means we return faster, can abort faster and we repeat less redundant calcs // we don't do this as separate requests, because we only want one background // task per Terrain instance in flight at once if ( ( ddr.TypeMask & DERIVED_DATA_DELTAS ) == ddr.TypeMask ) { ddres.DeltaUpdateRect = CalculateHeightDeltas( ddr.DirtyRect ); ddres.RemainingTypeMask &= (byte)~DERIVED_DATA_DELTAS; } else if ( ( ddr.TypeMask & DERIVED_DATA_NORMALS ) == ddr.TypeMask ) { ddres.NormalMapBox = CalculateNormals( ddr.DirtyRect, ref ddres.NormalUpdateRect ); ddres.RemainingTypeMask &= (byte)~DERIVED_DATA_NORMALS; } else if ( ( ddr.TypeMask & DERIVED_DATA_LIGHTMAP ) == ddr.TypeMask ) { ddres.LightMapPixelBox = CalculateLightMap( ddr.DirtyRect, ddr.LightmapExtraDirtyRect, ref ddres.LightMapUpdateRect ); ddres.RemainingTypeMask &= (byte)~DERIVED_DATA_LIGHTMAP; } ddres.Terrain = ddr.Terrain; return new WorkQueue.Response( req, true, ddres ); }
/// <see cref="Axiom.Core.WorkQueue.AddRequestHandler"/> ////[OgreVersion(1, 7, 2)] public override void AddRequestHandler(ushort channel, WorkQueue.IRequestHandler rh) { lock (requestHandlerMutex) { if (!this.requestHandlers.ContainsKey(channel)) { this.requestHandlers.Add(channel, new List<RequestHandlerHolder>()); } bool duplicate = false; foreach (var j in this.requestHandlers[channel]) { if (j.Handler == rh) { duplicate = true; break; } } if (!duplicate) { this.requestHandlers[channel].Add(new RequestHandlerHolder(rh)); } } }
public bool CanHandleResponse( WorkQueue.Response res, WorkQueue srcq ) { var ddreq = (DerivedDataRequest)res.Request.Data; // only deal with own requests // we do this because if we delete a terrain we want any pending tasks to be discarded if ( ddreq.Terrain != this ) { return false; } else { return true; } }
/// <see cref="Axiom.Core.WorkQueue.AddResponseHandler"/> //[OgreVersion(1, 7, 2)] public override void AddResponseHandler(ushort channel, WorkQueue.IResponseHandler rh) { if (!this.responseHandlers.ContainsKey(channel)) { this.responseHandlers.Add(channel, new List<IResponseHandler>()); } if (!this.responseHandlers[channel].Contains(rh)) { this.responseHandlers[channel].Add(rh); } }
public void HandleResponse( WorkQueue.Response res, WorkQueue srcq ) { // Main thread var ddres = (DerivedDataResponse)res.Data; var ddreq = (DerivedDataRequest)res.Request.Data; // only deal with own requests if ( ddreq.Terrain != this ) { return; } if ( ( ( ddreq.TypeMask & DERIVED_DATA_DELTAS ) == ddreq.TypeMask ) && ( ( ddres.RemainingTypeMask & DERIVED_DATA_DELTAS ) != DERIVED_DATA_DELTAS ) ) { FinalizeHeightDeltas( ddres.DeltaUpdateRect, false ); } if ( ( ( ddreq.TypeMask & DERIVED_DATA_NORMALS ) == ddreq.TypeMask ) && ( ( ddres.RemainingTypeMask & DERIVED_DATA_NORMALS ) != DERIVED_DATA_NORMALS ) ) { FinalizeNormals( ddres.NormalUpdateRect, ddres.NormalMapBox ); this.mCompositeMapDirtyRect.Merge( ddreq.DirtyRect ); } if ( ( ( ddreq.TypeMask & DERIVED_DATA_LIGHTMAP ) == ddreq.TypeMask ) && ( ( ddres.RemainingTypeMask & DERIVED_DATA_LIGHTMAP ) != DERIVED_DATA_LIGHTMAP ) ) { FinalizeLightMap( ddres.LightMapUpdateRect, ddres.LightMapPixelBox ); this.mCompositeMapDirtyRect.Merge( ddreq.DirtyRect ); this.mCompositeMapDirtyRectLightmapUpdate = true; } IsDerivedDataUpdateInProgress = false; // Re-trigger another request if there are still things to do, or if // we had a new request since this one var newRect = new Rectangle( 0, 0, 0, 0 ); if ( ddres.RemainingTypeMask != 0 ) { newRect.Merge( ddreq.DirtyRect ); } if ( this.mDerivedUpdatePendingMask != 0 ) { newRect.Merge( this.mDirtyDerivedDataRect ); this.mDirtyDerivedDataRect.IsNull = true; } var newLightmapExtraRext = new Rectangle( 0, 0, 0, 0 ); if ( ddres.RemainingTypeMask != 0 ) { newLightmapExtraRext.Merge( ddreq.LightmapExtraDirtyRect ); } if ( this.mDerivedUpdatePendingMask != 0 ) { newLightmapExtraRext.Merge( this.mDirtyLightmapFromNeighboursRect ); this.mDirtyLightmapFromNeighboursRect.IsNull = true; } var newMask = (byte)( ddres.RemainingTypeMask | this.mDerivedUpdatePendingMask ); if ( newMask != 0 ) { // trigger again UpdateDerivedDataImpl( newRect, newLightmapExtraRext, false, newMask ); } else { // we've finished all the background processes // update the composite map if enabled if ( this.mCompositeMapRequired ) { UpdateCompositeMap(); } } }
/// <summary> /// Process a request if possible. /// </summary> /// <returns>Valid response if processed, null otherwise</returns> ////[OgreVersion(1, 7, 2)] public Response HandleRequest(Request req, WorkQueue srcQ) { // Read mutex so that multiple requests can be processed by the // same handler in parallel if required Response response = null; lock (this._mutex) { if (this._handler != null) { if (this._handler.CanHandleRequest(req, srcQ)) { response = this._handler.HandleRequest(req, srcQ); } } } return response; }
public bool CanHandleRequest( WorkQueue.Request req, WorkQueue srcQ ) { var lreq = (LoadRequest)req.Data; // only deal with own requests if ( lreq.Origin != this ) { return false; } else { return !req.Aborted; } }