diff --git a/BizHawk.Client.Common/lua/EmuLuaLibrary.Emu.cs b/BizHawk.Client.Common/lua/EmuLuaLibrary.Emu.cs index 0009e3613e..7808b9295c 100644 --- a/BizHawk.Client.Common/lua/EmuLuaLibrary.Emu.cs +++ b/BizHawk.Client.Common/lua/EmuLuaLibrary.Emu.cs @@ -3,6 +3,8 @@ using System.Linq; using LuaInterface; using BizHawk.Emulation.Consoles.Nintendo; +using BizHawk.Emulation.Cores.PCEngine; +using BizHawk.Emulation.Cores.Sega.MasterSystem; namespace BizHawk.Client.Common { @@ -50,7 +52,7 @@ namespace BizHawk.Client.Common Global.CoreComm.NES_ShowOBJ = Global.Config.NESDispSprites = (bool)lua_p[0]; Global.CoreComm.NES_ShowBG = Global.Config.NESDispBackground = (bool)lua_p[1]; } - else if (Global.Emulator is Emulation.Consoles.TurboGrafx.PCEngine) + else if (Global.Emulator is PCEngine) { Global.CoreComm.PCE_ShowOBJ1 = Global.Config.PCEDispOBJ1 = (bool)lua_p[0]; Global.CoreComm.PCE_ShowBG1 = Global.Config.PCEDispBG1 = (bool)lua_p[1]; @@ -60,7 +62,7 @@ namespace BizHawk.Client.Common Global.CoreComm.PCE_ShowBG2 = Global.Config.PCEDispBG2 = (bool)lua_p[3]; } } - else if (Global.Emulator is Emulation.Consoles.Sega.SMS) + else if (Global.Emulator is SMS) { Global.CoreComm.SMS_ShowOBJ = Global.Config.SMSDispOBJ = (bool)lua_p[0]; Global.CoreComm.SMS_ShowBG = Global.Config.SMSDispBG = (bool)lua_p[1]; diff --git a/BizHawk.Client.Common/lua/EmuLuaLibrary.SNES.cs b/BizHawk.Client.Common/lua/EmuLuaLibrary.SNES.cs index 2cc1ddc30e..8983575f6f 100644 --- a/BizHawk.Client.Common/lua/EmuLuaLibrary.SNES.cs +++ b/BizHawk.Client.Common/lua/EmuLuaLibrary.SNES.cs @@ -1,4 +1,4 @@ -using BizHawk.Emulation.Consoles.Nintendo.SNES; +using BizHawk.Emulation.Cores.Nintendo.SNES; namespace BizHawk.Client.Common { diff --git a/BizHawk.Client.EmuHawk/MainForm.Events.cs b/BizHawk.Client.EmuHawk/MainForm.Events.cs index a7d67b69c5..ea0a592c6e 100644 --- a/BizHawk.Client.EmuHawk/MainForm.Events.cs +++ b/BizHawk.Client.EmuHawk/MainForm.Events.cs @@ -8,8 +8,8 @@ using BizHawk.Client.Common; using BizHawk.Emulation.Common; using BizHawk.Emulation.Cores.Calculators; using BizHawk.Emulation.Cores.Atari.Atari2600; +using BizHawk.Emulation.Cores.Nintendo.SNES; using BizHawk.Emulation.Cores.Nintendo.Gameboy; -using BizHawk.Emulation.Consoles.Nintendo.SNES; namespace BizHawk.Client.EmuHawk { diff --git a/BizHawk.Client.EmuHawk/MainForm.Movie.cs b/BizHawk.Client.EmuHawk/MainForm.Movie.cs index 870ae94ddf..d42da20fa7 100644 --- a/BizHawk.Client.EmuHawk/MainForm.Movie.cs +++ b/BizHawk.Client.EmuHawk/MainForm.Movie.cs @@ -4,9 +4,9 @@ using System.Windows.Forms; using BizHawk.Client.Common; using BizHawk.Emulation.Cores.Nintendo.GBA; -using BizHawk.Emulation.Consoles.Sega; -using BizHawk.Emulation.Consoles.Sega.Saturn; -using BizHawk.Emulation.Consoles.Sony.PSP; +using BizHawk.Emulation.Cores.Sega.Genesis; +using BizHawk.Emulation.Cores.Sega.Saturn; +using BizHawk.Emulation.Cores.Sony.PSP; namespace BizHawk.Client.EmuHawk { diff --git a/BizHawk.Client.EmuHawk/MainForm.cs b/BizHawk.Client.EmuHawk/MainForm.cs index 16db65697a..5853fb4d40 100644 --- a/BizHawk.Client.EmuHawk/MainForm.cs +++ b/BizHawk.Client.EmuHawk/MainForm.cs @@ -12,20 +12,28 @@ using BizHawk.Common; using BizHawk.Client.Common; using BizHawk.Emulation; using BizHawk.Emulation.Common; +using BizHawk.Emulation.DiscSystem; + using BizHawk.Emulation.Cores.Computers.Commodore64; using BizHawk.Emulation.Cores.Calculators; using BizHawk.Emulation.Cores.Atari.Atari2600; using BizHawk.Emulation.Cores.Atari.Atari7800; using BizHawk.Emulation.Cores.ColecoVision; -using BizHawk.Emulation.Cores.Nintendo.Gameboy; using BizHawk.Emulation.Cores.Intellivision; +using BizHawk.Emulation.Cores.PCEngine; + using BizHawk.Emulation.Consoles.Nintendo; -using BizHawk.Emulation.Cores.Nintendo.GBA; +using BizHawk.Emulation.Cores.Nintendo.SNES; using BizHawk.Emulation.Cores.Nintendo.N64; -using BizHawk.Emulation.Consoles.Nintendo.SNES; -using BizHawk.Emulation.Consoles.Sega; -using BizHawk.Emulation.Consoles.TurboGrafx; -using BizHawk.Emulation.DiscSystem; +using BizHawk.Emulation.Cores.Nintendo.Gameboy; +using BizHawk.Emulation.Cores.Nintendo.GBA; + +using BizHawk.Emulation.Cores.Sega.MasterSystem; +using BizHawk.Emulation.Cores.Sega.Genesis; +using BizHawk.Emulation.Cores.Sega.Saturn; + +using BizHawk.Emulation.Cores.Sony.PSX; +using BizHawk.Emulation.Cores.Sony.PSP; namespace BizHawk.Client.EmuHawk { @@ -1457,10 +1465,10 @@ namespace BizHawk.Client.EmuHawk return ret; } - private void SaturnSetPrefs(Emulation.Consoles.Sega.Saturn.Yabause e = null) + private void SaturnSetPrefs(Yabause e = null) { if (e == null) - e = Global.Emulator as Emulation.Consoles.Sega.Saturn.Yabause; + e = Global.Emulator as Yabause; if (Global.Config.SaturnUseGL != e.GLMode) { @@ -3128,20 +3136,20 @@ namespace BizHawk.Client.EmuHawk MessageBox.Show("Saturn BIOS not found. Please check firmware configurations."); return false; } - var saturn = new Emulation.Consoles.Sega.Saturn.Yabause(nextComm, disc, File.ReadAllBytes(biosPath), Global.Config.SaturnUseGL); + var saturn = new Yabause(nextComm, disc, File.ReadAllBytes(biosPath), Global.Config.SaturnUseGL); nextEmulator = saturn; SaturnSetPrefs(saturn); } break; case "PSP": { - var psp = new Emulation.Consoles.Sony.PSP.PSP(nextComm, file.Name); + var psp = new PSP(nextComm, file.Name); nextEmulator = psp; } break; case "PSX": { - var psx = new Emulation.Consoles.PSX.Octoshock(nextComm); + var psx = new Octoshock(nextComm); nextEmulator = psx; psx.LoadCuePath(file.CanonicalFullPath); nextEmulator.CoreComm.RomStatusDetails = "PSX etc."; diff --git a/BizHawk.Client.EmuHawk/movie/RecordMovie.cs b/BizHawk.Client.EmuHawk/movie/RecordMovie.cs index e4db41dbdd..c62a4c1b25 100644 --- a/BizHawk.Client.EmuHawk/movie/RecordMovie.cs +++ b/BizHawk.Client.EmuHawk/movie/RecordMovie.cs @@ -4,11 +4,11 @@ using System.IO; using BizHawk.Emulation.Common; using BizHawk.Emulation.Cores.ColecoVision; -using BizHawk.Emulation.Cores.Nintendo.Gameboy; -using BizHawk.Emulation.Consoles.Nintendo.SNES; -using BizHawk.Emulation.Consoles.Sega; +using BizHawk.Emulation.Cores.Sega.MasterSystem; using BizHawk.Emulation.Consoles.Nintendo; +using BizHawk.Emulation.Cores.Nintendo.SNES; using BizHawk.Emulation.Cores.Nintendo.N64; +using BizHawk.Emulation.Cores.Nintendo.Gameboy; using BizHawk.Client.Common; namespace BizHawk.Client.EmuHawk diff --git a/BizHawk.Client.EmuHawk/tools/Cheats/Cheats.cs b/BizHawk.Client.EmuHawk/tools/Cheats/Cheats.cs index ef212ca544..aaacb3f6c8 100644 --- a/BizHawk.Client.EmuHawk/tools/Cheats/Cheats.cs +++ b/BizHawk.Client.EmuHawk/tools/Cheats/Cheats.cs @@ -10,9 +10,9 @@ using System.Threading.Tasks; using System.Windows.Forms; using BizHawk.Client.Common; -using BizHawk.Emulation.Consoles.Nintendo.SNES; using BizHawk.Emulation.Consoles.Nintendo; -using BizHawk.Emulation.Consoles.Sega; +using BizHawk.Emulation.Cores.Nintendo.SNES; +using BizHawk.Emulation.Cores.Sega.Genesis; namespace BizHawk.Client.EmuHawk { diff --git a/BizHawk.Client.EmuHawk/tools/Genesis/GenGameGenie.cs b/BizHawk.Client.EmuHawk/tools/Genesis/GenGameGenie.cs index 552e37e565..3ca75db454 100644 --- a/BizHawk.Client.EmuHawk/tools/Genesis/GenGameGenie.cs +++ b/BizHawk.Client.EmuHawk/tools/Genesis/GenGameGenie.cs @@ -6,7 +6,7 @@ using System.Globalization; using System.Text.RegularExpressions; using BizHawk.Client.Common; -using BizHawk.Emulation.Consoles.Sega; +using BizHawk.Emulation.Cores.Sega.Genesis; #pragma warning disable 675 //TOOD: fix the potential problem this is masking diff --git a/BizHawk.Client.EmuHawk/tools/PCE/PCEBGViewer.cs b/BizHawk.Client.EmuHawk/tools/PCE/PCEBGViewer.cs index fc164f3ffe..730b199851 100644 --- a/BizHawk.Client.EmuHawk/tools/PCE/PCEBGViewer.cs +++ b/BizHawk.Client.EmuHawk/tools/PCE/PCEBGViewer.cs @@ -4,7 +4,7 @@ using System.Windows.Forms; using System.Drawing.Imaging; using BizHawk.Client.Common; -using BizHawk.Emulation.Consoles.TurboGrafx; +using BizHawk.Emulation.Cores.PCEngine; namespace BizHawk.Client.EmuHawk { diff --git a/BizHawk.Client.EmuHawk/tools/SNES/SNESGameGenie.cs b/BizHawk.Client.EmuHawk/tools/SNES/SNESGameGenie.cs index 6e8506e83b..0225fac087 100644 --- a/BizHawk.Client.EmuHawk/tools/SNES/SNESGameGenie.cs +++ b/BizHawk.Client.EmuHawk/tools/SNES/SNESGameGenie.cs @@ -4,9 +4,9 @@ using System.Drawing; using System.Windows.Forms; using System.Globalization; using System.Text.RegularExpressions; -using BizHawk.Emulation.Consoles.Nintendo.SNES; using BizHawk.Client.Common; +using BizHawk.Emulation.Cores.Nintendo.SNES; namespace BizHawk.Client.EmuHawk { @@ -36,9 +36,9 @@ namespace BizHawk.Client.EmuHawk { InitializeComponent(); Closing += (o, e) => SaveConfigSettings(); - //including transposition - //Code: D F 4 7 0 9 1 5 6 B C 8 A 2 3 E - //Hex: 0 1 2 3 4 5 6 7 8 9 A B C D E F + //including transposition + //Code: D F 4 7 0 9 1 5 6 B C 8 A 2 3 E + //Hex: 0 1 2 3 4 5 6 7 8 9 A B C D E F GameGenieTable.Add('D', 0); //0000 GameGenieTable.Add('F', 1); //0001 diff --git a/BizHawk.Client.EmuHawk/tools/SNES/SNESGraphicsDebugger.cs b/BizHawk.Client.EmuHawk/tools/SNES/SNESGraphicsDebugger.cs index 8df9810b58..80bbc29bfd 100644 --- a/BizHawk.Client.EmuHawk/tools/SNES/SNESGraphicsDebugger.cs +++ b/BizHawk.Client.EmuHawk/tools/SNES/SNESGraphicsDebugger.cs @@ -31,7 +31,7 @@ using System.Windows.Forms; using BizHawk.Common; using BizHawk.Client.Common; -using BizHawk.Emulation.Consoles.Nintendo.SNES; +using BizHawk.Emulation.Cores.Nintendo.SNES; using BizHawk.Client.EmuHawk; //TODO: What?? namespace BizHawk.Client.EmuHawk diff --git a/BizHawk.Client.EmuHawk/tools/ToolBox.cs b/BizHawk.Client.EmuHawk/tools/ToolBox.cs index 36a1c3b5d6..77ccd3127d 100644 --- a/BizHawk.Client.EmuHawk/tools/ToolBox.cs +++ b/BizHawk.Client.EmuHawk/tools/ToolBox.cs @@ -3,10 +3,9 @@ using System.Drawing; using System.Windows.Forms; using BizHawk.Client.Common; -using BizHawk.Emulation.Consoles.Nintendo; using BizHawk.Emulation.Cores.Calculators; -using BizHawk.Emulation.Consoles.Nintendo.SNES; -using BizHawk.Emulation.Consoles.Sega; +using BizHawk.Emulation.Consoles.Nintendo; +using BizHawk.Emulation.Cores.Nintendo.SNES; namespace BizHawk.Client.EmuHawk { diff --git a/BizHawk.Emulation/Consoles/Nintendo/Gameboy/GambatteLink.cs b/BizHawk.Emulation/Consoles/Nintendo/Gameboy/GambatteLink.cs index db03aa8eee..c774c58ae5 100644 --- a/BizHawk.Emulation/Consoles/Nintendo/Gameboy/GambatteLink.cs +++ b/BizHawk.Emulation/Consoles/Nintendo/Gameboy/GambatteLink.cs @@ -5,6 +5,7 @@ using System.Linq; using BizHawk.Common; using BizHawk.Emulation.Common; +using BizHawk.Emulation.Cores.Nintendo.SNES; namespace BizHawk.Emulation.Cores.Nintendo.Gameboy { @@ -31,8 +32,8 @@ namespace BizHawk.Emulation.Cores.Nintendo.Gameboy const int SampPerFrame = 35112; - Consoles.Nintendo.SNES.LibsnesCore.SnesSaveController LCont = new BizHawk.Emulation.Consoles.Nintendo.SNES.LibsnesCore.SnesSaveController(Gameboy.GbController); - Consoles.Nintendo.SNES.LibsnesCore.SnesSaveController RCont = new BizHawk.Emulation.Consoles.Nintendo.SNES.LibsnesCore.SnesSaveController(Gameboy.GbController); + LibsnesCore.SnesSaveController LCont = new LibsnesCore.SnesSaveController(Gameboy.GbController); + LibsnesCore.SnesSaveController RCont = new LibsnesCore.SnesSaveController(Gameboy.GbController); public GambatteLink(CoreComm comm, GameInfo leftinfo, byte[] leftrom, GameInfo rightinfo, byte[] rightrom) { diff --git a/BizHawk.Emulation/Consoles/Nintendo/SNES/LibsnesApi.cs b/BizHawk.Emulation/Consoles/Nintendo/SNES/LibsnesApi.cs index a48a0726f7..d80b9f4f04 100644 --- a/BizHawk.Emulation/Consoles/Nintendo/SNES/LibsnesApi.cs +++ b/BizHawk.Emulation/Consoles/Nintendo/SNES/LibsnesApi.cs @@ -6,7 +6,7 @@ using System.Collections.Generic; using System.Runtime.InteropServices; using System.IO.MemoryMappedFiles; -namespace BizHawk.Emulation.Consoles.Nintendo.SNES +namespace BizHawk.Emulation.Cores.Nintendo.SNES { /// diff --git a/BizHawk.Emulation/Consoles/Nintendo/SNES/LibsnesCore.cs b/BizHawk.Emulation/Consoles/Nintendo/SNES/LibsnesCore.cs index 1dba6f056c..4dc4a72d0a 100644 --- a/BizHawk.Emulation/Consoles/Nintendo/SNES/LibsnesCore.cs +++ b/BizHawk.Emulation/Consoles/Nintendo/SNES/LibsnesCore.cs @@ -18,7 +18,7 @@ using System.Runtime.InteropServices; using BizHawk.Common; using BizHawk.Emulation.Common; -namespace BizHawk.Emulation.Consoles.Nintendo.SNES +namespace BizHawk.Emulation.Cores.Nintendo.SNES { public class ScanlineHookManager diff --git a/BizHawk.Emulation/Consoles/Nintendo/SNES/SNESGraphicsDecoder.cs b/BizHawk.Emulation/Consoles/Nintendo/SNES/SNESGraphicsDecoder.cs index 87a56003f8..409f1ebf54 100644 --- a/BizHawk.Emulation/Consoles/Nintendo/SNES/SNESGraphicsDecoder.cs +++ b/BizHawk.Emulation/Consoles/Nintendo/SNES/SNESGraphicsDecoder.cs @@ -7,7 +7,7 @@ using System; -namespace BizHawk.Emulation.Consoles.Nintendo.SNES +namespace BizHawk.Emulation.Cores.Nintendo.SNES { public unsafe class SNESGraphicsDecoder : IDisposable diff --git a/BizHawk.Emulation/Consoles/Nintendo/SNES/SnesColors.cs b/BizHawk.Emulation/Consoles/Nintendo/SNES/SnesColors.cs index c99365c49d..3fdf6c2fbf 100644 --- a/BizHawk.Emulation/Consoles/Nintendo/SNES/SnesColors.cs +++ b/BizHawk.Emulation/Consoles/Nintendo/SNES/SnesColors.cs @@ -1,4 +1,4 @@ -namespace BizHawk.Emulation.Consoles.Nintendo.SNES +namespace BizHawk.Emulation.Cores.Nintendo.SNES { public static class SnesColors { diff --git a/BizHawk.Emulation/Consoles/PC Engine/ADPCM.cs b/BizHawk.Emulation/Consoles/PC Engine/ADPCM.cs index 1abffaad25..74a9877974 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/ADPCM.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/ADPCM.cs @@ -6,7 +6,7 @@ using System.Globalization; using BizHawk.Common; using BizHawk.Emulation.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { public sealed class ADPCM : ISoundProvider { diff --git a/BizHawk.Emulation/Consoles/PC Engine/ArcadeCard.cs b/BizHawk.Emulation/Consoles/PC Engine/ArcadeCard.cs index e8a7b57c85..e6a23f5c22 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/ArcadeCard.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/ArcadeCard.cs @@ -4,7 +4,7 @@ using System.Globalization; using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { partial class PCEngine { diff --git a/BizHawk.Emulation/Consoles/PC Engine/Input.cs b/BizHawk.Emulation/Consoles/PC Engine/Input.cs index 442dc8e820..c9a666b7ec 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/Input.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/Input.cs @@ -1,6 +1,6 @@ using BizHawk.Emulation.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { public partial class PCEngine { diff --git a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.Populous.cs b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.Populous.cs index 14560f1664..70b6fd0c4c 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.Populous.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.Populous.cs @@ -1,6 +1,6 @@ using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { public partial class PCEngine { diff --git a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.SF2.cs b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.SF2.cs index 55538acddb..1174f6bd98 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.SF2.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.SF2.cs @@ -1,6 +1,6 @@ using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { public partial class PCEngine { diff --git a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.SuperGrafx.cs b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.SuperGrafx.cs index f9a219b6a7..7b430e7b6d 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.SuperGrafx.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.SuperGrafx.cs @@ -1,6 +1,6 @@ using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { public partial class PCEngine { diff --git a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.TurboCD.cs b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.TurboCD.cs index 866e24b65d..7ab39609ee 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.TurboCD.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.TurboCD.cs @@ -1,6 +1,6 @@ using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { public partial class PCEngine { diff --git a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.cs b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.cs index 9a123f908b..41090b36c8 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/MemoryMap.cs @@ -1,6 +1,6 @@ using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { public partial class PCEngine { diff --git a/BizHawk.Emulation/Consoles/PC Engine/PCEngine.cs b/BizHawk.Emulation/Consoles/PC Engine/PCEngine.cs index 0de404e926..c835f42f11 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/PCEngine.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/PCEngine.cs @@ -9,7 +9,7 @@ using BizHawk.Emulation.CPUs.H6280; using BizHawk.Emulation.DiscSystem; using BizHawk.Emulation.Sound; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { public enum NecSystemType { TurboGrafx, TurboCD, SuperGrafx } diff --git a/BizHawk.Emulation/Consoles/PC Engine/ScsiCDBus.cs b/BizHawk.Emulation/Consoles/PC Engine/ScsiCDBus.cs index 4d473510a4..7d9542a64c 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/ScsiCDBus.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/ScsiCDBus.cs @@ -6,7 +6,7 @@ using BizHawk.Common; using BizHawk.Emulation.DiscSystem; using BizHawk.Emulation.Sound; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { // TODO we can adjust this to have Think take the number of cycles and not require // a reference to Cpu.TotalExecutedCycles diff --git a/BizHawk.Emulation/Consoles/PC Engine/TurboCD.cs b/BizHawk.Emulation/Consoles/PC Engine/TurboCD.cs index 36d7a1d371..cbcdd8bd5c 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/TurboCD.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/TurboCD.cs @@ -1,7 +1,7 @@ using System; using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { public partial class PCEngine { diff --git a/BizHawk.Emulation/Consoles/PC Engine/VCE.cs b/BizHawk.Emulation/Consoles/PC Engine/VCE.cs index 5c1ab9266d..478b1610fe 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/VCE.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/VCE.cs @@ -4,141 +4,141 @@ using System.IO; using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { - // HuC6260 Video Color Encoder - public sealed class VCE - { - public ushort VceAddress; - public ushort[] VceData = new ushort[512]; - public int[] Palette = new int[512]; - public byte CR; + // HuC6260 Video Color Encoder + public sealed class VCE + { + public ushort VceAddress; + public ushort[] VceData = new ushort[512]; + public int[] Palette = new int[512]; + public byte CR; - public int NumberOfScanlines { get { return ((CR & 4) != 0) ? 263 : 262; } } - public int DotClock - { - get - { - int clock = CR & 3; - if (clock == 3) - clock = 2; - return clock; - } - } + public int NumberOfScanlines { get { return ((CR & 4) != 0) ? 263 : 262; } } + public int DotClock + { + get + { + int clock = CR & 3; + if (clock == 3) + clock = 2; + return clock; + } + } - // guess the dot clock affects wait states in combination with the dot with regs. - // We dont currently emulate wait states, probably will have to eventually... + // guess the dot clock affects wait states in combination with the dot with regs. + // We dont currently emulate wait states, probably will have to eventually... - // Note: To keep the VCE class from needing a reference to the CPU, the 1-cycle access - // penalty for the VCE is handled by the memory mappers. - // One day I guess I could create an ICpu with a StealCycles method... + // Note: To keep the VCE class from needing a reference to the CPU, the 1-cycle access + // penalty for the VCE is handled by the memory mappers. + // One day I guess I could create an ICpu with a StealCycles method... - public void WriteVCE(int port, byte value) - { - port &= 0x07; - switch (port) - { - case 0: // Control Port - CR = value; - break; - case 2: // Address LSB - VceAddress &= 0xFF00; - VceAddress |= value; - break; - case 3: // Address MSB - VceAddress &= 0x00FF; - VceAddress |= (ushort) (value << 8); - VceAddress &= 0x01FF; - break; - case 4: // Data LSB - VceData[VceAddress] &= 0xFF00; - VceData[VceAddress] |= value; - PrecomputePalette(VceAddress); - break; - case 5: // Data MSB - VceData[VceAddress] &= 0x00FF; - VceData[VceAddress] |= (ushort) (value << 8); - PrecomputePalette(VceAddress); - VceAddress++; - VceAddress &= 0x1FF; - break; - } - } + public void WriteVCE(int port, byte value) + { + port &= 0x07; + switch (port) + { + case 0: // Control Port + CR = value; + break; + case 2: // Address LSB + VceAddress &= 0xFF00; + VceAddress |= value; + break; + case 3: // Address MSB + VceAddress &= 0x00FF; + VceAddress |= (ushort)(value << 8); + VceAddress &= 0x01FF; + break; + case 4: // Data LSB + VceData[VceAddress] &= 0xFF00; + VceData[VceAddress] |= value; + PrecomputePalette(VceAddress); + break; + case 5: // Data MSB + VceData[VceAddress] &= 0x00FF; + VceData[VceAddress] |= (ushort)(value << 8); + PrecomputePalette(VceAddress); + VceAddress++; + VceAddress &= 0x1FF; + break; + } + } - public byte ReadVCE(int port) - { - port &= 0x07; - switch (port) - { - case 4: // Data LSB - return (byte) (VceData[VceAddress] & 0xFF); - case 5: // Data MSB - byte value = (byte) ((VceData[VceAddress] >> 8) | 0xFE); - VceAddress++; - VceAddress &= 0x1FF; - return value; - default: return 0xFF; - } - } + public byte ReadVCE(int port) + { + port &= 0x07; + switch (port) + { + case 4: // Data LSB + return (byte)(VceData[VceAddress] & 0xFF); + case 5: // Data MSB + byte value = (byte)((VceData[VceAddress] >> 8) | 0xFE); + VceAddress++; + VceAddress &= 0x1FF; + return value; + default: return 0xFF; + } + } - static readonly byte[] PalConvert = {0, 36, 72, 109, 145, 182, 218, 255}; + static readonly byte[] PalConvert = { 0, 36, 72, 109, 145, 182, 218, 255 }; - public void PrecomputePalette(int slot) - { - byte r = PalConvert[(VceData[slot] >> 3) & 7]; - byte g = PalConvert[(VceData[slot] >> 6) & 7]; - byte b = PalConvert[VceData[slot] & 7]; - Palette[slot] = Colors.ARGB(r, g, b); - } + public void PrecomputePalette(int slot) + { + byte r = PalConvert[(VceData[slot] >> 3) & 7]; + byte g = PalConvert[(VceData[slot] >> 6) & 7]; + byte b = PalConvert[VceData[slot] & 7]; + Palette[slot] = Colors.ARGB(r, g, b); + } - public void SaveStateText(TextWriter writer) - { - writer.WriteLine("[VCE]"); - writer.WriteLine("VceAddress {0:X4}", VceAddress); - writer.WriteLine("CR {0}", CR); - writer.Write("VceData "); - VceData.SaveAsHex(writer); - writer.WriteLine("[/VCE]\n"); - } + public void SaveStateText(TextWriter writer) + { + writer.WriteLine("[VCE]"); + writer.WriteLine("VceAddress {0:X4}", VceAddress); + writer.WriteLine("CR {0}", CR); + writer.Write("VceData "); + VceData.SaveAsHex(writer); + writer.WriteLine("[/VCE]\n"); + } - public void LoadStateText(TextReader reader) - { - while (true) - { - string[] args = reader.ReadLine().Split(' '); - if (args[0].Trim() == "") continue; - if (args[0] == "[/VCE]") break; - if (args[0] == "VceAddress") - VceAddress = ushort.Parse(args[1], NumberStyles.HexNumber); - else if (args[0] == "CR") - CR = byte.Parse(args[1]); - else if (args[0] == "VceData") - VceData.ReadFromHex(args[1]); - else - Console.WriteLine("Skipping unrecognized identifier " + args[0]); - } + public void LoadStateText(TextReader reader) + { + while (true) + { + string[] args = reader.ReadLine().Split(' '); + if (args[0].Trim() == "") continue; + if (args[0] == "[/VCE]") break; + if (args[0] == "VceAddress") + VceAddress = ushort.Parse(args[1], NumberStyles.HexNumber); + else if (args[0] == "CR") + CR = byte.Parse(args[1]); + else if (args[0] == "VceData") + VceData.ReadFromHex(args[1]); + else + Console.WriteLine("Skipping unrecognized identifier " + args[0]); + } - for (int i = 0; i < VceData.Length; i++) - PrecomputePalette(i); - } + for (int i = 0; i < VceData.Length; i++) + PrecomputePalette(i); + } - public void SaveStateBinary(BinaryWriter writer) - { - writer.Write(VceAddress); - writer.Write(CR); - for (int i = 0; i < VceData.Length; i++) - writer.Write(VceData[i]); - } + public void SaveStateBinary(BinaryWriter writer) + { + writer.Write(VceAddress); + writer.Write(CR); + for (int i = 0; i < VceData.Length; i++) + writer.Write(VceData[i]); + } - public void LoadStateBinary(BinaryReader reader) - { - VceAddress = reader.ReadUInt16(); - CR = reader.ReadByte(); - for (int i = 0; i < VceData.Length; i++) - { - VceData[i] = reader.ReadUInt16(); - PrecomputePalette(i); - } - } - } + public void LoadStateBinary(BinaryReader reader) + { + VceAddress = reader.ReadUInt16(); + CR = reader.ReadByte(); + for (int i = 0; i < VceData.Length; i++) + { + VceData[i] = reader.ReadUInt16(); + PrecomputePalette(i); + } + } + } } diff --git a/BizHawk.Emulation/Consoles/PC Engine/VDC.Render.cs b/BizHawk.Emulation/Consoles/PC Engine/VDC.Render.cs index 4f4863ee14..2230ff4935 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/VDC.Render.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/VDC.Render.cs @@ -1,353 +1,353 @@ using System; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { - // This rendering code is only used for TurboGrafx/TurboCD Mode. - // In SuperGrafx mode, separate rendering functions in the VPC class are used. + // This rendering code is only used for TurboGrafx/TurboCD Mode. + // In SuperGrafx mode, separate rendering functions in the VPC class are used. - public partial class VDC - { - /* There are many line-counters here. Here is a breakdown of what they each are: + public partial class VDC + { + /* There are many line-counters here. Here is a breakdown of what they each are: - + ScanLine is the current NTSC scanline. It has a range from 0 to 262. - + ActiveLine is the current offset into the framebuffer. 0 is the first - line of active display, and the last value will be BufferHeight-1. - + BackgroundY is the current offset into the scroll plane. It is set with BYR - register at certain sync points and incremented every scanline. - Its values range from 0 - $1FF. - + RCRCounter is set to $40 at the first line of active display, and incremented each - scanline thereafter. - */ - public int ScanLine; - public int BackgroundY; - public int RCRCounter; - public int ActiveLine; + + ScanLine is the current NTSC scanline. It has a range from 0 to 262. + + ActiveLine is the current offset into the framebuffer. 0 is the first + line of active display, and the last value will be BufferHeight-1. + + BackgroundY is the current offset into the scroll plane. It is set with BYR + register at certain sync points and incremented every scanline. + Its values range from 0 - $1FF. + + RCRCounter is set to $40 at the first line of active display, and incremented each + scanline thereafter. + */ + public int ScanLine; + public int BackgroundY; + public int RCRCounter; + public int ActiveLine; - public int HBlankCycles = 79; - public bool PerformSpriteLimit; + public int HBlankCycles = 79; + public bool PerformSpriteLimit; - byte[] PriorityBuffer = new byte[512]; - byte[] InterSpritePriorityBuffer = new byte[512]; + byte[] PriorityBuffer = new byte[512]; + byte[] InterSpritePriorityBuffer = new byte[512]; - public void ExecFrame(bool render) - { - if (MultiResHack > 0 && render) - Array.Clear(FrameBuffer, 0, FrameBuffer.Length); - - while (true) - { - int ActiveDisplayStartLine = DisplayStartLine; - int VBlankLine = ActiveDisplayStartLine + Registers[VDW] + 1; - if (VBlankLine > 261) - VBlankLine = 261; - ActiveLine = ScanLine - ActiveDisplayStartLine; - bool InActiveDisplay = (ScanLine >= ActiveDisplayStartLine) && (ScanLine < VBlankLine); + public void ExecFrame(bool render) + { + if (MultiResHack > 0 && render) + Array.Clear(FrameBuffer, 0, FrameBuffer.Length); - if (ScanLine == ActiveDisplayStartLine) - RCRCounter = 0x40; + while (true) + { + int ActiveDisplayStartLine = DisplayStartLine; + int VBlankLine = ActiveDisplayStartLine + Registers[VDW] + 1; + if (VBlankLine > 261) + VBlankLine = 261; + ActiveLine = ScanLine - ActiveDisplayStartLine; + bool InActiveDisplay = (ScanLine >= ActiveDisplayStartLine) && (ScanLine < VBlankLine); - if (ScanLine == VBlankLine) - UpdateSpriteAttributeTable(); + if (ScanLine == ActiveDisplayStartLine) + RCRCounter = 0x40; - if (RCRCounter == (Registers[RCR] & 0x3FF)) - { - if (RasterCompareInterruptEnabled) - { - StatusByte |= StatusRasterCompare; - cpu.IRQ1Assert = true; - } - } + if (ScanLine == VBlankLine) + UpdateSpriteAttributeTable(); - cpu.Execute(HBlankCycles); + if (RCRCounter == (Registers[RCR] & 0x3FF)) + { + if (RasterCompareInterruptEnabled) + { + StatusByte |= StatusRasterCompare; + cpu.IRQ1Assert = true; + } + } - if (InActiveDisplay) - { - if (ScanLine == ActiveDisplayStartLine) - BackgroundY = Registers[BYR]; - else - { - BackgroundY++; - BackgroundY &= 0x01FF; - } - if (render) RenderScanLine(); - } + cpu.Execute(HBlankCycles); - if (ScanLine == VBlankLine && VBlankInterruptEnabled) - StatusByte |= StatusVerticalBlanking; + if (InActiveDisplay) + { + if (ScanLine == ActiveDisplayStartLine) + BackgroundY = Registers[BYR]; + else + { + BackgroundY++; + BackgroundY &= 0x01FF; + } + if (render) RenderScanLine(); + } - if (ScanLine == VBlankLine + 4 && SatDmaPerformed) - { - SatDmaPerformed = false; - if ((Registers[DCR] & 1) > 0) - StatusByte |= StatusVramSatDmaComplete; - } + if (ScanLine == VBlankLine && VBlankInterruptEnabled) + StatusByte |= StatusVerticalBlanking; - cpu.Execute(2); + if (ScanLine == VBlankLine + 4 && SatDmaPerformed) + { + SatDmaPerformed = false; + if ((Registers[DCR] & 1) > 0) + StatusByte |= StatusVramSatDmaComplete; + } - if ((StatusByte & (StatusVerticalBlanking | StatusVramSatDmaComplete)) != 0) - cpu.IRQ1Assert = true; + cpu.Execute(2); - cpu.Execute(455 - HBlankCycles - 2); + if ((StatusByte & (StatusVerticalBlanking | StatusVramSatDmaComplete)) != 0) + cpu.IRQ1Assert = true; - if (InActiveDisplay == false && DmaRequested) - RunDmaForScanline(); + cpu.Execute(455 - HBlankCycles - 2); - ScanLine++; - RCRCounter++; + if (InActiveDisplay == false && DmaRequested) + RunDmaForScanline(); - if (ScanLine == vce.NumberOfScanlines) - { - ScanLine = 0; - break; - } - } - } + ScanLine++; + RCRCounter++; - public void RenderScanLine() - { - if (ActiveLine >= FrameHeight) - return; + if (ScanLine == vce.NumberOfScanlines) + { + ScanLine = 0; + break; + } + } + } - RenderBackgroundScanline(pce.CoreComm.PCE_ShowBG1); - RenderSpritesScanline(pce.CoreComm.PCE_ShowOBJ1); - } + public void RenderScanLine() + { + if (ActiveLine >= FrameHeight) + return; - void RenderBackgroundScanline(bool show) - { - Array.Clear(PriorityBuffer, 0, FrameWidth); + RenderBackgroundScanline(pce.CoreComm.PCE_ShowBG1); + RenderSpritesScanline(pce.CoreComm.PCE_ShowOBJ1); + } - if (BackgroundEnabled == false) - { - for (int i = 0; i < FrameWidth; i++) - FrameBuffer[(ActiveLine * FramePitch) + i] = vce.Palette[256]; - return; - } + void RenderBackgroundScanline(bool show) + { + Array.Clear(PriorityBuffer, 0, FrameWidth); - int batHeight = BatHeight * 8; - int batWidth = BatWidth * 8; + if (BackgroundEnabled == false) + { + for (int i = 0; i < FrameWidth; i++) + FrameBuffer[(ActiveLine * FramePitch) + i] = vce.Palette[256]; + return; + } - int vertLine = BackgroundY; - vertLine %= batHeight; - int yTile = (vertLine / 8); - int yOfs = vertLine % 8; + int batHeight = BatHeight * 8; + int batWidth = BatWidth * 8; - // This is not optimized. But it seems likely to remain that way. - int xScroll = Registers[BXR] & 0x3FF; - for (int x = 0; x < FrameWidth; x++) - { - int xTile = ((x + xScroll) / 8) % BatWidth; - int xOfs = (x + xScroll) & 7; - int tileNo = VRAM[(ushort)(((yTile * BatWidth) + xTile))] & 2047; - int paletteNo = VRAM[(ushort)(((yTile * BatWidth) + xTile))] >> 12; - int paletteBase = paletteNo * 16; + int vertLine = BackgroundY; + vertLine %= batHeight; + int yTile = (vertLine / 8); + int yOfs = vertLine % 8; - byte c = PatternBuffer[(tileNo * 64) + (yOfs * 8) + xOfs]; - if (c == 0) - FrameBuffer[(ActiveLine * FramePitch) + x] = vce.Palette[0]; - else - { - FrameBuffer[(ActiveLine * FramePitch) + x] = show ? vce.Palette[paletteBase + c] : vce.Palette[0]; - PriorityBuffer[x] = 1; - } - } - } + // This is not optimized. But it seems likely to remain that way. + int xScroll = Registers[BXR] & 0x3FF; + for (int x = 0; x < FrameWidth; x++) + { + int xTile = ((x + xScroll) / 8) % BatWidth; + int xOfs = (x + xScroll) & 7; + int tileNo = VRAM[(ushort)(((yTile * BatWidth) + xTile))] & 2047; + int paletteNo = VRAM[(ushort)(((yTile * BatWidth) + xTile))] >> 12; + int paletteBase = paletteNo * 16; - byte[] heightTable = { 16, 32, 64, 64 }; + byte c = PatternBuffer[(tileNo * 64) + (yOfs * 8) + xOfs]; + if (c == 0) + FrameBuffer[(ActiveLine * FramePitch) + x] = vce.Palette[0]; + else + { + FrameBuffer[(ActiveLine * FramePitch) + x] = show ? vce.Palette[paletteBase + c] : vce.Palette[0]; + PriorityBuffer[x] = 1; + } + } + } - public void RenderSpritesScanline(bool show) - { - if (SpritesEnabled == false) - return; + byte[] heightTable = { 16, 32, 64, 64 }; - Array.Clear(InterSpritePriorityBuffer, 0, FrameWidth); - bool Sprite4ColorMode = Sprite4ColorModeEnabled; - int activeSprites = 0; + public void RenderSpritesScanline(bool show) + { + if (SpritesEnabled == false) + return; - for (int i = 0; i < 64; i++) - { - if (activeSprites >= 16 && PerformSpriteLimit) - break; - - int y = (SpriteAttributeTable[(i * 4) + 0] & 1023) - 64; - int x = (SpriteAttributeTable[(i * 4) + 1] & 1023) - 32; - ushort flags = SpriteAttributeTable[(i * 4) + 3]; - int height = heightTable[(flags >> 12) & 3]; - int width = (flags & 0x100) == 0 ? 16 : 32; + Array.Clear(InterSpritePriorityBuffer, 0, FrameWidth); + bool Sprite4ColorMode = Sprite4ColorModeEnabled; + int activeSprites = 0; - if (y + height <= ActiveLine || y > ActiveLine) - continue; + for (int i = 0; i < 64; i++) + { + if (activeSprites >= 16 && PerformSpriteLimit) + break; - activeSprites += width == 16 ? 1 : 2; - - int patternNo = (((SpriteAttributeTable[(i * 4) + 2]) >> 1) & 0x1FF); - int paletteBase = 256 + ((flags & 15) * 16); - bool priority = (flags & 0x80) != 0; - bool hflip = (flags & 0x0800) != 0; - bool vflip = (flags & 0x8000) != 0; + int y = (SpriteAttributeTable[(i * 4) + 0] & 1023) - 64; + int x = (SpriteAttributeTable[(i * 4) + 1] & 1023) - 32; + ushort flags = SpriteAttributeTable[(i * 4) + 3]; + int height = heightTable[(flags >> 12) & 3]; + int width = (flags & 0x100) == 0 ? 16 : 32; - int colorMask = 0xFF; - if (Sprite4ColorMode) - { - if ((SpriteAttributeTable[(i * 4) + 2] & 1) == 0) - colorMask = 0x03; - else - colorMask = 0x0C; - } + if (y + height <= ActiveLine || y > ActiveLine) + continue; - if (width == 32) - patternNo &= 0x1FE; + activeSprites += width == 16 ? 1 : 2; - int yofs = 0; - if (vflip == false) - { - yofs = (ActiveLine - y) & 15; - if (height == 32) - { - patternNo &= 0x1FD; - if (ActiveLine - y >= 16) - { - y += 16; - patternNo += 2; - } - } - else if (height == 64) - { - patternNo &= 0x1F9; - if (ActiveLine - y >= 48) - { - y += 48; - patternNo += 6; - } - else if (ActiveLine - y >= 32) - { - y += 32; - patternNo += 4; - } - else if (ActiveLine - y >= 16) - { - y += 16; - patternNo += 2; - } - } - } - else // vflip == true - { - yofs = 15 - ((ActiveLine - y) & 15); - if (height == 32) - { - patternNo &= 0x1FD; - if (ActiveLine - y < 16) - { - y += 16; - patternNo += 2; - } - } - else if (height == 64) - { - patternNo &= 0x1F9; - if (ActiveLine - y < 16) - { - y += 48; - patternNo += 6; - } - else if (ActiveLine - y < 32) - { - y += 32; - patternNo += 4; - } - else if (ActiveLine - y < 48) - { - y += 16; - patternNo += 2; - } - } - } - if (hflip == false) - { - if (x + width > 0 && y + height > 0) - { - for (int xs = x >= 0 ? x : 0; xs < x + 16 && xs >= 0 && xs < FrameWidth; xs++) - { - byte pixel = (byte)(SpriteBuffer[(patternNo * 256) + (yofs * 16) + (xs - x)] & colorMask); - if (colorMask == 0x0C) - pixel >>= 2; - if (pixel != 0 && InterSpritePriorityBuffer[xs] == 0) - { - InterSpritePriorityBuffer[xs] = 1; - if ((priority || PriorityBuffer[xs] == 0) && show) - FrameBuffer[(ActiveLine * FramePitch) + xs] = vce.Palette[paletteBase + pixel]; - } - } - } - if (width == 32) - { - patternNo++; - x += 16; - for (int xs = x >= 0 ? x : 0; xs < x + 16 && xs >= 0 && xs < FrameWidth; xs++) - { - byte pixel = (byte)(SpriteBuffer[(patternNo * 256) + (yofs * 16) + (xs - x)] & colorMask); - if (colorMask == 0x0C) - pixel >>= 2; - if (pixel != 0 && InterSpritePriorityBuffer[xs] == 0) - { - InterSpritePriorityBuffer[xs] = 1; - if ((priority || PriorityBuffer[xs] == 0) && show) - FrameBuffer[(ActiveLine * FramePitch) + xs] = vce.Palette[paletteBase + pixel]; - } + int patternNo = (((SpriteAttributeTable[(i * 4) + 2]) >> 1) & 0x1FF); + int paletteBase = 256 + ((flags & 15) * 16); + bool priority = (flags & 0x80) != 0; + bool hflip = (flags & 0x0800) != 0; + bool vflip = (flags & 0x8000) != 0; - } - } - } - else - { // hflip = true - if (x + width > 0 && y + height > 0) - { - if (width == 32) - patternNo++; - for (int xs = x >= 0 ? x : 0; xs < x + 16 && xs >= 0 && xs < FrameWidth; xs++) - { - byte pixel = (byte)(SpriteBuffer[(patternNo * 256) + (yofs * 16) + 15 - (xs - x)] & colorMask); - if (colorMask == 0x0C) - pixel >>= 2; - if (pixel != 0 && InterSpritePriorityBuffer[xs] == 0) - { - InterSpritePriorityBuffer[xs] = 1; - if ((priority || PriorityBuffer[xs] == 0) && show) - FrameBuffer[(ActiveLine * FramePitch) + xs] = vce.Palette[paletteBase + pixel]; - } - } - if (width == 32) - { - patternNo--; - x += 16; - for (int xs = x >= 0 ? x : 0; xs < x + 16 && xs >= 0 && xs < FrameWidth; xs++) - { - byte pixel = (byte)(SpriteBuffer[(patternNo * 256) + (yofs * 16) + 15 - (xs - x)] & colorMask); - if (colorMask == 0x0C) - pixel >>= 2; - if (pixel != 0 && InterSpritePriorityBuffer[xs] == 0) - { - InterSpritePriorityBuffer[xs] = 1; - if ((priority || PriorityBuffer[xs] == 0) && show) - FrameBuffer[(ActiveLine * FramePitch) + xs] = vce.Palette[paletteBase + pixel]; - } - } - } - } - } - } - } + int colorMask = 0xFF; + if (Sprite4ColorMode) + { + if ((SpriteAttributeTable[(i * 4) + 2] & 1) == 0) + colorMask = 0x03; + else + colorMask = 0x0C; + } - int FramePitch = 256; - int FrameWidth = 256; - int FrameHeight = 240; - int[] FrameBuffer = new int[256 * 240]; + if (width == 32) + patternNo &= 0x1FE; - public int[] GetVideoBuffer() { return FrameBuffer; } + int yofs = 0; + if (vflip == false) + { + yofs = (ActiveLine - y) & 15; + if (height == 32) + { + patternNo &= 0x1FD; + if (ActiveLine - y >= 16) + { + y += 16; + patternNo += 2; + } + } + else if (height == 64) + { + patternNo &= 0x1F9; + if (ActiveLine - y >= 48) + { + y += 48; + patternNo += 6; + } + else if (ActiveLine - y >= 32) + { + y += 32; + patternNo += 4; + } + else if (ActiveLine - y >= 16) + { + y += 16; + patternNo += 2; + } + } + } + else // vflip == true + { + yofs = 15 - ((ActiveLine - y) & 15); + if (height == 32) + { + patternNo &= 0x1FD; + if (ActiveLine - y < 16) + { + y += 16; + patternNo += 2; + } + } + else if (height == 64) + { + patternNo &= 0x1F9; + if (ActiveLine - y < 16) + { + y += 48; + patternNo += 6; + } + else if (ActiveLine - y < 32) + { + y += 32; + patternNo += 4; + } + else if (ActiveLine - y < 48) + { + y += 16; + patternNo += 2; + } + } + } + if (hflip == false) + { + if (x + width > 0 && y + height > 0) + { + for (int xs = x >= 0 ? x : 0; xs < x + 16 && xs >= 0 && xs < FrameWidth; xs++) + { + byte pixel = (byte)(SpriteBuffer[(patternNo * 256) + (yofs * 16) + (xs - x)] & colorMask); + if (colorMask == 0x0C) + pixel >>= 2; + if (pixel != 0 && InterSpritePriorityBuffer[xs] == 0) + { + InterSpritePriorityBuffer[xs] = 1; + if ((priority || PriorityBuffer[xs] == 0) && show) + FrameBuffer[(ActiveLine * FramePitch) + xs] = vce.Palette[paletteBase + pixel]; + } + } + } + if (width == 32) + { + patternNo++; + x += 16; + for (int xs = x >= 0 ? x : 0; xs < x + 16 && xs >= 0 && xs < FrameWidth; xs++) + { + byte pixel = (byte)(SpriteBuffer[(patternNo * 256) + (yofs * 16) + (xs - x)] & colorMask); + if (colorMask == 0x0C) + pixel >>= 2; + if (pixel != 0 && InterSpritePriorityBuffer[xs] == 0) + { + InterSpritePriorityBuffer[xs] = 1; + if ((priority || PriorityBuffer[xs] == 0) && show) + FrameBuffer[(ActiveLine * FramePitch) + xs] = vce.Palette[paletteBase + pixel]; + } - public int VirtualWidth { get { return FramePitch; } } - public int BufferWidth { get { return FramePitch; } } - public int BufferHeight { get { return FrameHeight; } } - public int BackgroundColor { get { return vce.Palette[256]; } } - } + } + } + } + else + { // hflip = true + if (x + width > 0 && y + height > 0) + { + if (width == 32) + patternNo++; + for (int xs = x >= 0 ? x : 0; xs < x + 16 && xs >= 0 && xs < FrameWidth; xs++) + { + byte pixel = (byte)(SpriteBuffer[(patternNo * 256) + (yofs * 16) + 15 - (xs - x)] & colorMask); + if (colorMask == 0x0C) + pixel >>= 2; + if (pixel != 0 && InterSpritePriorityBuffer[xs] == 0) + { + InterSpritePriorityBuffer[xs] = 1; + if ((priority || PriorityBuffer[xs] == 0) && show) + FrameBuffer[(ActiveLine * FramePitch) + xs] = vce.Palette[paletteBase + pixel]; + } + } + if (width == 32) + { + patternNo--; + x += 16; + for (int xs = x >= 0 ? x : 0; xs < x + 16 && xs >= 0 && xs < FrameWidth; xs++) + { + byte pixel = (byte)(SpriteBuffer[(patternNo * 256) + (yofs * 16) + 15 - (xs - x)] & colorMask); + if (colorMask == 0x0C) + pixel >>= 2; + if (pixel != 0 && InterSpritePriorityBuffer[xs] == 0) + { + InterSpritePriorityBuffer[xs] = 1; + if ((priority || PriorityBuffer[xs] == 0) && show) + FrameBuffer[(ActiveLine * FramePitch) + xs] = vce.Palette[paletteBase + pixel]; + } + } + } + } + } + } + } + + int FramePitch = 256; + int FrameWidth = 256; + int FrameHeight = 240; + int[] FrameBuffer = new int[256 * 240]; + + public int[] GetVideoBuffer() { return FrameBuffer; } + + public int VirtualWidth { get { return FramePitch; } } + public int BufferWidth { get { return FramePitch; } } + public int BufferHeight { get { return FrameHeight; } } + public int BackgroundColor { get { return vce.Palette[256]; } } + } } diff --git a/BizHawk.Emulation/Consoles/PC Engine/VDC.cs b/BizHawk.Emulation/Consoles/PC Engine/VDC.cs index feb9568a67..4ddde8af4d 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/VDC.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/VDC.cs @@ -6,7 +6,7 @@ using BizHawk.Common; using BizHawk.Emulation.Common; using BizHawk.Emulation.CPUs.H6280; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { // HuC6270 Video Display Controller diff --git a/BizHawk.Emulation/Consoles/PC Engine/VPC.cs b/BizHawk.Emulation/Consoles/PC Engine/VPC.cs index 3094013d1f..5c8cc360a3 100644 --- a/BizHawk.Emulation/Consoles/PC Engine/VPC.cs +++ b/BizHawk.Emulation/Consoles/PC Engine/VPC.cs @@ -5,7 +5,7 @@ using BizHawk.Common; using BizHawk.Emulation.Common; using BizHawk.Emulation.CPUs.H6280; -namespace BizHawk.Emulation.Consoles.TurboGrafx +namespace BizHawk.Emulation.Cores.PCEngine { // ------------------------------------------------------ // HuC6202 Video Priority Controller diff --git a/BizHawk.Emulation/Consoles/PSX/Octoshock.cs b/BizHawk.Emulation/Consoles/PSX/Octoshock.cs index d826dd3ca6..76bd217167 100644 --- a/BizHawk.Emulation/Consoles/PSX/Octoshock.cs +++ b/BizHawk.Emulation/Consoles/PSX/Octoshock.cs @@ -7,7 +7,7 @@ using BizHawk.Emulation.Common; #pragma warning disable 649 //adelikat: Disable dumb warnings until this file is complete -namespace BizHawk.Emulation.Consoles.PSX +namespace BizHawk.Emulation.Cores.Sony.PSX { public unsafe class Octoshock : IEmulator, IVideoProvider, ISoundProvider { diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/EEPROM.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/EEPROM.cs index 50223955c5..96d1e3f118 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/EEPROM.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/EEPROM.cs @@ -3,7 +3,7 @@ using System.Globalization; using BizHawk.Emulation.Common; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { partial class Genesis { diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/RomHeader.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/RomHeader.cs index e202e7479e..cf3652cefa 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/RomHeader.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/RomHeader.cs @@ -1,61 +1,61 @@ using System; using System.Text; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { - partial class Genesis - { - public string RH_Console { get { return GetRomString(0x100, 0x10); } } - public string RH_Copyright { get { return GetRomString(0x110, 0x10); } } - public string RH_NameDomestic { get { return GetRomString(0x120, 0x30); } } - public string RH_NameExport { get { return GetRomString(0x150, 0x30); } } - public int RH_RomSize { get { return GetRomLongWord(0x1A4); } } - public string RH_Region { get { return GetRomString(0x1F0, 3); } } + partial class Genesis + { + public string RH_Console { get { return GetRomString(0x100, 0x10); } } + public string RH_Copyright { get { return GetRomString(0x110, 0x10); } } + public string RH_NameDomestic { get { return GetRomString(0x120, 0x30); } } + public string RH_NameExport { get { return GetRomString(0x150, 0x30); } } + public int RH_RomSize { get { return GetRomLongWord(0x1A4); } } + public string RH_Region { get { return GetRomString(0x1F0, 3); } } - public bool RH_SRamPresent { get { return (RomData[0x1B2] & 0x40) != 0; } } - public int RH_SRamCode { get { return (RomData[0x1B2] >> 3) & 3; } } - public int RH_SRamStart { get { return GetRomLongWord(0x1B4); } } - public int RH_SRamEnd { get { return GetRomLongWord(0x1B8); } } + public bool RH_SRamPresent { get { return (RomData[0x1B2] & 0x40) != 0; } } + public int RH_SRamCode { get { return (RomData[0x1B2] >> 3) & 3; } } + public int RH_SRamStart { get { return GetRomLongWord(0x1B4); } } + public int RH_SRamEnd { get { return GetRomLongWord(0x1B8); } } - public string RH_SRamInterpretation() - { - switch (RH_SRamCode) - { - case 0: return "Even and odd addresses"; - case 2: return "Even addresses"; - case 3: return "Odd addresses"; - default: return "Invalid type"; - } - } + public string RH_SRamInterpretation() + { + switch (RH_SRamCode) + { + case 0: return "Even and odd addresses"; + case 2: return "Even addresses"; + case 3: return "Odd addresses"; + default: return "Invalid type"; + } + } - string GetRomString(int offset, int len) - { - return Encoding.ASCII.GetString(RomData, offset, len).Trim(); - } + string GetRomString(int offset, int len) + { + return Encoding.ASCII.GetString(RomData, offset, len).Trim(); + } - int GetRomLongWord(int offset) - { - return (RomData[offset] << 24) | (RomData[offset + 1] << 16) | (RomData[offset + 2] << 8) | RomData[offset + 3]; - } + int GetRomLongWord(int offset) + { + return (RomData[offset] << 24) | (RomData[offset + 1] << 16) | (RomData[offset + 2] << 8) | RomData[offset + 3]; + } - void LogCartInfo() - { - Console.WriteLine("=================="); - Console.WriteLine("ROM Cartridge Data"); - Console.WriteLine("=================="); - Console.WriteLine("System: {0}", RH_Console); - Console.WriteLine("Copyright: {0}", RH_Copyright); - Console.WriteLine("Name (Dom): {0}", RH_NameDomestic); - Console.WriteLine("Name (Exp): {0}", RH_NameExport); - Console.WriteLine("Region: {0}", RH_Region); - Console.WriteLine("Rom Size: {0,7} (${0:X})", RH_RomSize); - Console.WriteLine("SRAM Used: {0}", RH_SRamPresent); - if (RH_SRamPresent) - { - Console.WriteLine("SRAM Start: {0,7} (${0:X})", RH_SRamStart); - Console.WriteLine("SRAM End: {0,7} (${0:X})", RH_SRamEnd); - Console.WriteLine("SRAM Type: {0}", RH_SRamInterpretation()); - } - } - } + void LogCartInfo() + { + Console.WriteLine("=================="); + Console.WriteLine("ROM Cartridge Data"); + Console.WriteLine("=================="); + Console.WriteLine("System: {0}", RH_Console); + Console.WriteLine("Copyright: {0}", RH_Copyright); + Console.WriteLine("Name (Dom): {0}", RH_NameDomestic); + Console.WriteLine("Name (Exp): {0}", RH_NameExport); + Console.WriteLine("Region: {0}", RH_Region); + Console.WriteLine("Rom Size: {0,7} (${0:X})", RH_RomSize); + Console.WriteLine("SRAM Used: {0}", RH_SRamPresent); + if (RH_SRamPresent) + { + Console.WriteLine("SRAM Start: {0,7} (${0:X})", RH_SRamStart); + Console.WriteLine("SRAM End: {0,7} (${0:X})", RH_SRamEnd); + Console.WriteLine("SRAM Type: {0}", RH_SRamInterpretation()); + } + } + } } diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/SaveRAM.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/SaveRAM.cs index da1437b498..c5c8244f28 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/SaveRAM.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/Cart/SaveRAM.cs @@ -1,7 +1,7 @@ using System; using BizHawk.Emulation.Common; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { partial class Genesis { diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.DMA.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.DMA.cs index 947bf76bdb..71ecf22dd1 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.DMA.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.DMA.cs @@ -1,7 +1,7 @@ using System; using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { public partial class GenVDP { diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.Render.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.Render.cs index 49ec5df467..8474935ef4 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.Render.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.Render.cs @@ -1,515 +1,525 @@ using System; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { - public partial class GenVDP - { - // Priority buffer contents have the following values: - // 0 = Backdrop color - // 1 = Plane B Low Priority - // 2 = Plane A Low Priority - // 4 = Plane B High Priority - // 5 = Plane A High Priority - // 9 = Sprite has been drawn - - byte[] PriorityBuffer = new byte[320]; - - static readonly byte[] PalXlatTable = { 0, 0, 36, 36, 73, 73, 109, 109, 145, 145, 182, 182, 219, 219, 255, 255 }; - - public void RenderLine() - { - if (DisplayEnabled) - { - Array.Clear(PriorityBuffer, 0, 320); - - // TODO: I would like to be able to render Scroll A before Scroll B, in order to minimize overdraw. - // But at the moment it complicates priority stuff. - - if (CellBasedVertScroll == false) - { - RenderScrollB(); - RenderScrollA(); - } else { - RenderScrollBTwoCellVScroll(); - RenderScrollATwoCellVScroll(); - } - - RenderSpritesScanline(); - } - else - { - // If display is disabled, fill in with background color. - for (int i = 0; i < FrameWidth; i++) - FrameBuffer[(ScanLine * FrameWidth) + i] = BackgroundColor; - } - - //if (ScanLine == 223) // shrug - // RenderPalette(); - } - - void RenderPalette() - { - for (int p = 0; p < 4; p++) - for (int i = 0; i < 16; i++) - FrameBuffer[(p*FrameWidth) + i] = Palette[(p*16) + i]; - } - - void RenderScrollAScanline(int xScroll, int yScroll, int nameTableBase, int startPixel, int endPixel, bool window) - { - const int lowPriority = 2; - const int highPriority = 5; - int yTile = ((ScanLine + yScroll) / 8) % NameTableHeight; - int nameTableWidth = NameTableWidth; - if (window) - nameTableWidth = (DisplayWidth == 40) ? 64 : 32; - - // this is hellllla slow. but not optimizing until we implement & understand - // all scrolling modes, shadow & hilight, etc. - // in thinking about this, you could convince me to optimize the PCE background renderer now. - // Its way simple in comparison. But the PCE sprite renderer is way worse than gen. - for (int x = startPixel; x < endPixel; x++) - { - int xTile = Math.Abs(((x + (1024-xScroll)) / 8) % nameTableWidth); - int xOfs = Math.Abs((x + (1024-xScroll)) & 7); - int yOfs = (ScanLine + yScroll) % 8; - int cellOfs = nameTableBase + (yTile * nameTableWidth * 2) + (xTile * 2); - int nameTableEntry = VRAM[cellOfs] | (VRAM[cellOfs+1] << 8); - int patternNo = nameTableEntry & 0x7FF; - bool hFlip = ((nameTableEntry >> 11) & 1) != 0; - bool vFlip = ((nameTableEntry >> 12) & 1) != 0; - bool priority = ((nameTableEntry >> 15) & 1) != 0; - int palette = (nameTableEntry >> 13) & 3; - - if (priority && PriorityBuffer[x] >= highPriority) continue; - if (!priority && PriorityBuffer[x] >= lowPriority) continue; - - if (vFlip) yOfs = 7 - yOfs; - if (hFlip) xOfs = 7 - xOfs; - - int texel = PatternBuffer[(patternNo * 64) + (yOfs * 8) + (xOfs)]; - if (texel == 0) continue; - int pixel = Palette[(palette * 16) + texel]; - FrameBuffer[(ScanLine * FrameWidth) + x] = pixel; - PriorityBuffer[x] = (byte) (priority ? highPriority : lowPriority); - } - } - - void RenderScrollAScanlineTwoCellVScroll(int xScroll, int nameTableBase, int startPixel, int endPixel, bool window) - { - const int lowPriority = 2; - const int highPriority = 5; - - int fineHScroll = xScroll & 15; - int nameTableWidth = NameTableWidth; - if (window) - nameTableWidth = (DisplayWidth == 40) ? 64 : 32; - - for (int x = startPixel; x < endPixel; x++) - { - int vsramUnitOffset = ((x - fineHScroll) / 16) % 40; - int yScroll = VSRAM[vsramUnitOffset * 2] & 0x3FF; - int yTile = ((ScanLine + yScroll) / 8) % NameTableHeight; - - int xTile = Math.Abs(((x + (1024 - xScroll)) / 8) % nameTableWidth); - int xOfs = Math.Abs((x + (1024 - xScroll)) & 7); - int yOfs = (ScanLine + yScroll) % 8; - int cellOfs = nameTableBase + (yTile * nameTableWidth * 2) + (xTile * 2); - int nameTableEntry = VRAM[cellOfs] | (VRAM[cellOfs + 1] << 8); - int patternNo = nameTableEntry & 0x7FF; - bool hFlip = ((nameTableEntry >> 11) & 1) != 0; - bool vFlip = ((nameTableEntry >> 12) & 1) != 0; - bool priority = ((nameTableEntry >> 15) & 1) != 0; - int palette = (nameTableEntry >> 13) & 3; - - if (priority && PriorityBuffer[x] >= highPriority) continue; - if (!priority && PriorityBuffer[x] >= lowPriority) continue; - - if (vFlip) yOfs = 7 - yOfs; - if (hFlip) xOfs = 7 - xOfs; - - int texel = PatternBuffer[(patternNo * 64) + (yOfs * 8) + (xOfs)]; - if (texel == 0) continue; - int pixel = Palette[(palette * 16) + texel]; - FrameBuffer[(ScanLine * FrameWidth) + x] = pixel; - PriorityBuffer[x] = (byte)(priority ? highPriority : lowPriority); - } - } - - void CalculateWindowScanlines(out int startScanline, out int endScanline) - { - int data = Registers[0x12]; - int windowVPosition = data & 31; - bool fromTop = (data & 0x80) == 0; - - if (windowVPosition == 0) - { - startScanline = -1; - endScanline = -1; - return; - } - - if (fromTop) - { - startScanline = 0; - endScanline = (windowVPosition * 8); - } else { - startScanline = windowVPosition * 8; - endScanline = FrameHeight; - } - } - - void CalculateWindowPosition(out int startPixel, out int endPixel) - { - int data = Registers[0x11]; - int windowHPosition = (data & 31) * 2; // Window H position is set in 2-cell increments - bool fromLeft = (data & 0x80) == 0; - - if (windowHPosition == 0) - { - startPixel = -1; - endPixel = -1; - return; - } - - if (fromLeft) - { - startPixel = 0; - endPixel = (windowHPosition * 8); - if (endPixel > FrameWidth) - endPixel = FrameWidth; - } - else - { - startPixel = windowHPosition * 8; - endPixel = FrameWidth; - if (startPixel > FrameWidth) - { - startPixel = -1; - endPixel = -1; - } - } - } - - void RenderScrollA() - { - // Calculate scroll offsets - - int hscroll = CalcHScrollPlaneA(ScanLine); - int vscroll = VSRAM[0] & 0x3FF; - - // Calculate window dimensions - - int startWindowScanline, endWindowScanline; - int startWindowPixel, endWindowPixel; - CalculateWindowScanlines(out startWindowScanline, out endWindowScanline); - CalculateWindowPosition(out startWindowPixel, out endWindowPixel); - - // Render scanline - - if (ScanLine >= startWindowScanline && ScanLine < endWindowScanline) // Window takes up whole scanline - { - RenderScrollAScanline(0, 0, NameTableAddrWindow, 0, FrameWidth, true); - } - else if (startWindowPixel != -1) // Window takes up partial scanline - { - if (startWindowPixel == 0) // Window grows from left side - { - RenderScrollAScanline(0, 0, NameTableAddrWindow, 0, endWindowPixel, true); - RenderScrollAScanline(hscroll, vscroll, NameTableAddrA, endWindowPixel, FrameWidth, false); - } - else // Window grows from right side - { - RenderScrollAScanline(hscroll, vscroll, NameTableAddrA, 0, startWindowPixel, false); - RenderScrollAScanline(0, 0, NameTableAddrWindow, startWindowPixel, FrameWidth, true); - } - } - else // No window this scanline - { - RenderScrollAScanline(hscroll, vscroll, NameTableAddrA, 0, FrameWidth, false); - } - } - - void RenderScrollATwoCellVScroll() - { - // Calculate scroll offsets - - int hscroll = CalcHScrollPlaneA(ScanLine); - - // Calculate window dimensions - - int startWindowScanline, endWindowScanline; - int startWindowPixel, endWindowPixel; - CalculateWindowScanlines(out startWindowScanline, out endWindowScanline); - CalculateWindowPosition(out startWindowPixel, out endWindowPixel); - - // Render scanline - - if (ScanLine >= startWindowScanline && ScanLine < endWindowScanline) // Window takes up whole scanline - { - RenderScrollAScanline(0, 0, NameTableAddrWindow, 0, FrameWidth, true); - } - else if (startWindowPixel != -1) // Window takes up partial scanline - { - if (startWindowPixel == 0) // Window grows from left side - { - RenderScrollAScanline(0, 0, NameTableAddrWindow, 0, endWindowPixel, true); - RenderScrollAScanlineTwoCellVScroll(hscroll, NameTableAddrA, endWindowPixel, FrameWidth, false); - } - else // Window grows from right side - { - RenderScrollAScanlineTwoCellVScroll(hscroll, NameTableAddrA, 0, startWindowPixel, false); - RenderScrollAScanline(0, 0, NameTableAddrWindow, startWindowPixel, FrameWidth, true); - } - } - else // No window this scanline - { - RenderScrollAScanlineTwoCellVScroll(hscroll, NameTableAddrA, 0, FrameWidth, false); - } - } - - void RenderScrollB() - { - int bgColor = BackgroundColor; - int xScroll = CalcHScrollPlaneB(ScanLine); - int yScroll = VSRAM[1] & 0x3FF; - - const int lowPriority = 1; - const int highPriority = 4; - - int yTile = ((ScanLine + yScroll) / 8) % NameTableHeight; - - // this is hellllla slow. but not optimizing until we implement & understand - // all scrolling modes, shadow & hilight, etc. - // in thinking about this, you could convince me to optimize the PCE background renderer now. - // Its way simple in comparison. But the PCE sprite renderer is way worse than gen. - for (int x = 0; x < FrameWidth; x++) - { - int xTile = Math.Abs(((x + (1024 - xScroll)) / 8) % NameTableWidth); - int xOfs = Math.Abs((x + (1024 - xScroll)) & 7); - int yOfs = (ScanLine + yScroll) % 8; - int cellOfs = NameTableAddrB + (yTile * NameTableWidth * 2) + (xTile * 2); - int nameTableEntry = VRAM[cellOfs] | (VRAM[cellOfs + 1] << 8); - int patternNo = nameTableEntry & 0x7FF; - bool hFlip = ((nameTableEntry >> 11) & 1) != 0; - bool vFlip = ((nameTableEntry >> 12) & 1) != 0; - bool priority = ((nameTableEntry >> 15) & 1) != 0; - int palette = (nameTableEntry >> 13) & 3; - - if (priority && PriorityBuffer[x] >= highPriority) continue; - if (!priority && PriorityBuffer[x] >= lowPriority) continue; - - if (vFlip) yOfs = 7 - yOfs; - if (hFlip) xOfs = 7 - xOfs; - - int texel = PatternBuffer[(patternNo * 64) + (yOfs * 8) + (xOfs)]; - int pixel = Palette[(palette * 16) + texel]; - if (texel != 0) - { - FrameBuffer[(ScanLine * FrameWidth) + x] = pixel; - PriorityBuffer[x] = (byte)(priority ? highPriority : lowPriority); - } else { - FrameBuffer[(ScanLine * FrameWidth) + x] = bgColor; - } - } - } - - void RenderScrollBTwoCellVScroll() - { - int bgColor = BackgroundColor; - int xScroll = CalcHScrollPlaneB(ScanLine); - int fineHScroll = xScroll & 15; - - const int lowPriority = 1; - const int highPriority = 4; - - for (int x = 0; x < FrameWidth; x++) - { - int vsramUnitOffset = ((x - fineHScroll) / 16) % 40; - int yScroll = VSRAM[(vsramUnitOffset*2)+1] & 0x3FF; - int yTile = ((ScanLine + yScroll) / 8) % NameTableHeight; - - int xTile = Math.Abs(((x + (1024 - xScroll)) / 8) % NameTableWidth); - int xOfs = Math.Abs((x + (1024 - xScroll)) & 7); - int yOfs = (ScanLine + yScroll) % 8; - int cellOfs = NameTableAddrB + (yTile * NameTableWidth * 2) + (xTile * 2); - int nameTableEntry = VRAM[cellOfs] | (VRAM[cellOfs + 1] << 8); - int patternNo = nameTableEntry & 0x7FF; - bool hFlip = ((nameTableEntry >> 11) & 1) != 0; - bool vFlip = ((nameTableEntry >> 12) & 1) != 0; - bool priority = ((nameTableEntry >> 15) & 1) != 0; - int palette = (nameTableEntry >> 13) & 3; - - if (priority && PriorityBuffer[x] >= highPriority) continue; - if (!priority && PriorityBuffer[x] >= lowPriority) continue; - - if (vFlip) yOfs = 7 - yOfs; - if (hFlip) xOfs = 7 - xOfs; - - int texel = PatternBuffer[(patternNo * 64) + (yOfs * 8) + (xOfs)]; - int pixel = Palette[(palette * 16) + texel]; - if (texel != 0) - { - FrameBuffer[(ScanLine * FrameWidth) + x] = pixel; - PriorityBuffer[x] = (byte)(priority ? highPriority : lowPriority); - } else { - FrameBuffer[(ScanLine * FrameWidth) + x] = bgColor; - } - } - } - - static readonly int[] SpriteSizeTable = { 8, 16, 24, 32 }; - Sprite sprite; - - void RenderSpritesScanline() - { - int scanLineBase = ScanLine * FrameWidth; - int processedSprites = 0; - int processedSpritesThisLine = 0; - int processedDotsThisLine = 0; - bool spriteMaskPrecursor = false; - - // This is incredibly unoptimized. TODO... - - FetchSprite(0); - while (true) - { - if (sprite.Y > ScanLine || sprite.Y+sprite.HeightPixels <= ScanLine) - goto nextSprite; - - processedSpritesThisLine++; - processedDotsThisLine += sprite.WidthPixels; - - if (sprite.X > -128) - spriteMaskPrecursor = true; - - if (sprite.X == -128 && spriteMaskPrecursor) - break; // apply sprite mask - - if (sprite.X + sprite.WidthPixels <= 0) - goto nextSprite; - - if (sprite.HeightCells == 2) - sprite.HeightCells = 2; - - int yline = ScanLine - sprite.Y; - if (sprite.VFlip) - yline = sprite.HeightPixels - 1 - yline; - int paletteBase = sprite.Palette * 16; - if (sprite.HFlip == false) - { - int pattern = sprite.PatternIndex + ((yline / 8)); - - for (int xi = 0; xi < sprite.WidthPixels; xi++) - { - if (sprite.X + xi < 0 || sprite.X + xi >= FrameWidth) - continue; - - if (sprite.Priority == false && PriorityBuffer[sprite.X + xi] >= 3) continue; - if (PriorityBuffer[sprite.X + xi] == 9) continue; - - int pixel = PatternBuffer[((pattern + ((xi / 8) * sprite.HeightCells)) * 64) + ((yline & 7) * 8) + (xi & 7)]; - if (pixel != 0) - { - FrameBuffer[scanLineBase + sprite.X + xi] = Palette[paletteBase + pixel]; - PriorityBuffer[sprite.X + xi] = 9; - } - } - } else { // HFlip - int pattern = sprite.PatternIndex + ((yline / 8)) + (sprite.HeightCells * (sprite.WidthCells - 1)); - - for (int xi = 0; xi < sprite.WidthPixels; xi++) - { - if (sprite.X + xi < 0 || sprite.X + xi >= FrameWidth) - continue; - - if (sprite.Priority == false && PriorityBuffer[sprite.X + xi] >= 3) continue; - if (PriorityBuffer[sprite.X + xi] == 9) continue; - - int pixel = PatternBuffer[((pattern + ((-xi / 8) * sprite.HeightCells)) * 64) + ((yline & 7) * 8) + (7 - (xi & 7))]; - if (pixel != 0) - { - FrameBuffer[scanLineBase + sprite.X + xi] = Palette[paletteBase + pixel]; - PriorityBuffer[sprite.X + xi] = 9; - } - } - } - - nextSprite: - if (sprite.Link == 0) - break; - if (++processedSprites >= SpriteLimit) - break; - if (processedSpritesThisLine >= SpritePerLineLimit) - break; - if (processedDotsThisLine >= DotsPerLineLimit) - break; - if (DisplayWidth == 32 && sprite.Link >= 64) - break; - FetchSprite(sprite.Link); - } - } - - void FetchSprite(int spriteNo) - { - // Note - X/Y coordinates are 10-bits (3FF) but must be masked to 9-bits (1FF) - // In interlace mode this behavior should change - - int SatBase = SpriteAttributeTableAddr + (spriteNo*8); - sprite.Y = (VRAM[SatBase + 0] | (VRAM[SatBase + 1] << 8) & 0x1FF) - 128; - sprite.X = (VRAM[SatBase + 6] | (VRAM[SatBase + 7] << 8) & 0x1FF) - 128; - sprite.WidthPixels = SpriteSizeTable[(VRAM[SatBase + 3] >> 2) & 3]; - sprite.HeightPixels = SpriteSizeTable[VRAM[SatBase + 3] & 3]; - sprite.WidthCells = ((VRAM[SatBase + 3] >> 2) & 3) + 1; - sprite.HeightCells = (VRAM[SatBase + 3] & 3) + 1; - sprite.Link = VRAM[SatBase + 2] & 0x7F; - sprite.PatternIndex = (VRAM[SatBase + 4] | (VRAM[SatBase + 5] << 8)) & 0x7FF; - sprite.HFlip = ((VRAM[SatBase + 5] >> 3) & 1) != 0; - sprite.VFlip = ((VRAM[SatBase + 5] >> 4) & 1) != 0; - sprite.Palette = (VRAM[SatBase + 5] >> 5) & 3; - sprite.Priority = ((VRAM[SatBase + 5] >> 7) & 1) != 0; - } - - struct Sprite - { - public int X, Y; - public int WidthPixels, HeightPixels; - public int WidthCells, HeightCells; - public int Link; - public int Palette; - public int PatternIndex; - public bool Priority; - public bool HFlip; - public bool VFlip; - } - - int CalcHScrollPlaneA(int line) - { - int ofs = 0; - switch (Registers[11] & 3) - { - case 0: ofs = HScrollTableAddr; break; - case 1: ofs = HScrollTableAddr + ((line & 7) * 4); break; - case 2: ofs = HScrollTableAddr + ((line & ~7) * 4); break; - case 3: ofs = HScrollTableAddr + (line * 4); break; - } - - int value = VRAM[ofs] | (VRAM[ofs + 1] << 8); - return value & 0x3FF; - } - - int CalcHScrollPlaneB(int line) - { - int ofs = 0; - switch (Registers[11] & 3) - { - case 0: ofs = HScrollTableAddr; break; - case 1: ofs = HScrollTableAddr + ((line & 7) * 4); break; - case 2: ofs = HScrollTableAddr + ((line & ~7) * 4); break; - case 3: ofs = HScrollTableAddr + (line * 4); break; - } - - int value = VRAM[ofs + 2] | (VRAM[ofs + 3] << 8); - return value & 0x3FF; - } - } + public partial class GenVDP + { + // Priority buffer contents have the following values: + // 0 = Backdrop color + // 1 = Plane B Low Priority + // 2 = Plane A Low Priority + // 4 = Plane B High Priority + // 5 = Plane A High Priority + // 9 = Sprite has been drawn + + byte[] PriorityBuffer = new byte[320]; + + static readonly byte[] PalXlatTable = { 0, 0, 36, 36, 73, 73, 109, 109, 145, 145, 182, 182, 219, 219, 255, 255 }; + + public void RenderLine() + { + if (DisplayEnabled) + { + Array.Clear(PriorityBuffer, 0, 320); + + // TODO: I would like to be able to render Scroll A before Scroll B, in order to minimize overdraw. + // But at the moment it complicates priority stuff. + + if (CellBasedVertScroll == false) + { + RenderScrollB(); + RenderScrollA(); + } + else + { + RenderScrollBTwoCellVScroll(); + RenderScrollATwoCellVScroll(); + } + + RenderSpritesScanline(); + } + else + { + // If display is disabled, fill in with background color. + for (int i = 0; i < FrameWidth; i++) + FrameBuffer[(ScanLine * FrameWidth) + i] = BackgroundColor; + } + + //if (ScanLine == 223) // shrug + // RenderPalette(); + } + + void RenderPalette() + { + for (int p = 0; p < 4; p++) + for (int i = 0; i < 16; i++) + FrameBuffer[(p * FrameWidth) + i] = Palette[(p * 16) + i]; + } + + void RenderScrollAScanline(int xScroll, int yScroll, int nameTableBase, int startPixel, int endPixel, bool window) + { + const int lowPriority = 2; + const int highPriority = 5; + int yTile = ((ScanLine + yScroll) / 8) % NameTableHeight; + int nameTableWidth = NameTableWidth; + if (window) + nameTableWidth = (DisplayWidth == 40) ? 64 : 32; + + // this is hellllla slow. but not optimizing until we implement & understand + // all scrolling modes, shadow & hilight, etc. + // in thinking about this, you could convince me to optimize the PCE background renderer now. + // Its way simple in comparison. But the PCE sprite renderer is way worse than gen. + for (int x = startPixel; x < endPixel; x++) + { + int xTile = Math.Abs(((x + (1024 - xScroll)) / 8) % nameTableWidth); + int xOfs = Math.Abs((x + (1024 - xScroll)) & 7); + int yOfs = (ScanLine + yScroll) % 8; + int cellOfs = nameTableBase + (yTile * nameTableWidth * 2) + (xTile * 2); + int nameTableEntry = VRAM[cellOfs] | (VRAM[cellOfs + 1] << 8); + int patternNo = nameTableEntry & 0x7FF; + bool hFlip = ((nameTableEntry >> 11) & 1) != 0; + bool vFlip = ((nameTableEntry >> 12) & 1) != 0; + bool priority = ((nameTableEntry >> 15) & 1) != 0; + int palette = (nameTableEntry >> 13) & 3; + + if (priority && PriorityBuffer[x] >= highPriority) continue; + if (!priority && PriorityBuffer[x] >= lowPriority) continue; + + if (vFlip) yOfs = 7 - yOfs; + if (hFlip) xOfs = 7 - xOfs; + + int texel = PatternBuffer[(patternNo * 64) + (yOfs * 8) + (xOfs)]; + if (texel == 0) continue; + int pixel = Palette[(palette * 16) + texel]; + FrameBuffer[(ScanLine * FrameWidth) + x] = pixel; + PriorityBuffer[x] = (byte)(priority ? highPriority : lowPriority); + } + } + + void RenderScrollAScanlineTwoCellVScroll(int xScroll, int nameTableBase, int startPixel, int endPixel, bool window) + { + const int lowPriority = 2; + const int highPriority = 5; + + int fineHScroll = xScroll & 15; + int nameTableWidth = NameTableWidth; + if (window) + nameTableWidth = (DisplayWidth == 40) ? 64 : 32; + + for (int x = startPixel; x < endPixel; x++) + { + int vsramUnitOffset = ((x - fineHScroll) / 16) % 40; + int yScroll = VSRAM[vsramUnitOffset * 2] & 0x3FF; + int yTile = ((ScanLine + yScroll) / 8) % NameTableHeight; + + int xTile = Math.Abs(((x + (1024 - xScroll)) / 8) % nameTableWidth); + int xOfs = Math.Abs((x + (1024 - xScroll)) & 7); + int yOfs = (ScanLine + yScroll) % 8; + int cellOfs = nameTableBase + (yTile * nameTableWidth * 2) + (xTile * 2); + int nameTableEntry = VRAM[cellOfs] | (VRAM[cellOfs + 1] << 8); + int patternNo = nameTableEntry & 0x7FF; + bool hFlip = ((nameTableEntry >> 11) & 1) != 0; + bool vFlip = ((nameTableEntry >> 12) & 1) != 0; + bool priority = ((nameTableEntry >> 15) & 1) != 0; + int palette = (nameTableEntry >> 13) & 3; + + if (priority && PriorityBuffer[x] >= highPriority) continue; + if (!priority && PriorityBuffer[x] >= lowPriority) continue; + + if (vFlip) yOfs = 7 - yOfs; + if (hFlip) xOfs = 7 - xOfs; + + int texel = PatternBuffer[(patternNo * 64) + (yOfs * 8) + (xOfs)]; + if (texel == 0) continue; + int pixel = Palette[(palette * 16) + texel]; + FrameBuffer[(ScanLine * FrameWidth) + x] = pixel; + PriorityBuffer[x] = (byte)(priority ? highPriority : lowPriority); + } + } + + void CalculateWindowScanlines(out int startScanline, out int endScanline) + { + int data = Registers[0x12]; + int windowVPosition = data & 31; + bool fromTop = (data & 0x80) == 0; + + if (windowVPosition == 0) + { + startScanline = -1; + endScanline = -1; + return; + } + + if (fromTop) + { + startScanline = 0; + endScanline = (windowVPosition * 8); + } + else + { + startScanline = windowVPosition * 8; + endScanline = FrameHeight; + } + } + + void CalculateWindowPosition(out int startPixel, out int endPixel) + { + int data = Registers[0x11]; + int windowHPosition = (data & 31) * 2; // Window H position is set in 2-cell increments + bool fromLeft = (data & 0x80) == 0; + + if (windowHPosition == 0) + { + startPixel = -1; + endPixel = -1; + return; + } + + if (fromLeft) + { + startPixel = 0; + endPixel = (windowHPosition * 8); + if (endPixel > FrameWidth) + endPixel = FrameWidth; + } + else + { + startPixel = windowHPosition * 8; + endPixel = FrameWidth; + if (startPixel > FrameWidth) + { + startPixel = -1; + endPixel = -1; + } + } + } + + void RenderScrollA() + { + // Calculate scroll offsets + + int hscroll = CalcHScrollPlaneA(ScanLine); + int vscroll = VSRAM[0] & 0x3FF; + + // Calculate window dimensions + + int startWindowScanline, endWindowScanline; + int startWindowPixel, endWindowPixel; + CalculateWindowScanlines(out startWindowScanline, out endWindowScanline); + CalculateWindowPosition(out startWindowPixel, out endWindowPixel); + + // Render scanline + + if (ScanLine >= startWindowScanline && ScanLine < endWindowScanline) // Window takes up whole scanline + { + RenderScrollAScanline(0, 0, NameTableAddrWindow, 0, FrameWidth, true); + } + else if (startWindowPixel != -1) // Window takes up partial scanline + { + if (startWindowPixel == 0) // Window grows from left side + { + RenderScrollAScanline(0, 0, NameTableAddrWindow, 0, endWindowPixel, true); + RenderScrollAScanline(hscroll, vscroll, NameTableAddrA, endWindowPixel, FrameWidth, false); + } + else // Window grows from right side + { + RenderScrollAScanline(hscroll, vscroll, NameTableAddrA, 0, startWindowPixel, false); + RenderScrollAScanline(0, 0, NameTableAddrWindow, startWindowPixel, FrameWidth, true); + } + } + else // No window this scanline + { + RenderScrollAScanline(hscroll, vscroll, NameTableAddrA, 0, FrameWidth, false); + } + } + + void RenderScrollATwoCellVScroll() + { + // Calculate scroll offsets + + int hscroll = CalcHScrollPlaneA(ScanLine); + + // Calculate window dimensions + + int startWindowScanline, endWindowScanline; + int startWindowPixel, endWindowPixel; + CalculateWindowScanlines(out startWindowScanline, out endWindowScanline); + CalculateWindowPosition(out startWindowPixel, out endWindowPixel); + + // Render scanline + + if (ScanLine >= startWindowScanline && ScanLine < endWindowScanline) // Window takes up whole scanline + { + RenderScrollAScanline(0, 0, NameTableAddrWindow, 0, FrameWidth, true); + } + else if (startWindowPixel != -1) // Window takes up partial scanline + { + if (startWindowPixel == 0) // Window grows from left side + { + RenderScrollAScanline(0, 0, NameTableAddrWindow, 0, endWindowPixel, true); + RenderScrollAScanlineTwoCellVScroll(hscroll, NameTableAddrA, endWindowPixel, FrameWidth, false); + } + else // Window grows from right side + { + RenderScrollAScanlineTwoCellVScroll(hscroll, NameTableAddrA, 0, startWindowPixel, false); + RenderScrollAScanline(0, 0, NameTableAddrWindow, startWindowPixel, FrameWidth, true); + } + } + else // No window this scanline + { + RenderScrollAScanlineTwoCellVScroll(hscroll, NameTableAddrA, 0, FrameWidth, false); + } + } + + void RenderScrollB() + { + int bgColor = BackgroundColor; + int xScroll = CalcHScrollPlaneB(ScanLine); + int yScroll = VSRAM[1] & 0x3FF; + + const int lowPriority = 1; + const int highPriority = 4; + + int yTile = ((ScanLine + yScroll) / 8) % NameTableHeight; + + // this is hellllla slow. but not optimizing until we implement & understand + // all scrolling modes, shadow & hilight, etc. + // in thinking about this, you could convince me to optimize the PCE background renderer now. + // Its way simple in comparison. But the PCE sprite renderer is way worse than gen. + for (int x = 0; x < FrameWidth; x++) + { + int xTile = Math.Abs(((x + (1024 - xScroll)) / 8) % NameTableWidth); + int xOfs = Math.Abs((x + (1024 - xScroll)) & 7); + int yOfs = (ScanLine + yScroll) % 8; + int cellOfs = NameTableAddrB + (yTile * NameTableWidth * 2) + (xTile * 2); + int nameTableEntry = VRAM[cellOfs] | (VRAM[cellOfs + 1] << 8); + int patternNo = nameTableEntry & 0x7FF; + bool hFlip = ((nameTableEntry >> 11) & 1) != 0; + bool vFlip = ((nameTableEntry >> 12) & 1) != 0; + bool priority = ((nameTableEntry >> 15) & 1) != 0; + int palette = (nameTableEntry >> 13) & 3; + + if (priority && PriorityBuffer[x] >= highPriority) continue; + if (!priority && PriorityBuffer[x] >= lowPriority) continue; + + if (vFlip) yOfs = 7 - yOfs; + if (hFlip) xOfs = 7 - xOfs; + + int texel = PatternBuffer[(patternNo * 64) + (yOfs * 8) + (xOfs)]; + int pixel = Palette[(palette * 16) + texel]; + if (texel != 0) + { + FrameBuffer[(ScanLine * FrameWidth) + x] = pixel; + PriorityBuffer[x] = (byte)(priority ? highPriority : lowPriority); + } + else + { + FrameBuffer[(ScanLine * FrameWidth) + x] = bgColor; + } + } + } + + void RenderScrollBTwoCellVScroll() + { + int bgColor = BackgroundColor; + int xScroll = CalcHScrollPlaneB(ScanLine); + int fineHScroll = xScroll & 15; + + const int lowPriority = 1; + const int highPriority = 4; + + for (int x = 0; x < FrameWidth; x++) + { + int vsramUnitOffset = ((x - fineHScroll) / 16) % 40; + int yScroll = VSRAM[(vsramUnitOffset * 2) + 1] & 0x3FF; + int yTile = ((ScanLine + yScroll) / 8) % NameTableHeight; + + int xTile = Math.Abs(((x + (1024 - xScroll)) / 8) % NameTableWidth); + int xOfs = Math.Abs((x + (1024 - xScroll)) & 7); + int yOfs = (ScanLine + yScroll) % 8; + int cellOfs = NameTableAddrB + (yTile * NameTableWidth * 2) + (xTile * 2); + int nameTableEntry = VRAM[cellOfs] | (VRAM[cellOfs + 1] << 8); + int patternNo = nameTableEntry & 0x7FF; + bool hFlip = ((nameTableEntry >> 11) & 1) != 0; + bool vFlip = ((nameTableEntry >> 12) & 1) != 0; + bool priority = ((nameTableEntry >> 15) & 1) != 0; + int palette = (nameTableEntry >> 13) & 3; + + if (priority && PriorityBuffer[x] >= highPriority) continue; + if (!priority && PriorityBuffer[x] >= lowPriority) continue; + + if (vFlip) yOfs = 7 - yOfs; + if (hFlip) xOfs = 7 - xOfs; + + int texel = PatternBuffer[(patternNo * 64) + (yOfs * 8) + (xOfs)]; + int pixel = Palette[(palette * 16) + texel]; + if (texel != 0) + { + FrameBuffer[(ScanLine * FrameWidth) + x] = pixel; + PriorityBuffer[x] = (byte)(priority ? highPriority : lowPriority); + } + else + { + FrameBuffer[(ScanLine * FrameWidth) + x] = bgColor; + } + } + } + + static readonly int[] SpriteSizeTable = { 8, 16, 24, 32 }; + Sprite sprite; + + void RenderSpritesScanline() + { + int scanLineBase = ScanLine * FrameWidth; + int processedSprites = 0; + int processedSpritesThisLine = 0; + int processedDotsThisLine = 0; + bool spriteMaskPrecursor = false; + + // This is incredibly unoptimized. TODO... + + FetchSprite(0); + while (true) + { + if (sprite.Y > ScanLine || sprite.Y + sprite.HeightPixels <= ScanLine) + goto nextSprite; + + processedSpritesThisLine++; + processedDotsThisLine += sprite.WidthPixels; + + if (sprite.X > -128) + spriteMaskPrecursor = true; + + if (sprite.X == -128 && spriteMaskPrecursor) + break; // apply sprite mask + + if (sprite.X + sprite.WidthPixels <= 0) + goto nextSprite; + + if (sprite.HeightCells == 2) + sprite.HeightCells = 2; + + int yline = ScanLine - sprite.Y; + if (sprite.VFlip) + yline = sprite.HeightPixels - 1 - yline; + int paletteBase = sprite.Palette * 16; + if (sprite.HFlip == false) + { + int pattern = sprite.PatternIndex + ((yline / 8)); + + for (int xi = 0; xi < sprite.WidthPixels; xi++) + { + if (sprite.X + xi < 0 || sprite.X + xi >= FrameWidth) + continue; + + if (sprite.Priority == false && PriorityBuffer[sprite.X + xi] >= 3) continue; + if (PriorityBuffer[sprite.X + xi] == 9) continue; + + int pixel = PatternBuffer[((pattern + ((xi / 8) * sprite.HeightCells)) * 64) + ((yline & 7) * 8) + (xi & 7)]; + if (pixel != 0) + { + FrameBuffer[scanLineBase + sprite.X + xi] = Palette[paletteBase + pixel]; + PriorityBuffer[sprite.X + xi] = 9; + } + } + } + else + { // HFlip + int pattern = sprite.PatternIndex + ((yline / 8)) + (sprite.HeightCells * (sprite.WidthCells - 1)); + + for (int xi = 0; xi < sprite.WidthPixels; xi++) + { + if (sprite.X + xi < 0 || sprite.X + xi >= FrameWidth) + continue; + + if (sprite.Priority == false && PriorityBuffer[sprite.X + xi] >= 3) continue; + if (PriorityBuffer[sprite.X + xi] == 9) continue; + + int pixel = PatternBuffer[((pattern + ((-xi / 8) * sprite.HeightCells)) * 64) + ((yline & 7) * 8) + (7 - (xi & 7))]; + if (pixel != 0) + { + FrameBuffer[scanLineBase + sprite.X + xi] = Palette[paletteBase + pixel]; + PriorityBuffer[sprite.X + xi] = 9; + } + } + } + + nextSprite: + if (sprite.Link == 0) + break; + if (++processedSprites >= SpriteLimit) + break; + if (processedSpritesThisLine >= SpritePerLineLimit) + break; + if (processedDotsThisLine >= DotsPerLineLimit) + break; + if (DisplayWidth == 32 && sprite.Link >= 64) + break; + FetchSprite(sprite.Link); + } + } + + void FetchSprite(int spriteNo) + { + // Note - X/Y coordinates are 10-bits (3FF) but must be masked to 9-bits (1FF) + // In interlace mode this behavior should change + + int SatBase = SpriteAttributeTableAddr + (spriteNo * 8); + sprite.Y = (VRAM[SatBase + 0] | (VRAM[SatBase + 1] << 8) & 0x1FF) - 128; + sprite.X = (VRAM[SatBase + 6] | (VRAM[SatBase + 7] << 8) & 0x1FF) - 128; + sprite.WidthPixels = SpriteSizeTable[(VRAM[SatBase + 3] >> 2) & 3]; + sprite.HeightPixels = SpriteSizeTable[VRAM[SatBase + 3] & 3]; + sprite.WidthCells = ((VRAM[SatBase + 3] >> 2) & 3) + 1; + sprite.HeightCells = (VRAM[SatBase + 3] & 3) + 1; + sprite.Link = VRAM[SatBase + 2] & 0x7F; + sprite.PatternIndex = (VRAM[SatBase + 4] | (VRAM[SatBase + 5] << 8)) & 0x7FF; + sprite.HFlip = ((VRAM[SatBase + 5] >> 3) & 1) != 0; + sprite.VFlip = ((VRAM[SatBase + 5] >> 4) & 1) != 0; + sprite.Palette = (VRAM[SatBase + 5] >> 5) & 3; + sprite.Priority = ((VRAM[SatBase + 5] >> 7) & 1) != 0; + } + + struct Sprite + { + public int X, Y; + public int WidthPixels, HeightPixels; + public int WidthCells, HeightCells; + public int Link; + public int Palette; + public int PatternIndex; + public bool Priority; + public bool HFlip; + public bool VFlip; + } + + int CalcHScrollPlaneA(int line) + { + int ofs = 0; + switch (Registers[11] & 3) + { + case 0: ofs = HScrollTableAddr; break; + case 1: ofs = HScrollTableAddr + ((line & 7) * 4); break; + case 2: ofs = HScrollTableAddr + ((line & ~7) * 4); break; + case 3: ofs = HScrollTableAddr + (line * 4); break; + } + + int value = VRAM[ofs] | (VRAM[ofs + 1] << 8); + return value & 0x3FF; + } + + int CalcHScrollPlaneB(int line) + { + int ofs = 0; + switch (Registers[11] & 3) + { + case 0: ofs = HScrollTableAddr; break; + case 1: ofs = HScrollTableAddr + ((line & 7) * 4); break; + case 2: ofs = HScrollTableAddr + ((line & ~7) * 4); break; + case 3: ofs = HScrollTableAddr + (line * 4); break; + } + + int value = VRAM[ofs + 2] | (VRAM[ofs + 3] << 8); + return value & 0x3FF; + } + } } \ No newline at end of file diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.cs index 0cb8bbf34f..4937837414 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/GenVDP.cs @@ -5,7 +5,7 @@ using System.Globalization; using BizHawk.Common; using BizHawk.Emulation.Common; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { public sealed partial class GenVDP : IVideoProvider { diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/Genesis.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/Genesis.cs index 86ad1d9f91..25d7092b98 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/Genesis.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/Genesis.cs @@ -13,7 +13,7 @@ using BizHawk.Emulation.Sound; using Native68000; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { public sealed partial class Genesis : IEmulator { diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/IO.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/IO.cs index f1c01f61e1..c7089b3655 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/IO.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/IO.cs @@ -1,6 +1,6 @@ using BizHawk.Common; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { partial class Genesis { diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/Input.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/Input.cs index c1163957bf..b9a92f22f9 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/Input.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/Input.cs @@ -1,6 +1,6 @@ using BizHawk.Emulation.Common; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { partial class Genesis { diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/MemoryMap.68000.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/MemoryMap.68000.cs index fb9e706eb0..26d89235ad 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/MemoryMap.68000.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/MemoryMap.68000.cs @@ -1,254 +1,254 @@ using System; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { - partial class Genesis - { - public sbyte ReadByte(int address) - { - address &= 0x00FFFFFF; + partial class Genesis + { + public sbyte ReadByte(int address) + { + address &= 0x00FFFFFF; - if (address < 0x200000) - return (sbyte) RomData[address]; + if (address < 0x200000) + return (sbyte)RomData[address]; - if (address < 0x400000) - { - if (SaveRamEnabled && address >= SaveRamStartOffset && address < SaveRamEndOffset) - { - if (SaveRamEveryOtherByte) - return (sbyte) SaveRAM[(address - SaveRamStartOffset) >> 1]; - else - return (sbyte) SaveRAM[address - SaveRamStartOffset]; - } - return (sbyte)RomData[address]; - } + if (address < 0x400000) + { + if (SaveRamEnabled && address >= SaveRamStartOffset && address < SaveRamEndOffset) + { + if (SaveRamEveryOtherByte) + return (sbyte)SaveRAM[(address - SaveRamStartOffset) >> 1]; + else + return (sbyte)SaveRAM[address - SaveRamStartOffset]; + } + return (sbyte)RomData[address]; + } - if (address >= 0xE00000) - return (sbyte) Ram[address & 0xFFFF]; + if (address >= 0xE00000) + return (sbyte)Ram[address & 0xFFFF]; - if (address == 0xA11100) // Z80 BUS status - { - //Console.WriteLine("QUERY z80 bus status. 68000 can access? " + (M68000HasZ80Bus && Z80Reset == false)); - return (sbyte) (M68000HasZ80Bus && Z80Reset == false ? 0 : 1); - } + if (address == 0xA11100) // Z80 BUS status + { + //Console.WriteLine("QUERY z80 bus status. 68000 can access? " + (M68000HasZ80Bus && Z80Reset == false)); + return (sbyte)(M68000HasZ80Bus && Z80Reset == false ? 0 : 1); + } - if (address >= 0xA10000 && address <= 0xA1001F) - return (sbyte)ReadIO(address); + if (address >= 0xA10000 && address <= 0xA1001F) + return (sbyte)ReadIO(address); - if ((address & 0xFF0000) == 0xA00000) - return (sbyte) ReadMemoryZ80((ushort) (address & 0x7FFF)); + if ((address & 0xFF0000) == 0xA00000) + return (sbyte)ReadMemoryZ80((ushort)(address & 0x7FFF)); - if (address >= 0xC00000 && address < 0xC00010) - { - //Console.WriteLine("byte-reading the VDP. someone is probably stupid."); - ushort value = VDP.ReadVdp(address & 0x0E); - if ((address & 1) == 0) // read MSB - return (sbyte) (value >> 8); - return (sbyte) value; // read LSB - } + if (address >= 0xC00000 && address < 0xC00010) + { + //Console.WriteLine("byte-reading the VDP. someone is probably stupid."); + ushort value = VDP.ReadVdp(address & 0x0E); + if ((address & 1) == 0) // read MSB + return (sbyte)(value >> 8); + return (sbyte)value; // read LSB + } - Console.WriteLine("UNHANDLED READB {0:X6}", address); - return 0x7D; - } - - public short ReadWord(int address) - { - address &= 0x00FFFFFF; + Console.WriteLine("UNHANDLED READB {0:X6}", address); + return 0x7D; + } - int maskedAddr; - if (address < 0x400000) - return (short)((RomData[address] << 8) | RomData[address + 1]); + public short ReadWord(int address) + { + address &= 0x00FFFFFF; - if (address >= 0xE00000) // Work RAM - { - maskedAddr = address & 0xFFFE; - return (short)((Ram[maskedAddr] << 8) | Ram[maskedAddr + 1]); - } + int maskedAddr; + if (address < 0x400000) + return (short)((RomData[address] << 8) | RomData[address + 1]); - if (address >= 0xC00000 && address < 0xC00010) - return (short) VDP.ReadVdp(address & 0x0E); + if (address >= 0xE00000) // Work RAM + { + maskedAddr = address & 0xFFFE; + return (short)((Ram[maskedAddr] << 8) | Ram[maskedAddr + 1]); + } - if (address >= 0xA10000 && address <= 0xA1001F) - return (sbyte)ReadIO(address); + if (address >= 0xC00000 && address < 0xC00010) + return (short)VDP.ReadVdp(address & 0x0E); - if (address == 0xA11100) // Z80 BUS status - return (short)(M68000HasZ80Bus && Z80Reset == false ? 0x0000 : 0x0100); + if (address >= 0xA10000 && address <= 0xA1001F) + return (sbyte)ReadIO(address); - Console.WriteLine("UNHANDLED READW {0:X6}", address); - return 0x7DCD; - } + if (address == 0xA11100) // Z80 BUS status + return (short)(M68000HasZ80Bus && Z80Reset == false ? 0x0000 : 0x0100); - public int ReadLong(int address) - { - address &= 0x00FFFFFF; + Console.WriteLine("UNHANDLED READW {0:X6}", address); + return 0x7DCD; + } - int maskedAddr; - if (address < 0x400000) // Cartridge ROM - return (RomData[address] << 24) | (RomData[address + 1] << 16) | (RomData[address + 2] << 8) | RomData[address + 3]; + public int ReadLong(int address) + { + address &= 0x00FFFFFF; - if (address >= 0xE00000) // Work RAM - { - maskedAddr = address & 0xFFFF; - return (Ram[maskedAddr] << 24) | (Ram[maskedAddr + 1] << 16) | (Ram[maskedAddr + 2] << 8) | Ram[maskedAddr + 3]; - } + int maskedAddr; + if (address < 0x400000) // Cartridge ROM + return (RomData[address] << 24) | (RomData[address + 1] << 16) | (RomData[address + 2] << 8) | RomData[address + 3]; - if (address >= 0xC00000) - { - //Console.WriteLine("long-read from VDP"); - short msw = ReadWord(address); - short msl = ReadWord(address + 2); - return (msw << 16) | (ushort) msl; - } + if (address >= 0xE00000) // Work RAM + { + maskedAddr = address & 0xFFFF; + return (Ram[maskedAddr] << 24) | (Ram[maskedAddr + 1] << 16) | (Ram[maskedAddr + 2] << 8) | Ram[maskedAddr + 3]; + } - // try to handle certain things separate if they need to be separate? otherwise handle as 2x readwords? - { - return ((ushort)ReadWord(address) | (ushort)(ReadWord(address + 2) << 16)); - } - //if (address == 0xA10008) return 0; // FIXME HACK for tg-sync. + if (address >= 0xC00000) + { + //Console.WriteLine("long-read from VDP"); + short msw = ReadWord(address); + short msl = ReadWord(address + 2); + return (msw << 16) | (ushort)msl; + } - //Console.WriteLine("UNHANDLED READL {0:X6}", address); - //return 0x7DCDCDCD; - } + // try to handle certain things separate if they need to be separate? otherwise handle as 2x readwords? + { + return ((ushort)ReadWord(address) | (ushort)(ReadWord(address + 2) << 16)); + } + //if (address == 0xA10008) return 0; // FIXME HACK for tg-sync. - public void WriteByte(int address, sbyte value) - { - address &= 0x00FFFFFF; + //Console.WriteLine("UNHANDLED READL {0:X6}", address); + //return 0x7DCDCDCD; + } - if (address >= 0xE00000) // Work RAM - { - //Console.WriteLine("MEM[{0:X4}] change from {1:X2} to {2:X2}", address & 0xFFFF, Ram[address & 0xFFFF], value); - Ram[address & 0xFFFF] = (byte)value; - return; - } - if ((address & 0xFF0000) == 0xA00000) - { - WriteMemoryZ80((ushort)(address & 0x7FFF), (byte)value); - return; - } - if (address >= 0xA10000 && address <= 0xA1001F) - { - WriteIO(address, value); - return; - } - if (address == 0xA11100) - { - M68000HasZ80Bus = (value & 1) != 0; - //Console.WriteLine("68000 has the z80 bus: " + M68000HasZ80Bus); - return; - } - if (address == 0xA11200) // Z80 RESET - { - Z80Reset = (value & 1) == 0; - if (Z80Reset) - SoundCPU.SoftReset(); - //Console.WriteLine("z80 reset: " + Z80Reset); - return; - } - if (address >= 0xC00000 && address < 0xC00010) - { - // when writing to VDP in byte mode, the LSB is duplicated into the MSB - VDP.WriteVdp(address & 0x1E, (ushort)((ushort)value | ((ushort)value << 8))); - return; - } - if (address >= 0xC00011 && address <= 0xC00017 && (address & 1) != 0) - { - PSG.WritePsgData((byte) value, SoundCPU.TotalExecutedCycles); - return; - } + public void WriteByte(int address, sbyte value) + { + address &= 0x00FFFFFF; - if (SaveRamEnabled && address >= SaveRamStartOffset && address < SaveRamEndOffset) - { - if (SaveRamEveryOtherByte) - SaveRAM[(address - SaveRamStartOffset) >> 1] = (byte) value; - else - SaveRAM[address - SaveRamStartOffset] = (byte) value; - - SaveRamModified = true; - return; - } + if (address >= 0xE00000) // Work RAM + { + //Console.WriteLine("MEM[{0:X4}] change from {1:X2} to {2:X2}", address & 0xFFFF, Ram[address & 0xFFFF], value); + Ram[address & 0xFFFF] = (byte)value; + return; + } + if ((address & 0xFF0000) == 0xA00000) + { + WriteMemoryZ80((ushort)(address & 0x7FFF), (byte)value); + return; + } + if (address >= 0xA10000 && address <= 0xA1001F) + { + WriteIO(address, value); + return; + } + if (address == 0xA11100) + { + M68000HasZ80Bus = (value & 1) != 0; + //Console.WriteLine("68000 has the z80 bus: " + M68000HasZ80Bus); + return; + } + if (address == 0xA11200) // Z80 RESET + { + Z80Reset = (value & 1) == 0; + if (Z80Reset) + SoundCPU.SoftReset(); + //Console.WriteLine("z80 reset: " + Z80Reset); + return; + } + if (address >= 0xC00000 && address < 0xC00010) + { + // when writing to VDP in byte mode, the LSB is duplicated into the MSB + VDP.WriteVdp(address & 0x1E, (ushort)((ushort)value | ((ushort)value << 8))); + return; + } + if (address >= 0xC00011 && address <= 0xC00017 && (address & 1) != 0) + { + PSG.WritePsgData((byte)value, SoundCPU.TotalExecutedCycles); + return; + } - if (EepromEnabled && (address == SclAddr || address == SdaInAddr)) - { - WriteByteEeprom(address, (byte) value); - return; + if (SaveRamEnabled && address >= SaveRamStartOffset && address < SaveRamEndOffset) + { + if (SaveRamEveryOtherByte) + SaveRAM[(address - SaveRamStartOffset) >> 1] = (byte)value; + else + SaveRAM[address - SaveRamStartOffset] = (byte)value; - } + SaveRamModified = true; + return; + } - Console.WriteLine("UNHANDLED WRITEB {0:X6}:{1:X2}", address, value); - } + if (EepromEnabled && (address == SclAddr || address == SdaInAddr)) + { + WriteByteEeprom(address, (byte)value); + return; - public void WriteWord(int address, short value) - { - address &= 0x00FFFFFF; + } - if (address >= 0xE00000) // Work RAM - { - //Console.WriteLine("MEM[{0:X4}] change to {1:X4}", address & 0xFFFF, value); - Ram[(address & 0xFFFF) + 0] = (byte)(value >> 8); - Ram[(address & 0xFFFF) + 1] = (byte)value; - return; - } - if (address >= 0xC00000) - { - switch (address & 0x1F) - { - case 0x00: - case 0x02: - VDP.WriteVdpData((ushort)value); - return; - case 0x04: - case 0x06: - VDP.WriteVdpControl((ushort)value); - return; - } - } - if (address == 0xA11100) // Z80 BUSREQ - { - M68000HasZ80Bus = (value & 0x100) != 0; - //Console.WriteLine("68000 has the z80 bus: " + M68000HasZ80Bus); - return; - } - if (address == 0xA11200) // Z80 RESET - { - Z80Reset = (value & 0x100) == 0; - if (Z80Reset) - SoundCPU.SoftReset(); - //Console.WriteLine("z80 reset: " + Z80Reset); - return; - } - Console.WriteLine("UNHANDLED WRITEW {0:X6}:{1:X4}", address, value); - } + Console.WriteLine("UNHANDLED WRITEB {0:X6}:{1:X2}", address, value); + } - public void WriteLong(int address, int value) - { - address &= 0x00FFFFFF; + public void WriteWord(int address, short value) + { + address &= 0x00FFFFFF; - if (address >= 0xE00000) // Work RAM - { - //Console.WriteLine("MEM[{0:X4}] change to {1:X8}", address & 0xFFFF, value); - Ram[(address & 0xFFFF) + 0] = (byte)(value >> 24); - Ram[(address & 0xFFFF) + 1] = (byte)(value >> 16); - Ram[(address & 0xFFFF) + 2] = (byte)(value >> 8); - Ram[(address & 0xFFFF) + 3] = (byte)value; - return; - } - if (address >= 0xC00000) - { - WriteWord(address, (short)(value >> 16)); - WriteWord(address+2, (short)value); - return; - } + if (address >= 0xE00000) // Work RAM + { + //Console.WriteLine("MEM[{0:X4}] change to {1:X4}", address & 0xFFFF, value); + Ram[(address & 0xFFFF) + 0] = (byte)(value >> 8); + Ram[(address & 0xFFFF) + 1] = (byte)value; + return; + } + if (address >= 0xC00000) + { + switch (address & 0x1F) + { + case 0x00: + case 0x02: + VDP.WriteVdpData((ushort)value); + return; + case 0x04: + case 0x06: + VDP.WriteVdpControl((ushort)value); + return; + } + } + if (address == 0xA11100) // Z80 BUSREQ + { + M68000HasZ80Bus = (value & 0x100) != 0; + //Console.WriteLine("68000 has the z80 bus: " + M68000HasZ80Bus); + return; + } + if (address == 0xA11200) // Z80 RESET + { + Z80Reset = (value & 0x100) == 0; + if (Z80Reset) + SoundCPU.SoftReset(); + //Console.WriteLine("z80 reset: " + Z80Reset); + return; + } + Console.WriteLine("UNHANDLED WRITEW {0:X6}:{1:X4}", address, value); + } - Console.WriteLine("UNHANDLED WRITEL {0:X6}:{1:X8}", address, value); - } + public void WriteLong(int address, int value) + { + address &= 0x00FFFFFF; - // Mushashi interop test stuff. TODO kill this when we're ready to ditch musashi. + if (address >= 0xE00000) // Work RAM + { + //Console.WriteLine("MEM[{0:X4}] change to {1:X8}", address & 0xFFFF, value); + Ram[(address & 0xFFFF) + 0] = (byte)(value >> 24); + Ram[(address & 0xFFFF) + 1] = (byte)(value >> 16); + Ram[(address & 0xFFFF) + 2] = (byte)(value >> 8); + Ram[(address & 0xFFFF) + 3] = (byte)value; + return; + } + if (address >= 0xC00000) + { + WriteWord(address, (short)(value >> 16)); + WriteWord(address + 2, (short)value); + return; + } - public uint Read8(uint a) { /*Console.WriteLine("read8 {0:X}", a);*/ return (uint)ReadByte((int)a) & 0xFF; } - public uint Read16(uint a) { /*Console.WriteLine("read16 {0:X}", a);*/ return (uint)ReadWord((int)a) & 0xFFFF; } - public uint Read32(uint a) { /*Console.WriteLine("read32 {0:X}", a);*/ return (uint)ReadLong((int)a); } - public void Write8(uint a, uint v) { /*Console.WriteLine("write8 {0:X}:{1:X2}", a, v);*/ WriteByte((int)a, (sbyte)v); } - public void Write16(uint a, uint v) { /*Console.WriteLine("write16 {0:X}:{1:X4}", a, v);*/ WriteWord((int)a, (short)v); } - public void Write32(uint a, uint v) { /*Console.WriteLine("write32 {0:X}:{1:X8}", a, v);*/ WriteLong((int)a, (int)v); } - } + Console.WriteLine("UNHANDLED WRITEL {0:X6}:{1:X8}", address, value); + } + + // Mushashi interop test stuff. TODO kill this when we're ready to ditch musashi. + + public uint Read8(uint a) { /*Console.WriteLine("read8 {0:X}", a);*/ return (uint)ReadByte((int)a) & 0xFF; } + public uint Read16(uint a) { /*Console.WriteLine("read16 {0:X}", a);*/ return (uint)ReadWord((int)a) & 0xFFFF; } + public uint Read32(uint a) { /*Console.WriteLine("read32 {0:X}", a);*/ return (uint)ReadLong((int)a); } + public void Write8(uint a, uint v) { /*Console.WriteLine("write8 {0:X}:{1:X2}", a, v);*/ WriteByte((int)a, (sbyte)v); } + public void Write16(uint a, uint v) { /*Console.WriteLine("write16 {0:X}:{1:X4}", a, v);*/ WriteWord((int)a, (short)v); } + public void Write32(uint a, uint v) { /*Console.WriteLine("write32 {0:X}:{1:X8}", a, v);*/ WriteLong((int)a, (int)v); } + } } diff --git a/BizHawk.Emulation/Consoles/Sega/Genesis/MemoryMap.Z80.cs b/BizHawk.Emulation/Consoles/Sega/Genesis/MemoryMap.Z80.cs index f1f0fbd9d4..51cacdacc8 100644 --- a/BizHawk.Emulation/Consoles/Sega/Genesis/MemoryMap.Z80.cs +++ b/BizHawk.Emulation/Consoles/Sega/Genesis/MemoryMap.Z80.cs @@ -1,84 +1,84 @@ using System; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.Genesis { - partial class Genesis - { - private int BankRegion; + partial class Genesis + { + private int BankRegion; - public byte ReadMemoryZ80(ushort address) - { - if (address < 0x4000) - { - //Console.WriteLine("read z80 memory {0:X4}: {1:X2}",address, Z80Ram[address & 0x1FFF]); - return Z80Ram[address & 0x1FFF]; - } - if (address >= 0x4000 && address < 0x6000) - { - //Console.WriteLine(" === Z80 READS FM STATUS ==="); - return YM2612.ReadStatus(SoundCPU.TotalExecutedCycles); // TODO: more than 1 read port probably? - } - if (address >= 0x8000) - { - // 68000 Bank region - return (byte) ReadByte(BankRegion | (address & 0x7FFF)); - } - if (address <= 0x6100) // read from bank address register - returns FF - return 0xFF; - Console.WriteLine("UNHANDLED Z80 READ {0:X4}",address); - return 0xCD; - } + public byte ReadMemoryZ80(ushort address) + { + if (address < 0x4000) + { + //Console.WriteLine("read z80 memory {0:X4}: {1:X2}",address, Z80Ram[address & 0x1FFF]); + return Z80Ram[address & 0x1FFF]; + } + if (address >= 0x4000 && address < 0x6000) + { + //Console.WriteLine(" === Z80 READS FM STATUS ==="); + return YM2612.ReadStatus(SoundCPU.TotalExecutedCycles); // TODO: more than 1 read port probably? + } + if (address >= 0x8000) + { + // 68000 Bank region + return (byte)ReadByte(BankRegion | (address & 0x7FFF)); + } + if (address <= 0x6100) // read from bank address register - returns FF + return 0xFF; + Console.WriteLine("UNHANDLED Z80 READ {0:X4}", address); + return 0xCD; + } - public void WriteMemoryZ80(ushort address, byte value) - { - if (address < 0x4000) - { - //Console.WriteLine("write z80 memory {0:X4}: {1:X2}",address, value); - Z80Ram[address & 0x1FFF] = value; - return; - } - if (address >= 0x4000 && address < 0x6000) - { - //Console.WriteLine(" === Z80 WRITES YM2612 {0:X4}:{1:X2} ===",address, value); - YM2612.Write(address & 3, value, SoundCPU.TotalExecutedCycles); - return; - } - if (address < 0x6100) - { - BankRegion >>= 1; - BankRegion |= (value & 1) << 23; - BankRegion &= 0x00FF8000; - //Console.WriteLine("Bank pointing at {0:X8}",BankRegion); - return; - } - if (address >= 0x7F00 && address < 0x7F20) - { - switch (address & 0x1F) - { - case 0x00: - case 0x02: - VDP.WriteVdpData((ushort) ((value<<8) | value)); - return; - - case 0x04: - case 0x06: - VDP.WriteVdpControl((ushort)((value << 8) | value)); - return; + public void WriteMemoryZ80(ushort address, byte value) + { + if (address < 0x4000) + { + //Console.WriteLine("write z80 memory {0:X4}: {1:X2}",address, value); + Z80Ram[address & 0x1FFF] = value; + return; + } + if (address >= 0x4000 && address < 0x6000) + { + //Console.WriteLine(" === Z80 WRITES YM2612 {0:X4}:{1:X2} ===",address, value); + YM2612.Write(address & 3, value, SoundCPU.TotalExecutedCycles); + return; + } + if (address < 0x6100) + { + BankRegion >>= 1; + BankRegion |= (value & 1) << 23; + BankRegion &= 0x00FF8000; + //Console.WriteLine("Bank pointing at {0:X8}",BankRegion); + return; + } + if (address >= 0x7F00 && address < 0x7F20) + { + switch (address & 0x1F) + { + case 0x00: + case 0x02: + VDP.WriteVdpData((ushort)((value << 8) | value)); + return; - case 0x11: - case 0x13: - case 0x15: - case 0x17: - PSG.WritePsgData(value, SoundCPU.TotalExecutedCycles); - return; - } - } - if (address >= 0x8000) - { - WriteByte(BankRegion | (address & 0x7FFF), (sbyte) value); - return; - } - Console.WriteLine("UNHANDLED Z80 WRITE {0:X4}:{1:X2}", address, value); - } - } + case 0x04: + case 0x06: + VDP.WriteVdpControl((ushort)((value << 8) | value)); + return; + + case 0x11: + case 0x13: + case 0x15: + case 0x17: + PSG.WritePsgData(value, SoundCPU.TotalExecutedCycles); + return; + } + } + if (address >= 0x8000) + { + WriteByte(BankRegion | (address & 0x7FFF), (sbyte)value); + return; + } + Console.WriteLine("UNHANDLED Z80 WRITE {0:X4}:{1:X2}", address, value); + } + } } diff --git a/BizHawk.Emulation/Consoles/Sega/SMS/BIOS.cs b/BizHawk.Emulation/Consoles/Sega/SMS/BIOS.cs index 483e7b8644..3acd476c84 100644 --- a/BizHawk.Emulation/Consoles/Sega/SMS/BIOS.cs +++ b/BizHawk.Emulation/Consoles/Sega/SMS/BIOS.cs @@ -1,9 +1,9 @@ -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.MasterSystem { - public static class BIOS - { - #region USA System BIOS (SMS 1) [No Cartridge Present] - public static readonly byte[] USABios = + public static class BIOS + { + #region USA System BIOS (SMS 1) [No Cartridge Present] + public static readonly byte[] USABios = { 0xf3, 0xed, 0x56, 0x31, 0xf0, 0xdf, 0x18, 0x65, 0xf5, 0xe7, 0xf1, 0xd3, 0xbe, 0xc9, 0xff, 0xff, 0xe7, 0xaf, 0x0e, 0xbe, 0xed, 0xa3, 0xf5, 0xf1, 0xed, 0x79, @@ -637,10 +637,10 @@ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; - #endregion + #endregion - #region USA System BIOS [For Use With a ROM - Displays SEGA logo, then boots ROM] - public static readonly byte[] ROMBios = + #region USA System BIOS [For Use With a ROM - Displays SEGA logo, then boots ROM] + public static readonly byte[] ROMBios = { 0xf3, 0xed, 0x56, 0x31, 0xf0, 0xdf, 0x18, 0x65, 0xf5, 0xe7, 0xf1, 0xd3, 0xbe, 0xc9, 0xff, 0xff, 0xe7, 0xaf, 0x0e, 0xbe, 0xed, 0xa3, 0xf5, 0xf1, 0xed, 0x79, @@ -1274,10 +1274,10 @@ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; - #endregion + #endregion - #region Japanese Mark III System BIOS [No Cartridge Present] - public static readonly byte[] Mk3Bios = + #region Japanese Mark III System BIOS [No Cartridge Present] + public static readonly byte[] Mk3Bios = { 0xf3, 0xed, 0x56, 0x31, 0xef, 0xdf, 0x18, 0x60, 0xe7, 0x01, 0xbe, 0x00, 0x1e, 0x02, 0xed, 0xb3, 0xed, 0xb3, 0xed, 0xb3, 0x1d, 0x20, 0xf7, 0xc9, 0xe5, 0xe1, @@ -1911,6 +1911,6 @@ 0x04, 0x10, 0x02, 0x12, 0x1a, 0x10, 0x81, 0x12, 0x05, 0x10, 0x02, 0x12, 0x02, 0x10, 0x00, 0x00 }; - #endregion - } + #endregion + } } \ No newline at end of file diff --git a/BizHawk.Emulation/Consoles/Sega/SMS/Input.cs b/BizHawk.Emulation/Consoles/Sega/SMS/Input.cs index b2c86d07b7..f1c594acb5 100644 --- a/BizHawk.Emulation/Consoles/Sega/SMS/Input.cs +++ b/BizHawk.Emulation/Consoles/Sega/SMS/Input.cs @@ -1,6 +1,6 @@ using BizHawk.Emulation.Common; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.MasterSystem { public partial class SMS { diff --git a/BizHawk.Emulation/Consoles/Sega/SMS/MemoryMap.CodeMasters.cs b/BizHawk.Emulation/Consoles/Sega/SMS/MemoryMap.CodeMasters.cs index 839f79c08f..876e63fc82 100644 --- a/BizHawk.Emulation/Consoles/Sega/SMS/MemoryMap.CodeMasters.cs +++ b/BizHawk.Emulation/Consoles/Sega/SMS/MemoryMap.CodeMasters.cs @@ -1,4 +1,4 @@ -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.MasterSystem { public partial class SMS { diff --git a/BizHawk.Emulation/Consoles/Sega/SMS/MemoryMap.Sega.cs b/BizHawk.Emulation/Consoles/Sega/SMS/MemoryMap.Sega.cs index 5250bfc53c..9bce17b787 100644 --- a/BizHawk.Emulation/Consoles/Sega/SMS/MemoryMap.Sega.cs +++ b/BizHawk.Emulation/Consoles/Sega/SMS/MemoryMap.Sega.cs @@ -1,4 +1,4 @@ -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.MasterSystem { public partial class SMS { diff --git a/BizHawk.Emulation/Consoles/Sega/SMS/SMS.cs b/BizHawk.Emulation/Consoles/Sega/SMS/SMS.cs index bdbafca63f..c09421e80f 100644 --- a/BizHawk.Emulation/Consoles/Sega/SMS/SMS.cs +++ b/BizHawk.Emulation/Consoles/Sega/SMS/SMS.cs @@ -21,7 +21,7 @@ using BizHawk.Emulation.Sound; **********************************************************/ -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.MasterSystem { public sealed partial class SMS : IEmulator { diff --git a/BizHawk.Emulation/Consoles/Sega/SMS/VDP.Mode4.cs b/BizHawk.Emulation/Consoles/Sega/SMS/VDP.Mode4.cs index 6524c8b321..5548bbfb94 100644 --- a/BizHawk.Emulation/Consoles/Sega/SMS/VDP.Mode4.cs +++ b/BizHawk.Emulation/Consoles/Sega/SMS/VDP.Mode4.cs @@ -2,348 +2,348 @@ // Contains rendering functions for TMS9918 Mode 4. -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.MasterSystem { - public partial class VDP - { - internal void RenderBackgroundCurrentLine(bool show) - { - if (DisplayOn == false) - { - for (int x = 0; x < 256; x++) - FrameBuffer[(ScanLine*256) + x] = Palette[BackdropColor]; - return; - } + public partial class VDP + { + internal void RenderBackgroundCurrentLine(bool show) + { + if (DisplayOn == false) + { + for (int x = 0; x < 256; x++) + FrameBuffer[(ScanLine * 256) + x] = Palette[BackdropColor]; + return; + } - // Clear the priority buffer for this scanline - Array.Clear(ScanlinePriorityBuffer, 0, 256); + // Clear the priority buffer for this scanline + Array.Clear(ScanlinePriorityBuffer, 0, 256); - int mapBase = NameTableBase; + int mapBase = NameTableBase; - int vertOffset = ScanLine + Registers[9]; - if (FrameHeight == 192) - { - if (vertOffset >= 224) - vertOffset -= 224; - } - else - { - if (vertOffset >= 256) - vertOffset -= 256; - } - byte horzOffset = (HorizScrollLock && ScanLine < 16) ? (byte)0 : Registers[8]; + int vertOffset = ScanLine + Registers[9]; + if (FrameHeight == 192) + { + if (vertOffset >= 224) + vertOffset -= 224; + } + else + { + if (vertOffset >= 256) + vertOffset -= 256; + } + byte horzOffset = (HorizScrollLock && ScanLine < 16) ? (byte)0 : Registers[8]; - int yTile = vertOffset / 8; + int yTile = vertOffset / 8; - for (int xTile = 0; xTile < 32; xTile++) - { - if (xTile == 24 && VerticalScrollLock) - { - vertOffset = ScanLine; - yTile = vertOffset / 8; - } + for (int xTile = 0; xTile < 32; xTile++) + { + if (xTile == 24 && VerticalScrollLock) + { + vertOffset = ScanLine; + yTile = vertOffset / 8; + } - byte PaletteBase = 0; - int tileInfo = VRAM[mapBase + ((yTile * 32) + xTile) * 2] | (VRAM[mapBase + (((yTile * 32) + xTile) * 2) + 1] << 8); - int tileNo = tileInfo & 0x01FF; - if ((tileInfo & 0x800) != 0) - PaletteBase = 16; - bool Priority = (tileInfo & 0x1000) != 0; - bool VFlip = (tileInfo & 0x400) != 0; - bool HFlip = (tileInfo & 0x200) != 0; + byte PaletteBase = 0; + int tileInfo = VRAM[mapBase + ((yTile * 32) + xTile) * 2] | (VRAM[mapBase + (((yTile * 32) + xTile) * 2) + 1] << 8); + int tileNo = tileInfo & 0x01FF; + if ((tileInfo & 0x800) != 0) + PaletteBase = 16; + bool Priority = (tileInfo & 0x1000) != 0; + bool VFlip = (tileInfo & 0x400) != 0; + bool HFlip = (tileInfo & 0x200) != 0; - int yOfs = vertOffset & 7; - if (VFlip) - yOfs = 7 - yOfs; + int yOfs = vertOffset & 7; + if (VFlip) + yOfs = 7 - yOfs; - if (HFlip == false) - { - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 0] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 1] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 2] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 3] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 4] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 5] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 6] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 7] + PaletteBase] : Palette[BackdropColor]; + if (HFlip == false) + { + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 0] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 1] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 2] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 3] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 4] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 5] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 6] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 7] + PaletteBase] : Palette[BackdropColor]; - if (Priority) - { - horzOffset -= 8; - for (int k = 0; k < 8; k++) - { - if (PatternBuffer[(tileNo * 64) + (yOfs * 8) + k] != 0) - ScanlinePriorityBuffer[horzOffset] = 1; - horzOffset++; - } - } - } - else // Flipped Horizontally - { - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 7] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 6] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 5] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 4] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 3] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 2] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 1] + PaletteBase] : Palette[BackdropColor]; - FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 0] + PaletteBase] : Palette[BackdropColor]; + if (Priority) + { + horzOffset -= 8; + for (int k = 0; k < 8; k++) + { + if (PatternBuffer[(tileNo * 64) + (yOfs * 8) + k] != 0) + ScanlinePriorityBuffer[horzOffset] = 1; + horzOffset++; + } + } + } + else // Flipped Horizontally + { + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 7] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 6] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 5] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 4] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 3] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 2] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 1] + PaletteBase] : Palette[BackdropColor]; + FrameBuffer[(ScanLine * 256) + horzOffset++] = show ? Palette[PatternBuffer[(tileNo * 64) + (yOfs * 8) + 0] + PaletteBase] : Palette[BackdropColor]; - if (Priority) - { - horzOffset -= 8; - for (int k = 7; k >= 0; k--) - { - if (PatternBuffer[(tileNo * 64) + (yOfs * 8) + k] != 0) - ScanlinePriorityBuffer[horzOffset] = 1; - horzOffset++; - } - } - } - } - } + if (Priority) + { + horzOffset -= 8; + for (int k = 7; k >= 0; k--) + { + if (PatternBuffer[(tileNo * 64) + (yOfs * 8) + k] != 0) + ScanlinePriorityBuffer[horzOffset] = 1; + horzOffset++; + } + } + } + } + } - internal void RenderSpritesCurrentLine(bool show) - { - if (DisplayOn == false) return; - int SpriteBase = SpriteAttributeTableBase; - int SpriteHeight = EnableLargeSprites ? 16 : 8; + internal void RenderSpritesCurrentLine(bool show) + { + if (DisplayOn == false) return; + int SpriteBase = SpriteAttributeTableBase; + int SpriteHeight = EnableLargeSprites ? 16 : 8; - // Clear the sprite collision buffer for this scanline - Array.Clear(SpriteCollisionBuffer, 0, 256); + // Clear the sprite collision buffer for this scanline + Array.Clear(SpriteCollisionBuffer, 0, 256); - // Loop through these sprites and render the current scanline - int SpritesDrawnThisScanline = 0; - for (int i=0; i<64; i++) - { - if (SpritesDrawnThisScanline >= 8) - { - StatusByte |= 0x40; // Set Overflow bit - if (SpriteLimit) break; - } + // Loop through these sprites and render the current scanline + int SpritesDrawnThisScanline = 0; + for (int i = 0; i < 64; i++) + { + if (SpritesDrawnThisScanline >= 8) + { + StatusByte |= 0x40; // Set Overflow bit + if (SpriteLimit) break; + } - int x = VRAM[SpriteBase + 0x80 + (i * 2)]; - if (ShiftSpritesLeft8Pixels) - x -= 8; + int x = VRAM[SpriteBase + 0x80 + (i * 2)]; + if (ShiftSpritesLeft8Pixels) + x -= 8; - int y = VRAM[SpriteBase + i] + 1; - if (y == 209 && FrameHeight == 192) break; // 208 is special terminator sprite (in 192-line mode) - if (y >= (EnableLargeSprites ? 240 : 248)) y -= 256; + int y = VRAM[SpriteBase + i] + 1; + if (y == 209 && FrameHeight == 192) break; // 208 is special terminator sprite (in 192-line mode) + if (y >= (EnableLargeSprites ? 240 : 248)) y -= 256; - if (y + SpriteHeight <= ScanLine || y > ScanLine) - continue; + if (y + SpriteHeight <= ScanLine || y > ScanLine) + continue; - int tileNo = VRAM[SpriteBase + 0x80 + (i * 2) + 1]; - if (EnableLargeSprites) - tileNo &= 0xFE; - tileNo += SpriteTileBase; + int tileNo = VRAM[SpriteBase + 0x80 + (i * 2) + 1]; + if (EnableLargeSprites) + tileNo &= 0xFE; + tileNo += SpriteTileBase; - int ys = ScanLine - y; + int ys = ScanLine - y; - for (int xs = 0; xs < 8 && x + xs < 256; xs++) - { - byte color = PatternBuffer[(tileNo * 64) + (ys * 8) + xs]; - if (color != 0 && x + xs >= 0) - { - if (SpriteCollisionBuffer[x + xs] != 0) - StatusByte |= 0x20; // Set Collision bit - else if (ScanlinePriorityBuffer[x + xs] == 0) - { - if (show) FrameBuffer[(ys + y) * 256 + x + xs] = Palette[(color + 16)]; - SpriteCollisionBuffer[x + xs] = 1; - } - } - } - SpritesDrawnThisScanline++; - } - } + for (int xs = 0; xs < 8 && x + xs < 256; xs++) + { + byte color = PatternBuffer[(tileNo * 64) + (ys * 8) + xs]; + if (color != 0 && x + xs >= 0) + { + if (SpriteCollisionBuffer[x + xs] != 0) + StatusByte |= 0x20; // Set Collision bit + else if (ScanlinePriorityBuffer[x + xs] == 0) + { + if (show) FrameBuffer[(ys + y) * 256 + x + xs] = Palette[(color + 16)]; + SpriteCollisionBuffer[x + xs] = 1; + } + } + } + SpritesDrawnThisScanline++; + } + } - internal void RenderSpritesCurrentLineDoubleSize(bool show) - { - if (DisplayOn == false) return; - int SpriteBase = SpriteAttributeTableBase; - int SpriteHeight = EnableLargeSprites ? 16 : 8; + internal void RenderSpritesCurrentLineDoubleSize(bool show) + { + if (DisplayOn == false) return; + int SpriteBase = SpriteAttributeTableBase; + int SpriteHeight = EnableLargeSprites ? 16 : 8; - // Clear the sprite collision buffer for this scanline - Array.Clear(SpriteCollisionBuffer, 0, 256); + // Clear the sprite collision buffer for this scanline + Array.Clear(SpriteCollisionBuffer, 0, 256); - // Loop through these sprites and render the current scanline - int SpritesDrawnThisScanline = 0; - for (int i = 0; i <64; i++) - { - if (SpritesDrawnThisScanline >= 8) - { - StatusByte |= 0x40; // Set Overflow bit - if (SpriteLimit) break; - } + // Loop through these sprites and render the current scanline + int SpritesDrawnThisScanline = 0; + for (int i = 0; i < 64; i++) + { + if (SpritesDrawnThisScanline >= 8) + { + StatusByte |= 0x40; // Set Overflow bit + if (SpriteLimit) break; + } - int x = VRAM[SpriteBase + 0x80 + (i * 2)]; - if (ShiftSpritesLeft8Pixels) - x -= 8; + int x = VRAM[SpriteBase + 0x80 + (i * 2)]; + if (ShiftSpritesLeft8Pixels) + x -= 8; - int y = VRAM[SpriteBase + i] + 1; - if (y == 209 && FrameHeight == 192) break; // terminator sprite - if (y >= (EnableLargeSprites ? 240 : 248)) y -= 256; + int y = VRAM[SpriteBase + i] + 1; + if (y == 209 && FrameHeight == 192) break; // terminator sprite + if (y >= (EnableLargeSprites ? 240 : 248)) y -= 256; - if (y + (SpriteHeight*2) <= ScanLine || y > ScanLine) - continue; + if (y + (SpriteHeight * 2) <= ScanLine || y > ScanLine) + continue; - int tileNo = VRAM[SpriteBase + 0x80 + (i * 2) + 1]; - if (EnableLargeSprites) - tileNo &= 0xFE; - tileNo += SpriteTileBase; + int tileNo = VRAM[SpriteBase + 0x80 + (i * 2) + 1]; + if (EnableLargeSprites) + tileNo &= 0xFE; + tileNo += SpriteTileBase; - int ys = ScanLine - y; + int ys = ScanLine - y; - for (int xs = 0; xs < 16 && x + xs < 256; xs++) - { - byte color = PatternBuffer[(tileNo * 64) + ((ys/2) * 8) + (xs/2)]; - if (color != 0 && x + xs >= 0 && ScanlinePriorityBuffer[x + xs] == 0) - { - if (SpriteCollisionBuffer[x + xs] != 0) - StatusByte |= 0x20; // Set Collision bit - else - { - if (show) FrameBuffer[(ys + y) * 256 + x + xs] = Palette[(color + 16)]; - SpriteCollisionBuffer[x + xs] = 1; - } - } - } - SpritesDrawnThisScanline++; - } - } + for (int xs = 0; xs < 16 && x + xs < 256; xs++) + { + byte color = PatternBuffer[(tileNo * 64) + ((ys / 2) * 8) + (xs / 2)]; + if (color != 0 && x + xs >= 0 && ScanlinePriorityBuffer[x + xs] == 0) + { + if (SpriteCollisionBuffer[x + xs] != 0) + StatusByte |= 0x20; // Set Collision bit + else + { + if (show) FrameBuffer[(ys + y) * 256 + x + xs] = Palette[(color + 16)]; + SpriteCollisionBuffer[x + xs] = 1; + } + } + } + SpritesDrawnThisScanline++; + } + } - internal void ProcessSpriteCollisionForFrameskip() - { - if (DisplayOn == false) return; - int SpriteBase = SpriteAttributeTableBase; - int SpriteHeight = EnableLargeSprites ? 16 : 8; + internal void ProcessSpriteCollisionForFrameskip() + { + if (DisplayOn == false) return; + int SpriteBase = SpriteAttributeTableBase; + int SpriteHeight = EnableLargeSprites ? 16 : 8; - // Clear the sprite collision buffer for this scanline - Array.Clear(SpriteCollisionBuffer, 0, 256); + // Clear the sprite collision buffer for this scanline + Array.Clear(SpriteCollisionBuffer, 0, 256); - // 208 is a special terminator sprite (in 192-line mode). Lets find it... - int TerminalSprite = 64; - if (FrameHeight == 192) - for (int i = 0; i < 64; i++) - { - if (VRAM[SpriteBase + i] == 208) - { - TerminalSprite = i; - break; - } - } + // 208 is a special terminator sprite (in 192-line mode). Lets find it... + int TerminalSprite = 64; + if (FrameHeight == 192) + for (int i = 0; i < 64; i++) + { + if (VRAM[SpriteBase + i] == 208) + { + TerminalSprite = i; + break; + } + } - // Loop through these sprites and render the current scanline - int SpritesDrawnThisScanline = 0; - for (int i = TerminalSprite - 1; i >= 0; i--) - { - if (SpritesDrawnThisScanline >= 8) - StatusByte |= 0x40; // Set Overflow bit + // Loop through these sprites and render the current scanline + int SpritesDrawnThisScanline = 0; + for (int i = TerminalSprite - 1; i >= 0; i--) + { + if (SpritesDrawnThisScanline >= 8) + StatusByte |= 0x40; // Set Overflow bit - int x = VRAM[SpriteBase + 0x80 + (i * 2)]; - if (ShiftSpritesLeft8Pixels) - x -= 8; + int x = VRAM[SpriteBase + 0x80 + (i * 2)]; + if (ShiftSpritesLeft8Pixels) + x -= 8; - int y = VRAM[SpriteBase + i] + 1; - if (y >= (EnableLargeSprites ? 240 : 248)) y -= 256; + int y = VRAM[SpriteBase + i] + 1; + if (y >= (EnableLargeSprites ? 240 : 248)) y -= 256; - if (y + SpriteHeight <= ScanLine || y > ScanLine) - continue; + if (y + SpriteHeight <= ScanLine || y > ScanLine) + continue; - int tileNo = VRAM[SpriteBase + 0x80 + (i * 2) + 1]; - if (EnableLargeSprites) - tileNo &= 0xFE; - tileNo += SpriteTileBase; + int tileNo = VRAM[SpriteBase + 0x80 + (i * 2) + 1]; + if (EnableLargeSprites) + tileNo &= 0xFE; + tileNo += SpriteTileBase; - int ys = ScanLine - y; + int ys = ScanLine - y; - for (int xs = 0; xs < 8 && x + xs < 256; xs++) - { - byte color = PatternBuffer[(tileNo * 64) + (ys * 8) + xs]; - if (color != 0 && x + xs >= 0) - { - if (SpriteCollisionBuffer[x + xs] != 0) - StatusByte |= 0x20; // Set Collision bit - SpriteCollisionBuffer[x + xs] = 1; - } - } - SpritesDrawnThisScanline++; - } - } + for (int xs = 0; xs < 8 && x + xs < 256; xs++) + { + byte color = PatternBuffer[(tileNo * 64) + (ys * 8) + xs]; + if (color != 0 && x + xs >= 0) + { + if (SpriteCollisionBuffer[x + xs] != 0) + StatusByte |= 0x20; // Set Collision bit + SpriteCollisionBuffer[x + xs] = 1; + } + } + SpritesDrawnThisScanline++; + } + } - // Performs render buffer blanking. This includes the left-column blanking as well as Game Gear blanking if requested. - // Should be called at the end of the frame. - internal void RenderBlankingRegions() - { - int blankingColor = Palette[BackdropColor]; + // Performs render buffer blanking. This includes the left-column blanking as well as Game Gear blanking if requested. + // Should be called at the end of the frame. + internal void RenderBlankingRegions() + { + int blankingColor = Palette[BackdropColor]; - if (LeftBlanking) - { - for (int y = 0; y < FrameHeight; y++) - { - for (int x = 0; x < 8; x++) - FrameBuffer[(y * 256) + x] = blankingColor; - } - } + if (LeftBlanking) + { + for (int y = 0; y < FrameHeight; y++) + { + for (int x = 0; x < 8; x++) + FrameBuffer[(y * 256) + x] = blankingColor; + } + } - if (mode == VdpMode.GameGear) - { - if (Sms.CoreComm.GG_ShowClippedRegions == false) - { - int yStart = (FrameHeight - 144)/2; - for (int y = 0; y < 144; y++) - for (int x = 0; x < 160; x++) - GameGearFrameBuffer[(y * 160) + x] = FrameBuffer[((y + yStart) * 256) + x + 48]; - } + if (mode == VdpMode.GameGear) + { + if (Sms.CoreComm.GG_ShowClippedRegions == false) + { + int yStart = (FrameHeight - 144) / 2; + for (int y = 0; y < 144; y++) + for (int x = 0; x < 160; x++) + GameGearFrameBuffer[(y * 160) + x] = FrameBuffer[((y + yStart) * 256) + x + 48]; + } - if (Sms.CoreComm.GG_HighlightActiveDisplayRegion && Sms.CoreComm.GG_ShowClippedRegions) - { - // Top 24 scanlines - for (int y = 0; y < 24; y++) - { - for (int x = 0; x < 256; x++) - { - int frameOffset = (y * 256) + x; - int p = (FrameBuffer[frameOffset] >> 1) & 0x7F7F7F7F; - FrameBuffer[frameOffset] = (int)((uint)p | 0x80000000); - } - } + if (Sms.CoreComm.GG_HighlightActiveDisplayRegion && Sms.CoreComm.GG_ShowClippedRegions) + { + // Top 24 scanlines + for (int y = 0; y < 24; y++) + { + for (int x = 0; x < 256; x++) + { + int frameOffset = (y * 256) + x; + int p = (FrameBuffer[frameOffset] >> 1) & 0x7F7F7F7F; + FrameBuffer[frameOffset] = (int)((uint)p | 0x80000000); + } + } - // Bottom 24 scanlines - for (int y = 168; y < 192; y++) - { - for (int x = 0; x < 256; x++) - { - int frameOffset = (y * 256) + x; - int p = (FrameBuffer[frameOffset] >> 1) & 0x7F7F7F7F; - FrameBuffer[frameOffset] = (int)((uint)p | 0x80000000); - } - } + // Bottom 24 scanlines + for (int y = 168; y < 192; y++) + { + for (int x = 0; x < 256; x++) + { + int frameOffset = (y * 256) + x; + int p = (FrameBuffer[frameOffset] >> 1) & 0x7F7F7F7F; + FrameBuffer[frameOffset] = (int)((uint)p | 0x80000000); + } + } - // Left 48 pixels - for (int y = 24; y < 168; y++) - { - for (int x = 0; x < 48; x++) - { - int frameOffset = (y * 256) + x; - int p = (FrameBuffer[frameOffset] >> 1) & 0x7F7F7F7F; - FrameBuffer[frameOffset] = (int)((uint)p | 0x80000000); - } - } + // Left 48 pixels + for (int y = 24; y < 168; y++) + { + for (int x = 0; x < 48; x++) + { + int frameOffset = (y * 256) + x; + int p = (FrameBuffer[frameOffset] >> 1) & 0x7F7F7F7F; + FrameBuffer[frameOffset] = (int)((uint)p | 0x80000000); + } + } - // Right 48 pixels - for (int y = 24; y < 168; y++) - { - for (int x = 208; x < 256; x++) - { - int frameOffset = (y * 256) + x; - int p = (FrameBuffer[frameOffset] >> 1) & 0x7F7F7F7F; - FrameBuffer[frameOffset] = (int)((uint)p | 0x80000000); - } - } - } - } - } - } + // Right 48 pixels + for (int y = 24; y < 168; y++) + { + for (int x = 208; x < 256; x++) + { + int frameOffset = (y * 256) + x; + int p = (FrameBuffer[frameOffset] >> 1) & 0x7F7F7F7F; + FrameBuffer[frameOffset] = (int)((uint)p | 0x80000000); + } + } + } + } + } + } } diff --git a/BizHawk.Emulation/Consoles/Sega/SMS/VDP.ModeTMS.cs b/BizHawk.Emulation/Consoles/Sega/SMS/VDP.ModeTMS.cs index abcc7a5475..d909e87809 100644 --- a/BizHawk.Emulation/Consoles/Sega/SMS/VDP.ModeTMS.cs +++ b/BizHawk.Emulation/Consoles/Sega/SMS/VDP.ModeTMS.cs @@ -2,12 +2,12 @@ using System; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.MasterSystem { - public partial class VDP - { - int[] PaletteTMS9918 = new int[] - { + public partial class VDP + { + int[] PaletteTMS9918 = new int[] + { unchecked((int)0xFF000000), unchecked((int)0xFF000000), unchecked((int)0xFF47B73B), @@ -26,138 +26,138 @@ namespace BizHawk.Emulation.Consoles.Sega unchecked((int)0xFFFFFFFF) }; - void RenderBackgroundM0(bool show) - { - if (DisplayOn == false) - { - Array.Clear(FrameBuffer, ScanLine * 256, 256); - return; - } + void RenderBackgroundM0(bool show) + { + if (DisplayOn == false) + { + Array.Clear(FrameBuffer, ScanLine * 256, 256); + return; + } - int yc = ScanLine/8; - int yofs = ScanLine%8; - int FrameBufferOffset = ScanLine*256; - int PatternNameOffset = TmsPatternNameTableBase + (yc*32); - int ScreenBGColor = PaletteTMS9918[Registers[7] & 0x0F]; + int yc = ScanLine / 8; + int yofs = ScanLine % 8; + int FrameBufferOffset = ScanLine * 256; + int PatternNameOffset = TmsPatternNameTableBase + (yc * 32); + int ScreenBGColor = PaletteTMS9918[Registers[7] & 0x0F]; - for (int xc=0; xc<32; xc++) - { - int pn = VRAM[PatternNameOffset++]; - int pv = VRAM[PatternGeneratorBase + (pn*8) + yofs]; - int colorEntry = VRAM[ColorTableBase + (pn/8)]; - int fgIndex = (colorEntry >> 4) & 0x0F; - int bgIndex = colorEntry & 0x0F; - int fgColor = fgIndex == 0 ? ScreenBGColor : PaletteTMS9918[fgIndex]; - int bgColor = bgIndex == 0 ? ScreenBGColor : PaletteTMS9918[bgIndex]; + for (int xc = 0; xc < 32; xc++) + { + int pn = VRAM[PatternNameOffset++]; + int pv = VRAM[PatternGeneratorBase + (pn * 8) + yofs]; + int colorEntry = VRAM[ColorTableBase + (pn / 8)]; + int fgIndex = (colorEntry >> 4) & 0x0F; + int bgIndex = colorEntry & 0x0F; + int fgColor = fgIndex == 0 ? ScreenBGColor : PaletteTMS9918[fgIndex]; + int bgColor = bgIndex == 0 ? ScreenBGColor : PaletteTMS9918[bgIndex]; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x80) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x40) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x20) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x10) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x08) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x04) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x02) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x01) > 0) ? fgColor : bgColor) : 0; - } - } + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x80) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x40) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x20) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x10) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x08) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x04) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x02) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x01) > 0) ? fgColor : bgColor) : 0; + } + } - void RenderBackgroundM2(bool show) - { - if (DisplayOn == false) - { - Array.Clear(FrameBuffer, ScanLine * 256, 256); - return; - } + void RenderBackgroundM2(bool show) + { + if (DisplayOn == false) + { + Array.Clear(FrameBuffer, ScanLine * 256, 256); + return; + } - int yrow = ScanLine/8; - int yofs = ScanLine%8; - int FrameBufferOffset = ScanLine*256; - int PatternNameOffset = TmsPatternNameTableBase + (yrow*32); - int PatternGeneratorOffset = (((Registers[4] & 4) << 11) & 0x2000);// +((yrow / 8) * 0x100); - int ColorOffset = (ColorTableBase & 0x2000);// +((yrow / 8) * 0x100); - int ScreenBGColor = PaletteTMS9918[Registers[7] & 0x0F]; + int yrow = ScanLine / 8; + int yofs = ScanLine % 8; + int FrameBufferOffset = ScanLine * 256; + int PatternNameOffset = TmsPatternNameTableBase + (yrow * 32); + int PatternGeneratorOffset = (((Registers[4] & 4) << 11) & 0x2000);// +((yrow / 8) * 0x100); + int ColorOffset = (ColorTableBase & 0x2000);// +((yrow / 8) * 0x100); + int ScreenBGColor = PaletteTMS9918[Registers[7] & 0x0F]; - for (int xc=0; xc<32; xc++) - { - int pn = VRAM[PatternNameOffset++] + ((yrow/8)*0x100); - int pv = VRAM[PatternGeneratorOffset + (pn * 8) + yofs]; - int colorEntry = VRAM[ColorOffset + (pn * 8) + yofs]; - int fgIndex = (colorEntry >> 4) & 0x0F; - int bgIndex = colorEntry & 0x0F; - int fgColor = fgIndex == 0 ? ScreenBGColor : PaletteTMS9918[fgIndex]; - int bgColor = bgIndex == 0 ? ScreenBGColor : PaletteTMS9918[bgIndex]; + for (int xc = 0; xc < 32; xc++) + { + int pn = VRAM[PatternNameOffset++] + ((yrow / 8) * 0x100); + int pv = VRAM[PatternGeneratorOffset + (pn * 8) + yofs]; + int colorEntry = VRAM[ColorOffset + (pn * 8) + yofs]; + int fgIndex = (colorEntry >> 4) & 0x0F; + int bgIndex = colorEntry & 0x0F; + int fgColor = fgIndex == 0 ? ScreenBGColor : PaletteTMS9918[fgIndex]; + int bgColor = bgIndex == 0 ? ScreenBGColor : PaletteTMS9918[bgIndex]; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x80) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x40) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x20) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x10) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x08) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x04) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x02) > 0) ? fgColor : bgColor) : 0; - FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x01) > 0) ? fgColor : bgColor) : 0; - } - } + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x80) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x40) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x20) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x10) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x08) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x04) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x02) > 0) ? fgColor : bgColor) : 0; + FrameBuffer[FrameBufferOffset++] = show ? (((pv & 0x01) > 0) ? fgColor : bgColor) : 0; + } + } - void RenderTmsSprites(bool show) - { - if (DisplayOn == false) return; + void RenderTmsSprites(bool show) + { + if (DisplayOn == false) return; - Array.Clear(ScanlinePriorityBuffer, 0, 256); - Array.Clear(SpriteCollisionBuffer, 0, 256); + Array.Clear(ScanlinePriorityBuffer, 0, 256); + Array.Clear(SpriteCollisionBuffer, 0, 256); - bool Double = EnableDoubledSprites; - bool LargeSprites = EnableLargeSprites; + bool Double = EnableDoubledSprites; + bool LargeSprites = EnableLargeSprites; - int SpriteSize = 8; - if (LargeSprites) SpriteSize *= 2; - if (Double) SpriteSize *= 2; - int OneCellSize = Double ? 16 : 8; + int SpriteSize = 8; + if (LargeSprites) SpriteSize *= 2; + if (Double) SpriteSize *= 2; + int OneCellSize = Double ? 16 : 8; - int NumSpritesOnScanline = 0; - for (int i=0; i<32; i++) - { - int SpriteBase = TmsSpriteAttributeBase + (i*4); - int y = VRAM[SpriteBase++]; - int x = VRAM[SpriteBase++]; - int Pattern = VRAM[SpriteBase++]; - int Color = VRAM[SpriteBase]; + int NumSpritesOnScanline = 0; + for (int i = 0; i < 32; i++) + { + int SpriteBase = TmsSpriteAttributeBase + (i * 4); + int y = VRAM[SpriteBase++]; + int x = VRAM[SpriteBase++]; + int Pattern = VRAM[SpriteBase++]; + int Color = VRAM[SpriteBase]; - if (y == 208) break; // terminator sprite - if (y > 224) y -= 256; // sprite Y wrap - y++; // inexplicably, sprites start on Y+1 - if (y > ScanLine || y + SpriteSize <= ScanLine) continue; // sprite is not on this scanline - if ((Color & 0x80) > 0) x -= 32; // Early Clock adjustment + if (y == 208) break; // terminator sprite + if (y > 224) y -= 256; // sprite Y wrap + y++; // inexplicably, sprites start on Y+1 + if (y > ScanLine || y + SpriteSize <= ScanLine) continue; // sprite is not on this scanline + if ((Color & 0x80) > 0) x -= 32; // Early Clock adjustment - if (++NumSpritesOnScanline == 5) - { - StatusByte |= (byte) i; // set 5th sprite index - StatusByte |= 0x40; // set overflow bit - break; - } + if (++NumSpritesOnScanline == 5) + { + StatusByte |= (byte)i; // set 5th sprite index + StatusByte |= 0x40; // set overflow bit + break; + } - if (LargeSprites) Pattern &= 0xFC; // 16x16 sprites forced to 4-byte alignment - int SpriteLine = ScanLine - y; - if (Double) SpriteLine /= 2; + if (LargeSprites) Pattern &= 0xFC; // 16x16 sprites forced to 4-byte alignment + int SpriteLine = ScanLine - y; + if (Double) SpriteLine /= 2; - byte pv = VRAM[SpritePatternGeneratorBase + (Pattern*8) + SpriteLine]; + byte pv = VRAM[SpritePatternGeneratorBase + (Pattern * 8) + SpriteLine]; - for (int xp = 0; xp < SpriteSize && x + xp < 256; xp++) - { - if (x+xp < 0) continue; - if (LargeSprites && xp == OneCellSize) - pv = VRAM[SpritePatternGeneratorBase + (Pattern * 8) + SpriteLine + 16]; + for (int xp = 0; xp < SpriteSize && x + xp < 256; xp++) + { + if (x + xp < 0) continue; + if (LargeSprites && xp == OneCellSize) + pv = VRAM[SpritePatternGeneratorBase + (Pattern * 8) + SpriteLine + 16]; - if ((pv & (1 << (7 - (xp & 7)))) > 0) - { - // todo sprite collision - if (Color != 0 && ScanlinePriorityBuffer[x+xp] == 0) - { - ScanlinePriorityBuffer[x + xp] = 1; - if (show) FrameBuffer[(ScanLine*256) + x + xp] = PaletteTMS9918[Color & 0x0F]; - } - } - } - } - } - } + if ((pv & (1 << (7 - (xp & 7)))) > 0) + { + // todo sprite collision + if (Color != 0 && ScanlinePriorityBuffer[x + xp] == 0) + { + ScanlinePriorityBuffer[x + xp] = 1; + if (show) FrameBuffer[(ScanLine * 256) + x + xp] = PaletteTMS9918[Color & 0x0F]; + } + } + } + } + } + } } diff --git a/BizHawk.Emulation/Consoles/Sega/SMS/VDP.Tables.cs b/BizHawk.Emulation/Consoles/Sega/SMS/VDP.Tables.cs index 1a4c7f298b..dcd382b20a 100644 --- a/BizHawk.Emulation/Consoles/Sega/SMS/VDP.Tables.cs +++ b/BizHawk.Emulation/Consoles/Sega/SMS/VDP.Tables.cs @@ -1,4 +1,4 @@ -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.MasterSystem { public partial class VDP { diff --git a/BizHawk.Emulation/Consoles/Sega/SMS/VDP.cs b/BizHawk.Emulation/Consoles/Sega/SMS/VDP.cs index d164cd7beb..d1ad4d26e9 100644 --- a/BizHawk.Emulation/Consoles/Sega/SMS/VDP.cs +++ b/BizHawk.Emulation/Consoles/Sega/SMS/VDP.cs @@ -7,7 +7,7 @@ using BizHawk.Emulation.Common; using BizHawk.Emulation.CPUs.Z80; -namespace BizHawk.Emulation.Consoles.Sega +namespace BizHawk.Emulation.Cores.Sega.MasterSystem { public enum VdpMode { SMS, GameGear } diff --git a/BizHawk.Emulation/Consoles/Sega/Saturn/FilePiping.cs b/BizHawk.Emulation/Consoles/Sega/Saturn/FilePiping.cs index 1590741a06..e70af62716 100644 --- a/BizHawk.Emulation/Consoles/Sega/Saturn/FilePiping.cs +++ b/BizHawk.Emulation/Consoles/Sega/Saturn/FilePiping.cs @@ -6,7 +6,7 @@ using System.IO; using System.IO.Pipes; using System.Threading; -namespace BizHawk.Emulation.Consoles.Sega.Saturn +namespace BizHawk.Emulation.Cores.Sega.Saturn { /// /// helpers for moving files across named pipes diff --git a/BizHawk.Emulation/Consoles/Sega/Saturn/LibYabause.cs b/BizHawk.Emulation/Consoles/Sega/Saturn/LibYabause.cs index 53efd796b5..88b8691a5c 100644 --- a/BizHawk.Emulation/Consoles/Sega/Saturn/LibYabause.cs +++ b/BizHawk.Emulation/Consoles/Sega/Saturn/LibYabause.cs @@ -4,7 +4,7 @@ using System.Linq; using System.Text; using System.Runtime.InteropServices; -namespace BizHawk.Emulation.Consoles.Sega.Saturn +namespace BizHawk.Emulation.Cores.Sega.Saturn { public static class LibYabause { diff --git a/BizHawk.Emulation/Consoles/Sega/Saturn/Yabause.cs b/BizHawk.Emulation/Consoles/Sega/Saturn/Yabause.cs index 099ea01b0a..3e705d5657 100644 --- a/BizHawk.Emulation/Consoles/Sega/Saturn/Yabause.cs +++ b/BizHawk.Emulation/Consoles/Sega/Saturn/Yabause.cs @@ -9,7 +9,7 @@ using BizHawk.Common; using BizHawk.Emulation.Common; using BizHawk.Emulation.DiscSystem; -namespace BizHawk.Emulation.Consoles.Sega.Saturn +namespace BizHawk.Emulation.Cores.Sega.Saturn { public class Yabause : IEmulator, IVideoProvider, ISyncSoundProvider { diff --git a/BizHawk.Emulation/Consoles/Sony/PSP/PPSSPPDll.cs b/BizHawk.Emulation/Consoles/Sony/PSP/PPSSPPDll.cs index 9a7778079c..b4fc83ec7c 100644 --- a/BizHawk.Emulation/Consoles/Sony/PSP/PPSSPPDll.cs +++ b/BizHawk.Emulation/Consoles/Sony/PSP/PPSSPPDll.cs @@ -4,7 +4,7 @@ using System.Linq; using System.Text; using System.Runtime.InteropServices; -namespace BizHawk.Emulation.Consoles.Sony.PSP +namespace BizHawk.Emulation.Cores.Sony.PSP { public static class PPSSPPDll { diff --git a/BizHawk.Emulation/Consoles/Sony/PSP/PSP.cs b/BizHawk.Emulation/Consoles/Sony/PSP/PSP.cs index 3ee6ae573b..d089259955 100644 --- a/BizHawk.Emulation/Consoles/Sony/PSP/PSP.cs +++ b/BizHawk.Emulation/Consoles/Sony/PSP/PSP.cs @@ -6,7 +6,7 @@ using System.Runtime.InteropServices; using BizHawk.Emulation.Common; -namespace BizHawk.Emulation.Consoles.Sony.PSP +namespace BizHawk.Emulation.Cores.Sony.PSP { public class PSP : IEmulator, IVideoProvider, ISyncSoundProvider {