- enhancement: modify values in the memory view while debugging
- enhancement: auto update watch, local and memory view after expression evaluated - enhancement: auto update watch, local and memory view after memory modified
This commit is contained in:
parent
8edace1c1d
commit
3ca1a9fc4c
5
NEWS.md
5
NEWS.md
|
@ -5,6 +5,11 @@ Red Panda C++ Version 0.13.2
|
||||||
- enhancement: if there's no selection when copy/cut, select currect line by default
|
- enhancement: if there's no selection when copy/cut, select currect line by default
|
||||||
- enhancement: support ligatures in fonts like fira code ( disabled by default, can be turned on in options dialog's editor font page)
|
- enhancement: support ligatures in fonts like fira code ( disabled by default, can be turned on in options dialog's editor font page)
|
||||||
- enhancement: add "minimum id length required to show code completion" to the options dialog's editor code completion page
|
- enhancement: add "minimum id length required to show code completion" to the options dialog's editor code completion page
|
||||||
|
- enhancement: modify values in the memory view while debugging
|
||||||
|
- enhancement: auto update watch, local and memory view after expression evaluated
|
||||||
|
- enhancement: auto update watch, local and memory view after memory modified
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
Red Panda C++ Version 0.13.1
|
Red Panda C++ Version 0.13.1
|
||||||
- enhancement: suppoort localization info in project templates
|
- enhancement: suppoort localization info in project templates
|
||||||
|
|
|
@ -39,6 +39,9 @@ Debugger::Debugger(QObject *parent) : QObject(parent)
|
||||||
mBacktraceModel=new BacktraceModel(this);
|
mBacktraceModel=new BacktraceModel(this);
|
||||||
mWatchModel = new WatchModel(this);
|
mWatchModel = new WatchModel(this);
|
||||||
mRegisterModel = new RegisterModel(this);
|
mRegisterModel = new RegisterModel(this);
|
||||||
|
mMemoryModel = new MemoryModel(8,this);
|
||||||
|
connect(mMemoryModel,&MemoryModel::setMemoryData,
|
||||||
|
this, &Debugger::setMemoryData);
|
||||||
mExecuting = false;
|
mExecuting = false;
|
||||||
mReader = nullptr;
|
mReader = nullptr;
|
||||||
mTarget = nullptr;
|
mTarget = nullptr;
|
||||||
|
@ -98,6 +101,7 @@ bool Debugger::start(const QString& inferior)
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
mMemoryModel->reset();
|
||||||
mWatchModel->resetAllVarInfos();
|
mWatchModel->resetAllVarInfos();
|
||||||
if (pSettings->debugger().useGDBServer()) {
|
if (pSettings->debugger().useGDBServer()) {
|
||||||
mTarget = new DebugTarget(inferior,compilerSet->debugServer(),pSettings->debugger().GDBServerPort());
|
mTarget = new DebugTarget(inferior,compilerSet->debugServer(),pSettings->debugger().GDBServerPort());
|
||||||
|
@ -114,6 +118,7 @@ bool Debugger::start(const QString& inferior)
|
||||||
mReader = new DebugReader(this);
|
mReader = new DebugReader(this);
|
||||||
mReader->setDebuggerPath(debuggerPath);
|
mReader->setDebuggerPath(debuggerPath);
|
||||||
connect(mReader, &QThread::finished,this,&Debugger::cleanUpReader);
|
connect(mReader, &QThread::finished,this,&Debugger::cleanUpReader);
|
||||||
|
connect(mReader, &QThread::finished,mMemoryModel,&MemoryModel::reset);
|
||||||
connect(mReader, &DebugReader::parseFinished,this,&Debugger::syncFinishedParsing,Qt::BlockingQueuedConnection);
|
connect(mReader, &DebugReader::parseFinished,this,&Debugger::syncFinishedParsing,Qt::BlockingQueuedConnection);
|
||||||
connect(mReader, &DebugReader::changeDebugConsoleLastLine,this,&Debugger::onChangeDebugConsoleLastline);
|
connect(mReader, &DebugReader::changeDebugConsoleLastLine,this,&Debugger::onChangeDebugConsoleLastline);
|
||||||
connect(mReader, &DebugReader::cmdStarted,pMainWindow, &MainWindow::disableDebugActions);
|
connect(mReader, &DebugReader::cmdStarted,pMainWindow, &MainWindow::disableDebugActions);
|
||||||
|
@ -147,10 +152,9 @@ bool Debugger::start(const QString& inferior)
|
||||||
connect(mReader, &DebugReader::inferiorStopped,pMainWindow,
|
connect(mReader, &DebugReader::inferiorStopped,pMainWindow,
|
||||||
&MainWindow::setActiveBreakpoint);
|
&MainWindow::setActiveBreakpoint);
|
||||||
connect(mReader, &DebugReader::inferiorStopped,this,
|
connect(mReader, &DebugReader::inferiorStopped,this,
|
||||||
&Debugger::refreshWatchVars);
|
&Debugger::refreshAll);
|
||||||
|
|
||||||
mReader->registerInferiorStoppedCommand("-stack-list-frames","");
|
mReader->registerInferiorStoppedCommand("-stack-list-frames","");
|
||||||
mReader->registerInferiorStoppedCommand("-stack-list-variables", "--all-values");
|
|
||||||
mReader->start();
|
mReader->start();
|
||||||
mReader->waitStart();
|
mReader->waitStart();
|
||||||
|
|
||||||
|
@ -210,6 +214,14 @@ void Debugger::updateRegisterValues(const QHash<int, QString> &values)
|
||||||
mRegisterModel->updateValues(values);
|
mRegisterModel->updateValues(values);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Debugger::refreshAll()
|
||||||
|
{
|
||||||
|
refreshWatchVars();
|
||||||
|
sendCommand("-stack-list-variables", "--all-values");
|
||||||
|
if (memoryModel()->startAddress()>0)
|
||||||
|
sendCommand("-data-read-memory",QString("%1 x 1 8 8 ").arg(memoryModel()->startAddress()));
|
||||||
|
}
|
||||||
|
|
||||||
RegisterModel *Debugger::registerModel() const
|
RegisterModel *Debugger::registerModel() const
|
||||||
{
|
{
|
||||||
return mRegisterModel;
|
return mRegisterModel;
|
||||||
|
@ -407,6 +419,11 @@ void Debugger::fetchVarChildren(const QString &varName)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MemoryModel *Debugger::memoryModel() const
|
||||||
|
{
|
||||||
|
return mMemoryModel;
|
||||||
|
}
|
||||||
|
|
||||||
void Debugger::removeWatchVars(bool deleteparent)
|
void Debugger::removeWatchVars(bool deleteparent)
|
||||||
{
|
{
|
||||||
if (deleteparent) {
|
if (deleteparent) {
|
||||||
|
@ -567,8 +584,15 @@ void Debugger::syncFinishedParsing()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Debugger::setMemoryData(qulonglong address, unsigned char data)
|
||||||
|
{
|
||||||
|
sendCommand("-data-write-memory-bytes", QString("%1 \"%2\"").arg(address).arg(data,2,16,QChar('0')));
|
||||||
|
refreshAll();
|
||||||
|
}
|
||||||
|
|
||||||
void Debugger::updateMemory(const QStringList &value)
|
void Debugger::updateMemory(const QStringList &value)
|
||||||
{
|
{
|
||||||
|
mMemoryModel->updateMemory(value);
|
||||||
emit memoryExamineReady(value);
|
emit memoryExamineReady(value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2339,3 +2363,132 @@ void DebugTarget::run()
|
||||||
emit processError(mProcess->error());
|
emit processError(mProcess->error());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MemoryModel::MemoryModel(int dataPerLine, QObject *parent):
|
||||||
|
QAbstractTableModel(parent),
|
||||||
|
mDataPerLine(dataPerLine),
|
||||||
|
mStartAddress(0)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void MemoryModel::updateMemory(const QStringList &value)
|
||||||
|
{
|
||||||
|
QRegExp delimiter("(\\s+)");
|
||||||
|
QList<PMemoryLine> newModel;
|
||||||
|
for (int i=0;i<value.length();i++) {
|
||||||
|
QString line = value[i].trimmed();
|
||||||
|
QStringList dataLst = line.split(delimiter,QString::SkipEmptyParts);
|
||||||
|
PMemoryLine memoryLine = std::make_shared<MemoryLine>();
|
||||||
|
memoryLine->startAddress = -1;
|
||||||
|
if (dataLst.length()>0) {
|
||||||
|
memoryLine->startAddress = stringToHex(dataLst[0],0);
|
||||||
|
for (int j=1;j<dataLst.length();j++) {
|
||||||
|
qulonglong data = stringToHex(dataLst[j],-1);
|
||||||
|
if (data>=0)
|
||||||
|
memoryLine->datas.append((unsigned char)data);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
newModel.append(memoryLine);
|
||||||
|
}
|
||||||
|
if (newModel.count()>0 && newModel.count()== mLines.count() &&
|
||||||
|
newModel[0]->startAddress == mLines[0]->startAddress) {
|
||||||
|
for (int i=0;i<newModel.count();i++) {
|
||||||
|
PMemoryLine newLine = newModel[i];
|
||||||
|
PMemoryLine oldLine = mLines[i];
|
||||||
|
for (int j=0;j<newLine->datas.count();j++) {
|
||||||
|
if (j>=oldLine->datas.count())
|
||||||
|
break;
|
||||||
|
if (newLine->datas[j]!=oldLine->datas[j])
|
||||||
|
newLine->changedDatas.insert(j);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
mLines = newModel;
|
||||||
|
emit dataChanged(createIndex(0,0),
|
||||||
|
createIndex(mLines.count()-1,mDataPerLine-1));
|
||||||
|
} else {
|
||||||
|
beginResetModel();
|
||||||
|
mLines = newModel;
|
||||||
|
endResetModel();
|
||||||
|
}
|
||||||
|
if (mLines.count()>0) {
|
||||||
|
mStartAddress = mLines[0]->startAddress;
|
||||||
|
} else {
|
||||||
|
mStartAddress = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int MemoryModel::rowCount(const QModelIndex &parent) const
|
||||||
|
{
|
||||||
|
return mLines.count();
|
||||||
|
}
|
||||||
|
|
||||||
|
int MemoryModel::columnCount(const QModelIndex &parent) const
|
||||||
|
{
|
||||||
|
return mDataPerLine;
|
||||||
|
}
|
||||||
|
|
||||||
|
QVariant MemoryModel::data(const QModelIndex &index, int role) const
|
||||||
|
{
|
||||||
|
if (!index.isValid())
|
||||||
|
return QVariant();
|
||||||
|
if (index.row()<0 || index.row()>=mLines.count())
|
||||||
|
return QVariant();
|
||||||
|
PMemoryLine line = mLines[index.row()];
|
||||||
|
int col = index.column();
|
||||||
|
if (col<0 || col>=line->datas.count())
|
||||||
|
return QVariant();
|
||||||
|
if (role == Qt::DisplayRole)
|
||||||
|
return QString("%1").arg(line->datas[col],2,16,QChar('0'));
|
||||||
|
return QVariant();
|
||||||
|
}
|
||||||
|
|
||||||
|
QVariant MemoryModel::headerData(int section, Qt::Orientation orientation, int role) const
|
||||||
|
{
|
||||||
|
if (orientation == Qt::Vertical && role == Qt::DisplayRole) {
|
||||||
|
if (section<0 || section>=mLines.count())
|
||||||
|
return QVariant();
|
||||||
|
PMemoryLine line = mLines[section];
|
||||||
|
return QString("0x%1").arg(line->startAddress,0,16,QChar('0'));
|
||||||
|
}
|
||||||
|
return QVariant();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool MemoryModel::setData(const QModelIndex &index, const QVariant &value, int role)
|
||||||
|
{
|
||||||
|
if (!index.isValid())
|
||||||
|
return false;
|
||||||
|
if (index.row()<0 || index.row()>=mLines.count())
|
||||||
|
return false;
|
||||||
|
PMemoryLine line = mLines[index.row()];
|
||||||
|
int col = index.column();
|
||||||
|
if (col<0 || col>=line->datas.count())
|
||||||
|
return false;
|
||||||
|
if (role == Qt::EditRole && mStartAddress>0) {
|
||||||
|
bool ok;
|
||||||
|
unsigned char val = ("0x"+value.toString()).toUInt(&ok,16);
|
||||||
|
if (!ok || val>255)
|
||||||
|
return false;
|
||||||
|
emit setMemoryData(mStartAddress+mDataPerLine*index.row()+col,val);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
Qt::ItemFlags MemoryModel::flags(const QModelIndex &index) const
|
||||||
|
{
|
||||||
|
Qt::ItemFlags flags = Qt::ItemIsEnabled | Qt::ItemIsSelectable;
|
||||||
|
if (mStartAddress!=0)
|
||||||
|
flags |= Qt::ItemIsEditable;
|
||||||
|
return flags;
|
||||||
|
}
|
||||||
|
|
||||||
|
qulonglong MemoryModel::startAddress() const
|
||||||
|
{
|
||||||
|
return mStartAddress;
|
||||||
|
}
|
||||||
|
|
||||||
|
void MemoryModel::reset()
|
||||||
|
{
|
||||||
|
mStartAddress=0;
|
||||||
|
mLines.clear();
|
||||||
|
}
|
||||||
|
|
|
@ -27,6 +27,7 @@
|
||||||
#include <QQueue>
|
#include <QQueue>
|
||||||
#include <QQueue>
|
#include <QQueue>
|
||||||
#include <QSemaphore>
|
#include <QSemaphore>
|
||||||
|
#include <QSet>
|
||||||
#include <QThread>
|
#include <QThread>
|
||||||
#include <QTimer>
|
#include <QTimer>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
@ -204,6 +205,39 @@ private:
|
||||||
int mUpdateCount;
|
int mUpdateCount;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct MemoryLine {
|
||||||
|
uintptr_t startAddress;
|
||||||
|
QList<unsigned char> datas;
|
||||||
|
QSet<int> changedDatas;
|
||||||
|
};
|
||||||
|
|
||||||
|
using PMemoryLine = std::shared_ptr<MemoryLine>;
|
||||||
|
|
||||||
|
class MemoryModel: public QAbstractTableModel{
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
explicit MemoryModel(int dataPerLine,QObject* parent=nullptr);
|
||||||
|
|
||||||
|
void updateMemory(const QStringList& value);
|
||||||
|
qulonglong startAddress() const;
|
||||||
|
void reset();
|
||||||
|
// QAbstractItemModel interface
|
||||||
|
signals:
|
||||||
|
void setMemoryData(qlonglong address, unsigned char data);
|
||||||
|
public:
|
||||||
|
int rowCount(const QModelIndex &parent) const override;
|
||||||
|
int columnCount(const QModelIndex &parent) const override;
|
||||||
|
QVariant data(const QModelIndex &index, int role) const override;
|
||||||
|
QVariant headerData(int section, Qt::Orientation orientation, int role) const override;
|
||||||
|
bool setData(const QModelIndex &index, const QVariant &value, int role) override;
|
||||||
|
Qt::ItemFlags flags(const QModelIndex &index) const override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
int mDataPerLine;
|
||||||
|
QList<PMemoryLine> mLines;
|
||||||
|
qulonglong mStartAddress;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
class DebugReader;
|
class DebugReader;
|
||||||
class DebugTarget;
|
class DebugTarget;
|
||||||
|
@ -259,12 +293,15 @@ public:
|
||||||
|
|
||||||
RegisterModel *registerModel() const;
|
RegisterModel *registerModel() const;
|
||||||
|
|
||||||
|
MemoryModel *memoryModel() const;
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void evalValueReady(const QString& s);
|
void evalValueReady(const QString& s);
|
||||||
void memoryExamineReady(const QStringList& s);
|
void memoryExamineReady(const QStringList& s);
|
||||||
void localsReady(const QStringList& s);
|
void localsReady(const QStringList& s);
|
||||||
public slots:
|
public slots:
|
||||||
void stop();
|
void stop();
|
||||||
|
void refreshAll();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void sendWatchCommand(PWatchVar var);
|
void sendWatchCommand(PWatchVar var);
|
||||||
|
@ -275,6 +312,7 @@ private:
|
||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
void syncFinishedParsing();
|
void syncFinishedParsing();
|
||||||
|
void setMemoryData(qulonglong address, unsigned char data);
|
||||||
void updateMemory(const QStringList& value);
|
void updateMemory(const QStringList& value);
|
||||||
void updateEval(const QString& value);
|
void updateEval(const QString& value);
|
||||||
void updateDisassembly(const QString& file, const QString& func,const QStringList& value);
|
void updateDisassembly(const QString& file, const QString& func,const QStringList& value);
|
||||||
|
@ -291,6 +329,7 @@ private:
|
||||||
BacktraceModel *mBacktraceModel;
|
BacktraceModel *mBacktraceModel;
|
||||||
WatchModel *mWatchModel;
|
WatchModel *mWatchModel;
|
||||||
RegisterModel *mRegisterModel;
|
RegisterModel *mRegisterModel;
|
||||||
|
MemoryModel *mMemoryModel;
|
||||||
DebugReader *mReader;
|
DebugReader *mReader;
|
||||||
DebugTarget *mTarget;
|
DebugTarget *mTarget;
|
||||||
int mLeftPageIndexBackup;
|
int mLeftPageIndexBackup;
|
||||||
|
|
|
@ -135,6 +135,8 @@ MainWindow::MainWindow(QWidget *parent)
|
||||||
ui->tblBreakpoints->setModel(mDebugger->breakpointModel());
|
ui->tblBreakpoints->setModel(mDebugger->breakpointModel());
|
||||||
ui->tblStackTrace->setModel(mDebugger->backtraceModel());
|
ui->tblStackTrace->setModel(mDebugger->backtraceModel());
|
||||||
ui->watchView->setModel(mDebugger->watchModel());
|
ui->watchView->setModel(mDebugger->watchModel());
|
||||||
|
ui->tblMemoryView->setModel(mDebugger->memoryModel());
|
||||||
|
ui->tblMemoryView->horizontalHeader()->setSectionResizeMode(QHeaderView::ResizeToContents);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
mDebugger->breakpointModel()->load(includeTrailingPathDelimiter(pSettings->dirs().config())
|
mDebugger->breakpointModel()->load(includeTrailingPathDelimiter(pSettings->dirs().config())
|
||||||
|
@ -1116,7 +1118,8 @@ void MainWindow::updateDebuggerSettings()
|
||||||
QFont font(pSettings->debugger().fontName());
|
QFont font(pSettings->debugger().fontName());
|
||||||
font.setPixelSize(pointToPixel(pSettings->debugger().fontSize()));
|
font.setPixelSize(pointToPixel(pSettings->debugger().fontSize()));
|
||||||
ui->debugConsole->setFont(font);
|
ui->debugConsole->setFont(font);
|
||||||
ui->txtMemoryView->setFont(font);
|
ui->tblMemoryView->setFont(font);
|
||||||
|
//ui->txtMemoryView->setFont(font);
|
||||||
ui->txtLocals->setFont(font);
|
ui->txtLocals->setFont(font);
|
||||||
|
|
||||||
int idx = findTabIndex(ui->debugViews,ui->tabDebugConsole);
|
int idx = findTabIndex(ui->debugViews,ui->tabDebugConsole);
|
||||||
|
@ -4421,6 +4424,7 @@ void MainWindow::onDebugEvaluateInput()
|
||||||
connect(mDebugger, &Debugger::evalValueReady,
|
connect(mDebugger, &Debugger::evalValueReady,
|
||||||
this, &MainWindow::onEvalValueReady);
|
this, &MainWindow::onEvalValueReady);
|
||||||
mDebugger->sendCommand("-data-evaluate-expression",s);
|
mDebugger->sendCommand("-data-evaluate-expression",s);
|
||||||
|
pMainWindow->debugger()->refreshAll();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4428,8 +4432,8 @@ void MainWindow::onDebugMemoryAddressInput()
|
||||||
{
|
{
|
||||||
QString s=ui->cbMemoryAddress->currentText().trimmed();
|
QString s=ui->cbMemoryAddress->currentText().trimmed();
|
||||||
if (!s.isEmpty()) {
|
if (!s.isEmpty()) {
|
||||||
connect(mDebugger, &Debugger::memoryExamineReady,
|
// connect(mDebugger, &Debugger::memoryExamineReady,
|
||||||
this, &MainWindow::onMemoryExamineReady);
|
// this, &MainWindow::onMemoryExamineReady);
|
||||||
mDebugger->sendCommand("-data-read-memory",QString("%1 x 1 8 8 ").arg(s));
|
mDebugger->sendCommand("-data-read-memory",QString("%1 x 1 8 8 ").arg(s));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -4487,14 +4491,15 @@ void MainWindow::onEvalValueReady(const QString& value)
|
||||||
|
|
||||||
void MainWindow::onMemoryExamineReady(const QStringList& value)
|
void MainWindow::onMemoryExamineReady(const QStringList& value)
|
||||||
{
|
{
|
||||||
ui->txtMemoryView->clear();
|
// ui->txtMemoryView->clear();
|
||||||
foreach (QString s, value) {
|
// foreach (QString s, value) {
|
||||||
s.replace("\t"," ");
|
// s.replace("\t"," ");
|
||||||
ui->txtMemoryView->appendPlainText(s);
|
// ui->txtMemoryView->appendPlainText(s);
|
||||||
}
|
// }
|
||||||
ui->txtMemoryView->moveCursor(QTextCursor::Start);
|
// ui->txtMemoryView->moveCursor(QTextCursor::Start);
|
||||||
disconnect(mDebugger, &Debugger::memoryExamineReady,
|
|
||||||
this, &MainWindow::onMemoryExamineReady);
|
// disconnect(mDebugger, &Debugger::memoryExamineReady,
|
||||||
|
// this, &MainWindow::onMemoryExamineReady);
|
||||||
}
|
}
|
||||||
|
|
||||||
void MainWindow::onLocalsReady(const QStringList& value)
|
void MainWindow::onLocalsReady(const QStringList& value)
|
||||||
|
|
|
@ -702,7 +702,7 @@
|
||||||
<enum>QTabWidget::North</enum>
|
<enum>QTabWidget::North</enum>
|
||||||
</property>
|
</property>
|
||||||
<property name="currentIndex">
|
<property name="currentIndex">
|
||||||
<number>2</number>
|
<number>4</number>
|
||||||
</property>
|
</property>
|
||||||
<widget class="QWidget" name="tabDebugConsole">
|
<widget class="QWidget" name="tabDebugConsole">
|
||||||
<attribute name="title">
|
<attribute name="title">
|
||||||
|
@ -850,6 +850,13 @@
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
|
<item row="1" column="0" colspan="2">
|
||||||
|
<widget class="QTableView" name="tblMemoryView">
|
||||||
|
<attribute name="horizontalHeaderVisible">
|
||||||
|
<bool>false</bool>
|
||||||
|
</attribute>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
<item row="0" column="1">
|
<item row="0" column="1">
|
||||||
<widget class="QComboBox" name="cbMemoryAddress">
|
<widget class="QComboBox" name="cbMemoryAddress">
|
||||||
<property name="sizePolicy">
|
<property name="sizePolicy">
|
||||||
|
@ -866,16 +873,6 @@
|
||||||
</property>
|
</property>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
<item row="1" column="0" colspan="2">
|
|
||||||
<widget class="QPlainTextEdit" name="txtMemoryView">
|
|
||||||
<property name="lineWrapMode">
|
|
||||||
<enum>QPlainTextEdit::NoWrap</enum>
|
|
||||||
</property>
|
|
||||||
<property name="readOnly">
|
|
||||||
<bool>true</bool>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</item>
|
|
||||||
</layout>
|
</layout>
|
||||||
</widget>
|
</widget>
|
||||||
</widget>
|
</widget>
|
||||||
|
|
|
@ -38,6 +38,7 @@ static BOOL CALLBACK localeEnumProc(
|
||||||
}
|
}
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
ProjectVersionInfoWidget::ProjectVersionInfoWidget(const QString &name, const QString &group, QWidget *parent) :
|
ProjectVersionInfoWidget::ProjectVersionInfoWidget(const QString &name, const QString &group, QWidget *parent) :
|
||||||
SettingsWidget(name,group,parent),
|
SettingsWidget(name,group,parent),
|
||||||
ui(new Ui::ProjectVersionInfoWidget)
|
ui(new Ui::ProjectVersionInfoWidget)
|
||||||
|
|
|
@ -1077,3 +1077,12 @@ float desktopDpi()
|
||||||
{
|
{
|
||||||
return qApp->desktop()->logicalDpiY();
|
return qApp->desktop()->logicalDpiY();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
qulonglong stringToHex(const QString &str, qulonglong defaultValue)
|
||||||
|
{
|
||||||
|
bool isOk;
|
||||||
|
qulonglong value = str.toULongLong(&isOk,16);
|
||||||
|
if (isOk)
|
||||||
|
return value;
|
||||||
|
return defaultValue;
|
||||||
|
}
|
||||||
|
|
|
@ -190,6 +190,7 @@ bool stringIsBlank(const QString& s);
|
||||||
int compareFileModifiedTime(const QString& filename1, const QString& filename2);
|
int compareFileModifiedTime(const QString& filename1, const QString& filename2);
|
||||||
QByteArray getHTTPBody(const QByteArray& content);
|
QByteArray getHTTPBody(const QByteArray& content);
|
||||||
bool haveGoodContrast(const QColor& c1, const QColor &c2);
|
bool haveGoodContrast(const QColor& c1, const QColor &c2);
|
||||||
|
qulonglong stringToHex(const QString& str, qulonglong defaultValue = 0);
|
||||||
|
|
||||||
//void changeTheme(const QString& themeName);
|
//void changeTheme(const QString& themeName);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue