Dispose actors when tearing down the world.

This commit is contained in:
Paul Chote
2015-05-23 21:41:21 +01:00
parent 585a43fd8f
commit 4ff309811f
3 changed files with 24 additions and 2 deletions

View File

@@ -22,7 +22,7 @@ using OpenRA.Traits;
namespace OpenRA
{
public class Actor : IScriptBindable, IScriptNotifyBind, ILuaTableBinding, ILuaEqualityBinding, ILuaToStringBinding, IEquatable<Actor>
public sealed class Actor : IScriptBindable, IScriptNotifyBind, ILuaTableBinding, ILuaEqualityBinding, ILuaToStringBinding, IEquatable<Actor>, IDisposable
{
public readonly ActorInfo Info;

View File

@@ -123,6 +123,9 @@ namespace OpenRA.Graphics
public void Draw()
{
if (World.WorldActor.Disposed)
return;
RefreshPalette();
if (World.Type == WorldType.Shellmap && !Game.Settings.Game.ShowShellmap)
@@ -273,6 +276,12 @@ namespace OpenRA.Graphics
public void Dispose()
{
// HACK: Disposing the world from here violates ownership
// but the WorldRenderer lifetime matches the disposal
// behavior we want for the world, and the root object setup
// is so horrible that doing it properly would be a giant mess.
World.Dispose();
palette.Dispose();
Theater.Dispose();
terrainRenderer.Dispose();

View File

@@ -24,7 +24,7 @@ namespace OpenRA
{
public enum WorldType { Regular, Shellmap, Editor }
public class World
public sealed class World : IDisposable
{
class ActorIDComparer : IComparer<Actor>
{
@@ -369,6 +369,19 @@ namespace OpenRA
pi.OutcomeTimestampUtc = DateTime.UtcNow;
}
}
public void Dispose()
{
frameEndActions.Clear();
// Dispose newer actors first, and the world actor last
foreach (var a in actors.Reverse())
a.Dispose();
// Actor disposals are done in a FrameEndTask
while (frameEndActions.Count != 0)
frameEndActions.Dequeue()(this);
}
}
public struct TraitPair<T>