private void EvaluateSprites() { for (int i = 0; i < spritesNumber; ++i) { currentScanlineSprites[i].Reset(); } spritesNumber = 0; spriteZeroSelected = false; statusRegister.SpriteOverflow = false; // decide which sprites are visible on current scanline for (int i = 0; i < 64; ++i) { ObjectAttributeEntry currentSprite = Oam.EntryAt(i); int diff = scanLine - currentSprite.Y; if (diff >= 0 && diff < (controlRegister.SpriteSize ? 16 : 8)) { if (spritesNumber == 8) { statusRegister.SpriteOverflow = true; break; } // clone because we are modifying X value in each cycle currentScanlineSprites[spritesNumber++] = currentSprite.Clone() as ObjectAttributeEntry; // sprite zero is in current scanline if (i == 0) { spriteZeroSelected = true; } } } }
private NesSprite GetSprite(Oam oam) { bool flipHor = (oam.Attributes & 0b01000000) != 0; bool flipVer = (oam.Attributes & 0b10000000) != 0; return(GetSprite(0, oam.Id, oam.Attributes & 3, flipVer, flipHor)); }
public OamViewModel(Oam oam) { Oam = oam; OamResolutions = new Dictionary <string, int>() { ["8 x 8"] = 0, ["16 x 8"] = 1, ["32 x 8"] = 2, ["8 x 16"] = 3, ["16 x 16"] = 4, ["32 x 16"] = 5, ["8 x 32"] = 6, ["16 x 32"] = 7, ["32 x 32"] = 8, ["64 x 32"] = 9, ["32 x 64"] = 10, ["64 x 64"] = 11 }; X = oam.X; Y = oam.Y; Width = oam.Width; Height = oam.Height; OBJSize = oam.OBJSize; TileId = oam.TileId; Priority = oam.Priority; PaletteId = oam.PaletteId; RotateOrScaling = oam.RotateOrScaling; Mozaic = oam.Mozaic; HorizontalFlip = oam.HorizontalFlip; VerticalFlip = oam.VerticalFlip; }
public static Bitmap MarkSelectOam(Bitmap image, Oam oam) { Bitmap copy = image.Clone(new Rectangle(0, 0, image.Width, image.Height), image.PixelFormat); using (Graphics g = Graphics.FromImage(copy)) { Rectangle rect = new Rectangle((int)oam.X, (int)oam.Y, (int)oam.Width, (int)oam.Height); Pen pen = new Pen(Color.Red, 2); g.DrawRectangle(pen, rect); } copy.MakeTransparent(); return(copy); }
/// <summary> /// oamメモリへの書き込み /// </summary> /// <param name="offset">Offset.</param> /// <param name="x">The x coordinate.</param> /// <param name="y">The y coordinate.</param> /// <param name="tile">Tile.</param> /// <param name="attr">Attr.</param> public void WriteOamTable(int offset, int x, int y, int tile, int attr) { if (spritePosition[offset] != null) { foreach (int position in spritePosition[offset]) { spriteRenderPosition.Remove(position); } spritePosition[offset] = null; } bool spriteHit = false; if (offset == 0) { spriteHit = true; } int tileID = tile; int patternTableNumber = SpritePatternTable; if (SpriteSize > 8) { patternTableNumber = Nes.FetchBit(tileID, 0) * 256; tileID = 2 * (tileID >> 1); } bool verticalReverse = Nes.FetchBit(attr, 7) == 1; bool horizontalReverse = Nes.FetchBit(attr, 6) == 1; bool priority = Nes.FetchBit(attr, 5) == 0; int palette = Nes.FetchBit(attr, 1) * 2 + Nes.FetchBit(attr, 0); oamTable[offset] = new Oam { X = x, Y = y + 1, TileID = tileID, PatternTable = patternTableNumber, HorizontalReverse = horizontalReverse, VerticalReverse = verticalReverse, Priority = priority, Palette = palette, SpriteHit = spriteHit }; spritePosition[offset] = new List <int>(); for (int i = x + y * 256, k = 0; i < SpriteSize * 256 + y * 256 + x; i += 256, k++) { for (int j = 0; j < 8; j++) { if (!spriteRenderPosition.ContainsKey(i + j)) { spriteRenderPosition.Add(i + j, oamTable[offset]); } else { spriteRenderPosition[i + j] = oamTable[offset]; } spritePosition[offset].Add(i + j); } if (k == 7) { oamTable[offset] = new Oam { X = x, Y = y + 9, TileID = tileID + 1, PatternTable = patternTableNumber, HorizontalReverse = horizontalReverse, VerticalReverse = verticalReverse, Priority = priority, Palette = palette }; } } }