Skip to content

Commit 51caf35

Browse files
committed
provided by kinke: add navigation with forward/back mouse buttons
1 parent 92ec7a2 commit 51caf35

File tree

1 file changed

+43
-9
lines changed

1 file changed

+43
-9
lines changed

vdextensions/gotodef.cs

Lines changed: 43 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -180,6 +180,7 @@ internal sealed class GoToDefMouseHandlerProvider : IMouseProcessorProvider
180180
public IMouseProcessor GetAssociatedProcessor(IWpfTextView view)
181181
{
182182
var buffer = view.TextBuffer;
183+
IVsUIShell vsUIShell = GetVsUIShell();
183184

184185
IOleCommandTarget shellCommandDispatcher = GetShellCommandDispatcher(view);
185186

@@ -196,6 +197,7 @@ public IMouseProcessor GetAssociatedProcessor(IWpfTextView view)
196197

197198
return new GoToDefMouseHandler(view,
198199
shellCommandDispatcher,
200+
vsUIShell,
199201
_aggregatorFactory.GetClassifier(buffer),
200202
_navigatorService.GetTextStructureNavigator(buffer),
201203
CtrlKeyState.GetStateForView(view));
@@ -211,26 +213,36 @@ private IOleCommandTarget GetShellCommandDispatcher(ITextView view)
211213
return _globalServiceProvider.GetService(typeof(SUIHostCommandDispatcher)) as IOleCommandTarget;
212214
}
213215

216+
/// <summary>
217+
/// Get the SVsUIShell from the global service provider.
218+
/// </summary>
219+
private IVsUIShell GetVsUIShell()
220+
{
221+
return _globalServiceProvider.GetService(typeof(SVsUIShell)) as IVsUIShell;
222+
}
223+
214224
#endregion
215225
}
216226

217-
/// <summary>
218-
/// Handle ctrl+click on valid elements to send GoToDefinition to the shell. Also handle mouse moves
219-
/// (when control is pressed) to highlight references for which GoToDefinition will (likely) be valid.
220-
/// </summary>
221-
internal sealed class GoToDefMouseHandler : MouseProcessorBase
227+
/// <summary>
228+
/// Handle ctrl+click on valid elements to send GoToDefinition to the shell. Also handle mouse moves
229+
/// (when control is pressed) to highlight references for which GoToDefinition will (likely) be valid.
230+
/// </summary>
231+
internal sealed class GoToDefMouseHandler : MouseProcessorBase
222232
{
223233
private IWpfTextView _view;
224234
private CtrlKeyState _state;
225235
private IClassifier _aggregator;
226236
private ITextStructureNavigator _navigator;
227237
private IOleCommandTarget _commandTarget;
238+
private IVsUIShell _vsUIShell;
228239

229-
public GoToDefMouseHandler(IWpfTextView view, IOleCommandTarget commandTarget,
240+
public GoToDefMouseHandler(IWpfTextView view, IOleCommandTarget commandTarget, IVsUIShell vsUIShell,
230241
IClassifier aggregator, ITextStructureNavigator navigator, CtrlKeyState state)
231242
{
232243
_view = view;
233244
_commandTarget = commandTarget;
245+
_vsUIShell = vsUIShell;
234246
_state = state;
235247
_aggregator = aggregator;
236248
_navigator = navigator;
@@ -315,12 +327,34 @@ public override void PreprocessMouseUp(MouseButtonEventArgs e)
315327
_mouseDownAnchorPoint = null;
316328
}
317329

330+
// Support backward/forward navigation via extended mouse buttons.
331+
// Derived from https://github.com/tunnelvisionlabs/MouseNavigation/blob/master/Tvl.VisualStudio.MouseNavigation/MouseNavigationProcessor.cs.
332+
public override void PostprocessMouseUp(MouseButtonEventArgs e)
333+
{
334+
if (_vsUIShell == null)
335+
return;
336+
337+
uint cmdId;
338+
if (e.ChangedButton == MouseButton.XButton1)
339+
cmdId = (uint) VSConstants.VSStd97CmdID.ShellNavBackward;
340+
else if (e.ChangedButton == MouseButton.XButton2)
341+
cmdId = (uint) VSConstants.VSStd97CmdID.ShellNavForward;
342+
else
343+
return;
344+
345+
object obj = null;
346+
_vsUIShell.PostExecCommand(VSConstants.GUID_VSStandardCommandSet97, cmdId,
347+
(uint) OLECMDEXECOPT.OLECMDEXECOPT_DONTPROMPTUSER, ref obj);
348+
349+
e.Handled = true;
350+
}
351+
318352

319-
#endregion
353+
#endregion
320354

321-
#region Private helpers
355+
#region Private helpers
322356

323-
private Point RelativeToView(Point position)
357+
private Point RelativeToView(Point position)
324358
{
325359
return new Point(position.X + _view.ViewportLeft, position.Y + _view.ViewportTop);
326360
}

0 commit comments

Comments
 (0)