/
githubmirror
/
x64dbg
Обзор
Документация
Войти
/
githubmirror
/
x64dbg
Код
Запросы
0
Пакеты
0
Релизы
0
Аналитика
Безопасность
development
src/gui/Src/BasicView/LabeledSplitter.cpp
289 строк
8 KB
Duncan Ogilvie
Refactor AbstractTableView for cross-platform
19 сен 2023, 07:25
19 сен 2023, 07:25
7733012
Код
Авторство
О чём код?
#include "LabeledSplitter.h" #include "LabeledSplitterDetachedWindow.h" #include <QPainter> #include <QpaintEvent> #include <QMenu> #include <QDesktopWidget> #include <QApplication> #include "Bridge.h" #include "Configuration.h" //LabeledSplitterHandle class LabeledSplitterHandle::LabeledSplitterHandle(Qt::Orientation o, LabeledSplitter* parent) : QSplitterHandle(o, parent) { charHeight = QFontMetrics(font()).height(); setMouseTracking(true); originalSize = 0; } QSize LabeledSplitterHandle::sizeHint() const { QSize size; size.setHeight(charHeight + 2); return std::move(size); } QSize LabeledSplitterHandle::minimumSizeHint() const { return sizeHint(); } LabeledSplitter* LabeledSplitterHandle::getParent() const { return qobject_cast<LabeledSplitter*>(parent()); } int LabeledSplitterHandle::getIndex() { return getParent()->indexOf(this); } void LabeledSplitter::setupContextMenu() { mMenu = new QMenu(this); mExpandCollapseAction = new QAction(this); connect(mExpandCollapseAction, SIGNAL(triggered()), this, SLOT(collapseSlot())); mMenu->addAction(mExpandCollapseAction); QAction* mDetach = new QAction(tr("&Detach"), this); connect(mDetach, SIGNAL(triggered()), this, SLOT(detachSlot())); mMenu->addAction(mDetach); } void LabeledSplitterHandle::contextMenuEvent(QContextMenuEvent* event) { getParent()->currentIndex = getIndex(); QSplitterHandle::contextMenuEvent(event); return; } void LabeledSplitter::collapseSlot() { auto sizes = this->sizes(); int index2; int* originalSize = &(qobject_cast<LabeledSplitterHandle*>(handle(currentIndex))->originalSize); for(index2 = currentIndex - 1; sizes.at(index2) == 0 && index2 != 0; index2--); if(sizes.at(currentIndex) == 0) { if(*originalSize == 0) *originalSize = 100; if(sizes[index2] > *originalSize) sizes[index2] -= *originalSize; sizes[currentIndex] = *originalSize; } else { *originalSize = sizes[currentIndex]; sizes[currentIndex] = 0; sizes[index2] += *originalSize; } setSizes(sizes); } // Convert a tab to an external window void LabeledSplitter::detachSlot() { // Create the window LabeledSplitterDetachedWindow* detachedWidget = new LabeledSplitterDetachedWindow(this, this); detachedWidget->setWindowModality(Qt::NonModal); // Find Widget and connect connect(detachedWidget, SIGNAL(OnClose(LabeledSplitterDetachedWindow*)), this, SLOT(attachSlot(LabeledSplitterDetachedWindow*))); detachedWidget->setWindowTitle(mNames.at(currentIndex)); detachedWidget->index = currentIndex; // Remove from splitter QWidget* tearOffWidget = widget(currentIndex); tearOffWidget->setParent(detachedWidget); // Add it to the windows list mWindows.append(tearOffWidget); // Create and show detachedWidget->setCentralWidget(tearOffWidget); // Needs to be done explicitly tearOffWidget->showNormal(); QRect screenGeometry = QApplication::desktop()->screenGeometry(); int w = 640; int h = 480; int x = (screenGeometry.width() - w) / 2; int y = (screenGeometry.height() - h) / 2; detachedWidget->showNormal(); detachedWidget->setGeometry(x, y, w, h); detachedWidget->showNormal(); mNames.removeAt(currentIndex); } void LabeledSplitter::attachSlot(LabeledSplitterDetachedWindow* widget) { // Retrieve widget QWidget* tearOffWidget = widget->centralWidget(); // Remove it from the windows list for(int i = 0; i < mWindows.size(); i++) { if(mWindows.at(i) == tearOffWidget) { mWindows.removeAt(i); } } // Make Active insertWidget(widget->index, tearOffWidget, widget->windowTitle()); // Cleanup Window disconnect(widget, SIGNAL(OnClose(QWidget*)), this, SLOT(attachSlot(LabeledSplitterDetachedWindow*))); widget->hide(); widget->close(); } void LabeledSplitterHandle::paintEvent(QPaintEvent* event) { QPainter painter(this); const QRect & rect = event->rect(); painter.fillRect(rect, Qt::gray); painter.setPen(Qt::black); LabeledSplitter* parent = getParent(); int index = parent->indexOf(this); if(parent->sizes().at(index) != 0) { //hidden QPoint points[3] = {QPoint(charHeight / 5, charHeight / 3), QPoint(charHeight * 4 / 5, charHeight / 3), QPoint(charHeight / 2, charHeight * 2 / 3)}; painter.setPen(Qt::black); painter.setBrush(Qt::green); painter.drawConvexPolygon(points, 3); } else { QPoint points[3] = {QPoint(charHeight / 5, charHeight * 2 / 3), QPoint(charHeight * 4 / 5, charHeight * 2 / 3), QPoint(charHeight / 2, charHeight / 3)}; painter.setPen(Qt::black); painter.setBrush(Qt::green); painter.drawConvexPolygon(points, 3); painter.drawLine(rect.left(), rect.height() - 1, rect.right(), rect.height() - 1); } QRect textRect(rect.left() + charHeight, rect.top(), rect.width() - charHeight, rect.height()); painter.drawText(textRect, 0, parent->mNames.at(index)); } void LabeledSplitterHandle::mouseMoveEvent(QMouseEvent* event) { if(event->x() <= charHeight) { this->setCursor(QCursor(Qt::ArrowCursor)); event->accept(); } else { this->setCursor(QCursor(Qt::SplitVCursor)); QSplitterHandle::mouseMoveEvent(event); } } void LabeledSplitterHandle::mousePressEvent(QMouseEvent* event) { if(event->x() <= charHeight && event->button() & Qt::LeftButton) { LabeledSplitter* parent = getParent(); auto sizes = parent->sizes(); int index = parent->indexOf(this); int index2; for(index2 = index - 1; sizes.at(index2) == 0 && index2 != 0; index2--); if(sizes.at(index) == 0) { if(originalSize == 0) originalSize = 100; if(sizes[index2] > originalSize) sizes[index2] -= originalSize; sizes[index] = originalSize; } else { originalSize = sizes[index]; sizes[index] = 0; sizes[index2] += originalSize; } parent->setSizes(sizes); event->accept(); } else QSplitterHandle::mousePressEvent(event); } // LabeledSplitter class LabeledSplitter::LabeledSplitter(QWidget* parent) : QSplitter(Qt::Vertical, parent) { setupContextMenu(); } QSplitterHandle* LabeledSplitter::createHandle() { return new LabeledSplitterHandle(orientation(), this); } void LabeledSplitter::addWidget(QWidget* widget, const QString & name) { mNames.push_back(name); addWidget(widget); } void LabeledSplitter::addWidget(QWidget* widget) { QSplitter::addWidget(widget); } void LabeledSplitter::collapseLowerTabs() { if(count() > 3) { auto size = sizes(); size[0] = 1; size[1] = 1; size[2] = 1; for(int i = 3; i < size.count(); i++) size[i] = 0; setSizes(size); } } void LabeledSplitter::insertWidget(int index, QWidget* widget, const QString & name) { mNames.insert(index, name); insertWidget(index, widget); } void LabeledSplitter::insertWidget(int index, QWidget* widget) { QSplitter::insertWidget(index, widget); } void LabeledSplitter::contextMenuEvent(QContextMenuEvent* event) { event->accept(); if(sizes().at(currentIndex) != 0) mExpandCollapseAction->setText(tr("&Collapse")); else mExpandCollapseAction->setText(tr("&Expand")); mMenu->exec(mapToGlobal(event->pos())); } void LabeledSplitter::loadFromConfig(const QString & configName) { if(!configName.isEmpty()) { mConfigName = configName; char state[MAX_SETTING_SIZE]; memset(state, 0, sizeof(state)); BridgeSettingGet("Gui", mConfigName.toUtf8().constData(), state); size_t sizeofState = strlen(state); if(sizeofState > 0) this->restoreState(QByteArray::fromBase64(QByteArray(state, int(sizeofState)))); connect(Bridge::getBridge(), SIGNAL(close()), this, SLOT(shutdownSlot())); } } void LabeledSplitter::shutdownSlot() { if(Config()->getBool("Gui", "SaveColumnOrder")) BridgeSettingSet("Gui", mConfigName.toUtf8().constData(), this->saveState().toBase64().data()); }