TMOD2 takes "variable sized" tile editing to a new level. The purpose of this editor is to allow users to edit tiles without being limited to editing 1 tile at a time. In effect, this program was designed for multi-tile editing and tile copying. A few new concepts were implemented in TMOD2: buffers and a clipboard. Buffers are just a chunk of data. TMOD2 has the ablility to handle up to 12 buffers at a time (or the ability to load 12 files at once). The clipboard is the only data that can be edited. However, the clipboard is used to copy and paste data to the buffer. Therefore to edit a tile, one must copy a tile to clipboard, edit the clipboard, and then paste it to the current buffer.
Please read disclaimer before download. This is a development version therefore there may be bugs!
To make it short: I am not responsible for anything that happens to your computer by using this program. USE AT YOUR OWN RISK.
Unzip all files into a separate directory. Once done, if you just double click tmod2.exe, it will load up a new blank buffer. However, in order to load a file, drag the file onto the tmod2.exe executable. Use the left-click to copy a tile, right-click to paste a tile, and press 'e' to edit the clipboard. If you hold shift, you can see the clipboard content in the white rectangle. If you hold Ctrl, you may drag a rectangle to copy multiple tiles to the clipboard. Note: if you copy a tile from 1 buffer to another in 1BPP mode, make sure both buffers are set to 1BPP. While it is possible to copy a 1BPP mode data to a higher BPP mode, it is not possible to copy from a higher BPP mode to a lower BPP mode! You can try to copy a high BPP mode data to a lower BPP mode but you will get a conversion resulting in the loss of significant bits.
Quick ReferenceF1 - F12 : Select buffer 0 - 9 : Select bitplane/mode +/- : Increment/Decrement offset Up/Dn : Scrollup/down 1 line Left/right : Scroll left/right 1 char PgUp/PgDn : Scrollup/down 1 page [ : Decrement tile height (hold shift to adjust width, if supported) ] : Increment tile height (hold shift to adjust width, if supported) ; : Rotate pal R by 16 ' : Rotate pal L by 16 , : Decrement columns . : Increment columns e : Enter and exit clipboard edit mode f : Changes between Free/Grid Edit modes
TMOD2 introduces the concepts of buffers, decoders, and clipboard. A buffer is a chunk of memory allocated for tile editing. When you load a file, it gets loaded into a buffer. TMOD2 supports up to 12 buffers, thus you can load up to 12 files at one time. Each buffer may be accessed with the F1 .. F12 keys on the keyboard. However, there must be memory allocated at an available buffer slot in order to view or edit the data. By default, Buffer 1 (accessed by pressing F1) is the main working buffer. Buffer 1 is allocated on startup and will be loaded with a file if you dragged and dropped one onto tmod2.exe. Otherwise, Buffer 1 contains an empty buffer of size 64kb. On startup, Buffer 2 (accessed by pressing F2) is allocated as a "scratch" buffer. This scratch buffer is just a empty buffer (64kb in size) in which you may use to store data temporarily. There is no restriction on what you can use the scratch buffer for. You can allocate a new buffer by selecting the "New Buffer" button at the bottom of the screen. A dialog will prompt you to entering a name for the buffer and specify the size of the buffer. The size of a buffer will always be atleast 64kb and aligned on 16 bytes. Thus, if you allocate a buffer of 9 bytes, a buffer will be created as 64kb. However, 55 bytes are wasted. you may delete a buffer by selecting "Delete buffer" from the buttons at the bottom of the screen. You may not delete the main buffer, however.
Decoders are modules that decode and encode bitplane data from a file. All decoders are dynamic link modules stored as *.dm files in the modules/ directory. Prewritten decoders modules that comes with TMOD2 is the 1BPP, 2BPP, 4BPP, 8BPP, 16x?? and MODE7. Note: The mode7 module doesn't do true mode7; it just the tile part of it. TMOD2 has the ability for C programmers to code their own decoder modules to edit other modes (like NES, GENESIS, etc..), or decompression viewing for the advanced programmer. The decoding mode is selected by pressing 1 - 0 on the keyboard. So which key is which mode? It depends on the order of which DMs are loaded. Open up "module.cfg" in which you'll find a list of decoder modules. If you want to add or remove a DM, just add or remove it from the list.
A very special buffer is called a clipboard. Everytime you left-click on a tile in the editor, the data inside the rectangle is copied into the clipboard. When you press 'e', you will enter clipboard edit mode. There you may edit the clipboard. Press 'e' in clipboard edit mode to exit, then right-click to paste the updated data. Remember, if you hold Ctrl, you can drag a rectangle to edit multiple tiles at a time.
Now comes the powerhouse of TMOD2. By default, you'll be editing in GRID mode. In this mode, the edit rectangle snaps to each tile and edits each tile on a tile aligned boundary. Now, press 'f' to enter FREE mode. In free mode, you will notice that the rectangle does not snap to tiles allowing you to copy a tile from anywhere on the tile screen! Even better, if you drag a rectangle, it does not snap to tile width and height.
Press 'e' to enter clipboard edit mode. A palette is displayed below. Depending on which bitplane you are on, you will be limited to the amount of colours to choose from. For eg. in 1BPP mode, you can only choose the first 2 colours. While in 8BPP, you can choose from the entire range of 256 colours. Left/right click on a colour to select it. Then left/right click on the editing canvas to edit the clipboard contents. You can use ' or ; keys to rotate the palette. If you hold Ctrl and click on a colour, a dialog will pop up for you to edit the colour of that index.
You can load a buffer by clicking on the "Load buffer" button at the bottom of the screen. A file select dialog will pop up and prompt for a file to load. Once the file is selected, it will be loaded in to an unused buffer slot. "Save buffer" is the reverse of the load. It will prompt you with a filename to save as.
There is a "Load special" button that allows the program to parse formatted files like BMPs, TTFs, and palettes. Select the "Load special" button and a file select dialog will pop up. Depending on the extension of the file you select, the file loaded will processed as a BMP, TTF or palette. The table below describes what extension select which processor:
| Extension | File loaded |
| .bmp | Loads a bitmap (experimental) |
| .ttf | Loads a True Type Font |
| .pal | Load a 24-bit RGB palette |
| .pal | Loads a RIFF (PSP compatible) palette |
| .pal | Loads a TLayer 16-colour palette (determined by its 48 byte file size) |
| .cg | Loads a 15-bit BGR palette |
| .zst | Loads a palette from a ZST save state |
The "Save special" button allows you to save BMP of the tile screen or palette. You will be prompted to enter a filename to save, then prompted to select the format of save. You can save as a RGB palette, CG palette, TLayer palette, RIFF palette, and BMP.
The decoder module engine is still in development. This section describes how to code a basic module. Open up template.c to take a look:
/*****************************************************************************/
/* template.c */
/* Template for coding decoder modules for TMod2 */
/* (c) 2000 Jay */
/*****************************************************************************/
#include "dm.h"
void startup()
{
/* place startup code here */
}
int tile_pack(unsigned char *dest,const unsigned char *src,int width,int height)
{
/* insert tilepacker code here */
return 0;
}
int tile_unpack(unsigned char *dest,const unsigned char *src,int width,int height)
{
/* insert tile unpacker code here */
return 0;
}
/* you must define an EXPORTSTRUC with 'export' in order to export data */
static EXPORTSTRUC export =
{
/*entry*/ startup,
/*tile_pack*/ tile_pack,
/*tile_unpack*/ tile_unpack,
/*update*/ NULL,
/*save*/ NULL,
/*minwidth*/ 8,
/*minheight*/ 1,
/*maxwidth*/ 8,
/*maxheight*/ 16,
/*bpp*/ 1,
/*maxpal*/ 2,
/*modestr*/ "1 BPP",
/*help*/ NULL,
/*key*/ { 0, 0, 0, 0 },
/*KeyHandler*/ { NULL, NULL, NULL, NULL }
};
The startup( ) function is where you want to place startup code. This function is executed once when the module is loaded.
The tile_pack( ) function is where you want to place the code to pack a tile into bitplane data:
int tile_pack(unsigned char *dest,const unsigned char *src,int width,int height)'dest' is the pointer to the output for packed bitplane data. 'src' is the input data stored unpacked (1 byte, 1 pixel). 'width' and 'height' is the width and height of the tile to pack. The size of 'src' is determined by width x height and stored as a linear array. This function should return the size of the number of bytes written to the output.
The tile_uppack( ) function is where you want to place the code to unpack a tile into raw format:
int tile_unpack(unsigned char *dest,const unsigned char *src,int width,int height)'dest' is the pointer to the output for unpacked data. 'src' is the input data stored in raw format (1 byte, 1 pixel). 'width' and 'height' is the width and height of the tile to unpack. The size of output is determined by width x height. This function should return the number of bytes processed from 'src' which is usualy (width x height x bpp) / 8.
The export structure defines the mode information.
static EXPORTSTRUC export =
{
/*entry*/ startup,
/*tile_pack*/ tile_pack,
/*tile_unpack*/ tile_unpack,
/*update*/ NULL,
/*save*/ NULL,
/*minwidth*/ 8,
/*minheight*/ 1,
/*maxwidth*/ 8,
/*maxheight*/ 16,
/*bpp*/ 1,
/*maxpal*/ 2,
/*modestr*/ "1 BPP",
/*help*/ NULL,
/*key*/ { 0, 0, 0, 0 },
/*KeyHandler*/ { NULL, NULL, NULL, NULL }
};
The description for each field is displayed below:
| Field | Description |
| entry | Store the pointer to the startup function here. As you can see, the startup( ) is already entered for you. |
| tile_pack | Store the pointer to the tile_pack( ) function here. |
| tile_uppack | Store the pointer to the tile_uppack( ) function here. |
| update | The update( ) function (not documented) is for advanced user to have full control over tile decoding. Will be documented later. Please store NULL here. |
| save | The save( ) function (not documented) is for advanced user to have full control over tile encoding. Will be documented later. Please store NULL here. |
| minwidth | Defines the minimum width of the tile the decoder can display (This is for the variable width support {not to be confused with VWF}, but set it to the same as maxwidth for fixed width) |
| maxwidth | Defines the maximum width of the tile the decoder can display |
| minheight | The minimum height the decoder can display |
| maxheight | The maximum height the decoder can display |
| bpp | Bits Per Pixel used in this mode. This field is VERY important in computing tile sizes etc. (for scrolling and such) |
| maxpal | The number of palette indexes the user can select. Should be set to 2^bpp. |
| modestr | A string that describes your mode. |
| help | Pointer to a help page. In order to define a help page, you must define an array of strings in which the last element is NULL. Each element in the array is one page. (More documentation later, just see examples). |
| key | Hook key handlers (more on this later) |
| KeyHandler | Functions to call when pressed a key defined in 'key' |