private void ExportGif(string filename) { uint mapid = this.MapPictureBox.GetMapID(); if (mapid == U.NOT_FOUND) { return; } MapSettingForm.PLists plist = MapSettingForm.GetMapPListsWhereMapID(mapid); if (plist.palette_plist == 0) { return; } uint palette = MapPointerForm.PlistToOffsetAddr(MapPointerForm.PLIST_TYPE.PALETTE, plist.palette_plist); if (palette == U.NOT_FOUND) { return; } int palette_index = SamplePaletteComboBox.SelectedIndex; if (palette_index < 0) { palette_index = 0; } uint addr = InputFormRef.BaseAddress; if (!U.isSafetyOffset(addr)) { return; } //同じアニメを何度も出力しないように記録する. List <ImageUtilAnimeGif.Frame> bitmaps = new List <ImageUtilAnimeGif.Frame>(); for (int i = 0; i < InputFormRef.DataCount; i++, addr += InputFormRef.BlockSize) { uint wait = Program.ROM.u16(addr + 0); uint length = Program.ROM.u16(addr + 2); uint p4 = Program.ROM.p32(addr + 4); if (!U.isSafetyOffset(p4)) { continue; } MapSettingForm.MapAnimations anime = new MapSettingForm.MapAnimations(); anime.change_bitmap_bytes = GetTileAnime1(p4, length); Bitmap mapBitmap = MapSettingForm.DrawMap(mapid, anime); bitmaps.Add(new ImageUtilAnimeGif.Frame(mapBitmap, wait)); } //アニメgif生成 ImageUtilAnimeGif.SaveAnimatedGif(filename, bitmaps); U.SelectFileByExplorer(filename); }
private void AddressList_SelectedIndexChanged(object sender, EventArgs e) { uint mapid = this.MapPictureBox.GetMapID(); if (mapid == U.NOT_FOUND) { return; } N_InputFormRef.ReInit((uint)P0.Value, (uint)B5.Value); MapSettingForm.MapAnimations anime = new MapSettingForm.MapAnimations(); anime.change_palette_bytes = GetTileAnime2((uint)P0.Value, (uint)B5.Value); anime.change_palette_start_index = (uint)B6.Value; //マップの再描画 this.MapPictureBox.UpdateAnime(anime); }
private void AddressList_SelectedIndexChanged(object sender, EventArgs e) { uint mapid = this.MapPictureBox.GetMapID(); if (mapid == U.NOT_FOUND) { return; } MapSettingForm.PLists plist = MapSettingForm.GetMapPListsWhereMapID(mapid); if (plist.palette_plist == 0) { return; } uint palette = MapPointerForm.PlistToOffsetAddr(MapPointerForm.PLIST_TYPE.PALETTE, plist.palette_plist); if (palette == U.NOT_FOUND) { return; } int palette_index = SamplePaletteComboBox.SelectedIndex; if (palette_index < 0) { palette_index = 0; } this.ChangePaletteBitmap = GetTileAnime1((uint)P4.Value, (uint)W2.Value, palette, palette_index); this.X_SAMPLE_BIG_PIC.Image = this.ChangePaletteBitmap; MapSettingForm.MapAnimations anime = new MapSettingForm.MapAnimations(); anime.change_bitmap_bytes = GetTileAnime1((uint)P4.Value, (uint)W2.Value); //マップの再描画 this.MapPictureBox.UpdateAnime(anime); }
public void UpdateAnime(MapSettingForm.MapAnimations anime) { this.MapAnime = anime; ChangeComboBox_SelectedIndexChanged(null, null); }
//マップの部分変更 public static Bitmap DrawChangeMap( uint obj_plist , uint palette_plist , uint config_plist , int width , int height , uint change_address , MapSettingForm.MapAnimations anime = null ) { change_address = U.toOffset(change_address); if (!U.isSafetyOffset(change_address)) { return(ImageUtil.BlankDummy()); } //マップチップの読込 Bitmap obj_image = DrawMapChipOnly(obj_plist, palette_plist, anime); if (obj_image == null) { return(ImageUtil.BlankDummy()); } //チップセットの読込(マップチップの画像をどう解釈するか定義するデータ) byte[] configUZ = UnLZ77ChipsetData(config_plist); if (configUZ == null) { return(ImageUtil.BlankDummy()); } //マップ変更の場合、幅高さはユーザが指定する. UInt16[] tsa = new UInt16[(width * 2) * (height * 2)]; int x = 0; int y = 0; int length = width * height * 2; if (!U.isSafetyOffset(change_address + (uint)length - 1)) {//サイズ超過. R.Error("map size over {0}-{1}", U.ToHexString(change_address), U.ToHexString(length)); return(ImageUtil.BlankDummy()); } for (int i = 0; i + 1 < length; i += 2) { //マップデータを読む int m = (int)Program.ROM.u16((uint)(change_address + i)); int tile_tsa_index = m << 1; if (tile_tsa_index + 7 >= configUZ.Length) {//不正なTSA return(ImageUtil.BlankDummy(16)); } //チップセットのTSAデータを読み込む. UInt16 lefttop = (UInt16)(configUZ[tile_tsa_index] + ((UInt16)configUZ[tile_tsa_index + 1] << 8)); UInt16 righttop = (UInt16)(configUZ[tile_tsa_index + 2] + ((UInt16)configUZ[tile_tsa_index + 3] << 8)); UInt16 leftbottom = (UInt16)(configUZ[tile_tsa_index + 4] + ((UInt16)configUZ[tile_tsa_index + 5] << 8)); UInt16 rightbottom = (UInt16)(configUZ[tile_tsa_index + 6] + ((UInt16)configUZ[tile_tsa_index + 7] << 8)); tsa[(x) + ((y) * (width * 2))] = lefttop; tsa[(x + 1) + ((y) * (width * 2))] = righttop; tsa[(x) + ((y + 1) * (width * 2))] = leftbottom; tsa[(x + 1) + ((y + 1) * (width * 2))] = rightbottom; x += 2; if (x >= width * 2) { x = 0; y += 2; if (y >= height * 2) { break; } } } Bitmap mapcanvas = ImageUtil.Blank(width * 16, height * 16, obj_image); ImageUtil.BitBltTSA(mapcanvas, obj_image, tsa, 0); return(mapcanvas); }
//マップを描画する. public static Bitmap DrawMap( uint obj_plist //image , uint palette_plist //palette , uint config_plist //tsa , uint mappointer_plist //mar , MapSettingForm.MapAnimations anime = null ) { //マップチップの読込 Bitmap obj_image = DrawMapChipOnly(obj_plist, palette_plist, anime); if (obj_image == null) { return(ImageUtil.BlankDummy()); } //チップセットの読込(マップチップの画像をどう解釈するか定義するデータ) byte[] configUZ = UnLZ77ChipsetData(config_plist); if (configUZ == null) { return(ImageUtil.BlankDummy()); } //マップ配置データの読込 byte[] mappointerUZ = UnLZ77MapData(mappointer_plist); if (mappointerUZ == null) { return(ImageUtil.BlankDummy()); } if (mappointerUZ.Length < 2) { Debug.Assert(false); return(ImageUtil.BlankDummy()); } //マップデータの先頭2バイトにマップの幅高さが入っている. //チップの数なので、 16*width=ピクセル 16*height=ピクセル である. int width = mappointerUZ[0]; int height = mappointerUZ[1]; if (width <= 0 || height <= 0) {//サイズが不正 return(ImageUtil.BlankDummy()); } UInt16[] tsa = new UInt16[(width * 2) * (height * 2)]; int x = 0; int y = 0; for (int i = 2; i + 1 < mappointerUZ.Length; i += 2) { //マップデータを読む int m = (mappointerUZ[i] + ((UInt16)mappointerUZ[i + 1] << 8)); int tile_tsa_index = m << 1; if (tile_tsa_index + 7 >= configUZ.Length) {//不正なTSA return(ImageUtil.BlankDummy()); } //チップセットのTSAデータを読み込む. UInt16 lefttop = (UInt16)(configUZ[tile_tsa_index] + ((UInt16)configUZ[tile_tsa_index + 1] << 8)); UInt16 righttop = (UInt16)(configUZ[tile_tsa_index + 2] + ((UInt16)configUZ[tile_tsa_index + 3] << 8)); UInt16 leftbottom = (UInt16)(configUZ[tile_tsa_index + 4] + ((UInt16)configUZ[tile_tsa_index + 5] << 8)); UInt16 rightbottom = (UInt16)(configUZ[tile_tsa_index + 6] + ((UInt16)configUZ[tile_tsa_index + 7] << 8)); int tsaIndex; tsaIndex = (x) + ((y) * (width * 2)); if (tsaIndex < tsa.Length) { tsa[tsaIndex] = lefttop; } tsaIndex = (x + 1) + ((y) * (width * 2)); if (tsaIndex < tsa.Length) { tsa[tsaIndex] = righttop; } tsaIndex = (x) + ((y + 1) * (width * 2)); if (tsaIndex < tsa.Length) { tsa[tsaIndex] = leftbottom; } tsaIndex = (x + 1) + ((y + 1) * (width * 2)); if (tsaIndex < tsa.Length) { tsa[tsaIndex] = rightbottom; } x += 2; if (x >= width * 2) { x = 0; y += 2; if (y >= height * 2) { break; } } } Bitmap mapcanvas = ImageUtil.Blank(width * 16, height * 16, obj_image); ImageUtil.BitBltTSA(mapcanvas, obj_image, tsa, 0); return(mapcanvas); }
//マップチップだけを描画する public static Bitmap DrawMapChipOnly( uint obj_plist //image , uint palette_plist //palette , MapSettingForm.MapAnimations anime = null ) { uint obj_offset = MapPointerForm.PlistToOffsetAddr(MapPointerForm.PLIST_TYPE.OBJECT, obj_plist & 0xFF); uint obj2_plist = (obj_plist >> 8) & 0xFF; //FE8にはないが FE7は、 plistを2つ設定できることがある. uint obj2_offset = 0; uint palette_offset = MapPointerForm.PlistToOffsetAddr(MapPointerForm.PLIST_TYPE.PALETTE, palette_plist); if (!U.isSafetyOffset(obj_offset)) { return(null); } if (!U.isSafetyOffset(palette_offset)) { return(null); } if (obj2_plist > 0) {//plist2があれば obj2_offset = MapPointerForm.PlistToOffsetAddr(MapPointerForm.PLIST_TYPE.OBJECT, obj2_plist); if (!U.isSafetyOffset(obj2_offset)) { return(null); } } byte[] objUZ = LZ77.decompress(Program.ROM.Data, obj_offset); //image if (objUZ.Length <= 0) //image { return(null); } if (obj2_plist > 0) { //plist2があれば byte[] obj2UZ = LZ77.decompress(Program.ROM.Data, obj2_offset); if (obj2UZ.Length <= 0) //image { return(null); } objUZ = U.ArrayAppend(objUZ, obj2UZ); } byte[] paletteData = Program.ROM.getBinaryData(palette_offset, (2 * 16) * 16); //マップアニメが定義されていればアニメーション補正する. if (anime != null) { if (anime.change_bitmap_bytes != null) { U.ArrayPatch(anime.change_bitmap_bytes, 0, objUZ, 32 * (8 / 2) * 4 * 16); } if (anime.change_palette_bytes != null) { U.ArrayPatch(anime.change_palette_bytes, 0, paletteData, (anime.change_palette_start_index) * 2); } } //マップチップの読込 int obj_width = 32 * 8; int obj_height = ImageUtil.CalcHeight(obj_width, objUZ.Length); Bitmap obj_image = ImageUtil.ByteToImage16Tile(obj_width, obj_height , objUZ, 0 , paletteData, 0 , 0 ); return(obj_image); }