Initial add of assembly color option logic for Qt debugger.

This commit is contained in:
mjbudd77 2021-07-09 21:08:39 -04:00
parent 151bee01dc
commit ea7deb0fd0
5 changed files with 458 additions and 1 deletions

View File

@ -457,6 +457,7 @@ set(SRC_DRIVERS_SDL
${CMAKE_CURRENT_SOURCE_DIR}/drivers/Qt/FrameTimingStats.cpp
${CMAKE_CURRENT_SOURCE_DIR}/drivers/Qt/PaletteConf.cpp
${CMAKE_CURRENT_SOURCE_DIR}/drivers/Qt/PaletteEditor.cpp
${CMAKE_CURRENT_SOURCE_DIR}/drivers/Qt/ColorMenu.cpp
${CMAKE_CURRENT_SOURCE_DIR}/drivers/Qt/GuiConf.cpp
${CMAKE_CURRENT_SOURCE_DIR}/drivers/Qt/MoviePlay.cpp
${CMAKE_CURRENT_SOURCE_DIR}/drivers/Qt/MovieOptions.cpp

View File

@ -0,0 +1,245 @@
/* FCE Ultra - NES/Famicom Emulator
*
* Copyright notice for this file:
* Copyright (C) 2020 mjbudd77
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/
// ColorMenu.cpp
//
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <string>
#include <QHBoxLayout>
#include <QPushButton>
#include <QImage>
#include <QPixmap>
#include <QStyle>
#include "Qt/ColorMenu.h"
//----------------------------------------------------------------------------
ColorMenuItem::ColorMenuItem( QString txt, QWidget *parent)
: QAction( txt, parent)
{
title = txt;
picker = NULL;
colorPtr = &lastColor;
setImageColor( Qt::red );
connect( this, SIGNAL(triggered(void)), this, SLOT(openColorPicker(void)) );
}
//----------------------------------------------------------------------------
ColorMenuItem::~ColorMenuItem(void)
{
printf("Destroy Color Menu Item\n");
}
//----------------------------------------------------------------------------
void ColorMenuItem::connectColor( QColor *c )
{
if ( c != NULL )
{
colorPtr = c;
}
else
{
colorPtr = &lastColor;
}
setImageColor( *colorPtr );
}
//----------------------------------------------------------------------------
void ColorMenuItem::setImageColor( QColor c )
{
int i, x, y, w = 32, h = 32, bw = 4;
unsigned char pixelData[ 32 * 32 * 4 ];
QPixmap pixmap;
QColor b;
lastColor = c;
b = parentWidget()->palette().color(QPalette::WindowText);
i=0;
for (y=0; y<h; y++)
{
for (x=0; x<w; x++)
{
if ( (y < bw) || (y > h-bw) || (x < bw) || (x > w-bw) )
{
pixelData[i] = b.red(); i++;
pixelData[i] = b.green(); i++;
pixelData[i] = b.blue(); i++;
pixelData[i] = 0xFF; i++;
}
else
{
pixelData[i] = c.red(); i++;
pixelData[i] = c.green(); i++;
pixelData[i] = c.blue(); i++;
pixelData[i] = 0xFF; i++;
}
}
}
QImage img( pixelData, 32, 32, 32*4, QImage::Format_RGBA8888 );
pixmap.convertFromImage( img );
setIcon( QIcon(pixmap) );
}
//----------------------------------------------------------------------------
void ColorMenuItem::pickerClosed(int ret)
{
picker = NULL;
setImageColor( *colorPtr );
//printf("Picker Closed: %i\n", ret );
}
//----------------------------------------------------------------------------
void ColorMenuItem::openColorPicker(void)
{
//printf("Open Color Picker\n");
if ( picker == NULL )
{
picker = new ColorMenuPickerDialog_t( colorPtr, parentWidget() );
picker->show();
connect( picker, SIGNAL(finished(int)), this, SLOT(pickerClosed(int)) );
}
else
{
}
}
//----------------------------------------------------------------------------
//------ Color Menu Picker
//----------------------------------------------------------------------------
ColorMenuPickerDialog_t::ColorMenuPickerDialog_t( QColor *c, QWidget *parent )
: QDialog( parent )
{
QVBoxLayout *mainLayout;
QHBoxLayout *hbox;
QPushButton *okButton;
QPushButton *cancelButton;
QPushButton *resetButton;
QStyle *style;
char stmp[128];
style = this->style();
sprintf( stmp, "Pick Color");
setWindowTitle( stmp );
colorPtr = c;
origColor = *c;
mainLayout = new QVBoxLayout();
setLayout( mainLayout );
colorDialog = new QColorDialog(this);
mainLayout->addWidget( colorDialog );
colorDialog->setWindowFlags(Qt::Widget);
colorDialog->setOption( QColorDialog::DontUseNativeDialog, true );
colorDialog->setOption( QColorDialog::NoButtons, true );
colorDialog->setCurrentColor( *c );
connect( colorDialog, SIGNAL(colorSelected(const QColor &)) , this, SLOT(colorChanged( const QColor &)) );
connect( colorDialog, SIGNAL(currentColorChanged(const QColor &)), this, SLOT(colorChanged( const QColor &)) );
connect( colorDialog, SIGNAL(accepted(void)), this, SLOT(colorAccepted(void)) );
connect( colorDialog, SIGNAL(rejected(void)), this, SLOT(colorRejected(void)) );
hbox = new QHBoxLayout();
mainLayout->addLayout( hbox );
okButton = new QPushButton( tr("OK") );
cancelButton = new QPushButton( tr("Cancel") );
resetButton = new QPushButton( tr("Reset") );
okButton->setIcon( style->standardIcon( QStyle::SP_DialogApplyButton ) );
cancelButton->setIcon( style->standardIcon( QStyle::SP_DialogCancelButton ) );
resetButton->setIcon( style->standardIcon( QStyle::SP_DialogResetButton ) );
hbox->addWidget( resetButton, 1 );
hbox->addStretch( 10 );
hbox->addWidget( okButton, 1 );
hbox->addWidget( cancelButton, 1 );
connect( okButton , SIGNAL(clicked(void)), this, SLOT(colorAccepted(void)) );
connect( cancelButton, SIGNAL(clicked(void)), this, SLOT(colorRejected(void)) );
connect( resetButton , SIGNAL(clicked(void)), this, SLOT(resetColor(void)) );
}
//----------------------------------------------------------------------------
ColorMenuPickerDialog_t::~ColorMenuPickerDialog_t(void)
{
//printf("nesColorPicker Destroyed\n");
}
//----------------------------------------------------------------------------
void ColorMenuPickerDialog_t::closeEvent(QCloseEvent *event)
{
//printf("nesColorPicker Close Window Event\n");
done(0);
deleteLater();
event->accept();
}
//----------------------------------------------------------------------------
void ColorMenuPickerDialog_t::closeWindow(void)
{
//printf("Close Window\n");
done(0);
deleteLater();
}
//----------------------------------------------------------------------------
void ColorMenuPickerDialog_t::colorChanged( const QColor &color )
{
//printf("Color Changed: R:%i G%i B%i \n", color.red(), color.green(), color.blue() );
*colorPtr = color;
}
//----------------------------------------------------------------------------
void ColorMenuPickerDialog_t::colorAccepted(void)
{
//printf("nesColorPicker Accepted: %zi\n", colorChangeHistory.size() );
done(0);
deleteLater();
}
//----------------------------------------------------------------------------
void ColorMenuPickerDialog_t::colorRejected(void)
{
//printf("nesColorPicker Rejected\n");
// Reset to original color
*colorPtr = origColor;
done(0);
deleteLater();
}
//----------------------------------------------------------------------------
void ColorMenuPickerDialog_t::resetColor(void)
{
// Reset to original color
*colorPtr = origColor;
colorDialog->setCurrentColor( origColor );
}
//----------------------------------------------------------------------------

View File

@ -0,0 +1,58 @@
// ColorMenu.h
//
#pragma once
#include <QWidget>
#include <QWidgetAction>
#include <QAction>
#include <QColor>
#include <QDialog>
#include <QColorDialog>
#include <QCloseEvent>
class ColorMenuPickerDialog_t : public QDialog
{
Q_OBJECT
public:
ColorMenuPickerDialog_t( QColor *c, QWidget *parent = 0);
~ColorMenuPickerDialog_t(void);
protected:
void closeEvent(QCloseEvent *event);
private:
QColorDialog *colorDialog;
QColor *colorPtr;
QColor origColor;
public slots:
void closeWindow(void);
private slots:
void colorChanged( const QColor &color );
void colorAccepted(void);
void colorRejected(void);
void resetColor(void);
};
class ColorMenuItem : public QAction
{
Q_OBJECT
public:
ColorMenuItem( QString txt, QWidget *parent = 0);
~ColorMenuItem(void);
void connectColor( QColor *c );
protected:
QString title;
QColor *colorPtr;
QColor lastColor;
ColorMenuPickerDialog_t *picker;
void setImageColor( QColor c );
public slots:
void openColorPicker(void);
void pickerClosed(int ret);
};

View File

@ -71,6 +71,7 @@
#include "Qt/HexEditor.h"
#include "Qt/ConsoleDebugger.h"
#include "Qt/ConsoleUtilities.h"
#include "Qt/ColorMenu.h"
// Where are these defined?
extern int vblankScanLines;
@ -414,6 +415,24 @@ ConsoleDebugger::ConsoleDebugger(QWidget *parent)
subMenu->addAction(act);
// Options -> Color Selection
subMenu = optMenu->addMenu(tr("&Color Selection"));
// Options -> Color Selection -> Opcodes
opcodeColorAct = new ColorMenuItem( tr("&Opcodes"), this);
subMenu->addAction(opcodeColorAct);
// Options -> Color Selection -> Labels
labelColorAct = new ColorMenuItem( tr("&Labels"), this);
subMenu->addAction(labelColorAct);
// Options -> Color Selection -> Comments
commentColorAct = new ColorMenuItem( tr("&Comments"), this);
subMenu->addAction(commentColorAct);
optMenu->addSeparator();
// Symbols
@ -975,6 +994,10 @@ ConsoleDebugger::ConsoleDebugger(QWidget *parent)
restoreGeometry(settings.value("debugger/geometry").toByteArray());
setCpuStatusFont( cpuFont );
opcodeColorAct->connectColor( &asmView->opcodeColor );
labelColorAct->connectColor( &asmView->labelColor );
commentColorAct->connectColor( &asmView->commentColor);
}
//----------------------------------------------------------------------------
ConsoleDebugger::~ConsoleDebugger(void)
@ -3663,6 +3686,12 @@ QAsmView::QAsmView(QWidget *parent)
useDarkTheme = false;
opcodeColor.setRgb( 255, 0, 0 );
labelColor.setRgb( 255, 255, 0 );
commentColor.setRgb( 0, 255, 0 );
addressColor.setRgb( 0, 0, 255 );
immediateColor.setRgb( 255, 0, 255 );
g_config->getOption("SDL.DebuggerAsmFont", &fontString);
if ( fontString.size() > 0 )
@ -3761,6 +3790,10 @@ QAsmView::QAsmView(QWidget *parent)
//printf("clipboard->supportsSelection() : '%i' \n", clipboard->supportsSelection() );
//printf("clipboard->supportsFindBuffer(): '%i' \n", clipboard->supportsFindBuffer() );
pcLocLinePos = 4;
byteCodeLinePos = 12;
opcodeLinePos = 22;
operandLinePos = 25;
}
//----------------------------------------------------------------------------
QAsmView::~QAsmView(void)
@ -4616,6 +4649,102 @@ void QAsmView::drawText( QPainter *painter, int x, int y, const char *txt )
}
}
//----------------------------------------------------------------------------
void QAsmView::drawAsmLine( QPainter *painter, int x, int y, const char *txt )
{
int i=0;
char c[2];
c[0] = 0; c[1] = 0;
// CD Log Area
painter->setPen( this->palette().color(QPalette::WindowText));
while ( (i<pcLocLinePos) && (txt[i] != 0) )
{
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
}
// Address Area
painter->setPen( this->palette().color(QPalette::WindowText));
while ( (i<byteCodeLinePos) && (txt[i] != 0) )
{
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
}
// Byte Code Area
painter->setPen( this->palette().color(QPalette::WindowText));
while ( (i<opcodeLinePos) && (txt[i] != 0) )
{
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
}
// Opcode Area
painter->setPen( opcodeColor );
while ( (i<operandLinePos) && (txt[i] != 0) )
{
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
}
// Operand Area
painter->setPen( this->palette().color(QPalette::WindowText));
while ( (txt[i] != 0) )
{
if ( (txt[i] == '$') && isxdigit( txt[i+1] ) )
{
painter->setPen( addressColor );
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
while ( isxdigit( txt[i] ) )
{
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
}
}
else if ( (txt[i] == '#') && (txt[i+1] == '$') && isxdigit( txt[i+2] ) )
{
painter->setPen( immediateColor );
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
while ( isxdigit( txt[i] ) )
{
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
}
}
else
{
painter->setPen( this->palette().color(QPalette::WindowText));
c[0] = txt[i];
painter->drawText( x, y, tr(c) );
i++; x += pxCharWidth;
}
}
}
//----------------------------------------------------------------------------
void QAsmView::paintEvent(QPaintEvent *event)
{
int x,y,l, row, nrow, selAddr;
@ -4704,7 +4833,14 @@ void QAsmView::paintEvent(QPaintEvent *event)
{
painter.setPen( this->palette().color(QPalette::WindowText));
}
drawText( &painter, x, y, asmEntry[l]->text.c_str() );
if ( asmEntry[l]->type == dbg_asm_entry_t::ASM_TEXT )
{
drawAsmLine( &painter, x, y, asmEntry[l]->text.c_str() );
}
else
{
drawText( &painter, x, y, asmEntry[l]->text.c_str() );
}
if ( (selAddrLine == l) )
{ // Highlight ASM line for selected address.

View File

@ -28,6 +28,7 @@
#include "Qt/main.h"
#include "Qt/SymbolicDebug.h"
#include "Qt/ColorMenu.h"
#include "../../debug.h"
struct dbg_asm_entry_t
@ -122,6 +123,13 @@ class QAsmView : public QWidget
int isBreakpointAtAddr( int addr );
void determineLineBreakpoints(void);
void setFont( const QFont &font );
QColor opcodeColor;
QColor addressColor;
QColor immediateColor;
QColor commentColor;
QColor labelColor;
protected:
bool event(QEvent *event) override;
void paintEvent(QPaintEvent *event);
@ -142,6 +150,7 @@ class QAsmView : public QWidget
void setHighlightEndCoord( int x, int y );
void loadClipboard( const char *txt );
void drawText( QPainter *painter, int x, int y, const char *txt );
void drawAsmLine( QPainter *painter, int x, int y, const char *txt );
private:
ConsoleDebugger *parent;
@ -169,6 +178,10 @@ class QAsmView : public QWidget
int cursorLineAddr;
int pcLinePlacement;
int pcLineOffset;
int pcLocLinePos;
int byteCodeLinePos;
int opcodeLinePos;
int operandLinePos;
int selAddrLine;
int selAddrChar;
@ -298,6 +311,10 @@ class ConsoleDebugger : public QDialog
QTimer *periodicTimer;
QFont font;
ColorMenuItem *opcodeColorAct;
ColorMenuItem *commentColorAct;
ColorMenuItem *labelColorAct;
int selBmAddrVal;
bool windowUpdateReq;