Add filterable texture list to texture viewer

This commit is contained in:
baldurk
2016-10-10 18:48:38 +02:00
parent a1e9554e66
commit 2507634df9
8 changed files with 377 additions and 13 deletions
+23
View File
@@ -0,0 +1,23 @@
#include "RDListView.h"
#include <QMouseEvent>
RDListView::RDListView(QWidget *parent) : QListView(parent)
{
setMouseTracking(true);
}
void RDListView::mouseMoveEvent(QMouseEvent *e)
{
emit mouseMove(e);
if(indexAt(e->pos()).isValid() && m_Shape != Qt::ArrowCursor)
{
setCursor(QCursor(m_Shape));
}
else if(m_Shape != Qt::ArrowCursor)
{
unsetCursor();
}
QListView::mouseMoveEvent(e);
}
+24
View File
@@ -0,0 +1,24 @@
#ifndef RDLISTVIEW_H
#define RDLISTVIEW_H
#include <QListView>
class RDListView : public QListView
{
Q_OBJECT
public:
explicit RDListView(QWidget *parent = 0);
void setHoverCursor(Qt::CursorShape shape) { m_Shape = shape; }
signals:
void mouseMove(QMouseEvent *e);
public slots:
private:
void mouseMoveEvent(QMouseEvent *e) override;
Qt::CursorShape m_Shape = Qt::ArrowCursor;
};
#endif // RDLISTVIEW_H
+204 -5
View File
@@ -27,6 +27,8 @@
#include <QColorDialog>
#include <QJsonDocument>
#include <QMenu>
#include <QPainter>
#include <QStyledItemDelegate>
#include "3rdparty/toolwindowmanager/ToolWindowManagerArea.h"
#include "Code/CaptureContext.h"
#include "Widgets/ResourcePreview.h"
@@ -317,6 +319,140 @@ ShaderBindpointMapping Following::GetMapping(CaptureContext *ctx)
return GetMapping(ctx, Stage);
}
class TextureListItemModel : public QAbstractItemModel
{
public:
enum FilterType
{
Textures,
RenderTargets,
String
};
TextureListItemModel(QObject *parent) : QAbstractItemModel(parent) {}
void reset(FilterType type, const QString &filter, CaptureContext *ctx)
{
const rdctype::array<FetchTexture> src = ctx->GetTextures();
texs.clear();
texs.reserve(src.count);
emit beginResetModel();
int rtFlags = eTextureCreate_RTV | eTextureCreate_DSV;
for(const FetchTexture &t : src)
{
if(type == Textures)
{
if((t.creationFlags & rtFlags) == 0)
texs.push_back(t);
}
else if(type == RenderTargets)
{
if((t.creationFlags & rtFlags))
texs.push_back(t);
}
else
{
if(filter.isEmpty())
texs.push_back(t);
else if(QString(t.name).contains(filter, Qt::CaseInsensitive))
texs.push_back(t);
}
}
emit endResetModel();
}
QModelIndex index(int row, int column, const QModelIndex &parent = QModelIndex()) const override
{
if(row < 0 || row >= rowCount())
return QModelIndex();
return createIndex(row, 0);
}
QModelIndex parent(const QModelIndex &index) const override { return QModelIndex(); }
int rowCount(const QModelIndex &parent = QModelIndex()) const override { return texs.count(); }
int columnCount(const QModelIndex &parent = QModelIndex()) const override { return 1; }
Qt::ItemFlags flags(const QModelIndex &index) const override
{
if(!index.isValid())
return 0;
return QAbstractItemModel::flags(index);
}
QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override
{
if(index.isValid())
{
if(role == Qt::DisplayRole)
{
if(index.row() >= 0 && index.row() < texs.count())
return QVariant(texs[index.row()].name);
}
if(role == Qt::UserRole)
{
return QVariant::fromValue(texs[index.row()].ID);
}
if(role == Qt::DecorationRole)
{
QIcon goArrow;
goArrow.addFile(QStringLiteral(":/Resources/RightArrow_Gray_16x16.png"), QSize(),
QIcon::Normal, QIcon::Off);
goArrow.addFile(QStringLiteral(":/Resources/RightArrow_Green_16x16.png"), QSize(),
QIcon::Active, QIcon::Off);
return QVariant(goArrow);
}
}
return QVariant();
}
private:
QVector<FetchTexture> texs;
};
class TextureListItemDelegate : public QItemDelegate
{
public:
TextureListItemDelegate(QObject *parent = 0) : QItemDelegate(parent) {}
void paint(QPainter *painter, const QStyleOptionViewItem &opt, const QModelIndex &index) const override
{
if(index.isValid())
{
QStyleOptionViewItem option = opt;
option.decorationAlignment = Qt::AlignBaseline | Qt::AlignRight;
painter->eraseRect(option.rect);
QIcon icon = index.model()->data(index, Qt::DecorationRole).value<QIcon>();
drawBackground(painter, option, index);
if(option.state & QStyle::State_MouseOver)
drawDecoration(painter, option, option.rect,
icon.pixmap(option.decorationSize, QIcon::Active));
else
drawDecoration(painter, option, option.rect,
icon.pixmap(option.decorationSize, QIcon::Normal));
drawDisplay(painter, option, option.rect,
index.model()->data(index, Qt::DisplayRole).toString());
drawFocus(painter, option, option.rect);
if(option.state & QStyle::State_MouseOver)
{
QRect r = option.rect;
r.adjust(0, 0, -1, -1);
painter->drawRect(r);
}
}
}
};
FetchTexture *TextureViewer::GetCurrentTexture()
{
if(!m_Ctx->LogLoaded())
@@ -395,6 +531,8 @@ TextureViewer::TextureViewer(CaptureContext *ctx, QWidget *parent)
ui->dockarea->areaOf(ui->outputThumbs), 0.25f));
ui->dockarea->setToolWindowProperties(ui->pixelContextLayout, ToolWindowManager::HideCloseButton);
ui->dockarea->addToolWindow(ui->textureListFrame, ToolWindowManager::NoArea);
ui->dockarea->setAllowFloatingWindow(false);
ui->dockarea->setRubberBandLineWidth(50);
@@ -402,6 +540,9 @@ TextureViewer::TextureViewer(CaptureContext *ctx, QWidget *parent)
ui->pixelContextLayout->setWindowTitle(tr("Pixel Context"));
ui->outputThumbs->setWindowTitle(tr("Outputs"));
ui->inputThumbs->setWindowTitle(tr("Inputs"));
ui->textureListFrame->setWindowTitle(tr("Texture List"));
ui->textureList->setHoverCursor(Qt::PointingHandCursor);
m_Goto = new TextureGoto(this, [this](QPoint p) { GotoLocation(p.x(), p.y()); });
@@ -464,6 +605,12 @@ TextureViewer::TextureViewer(CaptureContext *ctx, QWidget *parent)
tr("Quad Overdraw (Pass)"), tr("Quad Overdraw (Draw)"),
tr("Triangle Size (Pass)"), tr("Triangle Size (Draw)")});
ui->textureListFilter->addItems({"", "Textures", "Render Targets"});
ui->textureList->setModel(new TextureListItemModel(this));
ui->textureList->setItemDelegate(new TextureListItemDelegate(ui->textureList));
ui->textureList->viewport()->setAttribute(Qt::WA_Hover);
ui->zoomOption->setCurrentText("");
ui->fitToWindow->toggle();
@@ -1986,7 +2133,7 @@ void TextureViewer::render_mouseMove(QMouseEvent *e)
if(e->buttons() == Qt::NoButton)
{
ui->render->setCursor(QCursor(Qt::ArrowCursor));
ui->render->unsetCursor();
}
UI_UpdateStatusText();
@@ -2247,6 +2394,10 @@ void TextureViewer::OnLogfileLoaded()
WId renderID = ui->render->winId();
WId contextID = ui->pixelContext->winId();
TextureListItemModel *model = (TextureListItemModel *)ui->textureList->model();
model->reset(TextureListItemModel::String, "", m_Ctx);
m_TexDisplay.darkBackgroundColour =
FloatVector(darkBack.redF(), darkBack.greenF(), darkBack.blueF(), 1.0f);
m_TexDisplay.lightBackgroundColour =
@@ -2734,10 +2885,58 @@ void TextureViewer::on_viewTexBuffer_clicked()
{
}
void TextureViewer::on_texListShow_clicked()
{
}
void TextureViewer::on_saveTex_clicked()
{
}
void TextureViewer::on_texListShow_clicked()
{
if(ui->textureListFrame->isVisible())
{
ui->dockarea->moveToolWindow(ui->textureListFrame, ToolWindowManager::NoArea);
}
else
{
ui->textureListFilter->setCurrentText("");
ui->dockarea->moveToolWindow(
ui->textureListFrame,
ToolWindowManager::AreaReference(ToolWindowManager::LeftOf,
ui->dockarea->areaOf(ui->renderContainer), 0.2f));
}
}
void TextureViewer::on_cancelTextureListFilter_clicked()
{
ui->textureListFilter->setCurrentText("");
}
void TextureViewer::on_textureListFilter_editTextChanged(const QString &text)
{
TextureListItemModel *model = (TextureListItemModel *)ui->textureList->model();
if(model == NULL)
return;
model->reset(TextureListItemModel::String, text, m_Ctx);
}
void TextureViewer::on_textureListFilter_currentIndexChanged(int index)
{
TextureListItemModel *model = (TextureListItemModel *)ui->textureList->model();
if(model == NULL)
return;
if(ui->textureListFilter->currentIndex() == 1)
model->reset(TextureListItemModel::Textures, "", m_Ctx);
else if(ui->textureListFilter->currentIndex() == 2)
model->reset(TextureListItemModel::RenderTargets, "", m_Ctx);
else
model->reset(TextureListItemModel::String, ui->textureListFilter->currentText(), m_Ctx);
}
void TextureViewer::on_textureList_clicked(const QModelIndex &index)
{
ResourceId id = index.model()->data(index, Qt::UserRole).value<ResourceId>();
ViewTexture(id, false);
}
+10 -6
View File
@@ -145,7 +145,6 @@ private slots:
void on_mipLevel_currentIndexChanged(int index);
void on_sliceFace_currentIndexChanged(int index);
void on_overlay_currentIndexChanged(int index);
void on_zoomRange_clicked();
@@ -155,6 +154,16 @@ private slots:
void on_backcolorPick_clicked();
void on_checkerBack_clicked();
void on_locationGoto_clicked();
void on_viewTexBuffer_clicked();
void on_texListShow_clicked();
void on_saveTex_clicked();
void on_cancelTextureListFilter_clicked();
void on_textureListFilter_editTextChanged(const QString &text);
void on_textureListFilter_currentIndexChanged(int index);
void on_textureList_clicked(const QModelIndex &index);
// manual slots
void render_mouseClick(QMouseEvent *e);
void render_mouseMove(QMouseEvent *e);
@@ -175,11 +184,6 @@ private slots:
void channelsWidget_toggled(bool checked) { UI_UpdateChannels(); }
void channelsWidget_selected(int index) { UI_UpdateChannels(); }
void on_locationGoto_clicked();
void on_viewTexBuffer_clicked();
void on_texListShow_clicked();
void on_saveTex_clicked();
private:
void RT_FetchCurrentPixel(uint32_t x, uint32_t y, PixelValue &pickValue, PixelValue &realValue);
void RT_PickPixelsAndUpdate(IReplayRenderer *);
+100
View File
@@ -1089,6 +1089,101 @@
</rect>
</property>
</widget>
<widget class="QFrame" name="textureListFrame">
<property name="geometry">
<rect>
<x>480</x>
<y>60</y>
<width>274</width>
<height>244</height>
</rect>
</property>
<property name="frameShape">
<enum>QFrame::NoFrame</enum>
</property>
<property name="frameShadow">
<enum>QFrame::Plain</enum>
</property>
<layout class="QVBoxLayout" name="verticalLayout">
<property name="spacing">
<number>6</number>
</property>
<property name="leftMargin">
<number>3</number>
</property>
<property name="topMargin">
<number>3</number>
</property>
<property name="rightMargin">
<number>3</number>
</property>
<property name="bottomMargin">
<number>3</number>
</property>
<item>
<layout class="QHBoxLayout" name="textureListControls">
<property name="spacing">
<number>0</number>
</property>
<item>
<widget class="QComboBox" name="textureListFilter">
<property name="sizePolicy">
<sizepolicy hsizetype="MinimumExpanding" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="editable">
<bool>true</bool>
</property>
</widget>
</item>
<item>
<widget class="QToolButton" name="cancelTextureListFilter">
<property name="text">
<string/>
</property>
<property name="icon">
<iconset resource="../resources.qrc">
<normaloff>:/Resources/cross.png</normaloff>:/Resources/cross.png</iconset>
</property>
<property name="autoRaise">
<bool>true</bool>
</property>
</widget>
</item>
</layout>
</item>
<item>
<widget class="RDListView" name="textureList">
<property name="frameShape">
<enum>QFrame::Box</enum>
</property>
<property name="frameShadow">
<enum>QFrame::Sunken</enum>
</property>
<property name="editTriggers">
<set>QAbstractItemView::NoEditTriggers</set>
</property>
<property name="showDropIndicator" stdset="0">
<bool>false</bool>
</property>
<property name="defaultDropAction">
<enum>Qt::CopyAction</enum>
</property>
<property name="selectionMode">
<enum>QAbstractItemView::NoSelection</enum>
</property>
<property name="viewMode">
<enum>QListView::ListMode</enum>
</property>
<property name="uniformItemSizes">
<bool>true</bool>
</property>
</widget>
</item>
</layout>
</widget>
</widget>
<customwidgets>
<customwidget>
@@ -1107,6 +1202,11 @@
<header>Widgets/ThumbnailStrip.h</header>
<container>1</container>
</customwidget>
<customwidget>
<class>RDListView</class>
<extends>QListView</extends>
<header>Widgets/RDListView.h</header>
</customwidget>
</customwidgets>
<resources>
<include location="../resources.qrc"/>
+4 -2
View File
@@ -98,7 +98,8 @@ SOURCES += Code/qrenderdoc.cpp \
Widgets/ThumbnailStrip.cpp \
Code/CommonPipelineState.cpp \
Widgets/TextureGoto.cpp \
Widgets/RDDoubleSpinBox.cpp
Widgets/RDDoubleSpinBox.cpp \
Widgets/RDListView.cpp
HEADERS += Windows/MainWindow.h \
Windows/EventBrowser.h \
@@ -118,7 +119,8 @@ HEADERS += Windows/MainWindow.h \
Widgets/ThumbnailStrip.h \
Code/CommonPipelineState.h \
Widgets/TextureGoto.h \
Widgets/RDDoubleSpinBox.h
Widgets/RDDoubleSpinBox.h \
Widgets/RDListView.h
FORMS += Windows/MainWindow.ui \
Windows/EventBrowser.ui \
+3
View File
@@ -286,6 +286,7 @@
<ClCompile Include="generated\moc_RDLabel.cpp" />
<ClCompile Include="generated\moc_RDLineEdit.cpp" />
<ClCompile Include="generated\moc_MainWindow.cpp" />
<ClCompile Include="generated\moc_RDListView.cpp" />
<ClCompile Include="generated\moc_ResourcePreview.cpp" />
<ClCompile Include="generated\moc_TextureGoto.cpp" />
<ClCompile Include="generated\moc_TextureViewer.cpp" />
@@ -296,6 +297,7 @@
<ClCompile Include="generated\qrc_resources.cpp" />
<ClCompile Include="Widgets\RDDoubleSpinBox.cpp" />
<ClCompile Include="Widgets\RDLabel.cpp" />
<ClCompile Include="Widgets\RDListView.cpp" />
<ClCompile Include="Widgets\ResourcePreview.cpp" />
<ClCompile Include="Widgets\TextureGoto.cpp" />
<ClCompile Include="Widgets\ThumbnailStrip.cpp" />
@@ -332,6 +334,7 @@
<ClInclude Include="generated\ui_ThumbnailStrip.h" />
<ClInclude Include="Widgets\RDDoubleSpinBox.h" />
<ClInclude Include="Widgets\RDLabel.h" />
<ClInclude Include="Widgets\RDListView.h" />
<ClInclude Include="Widgets\ResourcePreview.h" />
<ClInclude Include="Widgets\TextureGoto.h" />
<ClInclude Include="Widgets\ThumbnailStrip.h" />
@@ -148,6 +148,12 @@
<ClCompile Include="Widgets\RDDoubleSpinBox.cpp">
<Filter>Widgets</Filter>
</ClCompile>
<ClCompile Include="generated\moc_RDListView.cpp">
<Filter>Generated Files</Filter>
</ClCompile>
<ClCompile Include="Widgets\RDListView.cpp">
<Filter>Widgets</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<ClInclude Include="3rdparty\flowlayout\FlowLayout.h">
@@ -213,6 +219,9 @@
<ClInclude Include="Widgets\RDDoubleSpinBox.h">
<Filter>Widgets</Filter>
</ClInclude>
<ClInclude Include="Widgets\RDListView.h">
<Filter>Widgets</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<None Include="resources.qrc">