Reputation: 1848
I would like to allow the user to zoom only while the control key is held (depressed). I have implemented this as follows within a WindowKeyPressFcn
callback function:
function keypress_callback(obj, evd, hZoom)
switch evd.Key
case 'control'
set(hZoom,'Enable','on');
end
%disp(evd); % used for debugging purposes
This function accepts a zoom object handle (hZoom
) that is passed from the main program at the moment the callback function is activated (set(hFigure,'WindowKeyPressFcn',{@keypress_callback,hZoom});
). I have written a similar WindowKeyReleaseFcn
(set via set(hFigure,'WindowKeyReleaseFcn',{@keyrelease_callback,hZoom});
) to disable zooming when control is released.
function keyrelease_callback(obj, evd, hZoom)
switch evd.Key
case 'control'
set(hZoom,'Enable','off');
end
%disp(evd); % used for debugging purposes
The goal is to allow normal zooming behavior (click to zoom in by a factor; shift-click to zoom out by a factor; drag clicking to zoom in on a selected region) only while the Ctrl
key is depressed. As soon as this modifier key is released, zooming ability should be disabled.
However, this behavior does not work as intended. Simply testing (by disp(evd)
) whether a key is pressed reveals that any number of key presses can be made with arbitrary keys; however, if the pressed key is Ctrl
, only one such press can be made, and all subsequent presses of Ctrl
are ignored, while all subsequent presses of any other key cause the key to appear in the Matab command window instead of triggering the keypress_callback
function. Thus, pressing Ctrl
appears to somehow inactivate the keypress_callback
function, perhaps because focus is shifted from the figure to the zoom object? As a corollary question, the WindowKeyReleaseFcn
seems to work fine for non-modifier keys (the evd
shows the correct released key), but the key
in evd
is empty if the released key is a non-modifier key.
I would be grateful if someone could demonstrate the correct implementation of the control-dependent zoom behavior as envisaged.
Upvotes: 4
Views: 2259
Reputation: 15369
The more modern way to do things seems to be:
gca
zoom on
z = zoom(gcf);
set(z, 'ButtonDownFilter', @ZoomGate)
where ZoomGate.m
contains something like:
function inhibitZoom = ZoomGate(varargin)
if ismember('control', get(gcbo,'currentModifier'))
inhibitZoom = 0;
else
inhibitZoom = 1;
end
EDIT in response to questioner's comments:
My first suggestion was to use a WindowButtonDownFcn
callback which then calls zoom
itself if it detects the control modifier. This is fine provided you have control over the zoom
implementation. Looking back at my code (I did something like this anything up to 15 years ago) I find that it used to be simple — zoom
was an m-file and had an obvious way of calling it: zoom down
meant "the button has just been pressed". Then, in that way that they do, MathWorks moved the goal posts and changed zoom
. It looks like my response at the time was to re-implement my own zoom
in the older, simpler style. Doesn't help you, unless you actually want that code (let me know).
Upvotes: 1