Merge pull request 'dev_basemynes' (#2) from alienjack/AxibugEmuOnline:dev_basemynes into dev_basemynes

Reviewed-on: #2
This commit is contained in:
sin365 2024-07-03 18:24:03 +08:00
commit 37b297dff6
213 changed files with 29823 additions and 29591 deletions

View File

@ -2,8 +2,6 @@ using System.IO;
namespace MyNes.Core namespace MyNes.Core
{ {
internal abstract class Bandai : Board internal abstract class Bandai : Board
{ {
private bool irq_enable; private bool irq_enable;

View File

@ -1,7 +1,5 @@
namespace MyNes.Core namespace MyNes.Core
{ {
internal struct BankInfo internal struct BankInfo
{ {
public bool IsRAM; public bool IsRAM;

View File

@ -1,6 +1,5 @@
namespace MyNes.Core namespace MyNes.Core
{ {
internal class BlankShortuctsHandler : IShortcutsHandler internal class BlankShortuctsHandler : IShortcutsHandler
{ {
public void Update() public void Update()

View File

@ -333,7 +333,15 @@ namespace ComponentAce.Compression.Libs.zlib
internal static bool smaller(short[] tree, int n, int m, byte[] depth) internal static bool smaller(short[] tree, int n, int m, byte[] depth)
{ {
return tree[n * 2] < tree[m * 2] || (tree[n * 2] == tree[m * 2] && depth[n] <= depth[m]); if (tree[n * 2] >= tree[m * 2])
{
if (tree[n * 2] == tree[m * 2])
{
return depth[n] <= depth[m];
}
return false;
}
return true;
} }
internal void scan_tree(short[] tree, int max_code) internal void scan_tree(short[] tree, int max_code)
@ -738,9 +746,17 @@ namespace ComponentAce.Compression.Libs.zlib
flush_block_only(flush == 4); flush_block_only(flush == 4);
if (strm.avail_out == 0) if (strm.avail_out == 0)
{ {
return (flush == 4) ? 2 : 0; if (flush != 4)
{
return 0;
} }
return (flush != 4) ? 1 : 3; return 2;
}
if (flush != 4)
{
return 1;
}
return 3;
} }
internal void _tr_stored_block(int buf, int stored_len, bool eof) internal void _tr_stored_block(int buf, int stored_len, bool eof)
@ -928,7 +944,11 @@ namespace ComponentAce.Compression.Libs.zlib
} }
return 0; return 0;
} }
return (flush != 4) ? 1 : 3; if (flush != 4)
{
return 1;
}
return 3;
} }
internal int deflate_slow(int flush) internal int deflate_slow(int flush)
@ -1032,7 +1052,11 @@ namespace ComponentAce.Compression.Libs.zlib
} }
return 0; return 0;
} }
return (flush != 4) ? 1 : 3; if (flush != 4)
{
return 1;
}
return 3;
} }
internal int longest_match(int cur_match) internal int longest_match(int cur_match)
@ -1167,7 +1191,11 @@ namespace ComponentAce.Compression.Libs.zlib
head = null; head = null;
prev = null; prev = null;
window = null; window = null;
return (status == 113) ? (-3) : 0; if (status != 113)
{
return 0;
}
return -3;
} }
internal int deflateParams(ZStream strm, int _level, int _strategy) internal int deflateParams(ZStream strm, int _level, int _strategy)
@ -1181,7 +1209,7 @@ namespace ComponentAce.Compression.Libs.zlib
{ {
return -2; return -2;
} }
if (config_table[level].func != config_table[_level].func && strm.total_in != 0) if (config_table[level].func != config_table[_level].func && strm.total_in != 0L)
{ {
result = strm.deflate(1); result = strm.deflate(1);
} }
@ -1309,16 +1337,16 @@ namespace ComponentAce.Compression.Libs.zlib
{ {
status = 666; status = 666;
} }
if (num4 == 0 || num4 == 2) switch (num4)
{ {
case 0:
case 2:
if (strm.avail_out == 0) if (strm.avail_out == 0)
{ {
last_flush = -1; last_flush = -1;
} }
return 0; return 0;
} case 1:
if (num4 == 1)
{
if (flush == 1) if (flush == 1)
{ {
_tr_align(); _tr_align();
@ -1340,6 +1368,7 @@ namespace ComponentAce.Compression.Libs.zlib
last_flush = -1; last_flush = -1;
return 0; return 0;
} }
break;
} }
} }
if (flush != 4) if (flush != 4)
@ -1354,7 +1383,11 @@ namespace ComponentAce.Compression.Libs.zlib
putShortMSB((int)(strm.adler & 0xFFFF)); putShortMSB((int)(strm.adler & 0xFFFF));
strm.flush_pending(); strm.flush_pending();
noheader = -1; noheader = -1;
return (pending == 0) ? 1 : 0; if (pending == 0)
{
return 1;
}
return 0;
} }
static Deflate() static Deflate()

View File

@ -420,9 +420,8 @@ namespace ComponentAce.Compression.Libs.zlib
write = num4; write = num4;
return inflate_flush(z, r); return inflate_flush(z, r);
} }
if (tb[0] == -1) _ = tb[0];
{ _ = -1;
}
num6 = hufts[(tb[0] + (num3 & inflate_mask[num6])) * 3 + 1]; num6 = hufts[(tb[0] + (num3 & inflate_mask[num6])) * 3 + 1];
int num7 = hufts[(tb[0] + (num3 & inflate_mask[num6])) * 3 + 2]; int num7 = hufts[(tb[0] + (num3 & inflate_mask[num6])) * 3 + 2];
if (num7 < 16) if (num7 < 16)
@ -599,7 +598,11 @@ namespace ComponentAce.Compression.Libs.zlib
internal int sync_point() internal int sync_point()
{ {
return (mode == 1) ? 1 : 0; if (mode != 1)
{
return 0;
}
return 1;
} }
internal int inflate_flush(ZStream z, int r) internal int inflate_flush(ZStream z, int r)

View File

@ -54,7 +54,7 @@ namespace ComponentAce.Compression.Libs.zlib
internal int[] tree; internal int[] tree;
internal int tree_index = 0; internal int tree_index;
internal int need; internal int need;
@ -509,7 +509,6 @@ namespace ComponentAce.Compression.Libs.zlib
num8 += array[(num9 + num8) * 3 + 2]; num8 += array[(num9 + num8) * 3 + 2];
num8 += num2 & inflate_mask[num10]; num8 += num2 & inflate_mask[num10];
num10 = array[(num9 + num8) * 3]; num10 = array[(num9 + num8) * 3];
bool flag = true;
continue; continue;
} }
z.msg = "invalid distance code"; z.msg = "invalid distance code";
@ -611,7 +610,6 @@ namespace ComponentAce.Compression.Libs.zlib
num5--; num5--;
break; break;
} }
bool flag2 = true;
continue; continue;
} }
if (((uint)num10 & 0x20u) != 0) if (((uint)num10 & 0x20u) != 0)

View File

@ -398,7 +398,11 @@ namespace ComponentAce.Compression.Libs.zlib
} }
} }
} }
return (num5 != 0 && num4 != 1) ? (-5) : 0; if (num5 == 0 || num4 == 1)
{
return 0;
}
return -5;
} }
internal static int inflate_trees_bits(int[] c, int[] bb, int[] tb, int[] hp, ZStream z) internal static int inflate_trees_bits(int[] c, int[] bb, int[] tb, int[] hp, ZStream z)

View File

@ -250,7 +250,7 @@ namespace ComponentAce.Compression.Libs.zlib
case -3: case -3:
z.istate.mode = 13; z.istate.mode = 13;
z.istate.marker = 0; z.istate.marker = 0;
goto end_IL_004b; goto end_IL_0031;
case 0: case 0:
num = f; num = f;
break; break;
@ -327,7 +327,7 @@ namespace ComponentAce.Compression.Libs.zlib
{ {
return -2; return -2;
} }
end_IL_004b: end_IL_0031:
break; break;
} }
} }

View File

@ -166,7 +166,11 @@ namespace ComponentAce.Compression.Libs.zlib
internal static int d_code(int dist) internal static int d_code(int dist)
{ {
return (dist < 256) ? _dist_code[dist] : _dist_code[256 + SupportClass.URShift(dist, 7)]; if (dist >= 256)
{
return _dist_code[256 + SupportClass.URShift(dist, 7)];
}
return _dist_code[dist];
} }
internal void gen_bitlen(Deflate s) internal void gen_bitlen(Deflate s)

View File

