GB layers (#2490)
* Fixed OBJ layer toggle message (it was using the flag from BG toggle) * Added hotkey option for GB Window layer toggle * Added hotkey option for GB Window layer toggle * GB object viewer prototype [Gambatte] GPU Viewer add-on to display sprite tiles on the real position, just like what you have for the bsnes core Has several issues: - Drawing is identical to the current sprite display, so it doesn't have the transparency it should have; - Drawing doesn't take priority into account, so overlapping is usually wrong; - The drawing flickers, probably the way of refreshing (with `.Clear()`) is bad.
This commit is contained in:
parent
0aea6191ae
commit
81ef9ed88b
|
@ -240,6 +240,7 @@ namespace BizHawk.Client.Common
|
|||
|
||||
Bind("GB", "GB Toggle BG"),
|
||||
Bind("GB", "GB Toggle Obj"),
|
||||
Bind("GB", "GB Toggle Window"),
|
||||
|
||||
Bind("Analog", "Y Up Small", toolTip: "For Virtual Pad"),
|
||||
Bind("Analog", "Y Up Large", toolTip: "For Virtual Pad"),
|
||||
|
|
|
@ -710,7 +710,17 @@ namespace BizHawk.Client.EmuHawk
|
|||
var s = gb2.GetSettings();
|
||||
s.DisplayOBJ ^= true;
|
||||
gb2.PutSettings(s);
|
||||
AddOnScreenMessage($"OBJ toggled {(s.DisplayBG ? "on" : "off")}");
|
||||
AddOnScreenMessage($"OBJ toggled {(s.DisplayOBJ ? "on" : "off")}");
|
||||
}
|
||||
|
||||
break;
|
||||
case "GB Toggle Window":
|
||||
if (Emulator is Gameboy gb3)
|
||||
{
|
||||
var s = gb3.GetSettings();
|
||||
s.DisplayWindow ^= true;
|
||||
gb3.PutSettings(s);
|
||||
AddOnScreenMessage($"WIN toggled {(s.DisplayWindow ? "on" : "off")}");
|
||||
}
|
||||
|
||||
break;
|
||||
|
|
|
@ -38,6 +38,8 @@
|
|||
this.groupBox2 = new System.Windows.Forms.GroupBox();
|
||||
this.groupBox3 = new System.Windows.Forms.GroupBox();
|
||||
this.label7 = new BizHawk.WinForms.Controls.LocLabelEx();
|
||||
this.label8 = new BizHawk.WinForms.Controls.LocLabelEx();
|
||||
this.label9 = new BizHawk.WinForms.Controls.LocLabelEx();
|
||||
this.groupBox4 = new System.Windows.Forms.GroupBox();
|
||||
this.groupBox5 = new System.Windows.Forms.GroupBox();
|
||||
this.hScrollBarScanline = new System.Windows.Forms.HScrollBar();
|
||||
|
@ -60,6 +62,7 @@
|
|||
this.bmpViewMemory = new BizHawk.Client.EmuHawk.BmpView();
|
||||
this.bmpViewDetails = new BizHawk.Client.EmuHawk.BmpView();
|
||||
this.bmpViewOAM = new BizHawk.Client.EmuHawk.BmpView();
|
||||
this.bmpViewOBJ = new BizHawk.Client.EmuHawk.BmpView();
|
||||
this.bmpViewBGPal = new BizHawk.Client.EmuHawk.BmpView();
|
||||
this.bmpViewSPPal = new BizHawk.Client.EmuHawk.BmpView();
|
||||
this.bmpViewTiles1 = new BizHawk.Client.EmuHawk.BmpView();
|
||||
|
@ -159,15 +162,30 @@
|
|||
this.label7.Name = "label7";
|
||||
this.label7.Text = "Left-click a palette to use it for drawing the tiles display.";
|
||||
//
|
||||
// label8
|
||||
//
|
||||
this.label8.Location = new System.Drawing.Point(3, 16);
|
||||
this.label8.Name = "label8";
|
||||
this.label8.Text = "Sprites";
|
||||
//
|
||||
// label9
|
||||
//
|
||||
this.label9.Location = new System.Drawing.Point(3, 52);
|
||||
this.label9.Name = "label9";
|
||||
this.label9.Text = "Objects";
|
||||
//
|
||||
// groupBox4
|
||||
//
|
||||
this.groupBox4.Controls.Add(this.bmpViewOAM);
|
||||
this.groupBox4.Controls.Add(this.bmpViewOBJ);
|
||||
this.groupBox4.Controls.Add(this.label8);
|
||||
this.groupBox4.Controls.Add(this.label9);
|
||||
this.groupBox4.Location = new System.Drawing.Point(12, 327);
|
||||
this.groupBox4.Name = "groupBox4";
|
||||
this.groupBox4.Size = new System.Drawing.Size(332, 41);
|
||||
this.groupBox4.Size = new System.Drawing.Size(332, 331);
|
||||
this.groupBox4.TabIndex = 19;
|
||||
this.groupBox4.TabStop = false;
|
||||
this.groupBox4.Text = "Sprites";
|
||||
this.groupBox4.Text = "OAM";
|
||||
//
|
||||
// groupBox5
|
||||
//
|
||||
|
@ -250,9 +268,9 @@
|
|||
//
|
||||
this.groupBoxDetails.Controls.Add(this.labelDetails);
|
||||
this.groupBoxDetails.Controls.Add(this.bmpViewDetails);
|
||||
this.groupBoxDetails.Location = new System.Drawing.Point(12, 374);
|
||||
this.groupBoxDetails.Location = new System.Drawing.Point(350, 327);
|
||||
this.groupBoxDetails.Name = "groupBoxDetails";
|
||||
this.groupBoxDetails.Size = new System.Drawing.Size(262, 153);
|
||||
this.groupBoxDetails.Size = new System.Drawing.Size(192, 153);
|
||||
this.groupBoxDetails.TabIndex = 21;
|
||||
this.groupBoxDetails.TabStop = false;
|
||||
this.groupBoxDetails.Text = "Details";
|
||||
|
@ -260,7 +278,7 @@
|
|||
// labelDetails
|
||||
//
|
||||
this.labelDetails.Location = new System.Drawing.Point(76, 16);
|
||||
this.labelDetails.MaximumSize = new System.Drawing.Size(150, 0);
|
||||
this.labelDetails.MaximumSize = new System.Drawing.Size(115, 0);
|
||||
this.labelDetails.Name = "labelDetails";
|
||||
this.labelDetails.Text = "Mouse over an item to see details about it.";
|
||||
//
|
||||
|
@ -268,9 +286,9 @@
|
|||
//
|
||||
this.groupBoxMemory.Controls.Add(this.bmpViewMemory);
|
||||
this.groupBoxMemory.Controls.Add(this.labelMemory);
|
||||
this.groupBoxMemory.Location = new System.Drawing.Point(280, 374);
|
||||
this.groupBoxMemory.Location = new System.Drawing.Point(350, 486);
|
||||
this.groupBoxMemory.Name = "groupBoxMemory";
|
||||
this.groupBoxMemory.Size = new System.Drawing.Size(262, 153);
|
||||
this.groupBoxMemory.Size = new System.Drawing.Size(192, 153);
|
||||
this.groupBoxMemory.TabIndex = 22;
|
||||
this.groupBoxMemory.TabStop = false;
|
||||
this.groupBoxMemory.Text = "Details - Memory";
|
||||
|
@ -278,7 +296,7 @@
|
|||
// labelMemory
|
||||
//
|
||||
this.labelMemory.Location = new System.Drawing.Point(76, 16);
|
||||
this.labelMemory.MaximumSize = new System.Drawing.Size(150, 0);
|
||||
this.labelMemory.MaximumSize = new System.Drawing.Size(115, 0);
|
||||
this.labelMemory.Name = "labelMemory";
|
||||
this.labelMemory.Text = "Right-click an item to display it here.";
|
||||
//
|
||||
|
@ -314,7 +332,7 @@
|
|||
//
|
||||
this.labelSpriteBackColor.Location = new System.Drawing.Point(67, 24);
|
||||
this.labelSpriteBackColor.Name = "labelSpriteBackColor";
|
||||
this.labelSpriteBackColor.Text = "label8";
|
||||
this.labelSpriteBackColor.Text = "label10";
|
||||
//
|
||||
// buttonChangeColor
|
||||
//
|
||||
|
@ -364,7 +382,7 @@
|
|||
// bmpViewOAM
|
||||
//
|
||||
this.bmpViewOAM.BackColor = System.Drawing.Color.Black;
|
||||
this.bmpViewOAM.Location = new System.Drawing.Point(6, 19);
|
||||
this.bmpViewOAM.Location = new System.Drawing.Point(6, 32);
|
||||
this.bmpViewOAM.Name = "bmpViewOAM";
|
||||
this.bmpViewOAM.Size = new System.Drawing.Size(320, 16);
|
||||
this.bmpViewOAM.TabIndex = 14;
|
||||
|
@ -374,6 +392,19 @@
|
|||
this.bmpViewOAM.MouseLeave += new System.EventHandler(this.bmpViewOAM_MouseLeave);
|
||||
this.bmpViewOAM.MouseMove += new System.Windows.Forms.MouseEventHandler(this.bmpViewOAM_MouseMove);
|
||||
//
|
||||
// bmpViewOBJ
|
||||
//
|
||||
this.bmpViewOBJ.BackColor = System.Drawing.Color.Black;
|
||||
this.bmpViewOBJ.Location = new System.Drawing.Point(6, 67);
|
||||
this.bmpViewOBJ.Name = "bmpViewOBJ";
|
||||
this.bmpViewOBJ.Size = new System.Drawing.Size(256, 256);
|
||||
this.bmpViewOBJ.TabIndex = 15;
|
||||
this.bmpViewOBJ.Text = "Objects";
|
||||
this.bmpViewOBJ.MouseClick += new System.Windows.Forms.MouseEventHandler(this.bmpView_MouseClick);
|
||||
this.bmpViewOBJ.MouseEnter += new System.EventHandler(this.bmpViewOBJ_MouseEnter);
|
||||
this.bmpViewOBJ.MouseLeave += new System.EventHandler(this.bmpViewOBJ_MouseLeave);
|
||||
this.bmpViewOBJ.MouseMove += new System.Windows.Forms.MouseEventHandler(this.bmpViewOBJ_MouseMove);
|
||||
//
|
||||
// bmpViewBGPal
|
||||
//
|
||||
this.bmpViewBGPal.BackColor = System.Drawing.Color.Black;
|
||||
|
@ -456,7 +487,7 @@
|
|||
//
|
||||
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
|
||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||
this.ClientSize = new System.Drawing.Size(834, 593);
|
||||
this.ClientSize = new System.Drawing.Size(834, 664);
|
||||
this.Controls.Add(this.groupBox8);
|
||||
this.Controls.Add(this.groupBox6);
|
||||
this.Controls.Add(this.groupBoxMemory);
|
||||
|
@ -480,6 +511,7 @@
|
|||
this.groupBox3.ResumeLayout(false);
|
||||
this.groupBox3.PerformLayout();
|
||||
this.groupBox4.ResumeLayout(false);
|
||||
this.groupBox4.PerformLayout();
|
||||
this.groupBox5.ResumeLayout(false);
|
||||
this.groupBox5.PerformLayout();
|
||||
this.groupBoxDetails.ResumeLayout(false);
|
||||
|
@ -510,6 +542,7 @@
|
|||
private BizHawk.WinForms.Controls.LocLabelEx label5;
|
||||
private BizHawk.WinForms.Controls.LocLabelEx label6;
|
||||
private BmpView bmpViewOAM;
|
||||
private BmpView bmpViewOBJ;
|
||||
private System.Windows.Forms.GroupBox groupBox1;
|
||||
private System.Windows.Forms.GroupBox groupBox2;
|
||||
private System.Windows.Forms.GroupBox groupBox3;
|
||||
|
@ -528,6 +561,8 @@
|
|||
private BizHawk.WinForms.Controls.LocLabelEx labelMemory;
|
||||
private BmpView bmpViewMemory;
|
||||
private BizHawk.WinForms.Controls.LocLabelEx label7;
|
||||
private BizHawk.WinForms.Controls.LocLabelEx label8;
|
||||
private BizHawk.WinForms.Controls.LocLabelEx label9;
|
||||
private System.Windows.Forms.GroupBox groupBox6;
|
||||
private BizHawk.WinForms.Controls.LocLabelEx labelClipboard;
|
||||
private System.Windows.Forms.GroupBox groupBox8;
|
||||
|
|
|
@ -67,6 +67,7 @@ namespace BizHawk.Client.EmuHawk
|
|||
bmpViewBGPal.ChangeBitmapSize(8, 4);
|
||||
bmpViewSPPal.ChangeBitmapSize(8, 4);
|
||||
bmpViewOAM.ChangeBitmapSize(320, 16);
|
||||
bmpViewOBJ.ChangeBitmapSize(256, 256);
|
||||
bmpViewDetails.ChangeBitmapSize(8, 16);
|
||||
bmpViewMemory.ChangeBitmapSize(8, 16);
|
||||
|
||||
|
@ -97,6 +98,7 @@ namespace BizHawk.Client.EmuHawk
|
|||
bmpViewBGPal.Clear();
|
||||
bmpViewSPPal.Clear();
|
||||
bmpViewOAM.Clear();
|
||||
bmpViewOBJ.Clear();
|
||||
bmpViewDetails.Clear();
|
||||
bmpViewMemory.Clear();
|
||||
_cbScanlineEmu = -4; // force refresh
|
||||
|
@ -329,6 +331,63 @@ namespace BizHawk.Client.EmuHawk
|
|||
b.UnlockBits(lockData);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// draw objects from oam data
|
||||
/// </summary>
|
||||
/// <param name="b">bitmap to draw to. should be 320x8 (!tall), 320x16 (tall)</param>
|
||||
/// <param name="_oam">oam data, 4 * 40 bytes</param>
|
||||
/// <param name="_tiles">base tiledata location. cgb: second bank tiledata assumed to be @+8k</param>
|
||||
/// <param name="_pal">2 (dmg) or 8 (cgb) palettes</param>
|
||||
/// <param name="tall">true for 8x16 sprites; else 8x8</param>
|
||||
/// <param name="cgb">true for cgb (more palettes, second bank tiles)</param>
|
||||
private static unsafe void DrawObj(Bitmap b, IntPtr _oam, IntPtr _tiles, IntPtr _pal, bool tall, bool cgb)
|
||||
{
|
||||
var lockData = b.LockBits(new Rectangle(0, 0, 256, 256), ImageLockMode.WriteOnly, PixelFormat.Format32bppArgb);
|
||||
int* dest = (int*)lockData.Scan0;
|
||||
int pitch = lockData.Stride / sizeof(int);
|
||||
int* pal = (int*)_pal;
|
||||
byte* oam = (byte*)_oam;
|
||||
|
||||
for (int s = 0; s < 40; s++)
|
||||
{
|
||||
int yPos = *oam++;
|
||||
int xPos = *oam++;
|
||||
dest += xPos + yPos * pitch;
|
||||
int tileIndex = *oam++;
|
||||
int flags = *oam++;
|
||||
bool vFlip = flags.Bit(6);
|
||||
bool hFlip = flags.Bit(5);
|
||||
if (tall)
|
||||
{
|
||||
// i assume 8x16 vFlip flips the whole thing, not just each tile?
|
||||
if (vFlip)
|
||||
{
|
||||
tileIndex |= 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
tileIndex &= 0xfe;
|
||||
}
|
||||
}
|
||||
|
||||
byte* tile = (byte*)(_tiles + tileIndex * 16);
|
||||
int* thisPal = pal + 4 * (cgb ? flags & 7 : flags >> 4 & 1);
|
||||
if (cgb && flags.Bit(3))
|
||||
tile += 8192;
|
||||
|
||||
DrawTileHv(tile, dest, pitch, thisPal, hFlip, vFlip);
|
||||
|
||||
if (tall)
|
||||
{
|
||||
DrawTileHv(tile + 16, dest + pitch * 8, pitch, thisPal, hFlip, vFlip);
|
||||
}
|
||||
|
||||
dest -= xPos + yPos * pitch;
|
||||
}
|
||||
|
||||
b.UnlockBits(lockData);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// draw a palette directly
|
||||
/// </summary>
|
||||
|
@ -455,7 +514,7 @@ namespace BizHawk.Client.EmuHawk
|
|||
bmpViewBGPal.Refresh();
|
||||
bmpViewSPPal.Refresh();
|
||||
|
||||
// oam
|
||||
// oam (sprites)
|
||||
if (lcdc.Bit(2)) // 8x16
|
||||
{
|
||||
bmpViewOAM.ChangeBitmapSize(320, 16);
|
||||
|
@ -470,6 +529,11 @@ namespace BizHawk.Client.EmuHawk
|
|||
}
|
||||
DrawOam(bmpViewOAM.Bmp, oam, vram, spPal, lcdc.Bit(2), _cgb);
|
||||
bmpViewOAM.Refresh();
|
||||
|
||||
// oam (objects)
|
||||
bmpViewOBJ.Clear();
|
||||
DrawObj(bmpViewOBJ.Bmp, oam, vram, spPal, lcdc.Bit(2), _cgb);
|
||||
bmpViewOBJ.Refresh();
|
||||
}
|
||||
// try to run the current mouseover, to refresh if the mouse is being held over a pane while the emulator runs
|
||||
// this doesn't really work well; the update rate seems to be throttled
|
||||
|
@ -887,6 +951,22 @@ namespace BizHawk.Client.EmuHawk
|
|||
SpriteMouseover(e.X, e.Y);
|
||||
}
|
||||
|
||||
private void bmpViewOBJ_MouseEnter(object sender, EventArgs e)
|
||||
{
|
||||
SaveDetails();
|
||||
groupBoxDetails.Text = "Details - Objects";
|
||||
}
|
||||
|
||||
private void bmpViewOBJ_MouseLeave(object sender, EventArgs e)
|
||||
{
|
||||
LoadDetails();
|
||||
}
|
||||
|
||||
private void bmpViewOBJ_MouseMove(object sender, MouseEventArgs e)
|
||||
{
|
||||
SpriteMouseover(e.X, e.Y);
|
||||
}
|
||||
|
||||
private void bmpView_MouseClick(object sender, MouseEventArgs e)
|
||||
{
|
||||
if (e.Button == MouseButtons.Right)
|
||||
|
|
Loading…
Reference in New Issue