diff --git a/OpenRA.Game/FileSystem/InstallShieldCABExtractor.cs b/OpenRA.Game/FileSystem/InstallShieldCABExtractor.cs index 9086d90c33..8046394460 100644 --- a/OpenRA.Game/FileSystem/InstallShieldCABExtractor.cs +++ b/OpenRA.Game/FileSystem/InstallShieldCABExtractor.cs @@ -17,7 +17,7 @@ using ICSharpCode.SharpZipLib.Zip.Compression; namespace OpenRA.FileSystem { - public class InstallShieldCABExtractor : IFolder + public sealed class InstallShieldCABExtractor : IFolder { const uint FileSplit = 0x1; const uint FileObfuscated = 0x2; diff --git a/OpenRA.Game/GlobalChat.cs b/OpenRA.Game/GlobalChat.cs index 6ad2faf6c9..2e25b1d48e 100644 --- a/OpenRA.Game/GlobalChat.cs +++ b/OpenRA.Game/GlobalChat.cs @@ -66,7 +66,7 @@ namespace OpenRA.Chat } } - public class GlobalChat : IDisposable + public sealed class GlobalChat : IDisposable { readonly IrcClient client = new IrcClient(); volatile Channel channel; diff --git a/OpenRA.Game/Graphics/HardwareCursor.cs b/OpenRA.Game/Graphics/HardwareCursor.cs index f77d00aff5..0512799685 100644 --- a/OpenRA.Game/Graphics/HardwareCursor.cs +++ b/OpenRA.Game/Graphics/HardwareCursor.cs @@ -17,7 +17,7 @@ using OpenRA.Primitives; namespace OpenRA.Graphics { - public class HardwareCursor : ICursor + public sealed class HardwareCursor : ICursor { readonly Dictionary hardwareCursors = new Dictionary(); readonly CursorProvider cursorProvider; diff --git a/OpenRA.Game/Graphics/SoftwareCursor.cs b/OpenRA.Game/Graphics/SoftwareCursor.cs index 09725f1957..9be1f80b31 100644 --- a/OpenRA.Game/Graphics/SoftwareCursor.cs +++ b/OpenRA.Game/Graphics/SoftwareCursor.cs @@ -24,7 +24,7 @@ namespace OpenRA.Graphics void Tick(); } - public class SoftwareCursor : ICursor + public sealed class SoftwareCursor : ICursor { readonly HardwarePalette palette = new HardwarePalette(); readonly Cache paletteReferences; diff --git a/OpenRA.Game/Graphics/SpriteFont.cs b/OpenRA.Game/Graphics/SpriteFont.cs index 2d719d0ee6..d23bc0a728 100644 --- a/OpenRA.Game/Graphics/SpriteFont.cs +++ b/OpenRA.Game/Graphics/SpriteFont.cs @@ -17,7 +17,7 @@ using SharpFont; namespace OpenRA.Graphics { - public class SpriteFont + public sealed class SpriteFont : IDisposable { static readonly Library Library = new Library(); @@ -150,6 +150,11 @@ namespace OpenRA.Graphics return g; } + + public void Dispose() + { + face.Dispose(); + } } class GlyphInfo diff --git a/OpenRA.Game/Renderer.cs b/OpenRA.Game/Renderer.cs index 157362adc6..114ddbd98b 100644 --- a/OpenRA.Game/Renderer.cs +++ b/OpenRA.Game/Renderer.cs @@ -91,6 +91,9 @@ namespace OpenRA public void InitializeFonts(Manifest m) { + if (Fonts != null) + foreach (var font in Fonts.Values) + font.Dispose(); using (new Support.PerfTimer("SpriteFonts")) { if (fontSheetBuilder != null) @@ -175,7 +178,7 @@ namespace OpenRA public Size Resolution { get { return Device.WindowSize; } } - public interface IBatchRenderer { void Flush(); } + public interface IBatchRenderer { void Flush(); } public IBatchRenderer CurrentBatchRenderer { @@ -254,6 +257,9 @@ namespace OpenRA tempBuffer.Dispose(); if (fontSheetBuilder != null) fontSheetBuilder.Dispose(); + if (Fonts != null) + foreach (var font in Fonts.Values) + font.Dispose(); } public string GetClipboardText() diff --git a/OpenRA.Mods.Cnc/CncLoadScreen.cs b/OpenRA.Mods.Cnc/CncLoadScreen.cs index aedc046d1f..45dcb89473 100644 --- a/OpenRA.Mods.Cnc/CncLoadScreen.cs +++ b/OpenRA.Mods.Cnc/CncLoadScreen.cs @@ -124,12 +124,12 @@ namespace OpenRA.Mods.Cnc r.EndFrame(nih); } - public override void Dispose() + protected override void Dispose(bool disposing) { - if (sheet != null) + if (disposing && sheet != null) sheet.Dispose(); - base.Dispose(); + base.Dispose(disposing); } } } \ No newline at end of file diff --git a/OpenRA.Mods.Common/LoadScreens/BlankLoadScreen.cs b/OpenRA.Mods.Common/LoadScreens/BlankLoadScreen.cs index ef0964e987..1c11bd2745 100644 --- a/OpenRA.Mods.Common/LoadScreens/BlankLoadScreen.cs +++ b/OpenRA.Mods.Common/LoadScreens/BlankLoadScreen.cs @@ -90,6 +90,12 @@ namespace OpenRA.Mods.Common.LoadScreens Game.Settings.Save(); } - public virtual void Dispose() { } + protected virtual void Dispose(bool disposing) { } + + public void Dispose() + { + Dispose(true); + GC.SuppressFinalize(this); + } } } \ No newline at end of file diff --git a/OpenRA.Mods.Common/LoadScreens/LogoStripeLoadScreen.cs b/OpenRA.Mods.Common/LoadScreens/LogoStripeLoadScreen.cs index 150f9b65b2..429080f115 100644 --- a/OpenRA.Mods.Common/LoadScreens/LogoStripeLoadScreen.cs +++ b/OpenRA.Mods.Common/LoadScreens/LogoStripeLoadScreen.cs @@ -79,12 +79,12 @@ namespace OpenRA.Mods.Common.LoadScreens r.EndFrame(new NullInputHandler()); } - public override void Dispose() + protected override void Dispose(bool disposing) { - if (sheet != null) + if (disposing && sheet != null) sheet.Dispose(); - base.Dispose(); + base.Dispose(disposing); } } } diff --git a/OpenRA.Mods.Common/Widgets/RadarWidget.cs b/OpenRA.Mods.Common/Widgets/RadarWidget.cs index 06b263be49..bc88244422 100644 --- a/OpenRA.Mods.Common/Widgets/RadarWidget.cs +++ b/OpenRA.Mods.Common/Widgets/RadarWidget.cs @@ -19,7 +19,7 @@ using OpenRA.Widgets; namespace OpenRA.Mods.Common.Widgets { - public class RadarWidget : Widget + public sealed class RadarWidget : Widget, IDisposable { public string WorldInteractionController = null; public int AnimationLength = 5; @@ -447,6 +447,12 @@ namespace OpenRA.Mods.Common.Widgets base.Removed(); world.Map.MapTiles.Value.CellEntryChanged -= UpdateTerrainCell; world.Map.CustomTerrain.CellEntryChanged -= UpdateTerrainCell; + Dispose(); + } + + public void Dispose() + { + radarSheet.Dispose(); } } } diff --git a/OpenRA.Platforms.Default/OpenAlSoundEngine.cs b/OpenRA.Platforms.Default/OpenAlSoundEngine.cs index 914e507879..6d23802d8f 100644 --- a/OpenRA.Platforms.Default/OpenAlSoundEngine.cs +++ b/OpenRA.Platforms.Default/OpenAlSoundEngine.cs @@ -304,13 +304,24 @@ namespace OpenRA.Platforms.Default AL10.alListenerf(EFX.AL_METERS_PER_UNIT, .01f); } + ~OpenAlSoundEngine() + { + Game.RunAfterTick(() => Dispose(false)); + } + public void Dispose() { - if (device == IntPtr.Zero) - return; + Game.RunAfterTick(() => Dispose(true)); + GC.SuppressFinalize(this); + } - ALC10.alcCloseDevice(device); - device = IntPtr.Zero; + void Dispose(bool disposing) + { + if (device != IntPtr.Zero) + { + ALC10.alcCloseDevice(device); + device = IntPtr.Zero; + } } }