Added TBL support to Qt hex editor.
This commit is contained in:
parent
29e4825d12
commit
348c26d78c
|
@ -731,6 +731,195 @@ void HexBookMarkMenuAction::activateCB(void)
|
||||||
qedit->setAddr( bm->addr );
|
qedit->setAddr( bm->addr );
|
||||||
}
|
}
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
|
HexEditorCharTable_t::HexEditorCharTable_t(void)
|
||||||
|
{
|
||||||
|
extAsciiEnable = true;
|
||||||
|
customMapLoaded = false;
|
||||||
|
|
||||||
|
resetAscii();
|
||||||
|
}
|
||||||
|
//----------------------------------------------------------------------------
|
||||||
|
HexEditorCharTable_t::~HexEditorCharTable_t(void)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
//----------------------------------------------------------------------------
|
||||||
|
void HexEditorCharTable_t::resetAscii(void)
|
||||||
|
{
|
||||||
|
for (int i=0; i<256; i++)
|
||||||
|
{
|
||||||
|
if (i > 127)
|
||||||
|
{ // Extended Ascii
|
||||||
|
if ( extAsciiEnable )
|
||||||
|
{
|
||||||
|
map[i] = i;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
map[i] = '.';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{ // Normal Ascii
|
||||||
|
if ( isprint(i) )
|
||||||
|
{
|
||||||
|
map[i] = i;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
map[i] = '.';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
customMapLoaded = false;
|
||||||
|
}
|
||||||
|
//----------------------------------------------------------------------------
|
||||||
|
int HexEditorCharTable_t::loadFromFile( const char *filepath )
|
||||||
|
{
|
||||||
|
int i,j,hexValue,mapValue,retVal, lineNum = 0;
|
||||||
|
FILE *fp;
|
||||||
|
char line[256];
|
||||||
|
char tk[64];
|
||||||
|
char errMsg[256];
|
||||||
|
char tmpMap[256];
|
||||||
|
|
||||||
|
retVal = 0;
|
||||||
|
errMsg[0] = 0;
|
||||||
|
|
||||||
|
fp = ::fopen( filepath, "r");
|
||||||
|
|
||||||
|
if ( fp == NULL )
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
memset( tmpMap, '.', sizeof(tmpMap) );
|
||||||
|
|
||||||
|
while ( fgets( line, sizeof(line), fp ) != 0 )
|
||||||
|
{
|
||||||
|
lineNum++;
|
||||||
|
|
||||||
|
if ( retVal != 0 )
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
//printf("%s\n", line);
|
||||||
|
|
||||||
|
i=0;
|
||||||
|
while ( isspace(line[i]) ) i++;
|
||||||
|
|
||||||
|
if ( line[i] == '#' )
|
||||||
|
{ // Comment line, skip it
|
||||||
|
line[i] = 0; continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
while ( isspace(line[i]) ) i++;
|
||||||
|
|
||||||
|
j=0;
|
||||||
|
while ( isxdigit(line[i]) )
|
||||||
|
{
|
||||||
|
tk[j] = line[i]; i++; j++;
|
||||||
|
}
|
||||||
|
tk[j] = 0;
|
||||||
|
|
||||||
|
if ( j == 0 )
|
||||||
|
{ // Line did not start with a hex character, skip it
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
hexValue = strtol( tk, NULL, 16 );
|
||||||
|
|
||||||
|
if ( hexValue > 255 )
|
||||||
|
{
|
||||||
|
sprintf( errMsg, "Error: Line %i: Hex Value 0x%X exceeds 0xFF \n", lineNum, hexValue );
|
||||||
|
retVal = -1;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
while ( isspace(line[i]) ) i++;
|
||||||
|
|
||||||
|
if ( line[i] != '=' )
|
||||||
|
{
|
||||||
|
sprintf( errMsg, "Error: Line %i: Expected assignment operator '=' but got '%c' \n", lineNum, line[i] );
|
||||||
|
retVal = -1;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
i++;
|
||||||
|
|
||||||
|
while ( isspace(line[i]) ) i++;
|
||||||
|
|
||||||
|
mapValue = 0;
|
||||||
|
|
||||||
|
if (line[i] == '0')
|
||||||
|
{ // Hex Value Remap or '0'
|
||||||
|
i++;
|
||||||
|
if ( line[i] == 'x')
|
||||||
|
{
|
||||||
|
i++; j=0;
|
||||||
|
while ( isxdigit(line[i]) )
|
||||||
|
{
|
||||||
|
tk[j] = line[i]; i++; j++;
|
||||||
|
}
|
||||||
|
tk[j] = 0;
|
||||||
|
|
||||||
|
mapValue = strtol( tk, NULL, 16 );
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mapValue = '0';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (line[i] == '$')
|
||||||
|
{ // Hex Value Remap or '$'
|
||||||
|
i++;
|
||||||
|
if ( isxdigit(line[i]) )
|
||||||
|
{
|
||||||
|
j=0;
|
||||||
|
while ( isxdigit(line[i]) )
|
||||||
|
{
|
||||||
|
tk[j] = line[i]; i++; j++;
|
||||||
|
}
|
||||||
|
tk[j] = 0;
|
||||||
|
|
||||||
|
mapValue = strtol( tk, NULL, 16 );
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mapValue = '$';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{ // Hex to Character Mapping
|
||||||
|
mapValue = line[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( mapValue > 255 )
|
||||||
|
{
|
||||||
|
sprintf( errMsg, "Error: Line %i: Map Value 0x%X exceeds 0xFF \n", lineNum, mapValue );
|
||||||
|
retVal = -1;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
tmpMap[ hexValue ] = mapValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( retVal == 0 )
|
||||||
|
{
|
||||||
|
memcpy( map, tmpMap, 256 );
|
||||||
|
customMapLoaded = true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if ( errMsg[0] != 0 )
|
||||||
|
{
|
||||||
|
if ( consoleWindow != NULL )
|
||||||
|
{
|
||||||
|
consoleWindow->QueueErrorMsgWindow(errMsg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
::fclose(fp);
|
||||||
|
return retVal;
|
||||||
|
}
|
||||||
|
//----------------------------------------------------------------------------
|
||||||
HexEditorFindDialog_t::HexEditorFindDialog_t(QWidget *parent)
|
HexEditorFindDialog_t::HexEditorFindDialog_t(QWidget *parent)
|
||||||
: QDialog( parent )
|
: QDialog( parent )
|
||||||
{
|
{
|
||||||
|
@ -900,7 +1089,7 @@ HexEditorDialog_t::HexEditorDialog_t(QWidget *parent)
|
||||||
|
|
||||||
// File -> Save ROM
|
// File -> Save ROM
|
||||||
saveROM = new QAction(tr("&Save ROM"), this);
|
saveROM = new QAction(tr("&Save ROM"), this);
|
||||||
//saveROM->setShortcut(QKeySequence::Open);
|
saveROM->setShortcut(QKeySequence::Save);
|
||||||
saveROM->setStatusTip(tr("Save ROM File"));
|
saveROM->setStatusTip(tr("Save ROM File"));
|
||||||
connect(saveROM, SIGNAL(triggered()), this, SLOT(saveRomFile(void)) );
|
connect(saveROM, SIGNAL(triggered()), this, SLOT(saveRomFile(void)) );
|
||||||
|
|
||||||
|
@ -908,12 +1097,28 @@ HexEditorDialog_t::HexEditorDialog_t(QWidget *parent)
|
||||||
|
|
||||||
// File -> Save ROM As
|
// File -> Save ROM As
|
||||||
saveROM = new QAction(tr("Save ROM &As"), this);
|
saveROM = new QAction(tr("Save ROM &As"), this);
|
||||||
//saveROM->setShortcut(QKeySequence::Open);
|
saveROM->setShortcut(QKeySequence::SaveAs);
|
||||||
saveROM->setStatusTip(tr("Save ROM File As"));
|
saveROM->setStatusTip(tr("Save ROM File As"));
|
||||||
connect(saveROM, SIGNAL(triggered()), this, SLOT(saveRomFileAs(void)) );
|
connect(saveROM, SIGNAL(triggered()), this, SLOT(saveRomFileAs(void)) );
|
||||||
|
|
||||||
fileMenu->addAction(saveROM);
|
fileMenu->addAction(saveROM);
|
||||||
|
|
||||||
|
// File -> Load Table
|
||||||
|
loadTableAct = new QAction(tr("&Load TBL File"), this);
|
||||||
|
//loadTableAct->setShortcut(QKeySequence::Open);
|
||||||
|
loadTableAct->setStatusTip(tr("Load Table from File"));
|
||||||
|
connect(loadTableAct, SIGNAL(triggered()), this, SLOT(loadTableFromFile(void)) );
|
||||||
|
|
||||||
|
fileMenu->addAction(loadTableAct);
|
||||||
|
|
||||||
|
// File -> Unload Table
|
||||||
|
unloadTableAct = new QAction(tr("&Unload TBL File"), this);
|
||||||
|
//unloadTableAct->setShortcut(QKeySequence::Open);
|
||||||
|
unloadTableAct->setStatusTip(tr("Unload Table"));
|
||||||
|
connect(unloadTableAct, SIGNAL(triggered()), this, SLOT(unloadTable(void)) );
|
||||||
|
|
||||||
|
fileMenu->addAction(unloadTableAct);
|
||||||
|
|
||||||
// File -> Goto Address
|
// File -> Goto Address
|
||||||
gotoAddrAct = new QAction(tr("&Goto Address"), this);
|
gotoAddrAct = new QAction(tr("&Goto Address"), this);
|
||||||
gotoAddrAct->setShortcut(QKeySequence(tr("Ctrl+A")));
|
gotoAddrAct->setShortcut(QKeySequence(tr("Ctrl+A")));
|
||||||
|
@ -926,7 +1131,7 @@ HexEditorDialog_t::HexEditorDialog_t(QWidget *parent)
|
||||||
|
|
||||||
// File -> Close
|
// File -> Close
|
||||||
closeAct = new QAction(tr("&Close"), this);
|
closeAct = new QAction(tr("&Close"), this);
|
||||||
closeAct->setShortcut(QKeySequence(tr("Esc")));
|
closeAct->setShortcut(QKeySequence::Close);
|
||||||
closeAct->setStatusTip(tr("Close Window"));
|
closeAct->setStatusTip(tr("Close Window"));
|
||||||
connect(closeAct, SIGNAL(triggered()), this, SLOT(closeWindow(void)) );
|
connect(closeAct, SIGNAL(triggered()), this, SLOT(closeWindow(void)) );
|
||||||
|
|
||||||
|
@ -937,7 +1142,7 @@ HexEditorDialog_t::HexEditorDialog_t(QWidget *parent)
|
||||||
|
|
||||||
// Edit -> Undo
|
// Edit -> Undo
|
||||||
undoEditAct = new QAction(tr("&Undo"), this);
|
undoEditAct = new QAction(tr("&Undo"), this);
|
||||||
undoEditAct->setShortcut(QKeySequence(tr("U")));
|
undoEditAct->setShortcut(QKeySequence::Undo);
|
||||||
undoEditAct->setStatusTip(tr("Undo Edit"));
|
undoEditAct->setStatusTip(tr("Undo Edit"));
|
||||||
undoEditAct->setEnabled(false);
|
undoEditAct->setEnabled(false);
|
||||||
connect(undoEditAct, SIGNAL(triggered()), this, SLOT(undoRomPatch(void)) );
|
connect(undoEditAct, SIGNAL(triggered()), this, SLOT(undoRomPatch(void)) );
|
||||||
|
@ -1162,6 +1367,7 @@ HexEditorDialog_t::HexEditorDialog_t(QWidget *parent)
|
||||||
|
|
||||||
FCEUI_CreateCheatMap();
|
FCEUI_CreateCheatMap();
|
||||||
|
|
||||||
|
unloadTableAct->setEnabled( editor->charTable.customMapLoaded );
|
||||||
}
|
}
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
HexEditorDialog_t::~HexEditorDialog_t(void)
|
HexEditorDialog_t::~HexEditorDialog_t(void)
|
||||||
|
@ -1376,6 +1582,57 @@ void HexEditorDialog_t::saveRomFileAs(void)
|
||||||
iNesSaveAs( filename.toStdString().c_str() );
|
iNesSaveAs( filename.toStdString().c_str() );
|
||||||
}
|
}
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
|
void HexEditorDialog_t::loadTableFromFile(void)
|
||||||
|
{
|
||||||
|
int ret, useNativeFileDialogVal;
|
||||||
|
QString filename;
|
||||||
|
QFileDialog dialog(this, tr("Load Table From File") );
|
||||||
|
|
||||||
|
dialog.setFileMode(QFileDialog::ExistingFile);
|
||||||
|
|
||||||
|
dialog.setNameFilter(tr("TBL Files (*.tbl *.TBL) ;; All files (*)"));
|
||||||
|
|
||||||
|
dialog.setViewMode(QFileDialog::List);
|
||||||
|
dialog.setFilter( QDir::AllEntries | QDir::AllDirs | QDir::Hidden );
|
||||||
|
dialog.setLabelText( QFileDialog::Accept, tr("Load") );
|
||||||
|
dialog.setDefaultSuffix( tr(".tbl") );
|
||||||
|
|
||||||
|
// Check config option to use native file dialog or not
|
||||||
|
g_config->getOption ("SDL.UseNativeFileDialog", &useNativeFileDialogVal);
|
||||||
|
|
||||||
|
dialog.setOption(QFileDialog::DontUseNativeDialog, !useNativeFileDialogVal);
|
||||||
|
|
||||||
|
ret = dialog.exec();
|
||||||
|
|
||||||
|
if ( ret )
|
||||||
|
{
|
||||||
|
QStringList fileList;
|
||||||
|
fileList = dialog.selectedFiles();
|
||||||
|
|
||||||
|
if ( fileList.size() > 0 )
|
||||||
|
{
|
||||||
|
filename = fileList[0];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( filename.isNull() )
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
qDebug() << "selected file path : " << filename.toUtf8();
|
||||||
|
|
||||||
|
editor->charTable.loadFromFile( filename.toStdString().c_str() );
|
||||||
|
|
||||||
|
unloadTableAct->setEnabled( editor->charTable.customMapLoaded );
|
||||||
|
}
|
||||||
|
//----------------------------------------------------------------------------
|
||||||
|
void HexEditorDialog_t::unloadTable(void)
|
||||||
|
{
|
||||||
|
editor->charTable.resetAscii();
|
||||||
|
|
||||||
|
unloadTableAct->setEnabled( editor->charTable.customMapLoaded );
|
||||||
|
}
|
||||||
|
//----------------------------------------------------------------------------
|
||||||
void HexEditorDialog_t::setViewRAM(void)
|
void HexEditorDialog_t::setViewRAM(void)
|
||||||
{
|
{
|
||||||
editor->setMode( QHexEdit::MODE_NES_RAM );
|
editor->setMode( QHexEdit::MODE_NES_RAM );
|
||||||
|
@ -3214,7 +3471,8 @@ void QHexEdit::paintEvent(QPaintEvent *event)
|
||||||
{
|
{
|
||||||
int x, y, w, h, row, col, nrow, addr;
|
int x, y, w, h, row, col, nrow, addr;
|
||||||
int c, cx, cy, ca, l;
|
int c, cx, cy, ca, l;
|
||||||
char txt[32], asciiTxt[4];
|
char txt[32];
|
||||||
|
QString asciiTxt;
|
||||||
QPainter painter(this);
|
QPainter painter(this);
|
||||||
QColor white("white"), black("black"), blue("blue");
|
QColor white("white"), black("black"), blue("blue");
|
||||||
bool txtHlgtSet;
|
bool txtHlgtSet;
|
||||||
|
@ -3369,15 +3627,8 @@ void QHexEdit::paintEvent(QPaintEvent *event)
|
||||||
{
|
{
|
||||||
c = mb.buf[addr].data;
|
c = mb.buf[addr].data;
|
||||||
|
|
||||||
if ( ::isprint(c) )
|
asciiTxt.clear();
|
||||||
{
|
asciiTxt += QChar(charTable.map[c]);
|
||||||
asciiTxt[0] = c;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
asciiTxt[0] = '.';
|
|
||||||
}
|
|
||||||
asciiTxt[1] = 0;
|
|
||||||
|
|
||||||
if ( addr == editAddr )
|
if ( addr == editAddr )
|
||||||
{ // Set a cell currently being editting to red text
|
{ // Set a cell currently being editting to red text
|
||||||
|
@ -3466,7 +3717,8 @@ void QHexEdit::paintEvent(QPaintEvent *event)
|
||||||
painter.fillRect( cx , cy, pxCharWidth, pxCursorHeight, QColor("gray") );
|
painter.fillRect( cx , cy, pxCharWidth, pxCursorHeight, QColor("gray") );
|
||||||
}
|
}
|
||||||
painter.drawText( x, y, tr(txt) );
|
painter.drawText( x, y, tr(txt) );
|
||||||
painter.drawText( pxHexAscii + (col*pxCharWidth) - pxLineXScroll, y, tr(asciiTxt) );
|
//painter.drawText( pxHexAscii + (col*pxCharWidth) - pxLineXScroll, y, tr(asciiTxt) );
|
||||||
|
painter.drawText( pxHexAscii + (col*pxCharWidth) - pxLineXScroll, y, asciiTxt );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
x += (3*pxCharWidth);
|
x += (3*pxCharWidth);
|
||||||
|
|
|
@ -94,6 +94,21 @@ class HexBookMarkMenuAction : public QAction
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class HexEditorCharTable_t
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
HexEditorCharTable_t(void);
|
||||||
|
~HexEditorCharTable_t(void);
|
||||||
|
|
||||||
|
char map[256];
|
||||||
|
bool extAsciiEnable;
|
||||||
|
bool customMapLoaded;
|
||||||
|
|
||||||
|
void resetAscii(void);
|
||||||
|
|
||||||
|
int loadFromFile( const char *filepath );
|
||||||
|
};
|
||||||
|
|
||||||
class HexEditorDialog_t;
|
class HexEditorDialog_t;
|
||||||
|
|
||||||
class QHexEdit : public QWidget
|
class QHexEdit : public QWidget
|
||||||
|
@ -132,6 +147,9 @@ class QHexEdit : public QWidget
|
||||||
MODE_NES_ROM
|
MODE_NES_ROM
|
||||||
};
|
};
|
||||||
static const int HIGHLIGHT_ACTIVITY_NUM_COLORS = 16;
|
static const int HIGHLIGHT_ACTIVITY_NUM_COLORS = 16;
|
||||||
|
|
||||||
|
HexEditorCharTable_t charTable;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void paintEvent(QPaintEvent *event);
|
void paintEvent(QPaintEvent *event);
|
||||||
void keyPressEvent(QKeyEvent *event);
|
void keyPressEvent(QKeyEvent *event);
|
||||||
|
@ -282,6 +300,8 @@ class HexEditorDialog_t : public QDialog
|
||||||
QAction *viewROM;
|
QAction *viewROM;
|
||||||
QAction *gotoAddrAct;
|
QAction *gotoAddrAct;
|
||||||
QAction *undoEditAct;
|
QAction *undoEditAct;
|
||||||
|
QAction *loadTableAct;
|
||||||
|
QAction *unloadTableAct;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
|
@ -294,6 +314,8 @@ class HexEditorDialog_t : public QDialog
|
||||||
void hbarChanged(int value);
|
void hbarChanged(int value);
|
||||||
void saveRomFile(void);
|
void saveRomFile(void);
|
||||||
void saveRomFileAs(void);
|
void saveRomFileAs(void);
|
||||||
|
void loadTableFromFile(void);
|
||||||
|
void unloadTable(void);
|
||||||
void setViewRAM(void);
|
void setViewRAM(void);
|
||||||
void setViewPPU(void);
|
void setViewPPU(void);
|
||||||
void setViewOAM(void);
|
void setViewOAM(void);
|
||||||
|
|
Loading…
Reference in New Issue