From 5b74d2f90ac489451a9d8f16443c41a190293cf1 Mon Sep 17 00:00:00 2001 From: baldurk Date: Fri, 22 Jul 2016 12:28:26 +0200 Subject: [PATCH] Add a little Ctrl-G popup on the texture viewer to jump to a pixel --- docs/getting_started/tips_tricks.rst | 1 + docs/window/texture_viewer.rst | 15 ++ .../Windows/Dialogs/TextureGoto.Designer.cs | 144 ++++++++++++++++++ renderdocui/Windows/Dialogs/TextureGoto.cs | 117 ++++++++++++++ renderdocui/Windows/Dialogs/TextureGoto.resx | 126 +++++++++++++++ renderdocui/Windows/TextureViewer.Designer.cs | 41 +++-- renderdocui/Windows/TextureViewer.cs | 62 +++++++- renderdocui/renderdocui.csproj | 9 ++ 8 files changed, 498 insertions(+), 17 deletions(-) create mode 100644 renderdocui/Windows/Dialogs/TextureGoto.Designer.cs create mode 100644 renderdocui/Windows/Dialogs/TextureGoto.cs create mode 100644 renderdocui/Windows/Dialogs/TextureGoto.resx diff --git a/docs/getting_started/tips_tricks.rst b/docs/getting_started/tips_tricks.rst index ad206cead..48e8aa738 100644 --- a/docs/getting_started/tips_tricks.rst +++ b/docs/getting_started/tips_tricks.rst @@ -97,4 +97,5 @@ This page is a random hodge-podge of different tips and tricks that might not be D3DSetBlobPart(strippedBlob->GetBufferPointer(), strippedBlob->GetBufferSize(), D3D_BLOB_PRIVATE_DATA, 0, &path, pathSize, &annotatedBlob); // use annotatedBlob instead of strippedBlob from here on +#. You can hit :kbd:`Ctrl-G` to open a popup that lets you jump to a particular co-ordinate. #. More coming soon hopefully :). diff --git a/docs/window/texture_viewer.rst b/docs/window/texture_viewer.rst index 46cf65500..e5015b544 100644 --- a/docs/window/texture_viewer.rst +++ b/docs/window/texture_viewer.rst @@ -238,6 +238,21 @@ This button opens the texture in the :doc:`raw buffer viewer `. T The buffer viewer may not be able to handle the full number of columns that are appropriate for the full width of a texture, so it is better to limit the number of columns and manually calculate the offset into the table of data. +Goto Location +~~~~~~~~~~~~~ + +.. |find| image:: ../imgs/icons/find.png + +.. + + | |find| Goto pixel location + +This button opens a small popup above the main texture view that lets you type in a pixel location to jump to. This is useful if you're investigating a particular issue where you know what pixel the problem will lie on. + +.. note:: + + This popup is also available with the keyboard shortcut :kbd:`Ctrl-G`. + Zoom Controls ~~~~~~~~~~~~~~~~~ diff --git a/renderdocui/Windows/Dialogs/TextureGoto.Designer.cs b/renderdocui/Windows/Dialogs/TextureGoto.Designer.cs new file mode 100644 index 000000000..287b659fc --- /dev/null +++ b/renderdocui/Windows/Dialogs/TextureGoto.Designer.cs @@ -0,0 +1,144 @@ +namespace renderdocui.Windows.Dialogs +{ + partial class TextureGoto + { + /// + /// Required designer variable. + /// + private System.ComponentModel.IContainer components = null; + + /// + /// Clean up any resources being used. + /// + /// true if managed resources should be disposed; otherwise, false. + protected override void Dispose(bool disposing) + { + if (disposing && (components != null)) + { + components.Dispose(); + } + base.Dispose(disposing); + } + + #region Windows Form Designer generated code + + /// + /// Required method for Designer support - do not modify + /// the contents of this method with the code editor. + /// + private void InitializeComponent() + { + System.Windows.Forms.TableLayoutPanel tableLayoutPanel1; + System.Windows.Forms.Label label1; + this.chooseX = new System.Windows.Forms.NumericUpDown(); + this.chooseY = new System.Windows.Forms.NumericUpDown(); + tableLayoutPanel1 = new System.Windows.Forms.TableLayoutPanel(); + label1 = new System.Windows.Forms.Label(); + tableLayoutPanel1.SuspendLayout(); + ((System.ComponentModel.ISupportInitialize)(this.chooseX)).BeginInit(); + ((System.ComponentModel.ISupportInitialize)(this.chooseY)).BeginInit(); + this.SuspendLayout(); + // + // tableLayoutPanel1 + // + tableLayoutPanel1.AutoSize = true; + tableLayoutPanel1.ColumnCount = 2; + tableLayoutPanel1.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 50F)); + tableLayoutPanel1.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 50F)); + tableLayoutPanel1.Controls.Add(this.chooseX, 0, 1); + tableLayoutPanel1.Controls.Add(this.chooseY, 1, 1); + tableLayoutPanel1.Controls.Add(label1, 0, 0); + tableLayoutPanel1.Dock = System.Windows.Forms.DockStyle.Fill; + tableLayoutPanel1.Location = new System.Drawing.Point(4, 4); + tableLayoutPanel1.Name = "tableLayoutPanel1"; + tableLayoutPanel1.RowCount = 2; + tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle()); + tableLayoutPanel1.RowStyles.Add(new System.Windows.Forms.RowStyle()); + tableLayoutPanel1.Size = new System.Drawing.Size(137, 39); + tableLayoutPanel1.TabIndex = 0; + // + // label1 + // + label1.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left) + | System.Windows.Forms.AnchorStyles.Right))); + label1.AutoSize = true; + tableLayoutPanel1.SetColumnSpan(label1, 2); + label1.Location = new System.Drawing.Point(3, 0); + label1.Name = "label1"; + label1.Size = new System.Drawing.Size(131, 13); + label1.TabIndex = 0; + label1.Text = "Goto Location"; + label1.TextAlign = System.Drawing.ContentAlignment.BottomCenter; + // + // chooseX + // + this.chooseX.Location = new System.Drawing.Point(3, 16); + this.chooseX.Maximum = new decimal(new int[] { + 16384, + 0, + 0, + 0}); + this.chooseX.Name = "chooseX"; + this.chooseX.Size = new System.Drawing.Size(62, 20); + this.chooseX.TabIndex = 1; + this.chooseX.Value = new decimal(new int[] { + 16384, + 0, + 0, + 0}); + this.chooseX.Enter += new System.EventHandler(this.location_Enter); + this.chooseX.KeyDown += new System.Windows.Forms.KeyEventHandler(this.location_KeyDown); + // + // chooseY + // + this.chooseY.Location = new System.Drawing.Point(71, 16); + this.chooseY.Maximum = new decimal(new int[] { + 16384, + 0, + 0, + 0}); + this.chooseY.Name = "chooseY"; + this.chooseY.Size = new System.Drawing.Size(63, 20); + this.chooseY.TabIndex = 2; + this.chooseY.Value = new decimal(new int[] { + 16384, + 0, + 0, + 0}); + this.chooseY.Enter += new System.EventHandler(this.location_Enter); + this.chooseY.KeyDown += new System.Windows.Forms.KeyEventHandler(this.location_KeyDown); + // + // TextureGoto + // + this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F); + this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; + this.AutoSize = true; + this.ClientSize = new System.Drawing.Size(145, 47); + this.ControlBox = false; + this.Controls.Add(tableLayoutPanel1); + this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle; + this.MaximizeBox = false; + this.MinimizeBox = false; + this.Name = "TextureGoto"; + this.Padding = new System.Windows.Forms.Padding(4); + this.ShowIcon = false; + this.ShowInTaskbar = false; + this.SizeGripStyle = System.Windows.Forms.SizeGripStyle.Hide; + this.StartPosition = System.Windows.Forms.FormStartPosition.Manual; + this.TopMost = true; + this.Deactivate += new System.EventHandler(this.TextureGoto_Deactivate); + tableLayoutPanel1.ResumeLayout(false); + tableLayoutPanel1.PerformLayout(); + ((System.ComponentModel.ISupportInitialize)(this.chooseX)).EndInit(); + ((System.ComponentModel.ISupportInitialize)(this.chooseY)).EndInit(); + this.ResumeLayout(false); + this.PerformLayout(); + + } + + #endregion + + private System.Windows.Forms.NumericUpDown chooseX; + private System.Windows.Forms.NumericUpDown chooseY; + } +} \ No newline at end of file diff --git a/renderdocui/Windows/Dialogs/TextureGoto.cs b/renderdocui/Windows/Dialogs/TextureGoto.cs new file mode 100644 index 000000000..f135f9b36 --- /dev/null +++ b/renderdocui/Windows/Dialogs/TextureGoto.cs @@ -0,0 +1,117 @@ +using System; +using System.Collections.Generic; +using System.ComponentModel; +using System.Data; +using System.Drawing; +using System.Linq; +using System.Text; +using System.Windows.Forms; + +namespace renderdocui.Windows.Dialogs +{ + public partial class TextureGoto : Form + { + public delegate void OnFinishedMethod(int x, int y); + + private OnFinishedMethod m_FinishedCallback; + + public TextureGoto(OnFinishedMethod callback) + { + InitializeComponent(); + + m_FinishedCallback = callback; + } + + public int X + { + get + { + try + { + return (int)chooseX.Value; + } + catch (System.ArgumentOutOfRangeException) + { + return 0; + } + } + set + { + try + { + chooseX.Value = (decimal)value; + } + catch (System.ArgumentOutOfRangeException) + { + chooseX.Value = 0; + } + } + } + + public int Y + { + get + { + try + { + return (int)chooseY.Value; + } + catch (System.ArgumentOutOfRangeException) + { + return 0; + } + } + set + { + try + { + chooseY.Value = (decimal)value; + } + catch (System.ArgumentOutOfRangeException) + { + chooseY.Value = 0; + } + } + } + + public void Show(Control parent, Point p) + { + X = p.X; + Y = p.Y; + + Location = new Point( + parent.PointToScreen(parent.Location).X + parent.ClientRectangle.Width / 2 - ClientRectangle.Width / 2, + parent.PointToScreen(parent.Location).Y + parent.ClientRectangle.Height / 2 - ClientRectangle.Height / 2 + ); + + Show(); + + chooseY.Select(); + chooseX.Select(); + } + + private void location_KeyDown(object sender, KeyEventArgs e) + { + if (e.KeyCode == Keys.Enter) + { + m_FinishedCallback(X, Y); + Hide(); + return; + } + } + + private void TextureGoto_Deactivate(object sender, EventArgs e) + { + Hide(); + } + + private void location_Enter(object sender, EventArgs e) + { + NumericUpDown up = sender as NumericUpDown; + if (up != null) + { + up.Select(0, 100); + } + } + } +} diff --git a/renderdocui/Windows/Dialogs/TextureGoto.resx b/renderdocui/Windows/Dialogs/TextureGoto.resx new file mode 100644 index 000000000..997c833b1 --- /dev/null +++ b/renderdocui/Windows/Dialogs/TextureGoto.resx @@ -0,0 +1,126 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + text/microsoft-resx + + + 2.0 + + + System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + False + + + False + + \ No newline at end of file diff --git a/renderdocui/Windows/TextureViewer.Designer.cs b/renderdocui/Windows/TextureViewer.Designer.cs index a4419d903..06b3891dc 100644 --- a/renderdocui/Windows/TextureViewer.Designer.cs +++ b/renderdocui/Windows/TextureViewer.Designer.cs @@ -55,6 +55,8 @@ this.showEmpty = new System.Windows.Forms.ToolStripMenuItem(); this.usedSep = new System.Windows.Forms.ToolStripSeparator(); this.openNewTab = new System.Windows.Forms.ToolStripMenuItem(); + this.toolStripSeparator1 = new System.Windows.Forms.ToolStripSeparator(); + this.imageInLayoutMenuItem = new System.Windows.Forms.ToolStripMenuItem(); this.usedStartLabel = new System.Windows.Forms.ToolStripMenuItem(); this.colorDialog = new System.Windows.Forms.ColorDialog(); this.toolstripMenu = new System.Windows.Forms.ContextMenuStrip(this.components); @@ -149,8 +151,7 @@ this.pixelContextMenu = new System.Windows.Forms.ContextMenuStrip(this.components); this.highlightedPixelHistoryToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem(); this.highlightedPixelDebugToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem(); - this.imageInLayoutMenuItem = new System.Windows.Forms.ToolStripMenuItem(); - this.toolStripSeparator1 = new System.Windows.Forms.ToolStripSeparator(); + this.gotoLocationButton = new System.Windows.Forms.ToolStripButton(); subSep = new System.Windows.Forms.ToolStripSeparator(); toolStripLabel2 = new System.Windows.Forms.ToolStripLabel(); toolStripLabel3 = new System.Windows.Forms.ToolStripLabel(); @@ -220,7 +221,7 @@ this.usedStartLabel}); this.rightclickMenu.MaximumSize = new System.Drawing.Size(0, 480); this.rightclickMenu.Name = "rightclickMenu"; - this.rightclickMenu.Size = new System.Drawing.Size(181, 148); + this.rightclickMenu.Size = new System.Drawing.Size(181, 126); // // showDisabled // @@ -249,6 +250,17 @@ this.openNewTab.Text = "Open new Locked Tab"; this.openNewTab.Click += new System.EventHandler(this.resourceContextItem_Click); // + // toolStripSeparator1 + // + this.toolStripSeparator1.Name = "toolStripSeparator1"; + this.toolStripSeparator1.Size = new System.Drawing.Size(177, 6); + // + // imageInLayoutMenuItem + // + this.imageInLayoutMenuItem.Name = "imageInLayoutMenuItem"; + this.imageInLayoutMenuItem.Size = new System.Drawing.Size(180, 22); + this.imageInLayoutMenuItem.Text = "Image in layout "; + // // usedStartLabel // this.usedStartLabel.Name = "usedStartLabel"; @@ -994,11 +1006,12 @@ toolStripLabel1, this.saveTex, this.texListShow, - this.viewTexBuffer}); + this.viewTexBuffer, + this.gotoLocationButton}); this.actionsStrip.Location = new System.Drawing.Point(0, 25); this.actionsStrip.Margin = new System.Windows.Forms.Padding(0, 0, 12, 0); this.actionsStrip.Name = "actionsStrip"; - this.actionsStrip.Size = new System.Drawing.Size(114, 25); + this.actionsStrip.Size = new System.Drawing.Size(168, 25); this.actionsStrip.TabIndex = 8; this.actionsStrip.Text = "toolStrip1"; // @@ -1332,16 +1345,15 @@ this.highlightedPixelDebugToolStripMenuItem.Text = "Highlighted Pixel &Debug"; this.highlightedPixelDebugToolStripMenuItem.Click += new System.EventHandler(this.debugPixel_Click); // - // imageInLayoutMenuItem + // gotoLocationButton // - this.imageInLayoutMenuItem.Name = "imageInLayoutMenuItem"; - this.imageInLayoutMenuItem.Size = new System.Drawing.Size(180, 22); - this.imageInLayoutMenuItem.Text = "Image in layout "; - // - // toolStripSeparator1 - // - this.toolStripSeparator1.Name = "toolStripSeparator1"; - this.toolStripSeparator1.Size = new System.Drawing.Size(177, 6); + this.gotoLocationButton.DisplayStyle = System.Windows.Forms.ToolStripItemDisplayStyle.Image; + this.gotoLocationButton.Image = global::renderdocui.Properties.Resources.find; + this.gotoLocationButton.ImageTransparentColor = System.Drawing.Color.Magenta; + this.gotoLocationButton.Name = "gotoLocationButton"; + this.gotoLocationButton.Size = new System.Drawing.Size(23, 22); + this.gotoLocationButton.Text = "Goto"; + this.gotoLocationButton.Click += new System.EventHandler(this.gotoLocationButton_Click); // // TextureViewer // @@ -1507,6 +1519,7 @@ private System.Windows.Forms.ToolStripButton zoomExactSize; private System.Windows.Forms.ToolStripSeparator toolStripSeparator1; private System.Windows.Forms.ToolStripMenuItem imageInLayoutMenuItem; + private System.Windows.Forms.ToolStripButton gotoLocationButton; } } \ No newline at end of file diff --git a/renderdocui/Windows/TextureViewer.cs b/renderdocui/Windows/TextureViewer.cs index ad5ff6400..c803e20b8 100644 --- a/renderdocui/Windows/TextureViewer.cs +++ b/renderdocui/Windows/TextureViewer.cs @@ -49,6 +49,8 @@ namespace renderdocui.Windows private ReplayOutput m_Output = null; + private Dialogs.TextureGoto m_Goto = null; + private TextureDisplay m_TexDisplay = new TextureDisplay(); private ToolStripControlHost depthStencilToolstrip = null; @@ -368,6 +370,8 @@ namespace renderdocui.Windows InitializeComponent(); + m_Goto = new Dialogs.TextureGoto(GotoLocation); + textureList.Font = texturefilter.Font = rangeBlack.Font = @@ -403,7 +407,7 @@ namespace renderdocui.Windows render.Painting = true; pixelContext.Painting = true; - saveTex.Enabled = false; + saveTex.Enabled = gotoLocationButton.Enabled = viewTexBuffer.Enabled = false; DockHandler.GetPersistStringCallback = PersistString; @@ -666,6 +670,30 @@ namespace renderdocui.Windows private Dictionary lockedTabs = new Dictionary(); + public void GotoLocation(int x, int y) + { + if(!m_Core.LogLoaded || CurrentTexture == null) + return; + + m_PickedPoint = new Point(x, y); + + uint mipHeight = Math.Max(1, CurrentTexture.height >> (int)m_TexDisplay.mip); + if (m_Core.APIProps.pipelineType == APIPipelineStateType.OpenGL) + m_PickedPoint.Y = (int)(mipHeight - 1) - m_PickedPoint.Y; + if (m_TexDisplay.FlipY) + m_PickedPoint.Y = (int)(mipHeight - 1) - m_PickedPoint.Y; + + m_Core.Renderer.BeginInvoke((ReplayRenderer r) => + { + if (m_Output != null) + RT_PickPixelsAndUpdate(m_PickedPoint.X, m_PickedPoint.Y, true); + + RT_UpdateAndDisplay(r); + }); + + UI_UpdateStatusText(); + } + public void ViewTexture(ResourceId ID, bool focus) { if (this.InvokeRequired) @@ -997,7 +1025,7 @@ namespace renderdocui.Windows var outConfig = new OutputConfig(); outConfig.m_Type = OutputType.TexDisplay; - saveTex.Enabled = true; + saveTex.Enabled = gotoLocationButton.Enabled = viewTexBuffer.Enabled = true; m_Following = Following.Default; @@ -1061,7 +1089,7 @@ namespace renderdocui.Windows m_PrevSize = PointF.Empty; m_HighWaterStatusLength = 0; - saveTex.Enabled = false; + saveTex.Enabled = gotoLocationButton.Enabled = viewTexBuffer.Enabled = false; rwPanel.ClearThumbnails(); roPanel.ClearThumbnails(); @@ -2616,6 +2644,23 @@ namespace renderdocui.Windows this.BeginInvoke(new Action(UI_UpdateStatusText)); } + private void ShowGotoPopup() + { + if (CurrentTexture != null) + { + Point p = m_PickedPoint; + + uint mipHeight = Math.Max(1, CurrentTexture.height >> (int)m_TexDisplay.mip); + + if (m_Core.APIProps.pipelineType == APIPipelineStateType.OpenGL) + p.Y = (int)(mipHeight - 1) - p.Y; + if (m_TexDisplay.FlipY) + p.Y = (int)(mipHeight - 1) - p.Y; + + m_Goto.Show(render, p); + } + } + private void render_KeyDown(object sender, KeyEventArgs e) { bool nudged = false; @@ -2645,6 +2690,12 @@ namespace renderdocui.Windows if (!m_Core.LogLoaded) return; + if (e.KeyCode == Keys.G && e.Control) + { + ShowGotoPopup(); + + } + if (e.KeyCode == Keys.Up && m_PickedPoint.Y > 0) { m_PickedPoint = new Point(m_PickedPoint.X, m_PickedPoint.Y - 1); @@ -3563,6 +3614,11 @@ namespace renderdocui.Windows ViewTexture(e.ID, false); } + private void gotoLocationButton_Click(object sender, EventArgs e) + { + ShowGotoPopup(); + } + #endregion #region Thumbnail strip diff --git a/renderdocui/renderdocui.csproj b/renderdocui/renderdocui.csproj index fe6b3d45a..42a2f2eef 100644 --- a/renderdocui/renderdocui.csproj +++ b/renderdocui/renderdocui.csproj @@ -259,6 +259,12 @@ SettingsDialog.cs + + Form + + + TextureGoto.cs + Form @@ -412,6 +418,9 @@ SettingsDialog.cs + + TextureGoto.cs + TextureSaveDialog.cs