@ -16,9 +16,9 @@ namespace ComponentAce.Compression.Libs.zlib
protected bool compress; protected bool compress;
internal Stream in_Renamed = null; internal Stream in_Renamed;
internal bool nomoreinput = false; internal bool nomoreinput;
public virtual int FlushMode public virtual int FlushMode
{ {

View File

@ -173,8 +173,10 @@ namespace ComponentAce.Compression.Libs.zlib
} }
if (pending != 0) if (pending != 0)
{ {
if (dstate.pending_buf.Length <= dstate.pending_out || next_out.Length <= next_out_index || dstate.pending_buf.Length < dstate.pending_out + pending || next_out.Length < next_out_index + pending) if (dstate.pending_buf.Length > dstate.pending_out && next_out.Length > next_out_index && dstate.pending_buf.Length >= dstate.pending_out + pending)
{ {
_ = next_out.Length;
_ = next_out_index + pending;
} }
Array.Copy(dstate.pending_buf, dstate.pending_out, next_out, next_out_index, pending); Array.Copy(dstate.pending_buf, dstate.pending_out, next_out, next_out_index, pending);
next_out_index += pending; next_out_index += pending;

View File

@ -10,9 +10,9 @@ namespace MyNes.Core
public string SnapsFormat = ".png"; public string SnapsFormat = ".png";
public bool SnapsReplace = false; public bool SnapsReplace;
public int RegionSetting = 0; public int RegionSetting;
public string StateFolder = "States"; public string StateFolder = "States";

View File

@ -25,23 +25,23 @@ namespace MyNes.Core
private byte[] data; private byte[] data;
private EpromMode mode = EpromMode.Data; private EpromMode mode;
private EpromMode nextmode = EpromMode.Data; private EpromMode nextmode;
private EpromDevice device = EpromDevice.X24C01; private EpromDevice device;
private bool psda; private bool psda;
private bool pscl; private bool pscl;
private int output = 0; private int output;
private int cbit = 0; private int cbit;
private int caddress = 0; private int caddress;
private int cdata = 0; private int cdata;
private bool isRead; private bool isRead;

View File

@ -138,8 +138,7 @@ namespace MyNes.Core
int num5 = 0; int num5 = 0;
int num6 = 0; int num6 = 0;
int num7 = 0; int num7 = 0;
int num8 = 0; int num8 = (code >> 7) & 1;
num8 = (code >> 7) & 1;
num7 = (code >> 2) & 1; num7 = (code >> 2) & 1;
num6 = (code >> 1) & 1; num6 = (code >> 1) & 1;
num5 = code & 1; num5 = code & 1;

View File

@ -88,8 +88,7 @@ namespace MyNes.Core
{ {
if (File.Exists(FilePath)) if (File.Exists(FilePath))
{ {
FileInfo fileInfo = new FileInfo(FilePath); return new FileInfo(FilePath).Length;
return fileInfo.Length;
} }
return 0L; return 0L;
} }
@ -117,10 +116,8 @@ namespace MyNes.Core
stream.Read(buffer, 0, (int)stream.Length); stream.Read(buffer, 0, (int)stream.Length);
stream.Close(); stream.Close();
string text = ""; string text = "";
Crc32 crc = new Crc32(); byte[] array = new Crc32().ComputeHash(buffer);
byte[] array = crc.ComputeHash(buffer); foreach (byte b in array)
byte[] array2 = array;
foreach (byte b in array2)
{ {
text += b.ToString("x2").ToLower(); text += b.ToString("x2").ToLower();
} }
@ -139,10 +136,8 @@ namespace MyNes.Core
stream.Read(buffer, 0, (int)(stream.Length - bytesToSkip)); stream.Read(buffer, 0, (int)(stream.Length - bytesToSkip));
stream.Close(); stream.Close();
string text = ""; string text = "";
Crc32 crc = new Crc32(); byte[] array = new Crc32().ComputeHash(buffer);
byte[] array = crc.ComputeHash(buffer); foreach (byte b in array)
byte[] array2 = array;
foreach (byte b in array2)
{ {
text += b.ToString("x2").ToLower(); text += b.ToString("x2").ToLower();
} }
@ -157,10 +152,8 @@ namespace MyNes.Core
{ {
byte[] buffer = GetBuffer(filePath); byte[] buffer = GetBuffer(filePath);
string text = ""; string text = "";
SHA1Managed sHA1Managed = new SHA1Managed(); byte[] array = new SHA1Managed().ComputeHash(buffer);
byte[] array = sHA1Managed.ComputeHash(buffer); foreach (byte b in array)
byte[] array2 = array;
foreach (byte b in array2)
{ {
text += b.ToString("x2").ToLower(); text += b.ToString("x2").ToLower();
} }

View File

@ -25,10 +25,8 @@ namespace MyNes.Core
byte[] buffer = new byte[fileStream.Length - 16]; byte[] buffer = new byte[fileStream.Length - 16];
fileStream.Read(buffer, 0, (int)(fileStream.Length - 16)); fileStream.Read(buffer, 0, (int)(fileStream.Length - 16));
base.SHA1 = ""; base.SHA1 = "";
SHA1Managed sHA1Managed = new SHA1Managed(); byte[] array2 = new SHA1Managed().ComputeHash(buffer);
byte[] array2 = sHA1Managed.ComputeHash(buffer); foreach (byte b in array2)
byte[] array3 = array2;
foreach (byte b in array3)
{ {
base.SHA1 += b.ToString("x2").ToLower(); base.SHA1 += b.ToString("x2").ToLower();
} }

View File

@ -115,7 +115,11 @@ namespace MyNes.Core
} }
if (field.FieldType == typeof(bool)) if (field.FieldType == typeof(bool))
{ {
return ((bool)value) ? "1" : "0"; if (!(bool)value)
{
return "0";
}
return "1";
} }
if (field.FieldType == typeof(int)) if (field.FieldType == typeof(int))
{ {

View File

@ -39,7 +39,7 @@ namespace MyNes.Core
internal byte Read5010() internal byte Read5010()
{ {
byte result = (byte)((irqTrip & PCMIRQenable) ? 128u : 0u); byte result = (byte)((irqTrip & PCMIRQenable) ? 128 : 0);
irqTrip = false; irqTrip = false;
NesEmu.IRQFlags &= -9; NesEmu.IRQFlags &= -9;
return result; return result;

View File

@ -10,9 +10,9 @@ namespace MyNes.Core
private byte[] reg = new byte[4]; private byte[] reg = new byte[4];
private byte shift = 0; private byte shift;
private byte buffer = 0; private byte buffer;
private bool flag_p; private bool flag_p;

View File

@ -82,7 +82,9 @@ namespace MyNes.Core
private MMC5Pcm snd_3; private MMC5Pcm snd_3;
private double[][][][][] mix_table; private double[] audio_pulse_table;
private double[] audio_tnd_table;
internal override string Issues => MNInterfaceLanguage.IssueMapper5; internal override string Issues => MNInterfaceLanguage.IssueMapper5;
@ -92,46 +94,29 @@ namespace MyNes.Core
snd_1 = new MMC5Sqr(); snd_1 = new MMC5Sqr();
snd_2 = new MMC5Sqr(); snd_2 = new MMC5Sqr();
snd_3 = new MMC5Pcm(); snd_3 = new MMC5Pcm();
mix_table = new double[16][][][][]; audio_pulse_table = new double[32];
for (int i = 0; i < 16; i++) for (int i = 0; i < 32; i++)
{ {
mix_table[i] = new double[16][][][]; audio_pulse_table[i] = 95.52 / (8128.0 / (double)i + 100.0);
for (int j = 0; j < 16; j++)
{
mix_table[i][j] = new double[16][][];
for (int k = 0; k < 16; k++)
{
mix_table[i][j][k] = new double[16][];
for (int l = 0; l < 16; l++)
{
mix_table[i][j][k][l] = new double[256];
for (int m = 0; m < 256; m++)
{
double num = 95.88 / (8128.0 / (double)(i + j) + 100.0);
double num2 = 159.79 / (1.0 / ((double)k / 8227.0 + (double)l / 12241.0 + (double)m / 22638.0) + 100.0);
mix_table[i][j][k][l][m] = num + num2;
}
}
}
} }
audio_tnd_table = new double[204];
for (int j = 0; j < 204; j++)
{
audio_tnd_table[j] = 163.67 / (24329.0 / (double)j + 100.0);
} }
} }
internal override void HardReset() internal override void HardReset()
{ {
base.HardReset(); base.HardReset();
string text = SHA1.ToUpper(); switch (SHA1.ToUpper())
string text2 = text;
if (!(text2 == "37267833C984F176DB4B0BC9D45DABA0FFF45304"))
{
if (text2 == "800AEFE756E85A0A78CCB4DAE68EBBA5DF24BF41")
{ {
case "37267833C984F176DB4B0BC9D45DABA0FFF45304":
useSRAMmirroring = true; useSRAMmirroring = true;
} break;
} case "800AEFE756E85A0A78CCB4DAE68EBBA5DF24BF41":
else
{
useSRAMmirroring = true; useSRAMmirroring = true;
break;
} }
Console.WriteLine("MMC5: using PRG RAM mirroring = " + useSRAMmirroring); Console.WriteLine("MMC5: using PRG RAM mirroring = " + useSRAMmirroring);
CHROffset_spr = new int[8]; CHROffset_spr = new int[8];
@ -273,8 +258,7 @@ namespace MyNes.Core
case 20758: case 20758:
{ {
int num = prg_mode; int num = prg_mode;
int num2 = num; if ((uint)(num - 2) <= 1u)
if ((uint)(num2 - 2) <= 1u)
{ {
Toggle08KPRG_RAM((value & 0x80) == 0, PRGArea.AreaC000); Toggle08KPRG_RAM((value & 0x80) == 0, PRGArea.AreaC000);
Switch08KPRG(value & 0x7F, PRGArea.AreaC000); Switch08KPRG(value & 0x7F, PRGArea.AreaC000);
@ -531,9 +515,7 @@ namespace MyNes.Core
{ {
split_doit = split_watch_tile >= split_tile; split_doit = split_watch_tile >= split_tile;
} }
if (!split_doit) _ = split_doit;
{
}
} }
if (ExRAM_mode == 1) if (ExRAM_mode == 1)
{ {
@ -571,9 +553,7 @@ namespace MyNes.Core
internal override void ReadNMT(ref ushort address, out byte data) internal override void ReadNMT(ref ushort address, out byte data)
{ {
if (split_doit) _ = split_doit;
{
}
if (ExRAM_mode == 1) if (ExRAM_mode == 1)
{ {
if ((address & 0x3FF) <= 959) if ((address & 0x3FF) <= 959)
@ -756,7 +736,7 @@ namespace MyNes.Core
internal override double APUGetSample() internal override double APUGetSample()
{ {
return mix_table[snd_1.output][snd_2.output][0][0][snd_3.output]; return audio_pulse_table[snd_1.output + snd_2.output] + audio_tnd_table[snd_3.output];
} }
internal override void APUApplyChannelsSettings() internal override void APUApplyChannelsSettings()

View File

@ -5,9 +5,9 @@ namespace MyNes.Core
[BoardInfo("Caltron 6-in-1", 41)] [BoardInfo("Caltron 6-in-1", 41)]
internal class Mapper041 : Board internal class Mapper041 : Board
{ {
private bool enableReg = false; private bool enableReg;
private int vromReg = 0; private int vromReg;
internal override void HardReset() internal override void HardReset()
{ {

View File

@ -5,11 +5,11 @@ namespace MyNes.Core
[BoardInfo("Mario Baby", 42)] [BoardInfo("Mario Baby", 42)]
internal class Mapper042 : Board internal class Mapper042 : Board
{ {
private int SRAM_PRG_Page = 0; private int SRAM_PRG_Page;
private bool irqEnable = false; private bool irqEnable;
private int irqCounter = 0; private int irqCounter;
internal override void HardReset() internal override void HardReset()
{ {

View File

@ -5,7 +5,7 @@ namespace MyNes.Core
[BoardInfo("11-in-1", 51)] [BoardInfo("11-in-1", 51)]
internal class Mapper051 : Board internal class Mapper051 : Board
{ {
private int bank = 0; private int bank;
private int mode = 1; private int mode = 1;

View File

@ -3,15 +3,15 @@ namespace MyNes.Core
[BoardInfo("Pirate SMB3", 56)] [BoardInfo("Pirate SMB3", 56)]
internal class Mapper056 : Board internal class Mapper056 : Board
{ {
private int irqCounter = 0; private int irqCounter;
private int irqLatch = 0; private int irqLatch;
private bool irqEnabled = false; private bool irqEnabled;
private int irqControl = 0; private int irqControl;
private int switchControl = 0; private int switchControl;
internal override string Issues => MNInterfaceLanguage.IssueMapper56; internal override string Issues => MNInterfaceLanguage.IssueMapper56;

View File

@ -6,9 +6,9 @@ namespace MyNes.Core
[HassIssues] [HassIssues]
internal class Mapper060 : Board internal class Mapper060 : Board
{ {
private int latch = 0; private int latch;
private byte menu = 0; private byte menu;
internal override string Issues => MNInterfaceLanguage.IssueMapper60; internal override string Issues => MNInterfaceLanguage.IssueMapper60;

View File

@ -26,25 +26,25 @@ namespace MyNes.Core
private bool flag_s; private bool flag_s;
private int irqCounter = 0; private int irqCounter;
private bool IrqEnable = false; private bool IrqEnable;
private bool irqCountDownMode = false; private bool irqCountDownMode;
private bool irqCountUpMode = false; private bool irqCountUpMode;
private bool irqFunkyMode = false; private bool irqFunkyMode;
private bool irqPrescalerSize = false; private bool irqPrescalerSize;
private int irqSource = 0; private int irqSource;
private int irqPrescaler = 0; private int irqPrescaler;
private int irqPrescalerXOR = 0; private int irqPrescalerXOR;
private byte irqFunkyModeReg = 0; private byte irqFunkyModeReg;
private byte Dipswitch; private byte Dipswitch;

View File

@ -10,9 +10,9 @@ namespace MyNes.Core
private byte[] reg = new byte[4]; private byte[] reg = new byte[4];
private byte shift = 0; private byte shift;
private byte buffer = 0; private byte buffer;
private bool flag_p; private bool flag_p;

View File

@ -5,9 +5,7 @@ namespace MyNes.Core
{ {
internal override void WriteEX(ref ushort address, ref byte data) internal override void WriteEX(ref ushort address, ref byte data)
{ {
int num = address & 0x4100; if ((address & 0x4100) == 16640)
int num2 = num;
if (num2 == 16640)
{ {
Switch08KCHR((data & 7) | ((data & 0x40) >> 3)); Switch08KCHR((data & 7) | ((data & 0x40) >> 3));
Switch32KPRG((data >> 3) & 7, PRGArea.Area8000); Switch32KPRG((data >> 3) & 7, PRGArea.Area8000);

View File

@ -11,22 +11,15 @@ namespace MyNes.Core
internal override void WriteEX(ref ushort address, ref byte data) internal override void WriteEX(ref ushort address, ref byte data)
{ {
if (address >= 20480) if (address >= 20480 && (address & 0xF000) == 20480)
{
int num = address & 0xF000;
int num2 = num;
if (num2 == 20480)
{ {
Switch32KPRG(data, PRGArea.Area8000); Switch32KPRG(data, PRGArea.Area8000);
} }
} }
}
internal override void WritePRG(ref ushort address, ref byte data) internal override void WritePRG(ref ushort address, ref byte data)
{ {
int num = address & 0xF000; if ((address & 0xF000) == 53248)
int num2 = num;
if (num2 == 53248)
{ {
Switch32KPRG(data, PRGArea.Area8000); Switch32KPRG(data, PRGArea.Area8000);
} }

View File

@ -53,21 +53,32 @@ namespace MyNes.Core
internal override void WritePRG(ref ushort address, ref byte data) internal override void WritePRG(ref ushort address, ref byte data)
{ {
switch (address & 0xE001) int num = address & 0xE001;
if (num <= 40961)
{ {
case 32769: if (num <= 32769)
if (NMT_DEFAULT_MIRROR != Mirroring.Full) {
if (num != 32768 && num == 32769 && NMT_DEFAULT_MIRROR != Mirroring.Full)
{ {
Switch01KNMTFromMirroring(((data & 1) == 1) ? Mirroring.Horz : Mirroring.Vert); Switch01KNMTFromMirroring(((data & 1) == 1) ? Mirroring.Horz : Mirroring.Vert);
} }
break; }
case 40960: else if (num != 40960)
{
_ = 40961;
}
else
{
address_8001 = data & 7; address_8001 = data & 7;
flag_c = (data & 0x80) != 0; flag_c = (data & 0x80) != 0;
flag_p = (data & 0x40) != 0; flag_p = (data & 0x40) != 0;
SetupCHR(); SetupCHR();
SetupPRG(); SetupPRG();
break; }
return;
}
switch (num)
{
case 49152: case 49152:
switch (address_8001) switch (address_8001)
{ {

View File

@ -68,8 +68,7 @@ namespace MyNes.Core
case 32769: case 32769:
{ {
int num = address_8001; int num = address_8001;
int num2 = num; if ((uint)num <= 5u)
if ((uint)num2 <= 5u)
{ {
chr_reg[address_8001] = data; chr_reg[address_8001] = data;
SetupCHR(); SetupCHR();

View File

@ -4,7 +4,7 @@ namespace MyNes.Core
[HassIssues] [HassIssues]
internal class Mapper230 : Board internal class Mapper230 : Board
{ {
private bool contraMode = false; private bool contraMode;
internal override string Issues => MNInterfaceLanguage.IssueMapper230; internal override string Issues => MNInterfaceLanguage.IssueMapper230;

View File

@ -5,7 +5,7 @@ namespace MyNes.Core
[BoardInfo("Unknown", 233)] [BoardInfo("Unknown", 233)]
internal class Mapper233 : Board internal class Mapper233 : Board
{ {
private int title = 0; private int title;
private int bank; private int bank;

View File

@ -51,8 +51,7 @@ namespace MyNes.Core
VideoProviders = new List<IVideoProvider>(); VideoProviders = new List<IVideoProvider>();
AudioProviders = new List<IAudioProvider>(); AudioProviders = new List<IAudioProvider>();
string[] files = Directory.GetFiles(Path.GetDirectoryName(Environment.GetCommandLineArgs()[0]), "*", SearchOption.AllDirectories); string[] files = Directory.GetFiles(Path.GetDirectoryName(Environment.GetCommandLineArgs()[0]), "*", SearchOption.AllDirectories);
string[] array = files; foreach (string text in files)
foreach (string text in array)
{ {
try try
{ {
@ -67,8 +66,7 @@ namespace MyNes.Core
continue; continue;
} }
Type[] types = assembly.GetTypes(); Type[] types = assembly.GetTypes();
Type[] array2 = types; foreach (Type type in types)
foreach (Type type in array2)
{ {
if (type.IsSubclassOf(typeof(Board)) && !type.IsAbstract) if (type.IsSubclassOf(typeof(Board)) && !type.IsAbstract)
{ {

View File

@ -0,0 +1,109 @@
using System;
namespace MyNes.Core
{
public class NTSCPaletteGenerator
{
public const float default_saturation = 1.496f;
public const float default_hue_tweak = 0f;
public const float default_contrast = 1.016f;
public const float default_brightness = 1.075f;
public const float default_gamma = 1.975f;
private const float black = 0.518f;
private const float white = 1.962f;
private const float attenuation = 0.746f;
public static float saturation = 2f;
public static float hue_tweak = 0f;
public static float contrast = 1.4f;
public static float brightness = 1.07f;
public static float gamma = 2f;
private static float[] levels = new float[8] { 0.35f, 0.518f, 0.962f, 1.55f, 1.094f, 1.506f, 1.962f, 1.962f };
private static int wave(int p, int color)
{
if ((color + p + 8) % 12 >= 6)
{
return 0;
}
return 1;
}
private static float gammafix(float f, float gamma)
{
return (float)((f < 0f) ? 0.0 : Math.Pow(f, 2.2f / gamma));
}
private static int clamp(float v)
{
return (int)((v < 0f) ? 0f : ((v > 255f) ? 255f : v));
}
public static int MakeRGBcolor(int pixel)
{
int num = pixel & 0xF;
int num2 = ((num >= 14) ? 1 : ((pixel >> 4) & 3));
float[] array = new float[2]
{
levels[num2 + ((num == 0) ? 4 : 0)],
levels[num2 + ((num <= 12) ? 4 : 0)]
};
float num3 = 0f;
float num4 = 0f;
float num5 = 0f;
for (int i = 0; i < 12; i++)
{
float num6 = array[wave(i, num)];
if ((((uint)pixel & 0x40u) != 0 && wave(i, 12) == 1) || (((uint)pixel & 0x80u) != 0 && wave(i, 4) == 1) || (((uint)pixel & 0x100u) != 0 && wave(i, 8) == 1))
{
num6 *= 0.746f;
}
float num7 = (num6 - 0.518f) / 1.444f;
num7 = (num7 - 0.5f) * contrast + 0.5f;
num7 *= brightness / 12f;
num3 += num7;
num4 += (float)((double)num7 * Math.Cos(Math.PI / 6.0 * (double)((float)i + hue_tweak)));
num5 += (float)((double)num7 * Math.Sin(Math.PI / 6.0 * (double)((float)i + hue_tweak)));
}
num4 *= saturation;
num5 *= saturation;
return 65536 * clamp(255f * gammafix(num3 + 0.946882f * num4 + 0.623557f * num5, gamma)) + 256 * clamp(255f * gammafix(num3 - 245f / (328f * (float)Math.E) * num4 - 0.635691f * num5, gamma)) + clamp(255f * gammafix(num3 - 1.108545f * num4 + 1.709007f * num5, gamma));
}
public static int[] GeneratePalette()
{
int[] array = new int[512];
for (int i = 0; i < 512; i++)
{
array[i] = MakeRGBcolor(i) | -16777216;
}
return array;
}
public static int[] GeneratePaletteGBR()
{
int[] array = new int[512];
for (int i = 0; i < 512; i++)
{
int num = MakeRGBcolor(i);
byte b = (byte)((num & 0xFF0000) >> 16);
byte b2 = (byte)((num & 0xFF00) >> 8);
byte b3 = (byte)((uint)num & 0xFFu);
array[i] = -16777216 | (b3 << 16) | (b2 << 8) | b;
}
return array;
}
}
}

View File

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 29be0f25cd887b349ab47194ae46b123
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@ -283,11 +283,7 @@ namespace MyNes.Core
private static bool audio_playback_dac_initialized; private static bool audio_playback_dac_initialized;
public static double cpu_speed; public static int cpu_speed;
public static double cpu_clock_per_frame;
internal static double apu_target_samples_count_per_frame;
private static short[] audio_samples; private static short[] audio_samples;
@ -507,6 +503,8 @@ namespace MyNes.Core
private static int[] ppu_screen_pixels; private static int[] ppu_screen_pixels;
private static int[] ppu_palette;
private static int ppu_clock_h; private static int ppu_clock_h;
internal static ushort ppu_clock_v; internal static ushort ppu_clock_v;
@ -561,7 +559,7 @@ namespace MyNes.Core
private static bool ppu_reg_2001_show_sprites; private static bool ppu_reg_2001_show_sprites;
private static bool ppu_reg_2001_grayscale; private static int ppu_reg_2001_grayscale;
private static int ppu_reg_2001_emphasis; private static int ppu_reg_2001_emphasis;
@ -651,40 +649,6 @@ namespace MyNes.Core
private static bool ppu_sprite0_should_hit; private static bool ppu_sprite0_should_hit;
private static int ppu_palette_temp__val;
private static int ppu_color_temp__level;
private static int ppu_color_temp__red;
private static int ppu_color_temp__blue;
private static int ppu_color_temp__green;
private static bool ppu_color_temp__e_red;
private static bool ppu_color_temp__e_blue;
private static bool ppu_color_temp__e_green;
private static byte[] ppu_color_temp_blue__sequence = new byte[16]
{
7, 7, 6, 5, 4, 3, 2, 1, 2, 3,
4, 5, 6, 0, 0, 0
};
private static byte[] ppu_color_temp_red___sequence = new byte[16]
{
7, 1, 2, 3, 4, 5, 6, 7, 6, 5,
4, 3, 2, 0, 0, 0
};
private static byte[] ppu_color_temp_green_sequence = new byte[16]
{
7, 0, 0, 0, 1, 2, 3, 4, 5, 6,
7, 6, 5, 0, 0, 0
};
private static int ppu_temp_comparator; private static int ppu_temp_comparator;
public static bool ON; public static bool ON;
@ -731,10 +695,6 @@ namespace MyNes.Core
public static EmuRegion Region; public static EmuRegion Region;
internal static Action EmuClockComponents;
internal static int pal_add_cycle = 0;
private static int SystemIndex; private static int SystemIndex;
private static RequestMode emu_request_mode = RequestMode.None; private static RequestMode emu_request_mode = RequestMode.None;
@ -1742,22 +1702,19 @@ namespace MyNes.Core
switch (Region) switch (Region)
{ {
case EmuRegion.NTSC: case EmuRegion.NTSC:
cpu_speed = 1789773.0; cpu_speed = 1789773;
cpu_clock_per_frame = 29780.5;
apu_ferq_f = 14914; apu_ferq_f = 14914;
apu_ferq_e = 3728; apu_ferq_e = 3728;
apu_ferq_l = 7456; apu_ferq_l = 7456;
break; break;
case EmuRegion.PALB: case EmuRegion.PALB:
cpu_speed = 1662607.0; cpu_speed = 1662607;
cpu_clock_per_frame = 33247.5;
apu_ferq_f = 14914; apu_ferq_f = 14914;
apu_ferq_e = 3728; apu_ferq_e = 3728;
apu_ferq_l = 7456; apu_ferq_l = 7456;
break; break;
case EmuRegion.DENDY: case EmuRegion.DENDY:
cpu_speed = 1773448.0; cpu_speed = 1773448;
cpu_clock_per_frame = 35464.0;
apu_ferq_f = 14914; apu_ferq_f = 14914;
apu_ferq_e = 3728; apu_ferq_e = 3728;
apu_ferq_l = 7456; apu_ferq_l = 7456;
@ -2082,9 +2039,7 @@ namespace MyNes.Core
private static void CalculateAudioPlaybackValues() private static void CalculateAudioPlaybackValues()
{ {
apu_target_samples_count_per_frame = (double)MyNesMain.RendererSettings.Audio_Frequency / emu_time_target_fps; audio_timer_ratio = (double)cpu_speed / (double)MyNesMain.RendererSettings.Audio_Frequency;
audio_timer_ratio = cpu_clock_per_frame / apu_target_samples_count_per_frame;
cpu_speed = audio_timer_ratio * (double)MyNesMain.RendererSettings.Audio_Frequency;
audio_playback_peek_limit = MyNesMain.RendererSettings.Audio_InternalPeekLimit; audio_playback_peek_limit = MyNesMain.RendererSettings.Audio_InternalPeekLimit;
audio_samples_count = MyNesMain.RendererSettings.Audio_InternalSamplesCount; audio_samples_count = MyNesMain.RendererSettings.Audio_InternalSamplesCount;
audio_playback_amplitude = MyNesMain.RendererSettings.Audio_PlaybackAmplitude; audio_playback_amplitude = MyNesMain.RendererSettings.Audio_PlaybackAmplitude;
@ -2097,16 +2052,12 @@ namespace MyNes.Core
Tracer.WriteLine("AUDIO: timer ratio = " + audio_timer_ratio); Tracer.WriteLine("AUDIO: timer ratio = " + audio_timer_ratio);
Tracer.WriteLine("AUDIO: internal samples count = " + audio_samples_count); Tracer.WriteLine("AUDIO: internal samples count = " + audio_samples_count);
Tracer.WriteLine("AUDIO: amplitude = " + audio_playback_amplitude); Tracer.WriteLine("AUDIO: amplitude = " + audio_playback_amplitude);
double num = 0.0;
if (MyNesMain.RendererSettings.Audio_EnableFilters) if (MyNesMain.RendererSettings.Audio_EnableFilters)
{ {
apu_update_playback_func = APUUpdatePlaybackWithFilters; apu_update_playback_func = APUUpdatePlaybackWithFilters;
num = cpu_speed / 14000.0; audio_low_pass_filter_14K = new SoundLowPassFilter(SoundLowPassFilter.GetK((double)cpu_speed / 14000.0, 14000.0));
audio_low_pass_filter_14K = new SoundLowPassFilter(SoundLowPassFilter.GetK(num, 14000.0)); audio_high_pass_filter_90 = new SoundHighPassFilter(SoundHighPassFilter.GetK((double)cpu_speed / 90.0, 90.0));
num = cpu_speed / 90.0; audio_high_pass_filter_440 = new SoundHighPassFilter(SoundHighPassFilter.GetK((double)cpu_speed / 440.0, 440.0));
audio_high_pass_filter_90 = new SoundHighPassFilter(SoundHighPassFilter.GetK(num, 90.0));
num = cpu_speed / 440.0;
audio_high_pass_filter_440 = new SoundHighPassFilter(SoundHighPassFilter.GetK(num, 440.0));
} }
else else
{ {
@ -3766,11 +3717,11 @@ namespace MyNes.Core
SRAMFileName = Path.Combine(MyNesMain.EmuSettings.SRAMFolder, Path.GetFileNameWithoutExtension(CurrentFilePath) + ".srm"); SRAMFileName = Path.Combine(MyNesMain.EmuSettings.SRAMFolder, Path.GetFileNameWithoutExtension(CurrentFilePath) + ".srm");
if (File.Exists(SRAMFileName)) if (File.Exists(SRAMFileName))
{ {
Stream stream = new FileStream(SRAMFileName, FileMode.Open, FileAccess.Read); FileStream fileStream = new FileStream(SRAMFileName, FileMode.Open, FileAccess.Read);
byte[] array = new byte[stream.Length]; byte[] array = new byte[fileStream.Length];
stream.Read(array, 0, array.Length); fileStream.Read(array, 0, array.Length);
stream.Flush(); fileStream.Flush();
stream.Close(); fileStream.Close();
byte[] outData = new byte[0]; byte[] outData = new byte[0];
ZlipWrapper.DecompressData(array, out outData); ZlipWrapper.DecompressData(array, out outData);
mem_board.LoadSRAM(outData); mem_board.LoadSRAM(outData);
@ -3894,10 +3845,10 @@ namespace MyNes.Core
Tracer.WriteLine("Saving SRAM ..."); Tracer.WriteLine("Saving SRAM ...");
byte[] outData = new byte[0]; byte[] outData = new byte[0];
ZlipWrapper.CompressData(mem_board.GetSRAMBuffer(), out outData); ZlipWrapper.CompressData(mem_board.GetSRAMBuffer(), out outData);
Stream stream = new FileStream(SRAMFileName, FileMode.Create, FileAccess.Write); FileStream fileStream = new FileStream(SRAMFileName, FileMode.Create, FileAccess.Write);
stream.Write(outData, 0, outData.Length); fileStream.Write(outData, 0, outData.Length);
stream.Flush(); fileStream.Flush();
stream.Close(); fileStream.Close();
Tracer.WriteLine("SRAM saved successfully."); Tracer.WriteLine("SRAM saved successfully.");
} }
} }
@ -4029,6 +3980,11 @@ namespace MyNes.Core
inputStrobe = bin.ReadInt32(); inputStrobe = bin.ReadInt32();
} }
public static void SetupPalette(int[] pal)
{
ppu_palette = pal;
}
private static void PPUInitialize() private static void PPUInitialize()
{ {
ppu_reg_update_func = new Action[8] { PPUOnRegister2000, PPUOnRegister2001, PPUOnRegister2002, PPUOnRegister2003, PPUOnRegister2004, PPUOnRegister2005, PPUOnRegister2006, PPUOnRegister2007 }; ppu_reg_update_func = new Action[8] { PPUOnRegister2000, PPUOnRegister2001, PPUOnRegister2002, PPUOnRegister2003, PPUOnRegister2004, PPUOnRegister2005, PPUOnRegister2006, PPUOnRegister2007 };
@ -4066,11 +4022,12 @@ namespace MyNes.Core
ppu_bkg_pixels = new int[512]; ppu_bkg_pixels = new int[512];
ppu_spr_pixels = new int[512]; ppu_spr_pixels = new int[512];
ppu_screen_pixels = new int[61440]; ppu_screen_pixels = new int[61440];
ppu_palette = NTSCPaletteGenerator.GeneratePalette();
} }
private static void PPUHardReset() private static void PPUHardReset()
{ {
ppu_reg_2001_grayscale = false; ppu_reg_2001_grayscale = 243;
switch (Region) switch (Region)
{ {
case EmuRegion.NTSC: case EmuRegion.NTSC:
@ -4124,7 +4081,7 @@ namespace MyNes.Core
ppu_reg_2001_show_sprites_in_leftmost_8_pixels_of_screen = false; ppu_reg_2001_show_sprites_in_leftmost_8_pixels_of_screen = false;
ppu_reg_2001_show_background = false; ppu_reg_2001_show_background = false;
ppu_reg_2001_show_sprites = false; ppu_reg_2001_show_sprites = false;
ppu_reg_2001_grayscale = false; ppu_reg_2001_grayscale = 63;
ppu_reg_2001_emphasis = 0; ppu_reg_2001_emphasis = 0;
ppu_reg_2002_SpriteOverflow = false; ppu_reg_2002_SpriteOverflow = false;
ppu_reg_2002_Sprite0Hit = false; ppu_reg_2002_Sprite0Hit = false;
@ -4147,12 +4104,13 @@ namespace MyNes.Core
if (ppu_clock_v == ppu_clock_vblank_end) if (ppu_clock_v == ppu_clock_vblank_end)
{ {
ppu_clock_v = 0; ppu_clock_v = 0;
ppu_frame_finished = true;
} }
else else
{ {
ppu_clock_v++; ppu_clock_v++;
} }
ppu_clock_h = 0; ppu_clock_h -= 341;
} }
if (ppu_reg_access_happened) if (ppu_reg_access_happened)
{ {
@ -4179,7 +4137,6 @@ namespace MyNes.Core
if (ppu_clock_h == 1) if (ppu_clock_h == 1)
{ {
ppu_reg_2002_VblankStartedFlag = true; ppu_reg_2002_VblankStartedFlag = true;
ppu_frame_finished = true;
} }
PPU_NMI_Current = ppu_reg_2002_VblankStartedFlag & ppu_reg_2000_VBI; PPU_NMI_Current = ppu_reg_2002_VblankStartedFlag & ppu_reg_2000_VBI;
} }
@ -4255,9 +4212,27 @@ namespace MyNes.Core
RenderPixel(); RenderPixel();
} }
} }
else if (ppu_clock_v < 240) else
{ {
ppu_screen_pixels[ppu_clock_h - 1 + ppu_clock_v * 256] = MakeRGBColor(ppu_vram_addr); if (ppu_clock_v >= 240)
{
return;
}
if ((ppu_vram_addr & 0x3F00) == 16128)
{
if ((ppu_vram_addr & 3) == 0)
{
ppu_screen_pixels[ppu_clock_h - 1 + ppu_clock_v * 256] = ppu_palette[(ppu_palette_bank[ppu_vram_addr & 0xC] & ppu_reg_2001_grayscale) | ppu_reg_2001_emphasis];
}
else
{
ppu_screen_pixels[ppu_clock_h - 1 + ppu_clock_v * 256] = ppu_palette[(ppu_palette_bank[ppu_vram_addr & 0x1F] & ppu_reg_2001_grayscale) | ppu_reg_2001_emphasis];
}
}
else
{
ppu_screen_pixels[ppu_clock_h - 1 + ppu_clock_v * 256] = ppu_palette[(ppu_palette_bank[0] & ppu_reg_2001_grayscale) | ppu_reg_2001_emphasis];
}
} }
} }
@ -4660,51 +4635,14 @@ namespace MyNes.Core
{ {
ppu_reg_2002_Sprite0Hit = true; ppu_reg_2002_Sprite0Hit = true;
} }
ppu_screen_pixels[ppu_render_x + ppu_render_y] = MakeRGBColor(ppu_current_pixel); if ((ppu_current_pixel & 3) == 0)
}
private static int MakeRGBColor(int pixel)
{ {
pixel = ((pixel < 16128) ? 15 : ((((uint)ppu_current_pixel & 3u) != 0) ? ppu_palette_bank[pixel & 0x1F] : ppu_palette_bank[pixel & 0xC])); ppu_screen_pixels[ppu_render_x + ppu_render_y] = ppu_palette[(ppu_palette_bank[ppu_current_pixel & 0xC] & ppu_reg_2001_grayscale) | ppu_reg_2001_emphasis];
ppu_palette_temp__val = pixel & 0xF;
ppu_color_temp__level = (pixel & 0x30) << 2;
if (ppu_reg_2001_grayscale)
{
ppu_palette_temp__val = 0;
}
ppu_color_temp__blue = (ppu_color_temp_blue__sequence[ppu_palette_temp__val] << 3) | ppu_color_temp__level;
ppu_color_temp__red = (ppu_color_temp_red___sequence[ppu_palette_temp__val] << 3) | ppu_color_temp__level;
ppu_color_temp__green = (ppu_color_temp_green_sequence[ppu_palette_temp__val] << 3) | ppu_color_temp__level;
if (SystemIndex == 0)
{
ppu_color_temp__e_red = (ppu_reg_2001_emphasis & 1) != 0;
} }
else else
{ {
ppu_color_temp__e_green = (ppu_reg_2001_emphasis & 1) != 0; ppu_screen_pixels[ppu_render_x + ppu_render_y] = ppu_palette[(ppu_palette_bank[ppu_current_pixel & 0x1F] & ppu_reg_2001_grayscale) | ppu_reg_2001_emphasis];
} }
if (SystemIndex == 0)
{
ppu_color_temp__e_green = (ppu_reg_2001_emphasis & 2) != 0;
}
else
{
ppu_color_temp__e_red = (ppu_reg_2001_emphasis & 2) != 0;
}
ppu_color_temp__e_blue = (ppu_reg_2001_emphasis & 4) != 0;
if (ppu_color_temp__e_blue)
{
ppu_color_temp__blue |= 7;
}
if (ppu_color_temp__e_red)
{
ppu_color_temp__red |= 7;
}
if (ppu_color_temp__e_green)
{
ppu_color_temp__green |= 7;
}
return (ppu_color_temp__red << 16) | (ppu_color_temp__green << 8) | ppu_color_temp__blue;
} }
private static void PPUIORead(ref ushort addr, out byte value) private static void PPUIORead(ref ushort addr, out byte value)
@ -4781,8 +4719,8 @@ namespace MyNes.Core
ppu_reg_2001_show_sprites_in_leftmost_8_pixels_of_screen = (ppu_reg_io_db & 4) != 0; ppu_reg_2001_show_sprites_in_leftmost_8_pixels_of_screen = (ppu_reg_io_db & 4) != 0;
ppu_reg_2001_show_background = (ppu_reg_io_db & 8) != 0; ppu_reg_2001_show_background = (ppu_reg_io_db & 8) != 0;
ppu_reg_2001_show_sprites = (ppu_reg_io_db & 0x10) != 0; ppu_reg_2001_show_sprites = (ppu_reg_io_db & 0x10) != 0;
ppu_reg_2001_grayscale = (ppu_reg_io_db & 1) != 0; ppu_reg_2001_grayscale = ((((uint)ppu_reg_io_db & (true ? 1u : 0u)) != 0) ? 48 : 63);
ppu_reg_2001_emphasis = (ppu_reg_io_db & 0xE0) >> 5; ppu_reg_2001_emphasis = (ppu_reg_io_db & 0xE0) << 1;
} }
} }
@ -4978,12 +4916,20 @@ namespace MyNes.Core
internal static bool IsRenderingOn() internal static bool IsRenderingOn()
{ {
return ppu_reg_2001_show_background || ppu_reg_2001_show_sprites; if (!ppu_reg_2001_show_background)
{
return ppu_reg_2001_show_sprites;
}
return true;
} }
internal static bool IsInRender() internal static bool IsInRender()
{ {
return ppu_clock_v < 240 || ppu_clock_v == ppu_clock_vblank_end; if (ppu_clock_v >= 240)
{
return ppu_clock_v == ppu_clock_vblank_end;
}
return true;
} }
private static void PPUWriteState(ref BinaryWriter bin) private static void PPUWriteState(ref BinaryWriter bin)
@ -5012,7 +4958,7 @@ namespace MyNes.Core
bin.Write(ppu_reg_2001_show_sprites_in_leftmost_8_pixels_of_screen); bin.Write(ppu_reg_2001_show_sprites_in_leftmost_8_pixels_of_screen);
bin.Write(ppu_reg_2001_show_background); bin.Write(ppu_reg_2001_show_background);
bin.Write(ppu_reg_2001_show_sprites); bin.Write(ppu_reg_2001_show_sprites);
bin.Write(ppu_reg_2001_grayscale ? 1 : 0); bin.Write(ppu_reg_2001_grayscale);
bin.Write(ppu_reg_2001_emphasis); bin.Write(ppu_reg_2001_emphasis);
bin.Write(ppu_reg_2002_SpriteOverflow); bin.Write(ppu_reg_2002_SpriteOverflow);
bin.Write(ppu_reg_2002_Sprite0Hit); bin.Write(ppu_reg_2002_Sprite0Hit);
@ -5084,7 +5030,7 @@ namespace MyNes.Core
ppu_reg_2001_show_sprites_in_leftmost_8_pixels_of_screen = bin.ReadBoolean(); ppu_reg_2001_show_sprites_in_leftmost_8_pixels_of_screen = bin.ReadBoolean();
ppu_reg_2001_show_background = bin.ReadBoolean(); ppu_reg_2001_show_background = bin.ReadBoolean();
ppu_reg_2001_show_sprites = bin.ReadBoolean(); ppu_reg_2001_show_sprites = bin.ReadBoolean();
ppu_reg_2001_grayscale = bin.ReadInt32() == 1; ppu_reg_2001_grayscale = bin.ReadInt32();
ppu_reg_2001_emphasis = bin.ReadInt32(); ppu_reg_2001_emphasis = bin.ReadInt32();
ppu_reg_2002_SpriteOverflow = bin.ReadBoolean(); ppu_reg_2002_SpriteOverflow = bin.ReadBoolean();
ppu_reg_2002_Sprite0Hit = bin.ReadBoolean(); ppu_reg_2002_Sprite0Hit = bin.ReadBoolean();
@ -5133,8 +5079,7 @@ namespace MyNes.Core
internal static void CheckGame(string fileName, out bool valid) internal static void CheckGame(string fileName, out bool valid)
{ {
string text = Path.GetExtension(fileName).ToLower(); string text = Path.GetExtension(fileName).ToLower();
string text2 = text; if (text != null && text == ".nes")
if (text2 == ".nes")
{ {
Tracer.WriteLine("Checking INES header ..."); Tracer.WriteLine("Checking INES header ...");
INes nes = new INes(); INes nes = new INes();
@ -5170,7 +5115,6 @@ namespace MyNes.Core
{ {
Tracer.WriteWarning("Nes Cart database file cannot be located at " + text); Tracer.WriteWarning("Nes Cart database file cannot be located at " + text);
} }
EmuClockComponents = EmuClockComponentsNTSC;
FrameLimiterEnabled = true; FrameLimiterEnabled = true;
CPUInitialize(); CPUInitialize();
PPUInitialize(); PPUInitialize();
@ -5195,7 +5139,7 @@ namespace MyNes.Core
Tracer.WriteError("Faild to initialize the renderers methods. Please use the method 'SetupRenderingMethods' to initialize the renderers methods before you can run the emulation."); Tracer.WriteError("Faild to initialize the renderers methods. Please use the method 'SetupRenderingMethods' to initialize the renderers methods before you can run the emulation.");
} }
public static void LoadGame(string fileName, out bool success) public static void LoadGame(string fileName, out bool success, bool useThread)
{ {
if (!render_initialized) if (!render_initialized)
{ {
@ -5205,8 +5149,7 @@ namespace MyNes.Core
return; return;
} }
string text = Path.GetExtension(fileName).ToLower(); string text = Path.GetExtension(fileName).ToLower();
string text2 = text; if (text != null && text == ".nes")
if (text2 == ".nes")
{ {
Tracer.WriteLine("Checking INES header ..."); Tracer.WriteLine("Checking INES header ...");
INes nes = new INes(); INes nes = new INes();
@ -5220,22 +5163,22 @@ namespace MyNes.Core
ShutDown(); ShutDown();
} }
Tracer.WriteLine("INES header is valid, loading game ..."); Tracer.WriteLine("INES header is valid, loading game ...");
MEMInitialize(nes);
ApplyRegionSetting(); ApplyRegionSetting();
MEMInitialize(nes);
ApplyAudioSettings(); ApplyAudioSettings();
ApplyFrameSkipSettings(); ApplyFrameSkipSettings();
ApplyPaletteSetting();
PORTSInitialize(); PORTSInitialize();
hardReset(); hardReset();
Tracer.WriteLine("EMU is ready."); Tracer.WriteLine("EMU is ready.");
success = true; success = true;
emu_frame_clocking_mode = !MyNesMain.RendererSettings.UseEmuThread; emu_frame_clocking_mode = !useThread;
ON = true; ON = true;
PAUSED = false; PAUSED = false;
isPaused = false; if (useThread)
FrameLimiterEnabled = true;
if (MyNesMain.RendererSettings.UseEmuThread)
{ {
Tracer.WriteLine("Running in a thread ... using custom frame limiter."); Tracer.WriteLine("Running in a thread ... using custom frame limiter.");
FrameLimiterEnabled = true;
mainThread = new Thread(EmuClock); mainThread = new Thread(EmuClock);
mainThread.Start(); mainThread.Start();
} }
@ -5346,107 +5289,20 @@ namespace MyNes.Core
NesEmu.EmuShutdown?.Invoke(null, new EventArgs()); NesEmu.EmuShutdown?.Invoke(null, new EventArgs());
} }
public static void EMUClockFrame() internal static void EMUClockFrame()
{ {
if (PAUSED)
{
render_audio_get_is_playing(out render_audio_is_playing);
if (render_audio_is_playing)
{
render_audio_toggle_pause(paused: true);
}
shortucts.Update();
switch (emu_request_mode)
{
case RequestMode.HardReset:
hardReset();
PAUSED = false;
emu_request_mode = RequestMode.None;
break;
case RequestMode.SoftReset:
softReset();
PAUSED = false;
emu_request_mode = RequestMode.None;
break;
case RequestMode.SaveState:
StateHandler.SaveState();
PAUSED = false;
emu_request_mode = RequestMode.None;
break;
case RequestMode.LoadState:
StateHandler.LoadState();
PAUSED = false;
emu_request_mode = RequestMode.None;
break;
case RequestMode.TakeSnapshot:
MyNesMain.VideoProvider.TakeSnapshot();
PAUSED = false;
emu_request_mode = RequestMode.None;
break;
}
isPaused = true;
return;
}
emu_frame_done = false; emu_frame_done = false;
while (!ppu_frame_finished && ON) while (!emu_frame_done && ON)
{
if (!PAUSED)
{ {
CPUClock(); CPUClock();
} }
if (!FrameSkipEnabled)
{
render_video(ref ppu_screen_pixels);
}
else else
{ {
FrameSkipCounter++; Thread.Sleep(100);
if (FrameSkipCounter >= FrameSkipInterval)
{
render_video(ref ppu_screen_pixels);
FrameSkipCounter = 0;
} }
} }
isPaused = false;
ppu_frame_finished = false;
emu_frame_done = true;
joypad1.Update();
joypad2.Update();
if (IsFourPlayers)
{
joypad3.Update();
joypad4.Update();
}
shortucts.Update();
if (SoundEnabled)
{
render_audio_get_is_playing(out render_audio_is_playing);
if (!render_audio_is_playing)
{
render_audio_toggle_pause(paused: false);
}
render_audio(ref audio_samples, ref audio_samples_added);
audio_w_pos = 0;
audio_samples_added = 0;
audio_timer = 0.0;
}
fps_time_token = GetTime() - fps_time_start;
fps_time_last = GetTime();
fps_time_frame_time = fps_time_last - fps_time_start;
fps_time_start = GetTime();
}
public static void EMUClockSamples(int samples_required, out int audio_added_samples)
{
int num = audio_samples_added;
while (samples_required > 0 && audio_w_pos < audio_samples_count)
{
CPUClock();
if (audio_samples_added - num >= 1)
{
samples_required--;
}
num = audio_samples_added;
}
audio_added_samples = audio_samples_added;
} }
private static void EmuClock() private static void EmuClock()
@ -5501,7 +5357,7 @@ namespace MyNes.Core
} }
} }
internal static void EmuClockComponentsNTSC() internal static void EmuClockComponents()
{ {
PPUClock(); PPUClock();
PollInterruptStatus(); PollInterruptStatus();
@ -5512,23 +5368,6 @@ namespace MyNes.Core
mem_board.OnCPUClock(); mem_board.OnCPUClock();
} }
internal static void EmuClockComponentsPALB()
{
PPUClock();
PollInterruptStatus();
PPUClock();
PPUClock();
pal_add_cycle++;
if (pal_add_cycle == 5)
{
pal_add_cycle = 0;
PPUClock();
}
APUClock();
DMAClock();
mem_board.OnCPUClock();
}
internal static void ApplyFrameSkipSettings() internal static void ApplyFrameSkipSettings()
{ {
FrameSkipEnabled = MyNesMain.RendererSettings.FrameSkipEnabled; FrameSkipEnabled = MyNesMain.RendererSettings.FrameSkipEnabled;
@ -5611,70 +5450,105 @@ namespace MyNes.Core
fps_time_period = period; fps_time_period = period;
} }
public static void GetTargetFPS(out double fps)
{
fps = emu_time_target_fps;
}
public static void ApplyRegionSetting() public static void ApplyRegionSetting()
{ {
switch ((RegionSetting)MyNesMain.EmuSettings.RegionSetting) switch ((RegionSetting)MyNesMain.EmuSettings.RegionSetting)
{ {
case RegionSetting.AUTO: case RegionSetting.AUTO:
{
Tracer.WriteLine("REGION = AUTO"); Tracer.WriteLine("REGION = AUTO");
Region = EmuRegion.NTSC; Region = EmuRegion.NTSC;
EmuClockComponents = EmuClockComponentsNTSC; if (CurrentFilePath.Contains("(E)"))
bool flag = false;
if (mem_board != null && mem_board.IsGameFoundOnDB)
{
Tracer.WriteLine("REGION SELECTION IS FROM DATABASE !!");
if (mem_board.GameCartInfo.System.ToUpper().Contains("PAL"))
{ {
Region = EmuRegion.PALB; Region = EmuRegion.PALB;
EmuClockComponents = EmuClockComponentsPALB;
flag = true;
}
else if (mem_board.GameCartInfo.System.ToUpper().Contains("DENDY"))
{
Region = EmuRegion.DENDY;
EmuClockComponents = EmuClockComponentsNTSC;
flag = true;
}
else
{
Region = EmuRegion.NTSC;
EmuClockComponents = EmuClockComponentsNTSC;
flag = true;
}
}
if (!flag && CurrentFilePath.Contains("(E)"))
{
Region = EmuRegion.PALB;
EmuClockComponents = EmuClockComponentsPALB;
} }
Tracer.WriteLine("REGION SELECTED: " + Region); Tracer.WriteLine("REGION SELECTED: " + Region);
break; break;
}
case RegionSetting.ForceNTSC: case RegionSetting.ForceNTSC:
Tracer.WriteLine("REGION: FORCE NTSC"); Tracer.WriteLine("REGION: FORCE NTSC");
Region = EmuRegion.NTSC; Region = EmuRegion.NTSC;
EmuClockComponents = EmuClockComponentsNTSC;
break; break;
case RegionSetting.ForcePALB: case RegionSetting.ForcePALB:
Tracer.WriteLine("REGION: FORCE PALB"); Tracer.WriteLine("REGION: FORCE PALB");
Region = EmuRegion.PALB; Region = EmuRegion.PALB;
EmuClockComponents = EmuClockComponentsPALB;
break; break;
case RegionSetting.ForceDENDY: case RegionSetting.ForceDENDY:
Tracer.WriteLine("REGION: FORCE DENDY"); Tracer.WriteLine("REGION: FORCE DENDY");
Region = EmuRegion.DENDY; Region = EmuRegion.DENDY;
EmuClockComponents = EmuClockComponentsNTSC;
break; break;
} }
SystemIndex = (int)Region; SystemIndex = (int)Region;
} }
public static void ApplyPaletteSetting()
{
Tracer.WriteLine("Loading palette generators values from settings...");
NTSCPaletteGenerator.brightness = MyNesMain.RendererSettings.Palette_NTSC_brightness;
NTSCPaletteGenerator.contrast = MyNesMain.RendererSettings.Palette_NTSC_contrast;
NTSCPaletteGenerator.gamma = MyNesMain.RendererSettings.Palette_NTSC_gamma;
NTSCPaletteGenerator.hue_tweak = MyNesMain.RendererSettings.Palette_NTSC_hue_tweak;
NTSCPaletteGenerator.saturation = MyNesMain.RendererSettings.Palette_NTSC_saturation;
PALBPaletteGenerator.brightness = MyNesMain.RendererSettings.Palette_PALB_brightness;
PALBPaletteGenerator.contrast = MyNesMain.RendererSettings.Palette_PALB_contrast;
PALBPaletteGenerator.gamma = MyNesMain.RendererSettings.Palette_PALB_gamma;
PALBPaletteGenerator.hue_tweak = MyNesMain.RendererSettings.Palette_PALB_hue_tweak;
PALBPaletteGenerator.saturation = MyNesMain.RendererSettings.Palette_PALB_saturation;
Tracer.WriteLine("Setting up palette ....");
switch ((PaletteSelectSetting)MyNesMain.RendererSettings.Palette_PaletteSetting)
{
case PaletteSelectSetting.AUTO:
Tracer.WriteLine("Palette set to auto detect depending on region.");
switch (Region)
{
case EmuRegion.NTSC:
SetupPalette(NTSCPaletteGenerator.GeneratePalette());
Tracer.WriteLine("Region is NTSC, Palette set from NTSC generator.");
break;
case EmuRegion.PALB:
case EmuRegion.DENDY:
SetupPalette(PALBPaletteGenerator.GeneratePalette());
Tracer.WriteLine("Region is PALB/DENDY, Palette set from PALB generator.");
break;
}
break;
case PaletteSelectSetting.ForceNTSC:
Tracer.WriteLine("Palette set to always use NTSC palette generator.");
SetupPalette(NTSCPaletteGenerator.GeneratePalette());
Tracer.WriteLine("Palette set from NTSC generator.");
break;
case PaletteSelectSetting.ForcePALB:
Tracer.WriteLine("Palette set to always use PALB palette generator.");
SetupPalette(NTSCPaletteGenerator.GeneratePalette());
Tracer.WriteLine("Palette set from PALB generator.");
break;
case PaletteSelectSetting.File:
{
Tracer.WriteLine("Palette set to load from file.");
string fullPath = Path.GetFullPath(MyNesMain.RendererSettings.Palette_CurrentPaletteFilePath);
if (File.Exists(fullPath))
{
PaletteFileWrapper.LoadFile(fullPath, out var palette);
SetupPalette(palette);
Tracer.WriteLine("Palette set from file: " + fullPath);
break;
}
Tracer.WriteError("Palette file: " + fullPath + " is not exist. Setting up palette from generators.");
switch (Region)
{
case EmuRegion.NTSC:
SetupPalette(NTSCPaletteGenerator.GeneratePalette());
Tracer.WriteLine("Region is NTSC, Palette set from NTSC generator.");
break;
case EmuRegion.PALB:
case EmuRegion.DENDY:
SetupPalette(PALBPaletteGenerator.GeneratePalette());
Tracer.WriteLine("Region is PALB/DENDY, Palette set from PALB generator.");
break;
}
break;
}
}
}
internal static void WriteStateData(ref BinaryWriter bin) internal static void WriteStateData(ref BinaryWriter bin)
{ {
APUWriteState(ref bin); APUWriteState(ref bin);

View File

@ -0,0 +1,109 @@
using System;
namespace MyNes.Core
{
public class PALBPaletteGenerator
{
public const float default_saturation = 1.496f;
public const float default_hue_tweak = 0f;
public const float default_contrast = 1.016f;
public const float default_brightness = 1.075f;
public const float default_gamma = 1.975f;
private const float black = 0.518f;
private const float white = 1.962f;
private const float attenuation = 0.746f;
public static float saturation = 2f;
public static float hue_tweak = 0f;
public static float contrast = 1.4f;
public static float brightness = 1.07f;
public static float gamma = 2f;
private static float[] levels = new float[8] { 0.35f, 0.518f, 0.962f, 1.55f, 1.094f, 1.506f, 1.962f, 1.962f };
private static int wave(int p, int color)
{
if ((color + p + 8) % 12 >= 6)
{
return 0;
}
return 1;
}
private static float gammafix(float f, float gamma)
{
return (float)((f < 0f) ? 0.0 : Math.Pow(f, 2.2f / gamma));
}
private static int clamp(float v)
{
return (int)((v < 0f) ? 0f : ((v > 255f) ? 255f : v));
}
public static int MakeRGBcolor(int pixel)
{
int num = pixel & 0xF;
int num2 = ((num >= 14) ? 1 : ((pixel >> 4) & 3));
float[] array = new float[2]
{
levels[num2 + ((num == 0) ? 4 : 0)],
levels[num2 + ((num <= 12) ? 4 : 0)]
};
float num3 = 0f;
float num4 = 0f;
float num5 = 0f;
for (int i = 0; i < 12; i++)
{
float num6 = array[wave(i, num)];
if ((((uint)pixel & 0x40u) != 0 && wave(i, 12) == 1) || (((uint)pixel & 0x80u) != 0 && wave(i, 4) == 1) || (((uint)pixel & 0x100u) != 0 && wave(i, 8) == 1))
{
num6 *= 0.746f;
}
float num7 = (num6 - 0.518f) / 1.444f;
num7 = (num7 - 0.5f) * contrast + 0.5f;
num7 *= brightness / 12f;
num3 += num7;
num4 += (float)((double)num7 * Math.Cos(Math.PI / 6.0 * (double)((float)i + 0.5f + hue_tweak)));
num5 += (float)((double)num7 * Math.Sin(Math.PI / 6.0 * (double)((float)i + 0.5f + hue_tweak)));
}
num4 *= saturation;
num5 *= saturation;
return 65536 * clamp(255f * gammafix(num3 + 0.946882f * num4 + 0.623557f * num5, gamma)) + 256 * clamp(255f * gammafix(num3 - 245f / (328f * (float)Math.E) * num4 - 0.635691f * num5, gamma)) + clamp(255f * gammafix(num3 - 1.108545f * num4 + 1.709007f * num5, gamma));
}
public static int[] GeneratePalette()
{
int[] array = new int[512];
for (int i = 0; i < 512; i++)
{
array[i] = MakeRGBcolor(i) | -16777216;
}
return array;
}
public static int[] GeneratePaletteGBR()
{
int[] array = new int[512];
for (int i = 0; i < 512; i++)
{
int num = MakeRGBcolor(i);
byte b = (byte)((num & 0xFF0000) >> 16);
byte b2 = (byte)((num & 0xFF00) >> 8);
byte b3 = (byte)((uint)num & 0xFFu);
array[i] = -16777216 | (b3 << 16) | (b2 << 8) | b;
}
return array;
}
}
}

View File

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 3a50696d24d84244db471bd77c8e8ace
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@ -0,0 +1,61 @@
using System.Collections.Generic;
using System.IO;
namespace MyNes.Core
{
public class PaletteFileWrapper
{
public static bool LoadFile(string file, out int[] palette)
{
Stream stream = new FileStream(file, FileMode.Open, FileAccess.Read);
if (stream.Length == 192 || stream.Length == 1536)
{
int[] array = new int[512];
byte[] array2 = new byte[stream.Length];
stream.Read(array2, 0, array2.Length);
int num = 0;
for (int i = 0; i < 512; i++)
{
byte b = array2[num];
num++;
if (num == array2.Length)
{
num = 0;
}
byte b2 = array2[num];
num++;
if (num == array2.Length)
{
num = 0;
}
byte b3 = array2[num];
num++;
if (num == array2.Length)
{
num = 0;
}
array[i] = -16777216 | (b << 16) | (b2 << 8) | b3;
}
stream.Close();
palette = array;
return true;
}
palette = null;
return false;
}
public static void SaveFile(string file, int[] palette)
{
Stream stream = new FileStream(file, FileMode.Create, FileAccess.Write);
List<byte> list = new List<byte>();
foreach (int num in palette)
{
list.Add((byte)((uint)(num >> 16) & 0xFFu));
list.Add((byte)((uint)(num >> 8) & 0xFFu));
list.Add((byte)((uint)num & 0xFFu));
}
stream.Write(list.ToArray(), 0, list.Count);
stream.Close();
}
}
}

View File

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: f15f9fdbee4f6704ebf4de045e49573c
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@ -1,3 +1,5 @@
using System.IO;
namespace MyNes.Core namespace MyNes.Core
{ {
public class RendererSettings : ISettings public class RendererSettings : ISettings
@ -6,34 +8,28 @@ namespace MyNes.Core
public bool Vid_AutoStretch = true; public bool Vid_AutoStretch = true;
public bool Vid_Res_Upscale = true; public int Vid_StretchMultiply = 3;
public int Vid_Res_W = 640; public bool Vid_KeepAspectRatio;
public int Vid_Res_H = 480; public bool Vid_ShowFPS;
public int Vid_StretchMultiply = 2; public bool Vid_HideLines = true;
public bool Vid_KeepAspectRatio = true; public bool Vid_Fullscreen;
public bool Vid_ShowFPS = false; public bool Vid_HardwareVertexProcessing;
public bool Vid_Fullscreen = false; public bool Vid_VSync;
public bool Vid_HardwareVertexProcessing = false;
public bool Vid_VSync = false;
public bool Vid_ShowNotifications = true; public bool Vid_ShowNotifications = true;
public int Vid_Filter = 1; public int Vid_Filter = 1;
public bool FrameSkipEnabled = false; public bool FrameSkipEnabled;
public int FrameSkipInterval = 2; public int FrameSkipInterval = 2;
public bool UseEmuThread = true;
public string Audio_ProviderID = ""; public string Audio_ProviderID = "";
public bool Audio_EnableFilters = true; public bool Audio_EnableFilters = true;
@ -42,17 +38,17 @@ namespace MyNes.Core
public bool Audio_SoundEnabled = true; public bool Audio_SoundEnabled = true;
public int Audio_Frequency = 44100; public int Audio_Frequency = 48000;
public int Audio_InternalSamplesCount = 4096; public int Audio_InternalSamplesCount = 1024;
public int Audio_InternalPeekLimit = 124; public int Audio_InternalPeekLimit = 124;
public int Audio_PlaybackAmplitude = 200; public int Audio_PlaybackAmplitude = 200;
public int Audio_PlaybackBufferSizeInKB = 8; public int Audio_PlaybackBufferSizeInKB = 16;
public bool Audio_UseDefaultMixer = true; public bool Audio_UseDefaultMixer;
public bool Audio_ChannelEnabled_SQ1 = true; public bool Audio_ChannelEnabled_SQ1 = true;
@ -98,9 +94,43 @@ namespace MyNes.Core
public bool Audio_ChannelEnabled_NMT8 = true; public bool Audio_ChannelEnabled_NMT8 = true;
public int Palette_PaletteSetting;
public string Palette_CurrentPaletteFilePath = "default_ntsc.pal";
public float Palette_NTSC_brightness = 1.075f;
public float Palette_NTSC_contrast = 1.016f;
public float Palette_NTSC_gamma = 1.975f;
public float Palette_NTSC_hue_tweak;
public float Palette_NTSC_saturation = 1.496f;
public float Palette_PALB_brightness = 1.075f;
public float Palette_PALB_contrast = 1.016f;
public float Palette_PALB_gamma = 1.975f;
public float Palette_PALB_hue_tweak;
public float Palette_PALB_saturation = 1.496f;
public RendererSettings(string path) public RendererSettings(string path)
: base(path) : base(path)
{ {
} }
public override void LoadSettings()
{
base.LoadSettings();
if (Palette_CurrentPaletteFilePath == "default_ntsc.pal" || Palette_CurrentPaletteFilePath == "" || !File.Exists(Palette_CurrentPaletteFilePath))
{
Palette_CurrentPaletteFilePath = Path.Combine(MyNesMain.AppPath, "Palettes");
Palette_CurrentPaletteFilePath = Path.Combine(Palette_CurrentPaletteFilePath, "default_ntsc.pal");
}
}
} }
} }

View File

@ -43,8 +43,7 @@ namespace MyNes.Core
return; return;
} }
IsSavingState = true; IsSavingState = true;
Stream output = new MemoryStream(); BinaryWriter bin = new BinaryWriter(new MemoryStream());
BinaryWriter bin = new BinaryWriter(output);
bin.Write(Encoding.ASCII.GetBytes("MNS")); bin.Write(Encoding.ASCII.GetBytes("MNS"));
bin.Write((byte)7); bin.Write((byte)7);
for (int i = 0; i < NesEmu.SHA1.Length; i += 2) for (int i = 0; i < NesEmu.SHA1.Length; i += 2)
@ -55,13 +54,13 @@ namespace MyNes.Core
NesEmu.WriteStateData(ref bin); NesEmu.WriteStateData(ref bin);
byte[] outData = new byte[0]; byte[] outData = new byte[0];
ZlipWrapper.CompressData(((MemoryStream)bin.BaseStream).GetBuffer(), out outData); ZlipWrapper.CompressData(((MemoryStream)bin.BaseStream).GetBuffer(), out outData);
Stream stream = new FileStream(fileName, FileMode.Create, FileAccess.Write); FileStream fileStream = new FileStream(fileName, FileMode.Create, FileAccess.Write);
stream.Write(outData, 0, outData.Length); fileStream.Write(outData, 0, outData.Length);
MyNesMain.VideoProvider.TakeSnapshotAs(fileName.Replace(".mns", ".jpg"), ".jpg"); MyNesMain.VideoProvider.TakeSnapshotAs(fileName.Replace(".mns", ".jpg"), ".jpg");
bin.Flush(); bin.Flush();
bin.Close(); bin.Close();
stream.Flush(); fileStream.Flush();
stream.Close(); fileStream.Close();
IsSavingState = false; IsSavingState = false;
Tracer.WriteInformation("State saved at slot " + Slot); Tracer.WriteInformation("State saved at slot " + Slot);
MyNesMain.VideoProvider.WriteInfoNotification(MNInterfaceLanguage.Message_Info1 + " " + Slot, instant: false); MyNesMain.VideoProvider.WriteInfoNotification(MNInterfaceLanguage.Message_Info1 + " " + Slot, instant: false);
@ -74,8 +73,7 @@ namespace MyNes.Core
StateFolder = Path.Combine(MyNesMain.WorkingFolder, "States"); StateFolder = Path.Combine(MyNesMain.WorkingFolder, "States");
} }
Directory.CreateDirectory(StateFolder); Directory.CreateDirectory(StateFolder);
string fileName = Path.Combine(StateFolder, Path.GetFileNameWithoutExtension(NesEmu.CurrentFilePath)) + "_" + Slot + ".mns"; SaveState(Path.Combine(StateFolder, Path.GetFileNameWithoutExtension(NesEmu.CurrentFilePath)) + "_" + Slot + ".mns", saveImage: false);
SaveState(fileName, saveImage: false);
} }
public static void SaveState() public static void SaveState()
@ -121,11 +119,11 @@ namespace MyNes.Core
return; return;
} }
IsLoadingState = true; IsLoadingState = true;
Stream stream = new FileStream(fileName, FileMode.Open, FileAccess.Read); FileStream fileStream = new FileStream(fileName, FileMode.Open, FileAccess.Read);
byte[] array = new byte[stream.Length]; byte[] array = new byte[fileStream.Length];
byte[] outData = new byte[0]; byte[] outData = new byte[0];
stream.Read(array, 0, array.Length); fileStream.Read(array, 0, array.Length);
stream.Close(); fileStream.Close();
ZlipWrapper.DecompressData(array, out outData); ZlipWrapper.DecompressData(array, out outData);
BinaryReader bin = new BinaryReader(new MemoryStream(outData)); BinaryReader bin = new BinaryReader(new MemoryStream(outData));
byte[] array2 = new byte[3]; byte[] array2 = new byte[3];
@ -172,8 +170,7 @@ namespace MyNes.Core
StateFolder = Path.Combine(MyNesMain.WorkingFolder, "States"); StateFolder = Path.Combine(MyNesMain.WorkingFolder, "States");
} }
Directory.CreateDirectory(StateFolder); Directory.CreateDirectory(StateFolder);
string fileName = Path.Combine(StateFolder, Path.GetFileNameWithoutExtension(NesEmu.CurrentFilePath)) + "_" + Slot + ".mns"; LoadState(Path.Combine(StateFolder, Path.GetFileNameWithoutExtension(NesEmu.CurrentFilePath)) + "_" + Slot + ".mns");
LoadState(fileName);
} }
public static string GetStateFile(int slot) public static string GetStateFile(int slot)

View File

@ -8,7 +8,7 @@ namespace MyNes.Core
internal byte Volume; internal byte Volume;
private int dutyStep = 0; private int dutyStep;
private int freqTimer; private int freqTimer;

View File

@ -1,4 +1,6 @@
#define TRACE
using System; using System;
using System.Diagnostics;
namespace MyNes.Core namespace MyNes.Core
{ {
@ -9,21 +11,25 @@ namespace MyNes.Core
public static void WriteLine(string message) public static void WriteLine(string message)
{ {
Tracer.EventRaised?.Invoke(null, new TracerEventArgs(message, TracerStatus.Normal)); Tracer.EventRaised?.Invoke(null, new TracerEventArgs(message, TracerStatus.Normal));
Trace.WriteLine(message);
} }
public static void WriteLine(string message, string category) public static void WriteLine(string message, string category)
{ {
Tracer.EventRaised?.Invoke(null, new TracerEventArgs($"{category}: {message}", TracerStatus.Normal)); Tracer.EventRaised?.Invoke(null, new TracerEventArgs($"{category}: {message}", TracerStatus.Normal));
Trace.WriteLine($"{category}: {message}");
} }
public static void WriteLine(string message, TracerStatus status) public static void WriteLine(string message, TracerStatus status)
{ {
Tracer.EventRaised?.Invoke(null, new TracerEventArgs(message, status)); Tracer.EventRaised?.Invoke(null, new TracerEventArgs(message, status));
Trace.WriteLine(message);
} }
public static void WriteLine(string message, string category, TracerStatus status) public static void WriteLine(string message, string category, TracerStatus status)
{ {
Tracer.EventRaised?.Invoke(null, new TracerEventArgs($"{category}: {message}", status)); Tracer.EventRaised?.Invoke(null, new TracerEventArgs($"{category}: {message}", status));
Trace.WriteLine($"{category}: {message}");
} }
public static void WriteError(string message) public static void WriteError(string message)

View File

@ -12,7 +12,7 @@ namespace MyNes.Core
internal bool Outputable; internal bool Outputable;
private bool mode = false; private bool mode;
private byte volume; private byte volume;

View File

@ -10,15 +10,15 @@ namespace MyNes.Core
private Stream STR; private Stream STR;
private bool _IsRecording = false; private bool _IsRecording;
private int SIZE = 0; private int SIZE;
private int NoOfSamples = 0; private int NoOfSamples;
private int _Time = 0; private int _Time;
private int TimeSamples = 0; private int TimeSamples;
private short channels; private short channels;

View File

@ -92,6 +92,7 @@ namespace AxibugEmuOnline.Client.Manager
sevenZipExtractor.ExtractFiles(text2, fileNames); sevenZipExtractor.ExtractFiles(text2, fileNames);
text = text2 + formFilesList.SelectedRom; text = text2 + formFilesList.SelectedRom;
} }
NesEmu.LoadGame(text, out success); NesEmu.LoadGame(text, out success);
break; break;
} }