public DynamicAtlas( RenderCoordinator coordinator, int width, int height, SurfaceFormat format, int spacing = 2, MipGenerator <T> mipGenerator = null ) { Coordinator = coordinator; Width = width; Height = height; Spacing = spacing; X = Y = Spacing; RowHeight = 0; _BeforePrepare = Flush; lock (Coordinator.CreateResourceLock) Texture = new Texture2D(coordinator.Device, width, height, mipGenerator != null, format); Pixels = new T[width * height]; if (mipGenerator != null) { MipBuffer = new T[(width / 2) * (height / 2)]; } GenerateMip = mipGenerator; MipLevelCount = Texture.LevelCount; Invalidate(); }
sealed protected override void Draw(GameTime gameTime) { RenderCoordinator.WorkStopwatch.Restart(); var priorIndex = Batch.LifetimeCount; NextFrameTiming.PriorPrimitiveCount = NativeBatch.LifetimePrimitiveCount; NextFrameTiming.PriorCommandCount = NativeBatch.LifetimeCommandCount; // ???? RenderCoordinator.WaitForActiveDraws(); try { OnBeforeDraw(gameTime); var frame = RenderCoordinator.BeginFrame(true); Squared.Threading.Profiling.Superluminal.BeginEventFormat("Build Frame", "SRFrame #{0}", frame.Index, color: 0x1010CF); Draw(gameTime, frame); } finally { Squared.Threading.Profiling.Superluminal.EndEvent(); RenderCoordinator.SynchronousDrawsEnabled = true; RenderCoordinator.WorkStopwatch.Stop(); NextFrameTiming.Draw = RenderCoordinator.WorkStopwatch.Elapsed; NextFrameTiming.BatchCount = (int)(Batch.LifetimeCount - priorIndex); } }
protected override void Initialize() { var gds = Services.GetService(typeof(IGraphicsDeviceService)) as IGraphicsDeviceService; if (gds != null) { RenderCoordinator = new RenderCoordinator(gds, Thread.CurrentThread, ThreadGroup, base.BeginDraw, base.EndDraw); RenderManager = RenderCoordinator.Manager; } else { RenderManager = new RenderManager(GraphicsDevice, Thread.CurrentThread, ThreadGroup); RenderCoordinator = new RenderCoordinator( RenderManager, base.BeginDraw, base.EndDraw ); } // FIXME: Preloading shaders crashes when done from a worker thread RenderCoordinator.DoThreadedIssue = false; RenderCoordinator.DoThreadedPrepare = true; RenderCoordinator.DeviceReset += (s, e) => OnDeviceReset(); gds.DeviceResetting += Gds_DeviceResetting; SetupCloseHook(); base.Initialize(); }
private IEnumerator <object> PreloadShadersAsyncImpl(RenderCoordinator coordinator, DeviceManager dm, IndexBuffer tempIb, List <Material> materials, Action <float> onProgress, int speed) { var sw = Stopwatch.StartNew(); var wfns = new Task.WaitForNextStep(); for (int i = 0; i < materials.Count; i++) { var m = materials[i]; if (onProgress != null) { onProgress(i / (float)materials.Count); } coordinator.BeforeIssue(() => m.Preload(coordinator, dm, tempIb)); if ((i % speed) == 0) { yield return(wfns); } } onProgress(1f); coordinator.DisposeResource(tempIb); var elapsed = sw.Elapsed.TotalMilliseconds; Debug.WriteLine($"Async shader preload took {elapsed:000.00}ms"); }
public unsafe void SetToIdentity16(RenderCoordinator coordinator, bool useMatrix, ref Matrix colorMatrix) { var scratch = stackalloc Vector3[Resolution]; var stride = Resolution * Resolution; var buf = new Rgba64[stride * Resolution]; for (int z = 0; z < Resolution; z += 1) { int xOffset = z * Resolution; for (int y = 0; y < Resolution; y += 1) { int rowOffset = xOffset + (y * stride); SetToIdentityInner(y, z, scratch, useMatrix, ref colorMatrix); for (int x = 0; x < Resolution; x += 1) { var v = scratch[x]; buf[rowOffset + x] = new Rgba64(v.X, v.Y, v.Z, 1.0f); } } } lock (coordinator.UseResourceLock) Texture.SetData(buf); }
private void Gds_DeviceResetting(object sender, EventArgs e) { if (!RenderCoordinator.WaitForActiveDraws()) { ; } }
protected override bool BeginDraw() { RenderCoordinator.WorkStopwatch.Restart(); ThreadGroup.TryStepMainThreadUntilDrained(); var settling = RenderCoordinator.IsWaitingForDeviceToSettle; try { var ok = IsContentLoaded && !settling && RenderCoordinator.BeginDraw(); if (!ok) { if (BeginDrawFailed != null) { BeginDrawFailed(); } else if (!settling) { Console.Error.WriteLine("BeginDraw failed"); } } return(ok); } finally { RenderCoordinator.WorkStopwatch.Stop(); NextFrameTiming.BeginDraw = RenderCoordinator.WorkStopwatch.Elapsed; } }
protected override void EndDraw() { RenderCoordinator.WorkStopwatch.Restart(); try { RenderCoordinator.EndDraw(); } catch (Exception exc) { Console.WriteLine("Caught {0} in EndDraw", exc); throw; } finally { RenderCoordinator.WorkStopwatch.Stop(); var lpc = NativeBatch.LifetimePrimitiveCount; var ppc = NextFrameTiming.PriorPrimitiveCount; var lcc = NativeBatch.LifetimeCommandCount; var pcc = NextFrameTiming.PriorCommandCount; NextFrameTiming.Prepare = RenderCoordinator.PrepareStopwatch.Elapsed; NextFrameTiming.EndDraw = RenderCoordinator.WorkStopwatch.Elapsed; NextFrameTiming.BeforeIssue = RenderCoordinator.BeforeIssueStopwatch.Elapsed; NextFrameTiming.BeforePresent = RenderCoordinator.BeforePresentStopwatch.Elapsed; NextFrameTiming.AfterPresent = RenderCoordinator.AfterPresentStopwatch.Elapsed; NextFrameTiming.Wait = RenderCoordinator.WaitStopwatch.Elapsed; NextFrameTiming.PrimitiveCount = (int)(lpc - ppc); NextFrameTiming.CommandCount = (int)(lcc - pcc); PreviousFrameTiming = NextFrameTiming; RenderCoordinator.WaitStopwatch.Reset(); RenderCoordinator.BeforePresentStopwatch.Reset(); RenderCoordinator.AfterPresentStopwatch.Reset(); } ThreadGroup.TryStepMainThreadUntilDrained(); }
public void PreloadShaders(RenderCoordinator coordinator) { if (IsDisposed) { throw new ObjectDisposedException("MaterialSetBase"); } var sw = Stopwatch.StartNew(); var dm = coordinator.Manager.DeviceManager; // HACK: Applying a shader does an on-demand compile // HACK: We should really only need 6 indices but drivers seem to want more sometimes var tempIb = new IndexBuffer(dm.Device, IndexElementSize.SixteenBits, 128, BufferUsage.WriteOnly); var count = 0; foreach (var m in GetShadersToPreload()) { m.Preload(coordinator, dm, tempIb); count++; } coordinator.DisposeResource(tempIb); var elapsed = sw.Elapsed.TotalMilliseconds; Debug.WriteLine($"Shader preload took {elapsed:000.00}ms for {count} material(s)"); }
public Texture2DProvider(IResourceProviderStreamSource source, RenderCoordinator coordinator) : base( source, coordinator, enableThreadedCreate: false, enableThreadedPreload: true ) { DisposeHandler = _DisposeHandler; }
protected override void EndRun() { if (RenderCoordinator != null) { RenderCoordinator.Dispose(); } base.EndRun(); }
public static void ApplyChangesAfterPresent(this GraphicsDeviceManager gdm, RenderCoordinator rc) { // HACK: Wait until rendering has finished, then reset the device on the main thread var sc = SynchronizationContext.Current; rc.AfterPresent(() => { sc.Post((_) => gdm.ApplyChanges(), null); }); }
protected override void Dispose(bool disposing) { if (RenderCoordinator != null) { RenderCoordinator.Dispose(); } base.Dispose(disposing); }
protected override void Initialize() { RenderManager = new RenderManager(GraphicsDevice, Thread.CurrentThread); RenderCoordinator = new RenderCoordinator( RenderManager, base.BeginDraw, base.EndDraw ); RenderCoordinator.EnableThreading = _UseThreadedDraw; base.Initialize(); }
protected override bool BeginDraw() { RenderCoordinator.WorkStopwatch.Restart(); try { return(RenderCoordinator.BeginDraw()); } finally { RenderCoordinator.WorkStopwatch.Stop(); NextFrameTiming.BeginDraw = RenderCoordinator.WorkStopwatch.Elapsed; } }
public static ColorLUT CreateIdentity( RenderCoordinator coordinator, LUTPrecision precision = LUTPrecision.UInt8, LUTResolution resolution = LUTResolution.Low, bool renderable = false, Matrix?colorMatrix = null ) { var surfaceFormat = precision == LUTPrecision.UInt8 ? SurfaceFormat.Color : (precision == LUTPrecision.UInt16 ? SurfaceFormat.Rgba64 : SurfaceFormat.Vector4); var width = (int)resolution * (int)resolution; var height = (int)resolution; Texture2D tex; lock (coordinator.CreateResourceLock) { if (renderable) { tex = new RenderTarget2D(coordinator.Device, width, height, false, surfaceFormat, DepthFormat.None, 0, RenderTargetUsage.PreserveContents); } else { tex = new Texture2D(coordinator.Device, width, height, false, surfaceFormat); } tex.Tag = $"ColorLUT"; coordinator.AutoAllocatedTextureResources.Add(tex); } var _matrix = colorMatrix.HasValue ? colorMatrix.Value : default(Matrix); var result = new ColorLUT(tex, true); switch (precision) { case LUTPrecision.UInt8: result.SetToIdentity8(coordinator, colorMatrix.HasValue, ref _matrix); break; case LUTPrecision.UInt16: result.SetToIdentity16(coordinator, colorMatrix.HasValue, ref _matrix); break; case LUTPrecision.Float32: result.SetToIdentityF(coordinator, colorMatrix.HasValue, ref _matrix); break; default: throw new ArgumentOutOfRangeException("precision"); } return(result); }
public DynamicAtlas( RenderCoordinator coordinator, int width, int height, SurfaceFormat format, int spacing = 2, MipGeneratorFn mipGenerator = null, object tag = null ) { Id = NextId++; Coordinator = coordinator; Width = width; Height = height; Format = format; int temp; BytesPerPixel = Evil.TextureUtils.GetBytesPerPixelAndComponents(Format, out temp); Spacing = spacing; X = Y = Spacing; RowHeight = 0; _BeforeIssue = Flush; _BeforePrepare = QueueGenerateMips; Tag = tag; GenerateMip = mipGenerator; EnsureValidResource(); Pixels = new T[width * height]; if (mipGenerator != null) { var totalMipSize = 4; var currentMipSizePixels = (width / 2) * (height / 2); while (currentMipSizePixels > 1) { totalMipSize += (currentMipSizePixels + 1); currentMipSizePixels /= 2; } MipBuffer = new T[totalMipSize]; } if (DebugColors) { var p = Pixels as Color[]; if (p != null) { var w = 4096 * 4; for (int i = 0, l = p.Length; i < l; i++) { p[i] = (Color) new Color(i % 255, (Id * 64) % 255, (Id * 192) % 255, 255); } } } MipLevelCount = Texture.LevelCount; Invalidate(); }
private void InternalDispose() { if (RenderCoordinator != null) { RenderCoordinator.Dispose(); } if (ThreadGroup != null) { ThreadGroup.Dispose(); } }
protected override void Initialize() { RenderManager = new RenderManager(GraphicsDevice, Thread.CurrentThread, ThreadGroup); RenderCoordinator = new RenderCoordinator( RenderManager, base.BeginDraw, base.EndDraw ); RenderCoordinator.EnableThreading = UseThreadedDraw; RenderCoordinator.DeviceReset += (s, e) => OnDeviceReset(); SetupCloseHook(); base.Initialize(); }
public IFuture PreloadShadersAsync(RenderCoordinator coordinator, Task.TaskScheduler scheduler, Action <float> onProgress = null, int speed = 1) { if (IsDisposed) { throw new ObjectDisposedException("MaterialSetBase"); } var dm = coordinator.Manager.DeviceManager; var materials = GetShadersToPreload().ToList(); var tempIb = new IndexBuffer(dm.Device, IndexElementSize.SixteenBits, 128, BufferUsage.WriteOnly); var f = scheduler.Start(PreloadShadersAsyncImpl(coordinator, dm, tempIb, materials, onProgress, speed), Task.TaskExecutionPolicy.RunAsBackgroundTask); return(f); }
public RenderTargetRing( RenderCoordinator coordinator, int capacity, int width, int height, bool mipMap = false, SurfaceFormat preferredFormat = SurfaceFormat.Color, DepthFormat preferredDepthFormat = DepthFormat.None, int preferredMultiSampleCount = 1 ) : base( coordinator, width, height, mipMap, preferredFormat, preferredDepthFormat, preferredMultiSampleCount ) { Capacity = Math.Max(1, capacity); for (int i = 0; i < Capacity; i++) { AvailableTargets.Enqueue(CreateInstance()); } }
sealed protected override void UnloadContent() { if (IsUnloadingContent) { return; } RenderCoordinator.WaitForActiveDraws(); IsUnloadingContent = true; try { OnUnloadContent(); base.UnloadContent(); } finally { IsContentLoaded = false; IsUnloadingContent = false; } }
protected override void EndDraw() { RenderCoordinator.WorkStopwatch.Restart(); try { RenderCoordinator.EndDraw(); } finally { RenderCoordinator.WorkStopwatch.Stop(); NextFrameTiming.EndDraw = RenderCoordinator.WorkStopwatch.Elapsed; NextFrameTiming.Wait = RenderCoordinator.WaitStopwatch.Elapsed; PreviousFrameTiming = NextFrameTiming; RenderCoordinator.WaitStopwatch.Reset(); } RenderCoordinator.EnableThreading = _UseThreadedDraw; }
public AutoRenderTargetBase( RenderCoordinator coordinator, int width, int height, bool mipMap = false, SurfaceFormat preferredFormat = SurfaceFormat.Color, DepthFormat preferredDepthFormat = DepthFormat.None, int preferredMultiSampleCount = 1 ) { Coordinator = coordinator; Width = width; Height = height; MipMap = mipMap; PreferredFormat = preferredFormat; PreferredDepthFormat = preferredDepthFormat; PreferredMultiSampleCount = preferredMultiSampleCount; }
sealed protected override void LoadContent() { if (IsLoadingContent) { return; } RenderCoordinator.WaitForActiveDraws(); IsLoadingContent = true; try { base.LoadContent(); OnLoadContent(HasEverLoadedContent); HasEverLoadedContent = true; IsContentLoaded = true; } finally { IsLoadingContent = false; } }
internal void Initialize(RenderCoordinator coordinator, RenderManager renderManager, int index) { Batches.ListPoolOrAllocator = _ListPool; Batches.Clear(); Coordinator = coordinator; this.RenderManager = renderManager; Index = index; State = (int)States.Initialized; Label = "Frame"; ChangeRenderTargets = true; if (PrepareData == null) { PrepareData = new FramePrepareData(); } else { PrepareData.Initialize(); } }
sealed protected override void Draw(GameTime gameTime) { RenderCoordinator.WorkStopwatch.Restart(); var priorIndex = Batch.LifetimeCount; NextFrameTiming.PriorPrimitiveCount = NativeBatch.LifetimePrimitiveCount; try { OnBeforeDraw(gameTime); var frame = RenderCoordinator.BeginFrame(); RenderCoordinator.SynchronousDrawsEnabled = false; Draw(gameTime, frame); } finally { RenderCoordinator.SynchronousDrawsEnabled = true; RenderCoordinator.WorkStopwatch.Stop(); NextFrameTiming.Draw = RenderCoordinator.WorkStopwatch.Elapsed; NextFrameTiming.BatchCount = (int)(Batch.LifetimeCount - priorIndex); } }
public AutoRenderTarget( RenderCoordinator coordinator, int width, int height, bool mipMap = false, SurfaceFormat preferredFormat = SurfaceFormat.Color, DepthFormat preferredDepthFormat = DepthFormat.None, int preferredMultiSampleCount = 1 ) : base( coordinator, width, height, mipMap, preferredFormat, preferredDepthFormat, preferredMultiSampleCount ) { if (coordinator == null) { throw new ArgumentNullException(nameof(coordinator)); } GetOrCreateInstance(true); }
public Frame CreateFrame(RenderCoordinator coordinator) { lock (_FrameLock) { /* * if (_FrameInUse) * throw new InvalidOperationException("A frame is already in use"); * * _FrameInUse = true; * CollectAllocators(); */ // UGH if (!_FrameInUse) { CollectAllocators(); } _FrameInUse = true; _Frame = _ReusableFrame ?? new Frame(); _Frame.Initialize(coordinator, this, PickFrameIndex()); return(_Frame); } }
protected override void EndDraw() { RenderCoordinator.WorkStopwatch.Restart(); try { RenderCoordinator.EndDraw(); } finally { RenderCoordinator.WorkStopwatch.Stop(); var lpc = NativeBatch.LifetimePrimitiveCount; var ppc = NextFrameTiming.PriorPrimitiveCount; NextFrameTiming.EndDraw = RenderCoordinator.WorkStopwatch.Elapsed; NextFrameTiming.BeforePresent = RenderCoordinator.BeforePresentStopwatch.Elapsed; NextFrameTiming.Wait = RenderCoordinator.WaitStopwatch.Elapsed; NextFrameTiming.PrimitiveCount = (int)(lpc - ppc); PreviousFrameTiming = NextFrameTiming; RenderCoordinator.WaitStopwatch.Reset(); RenderCoordinator.BeforePresentStopwatch.Reset(); } RenderCoordinator.EnableThreading = UseThreadedDraw; }
protected override void Initialize() { RenderManager = new RenderManager(GraphicsDevice); RenderCoordinator = new RenderCoordinator( RenderManager, base.BeginDraw, base.EndDraw ); RenderCoordinator.EnableThreading = _UseThreadedDraw; base.Initialize(); }