How do you set a default datatip callback function?

35 views (last 30 days)
I'm trying to add callback code to a scatterplot that activates when the use clicks on a data point. To do this, I want to assign the callback to the creation function of a datatip. The datatip documentation says that datatips have a creation callback. I want to set a default value for this callback function so it executes whenever any new datatip is created. However, when I try to set this default value as described here, I get an error that says "datatip is an invalid class name".
My primary question is how do I assign a callback function that is executed whenever any datatip is created. A more general question is, what's the best way to set code to execute whenever the user clicks on an existing data point in a figure? Lines are objects that have properties, but the data points themselves are not.
Code to recreate the error:
x=1:10;
y=1:10;
figure
hold on
scatter(x,y,'filled');
hold off
set(groot,'defaultDataTipCreateFcn',@tipcreate);
function tipcreate(~,~)
disp('Hello World!');
end

Answers (3)

Adam Danz
Adam Danz on 27 Oct 2021
Edited: Adam Danz on 27 Oct 2021
It doesn't appear that there is a factory CreateFcn for Data Tips and its default value is an empty character array ('').
The list below shows all factory options for CreateFcn functions.
You could, of course, define a function in an m-file, add the file to the path in startup.m, and assign the function to all datatips. But I realize that isn't as ideal as setting a default function to be applied to all of your existing datatips. You could also suggest making this feature available [Contact tech support].
List of factory CreateFcn functions
factoryAnimatedlineCreateFcn
factoryAreaCreateFcn
factoryArrowshapeCreateFcn
factoryAxesCreateFcn
factoryAxestoolbarCreateFcn
factoryBarCreateFcn
factoryBinscatterCreateFcn
factoryBubblechartCreateFcn
factoryBubblelegendCreateFcn
factoryCategoricalhistogramCreateFcn
factoryColorbarCreateFcn
factoryConstantlineCreateFcn
factoryContourCreateFcn
factoryDoubleendarrowshapeCreateFcn
factoryEllipseshapeCreateFcn
factoryErrorbarCreateFcn
factoryFigureCreateFcn
factoryFunctioncontourCreateFcn
factoryFunctionlineCreateFcn
factoryFunctionsurfaceCreateFcn
factoryGeoaxesCreateFcn
factoryGraphplotCreateFcn
factoryHggroupCreateFcn
factoryHgjavacomponentCreateFcn
factoryHgtransformCreateFcn
factoryHistogram2CreateFcn
factoryHistogramCreateFcn
factoryImageCreateFcn
factoryImplicitfunctionlineCreateFcn
factoryImplicitfunctionsurfaceCreateFcn
factoryLegendCreateFcn
factoryLightCreateFcn
factoryLineCreateFcn
factoryLineshapeCreateFcn
factoryParameterizedfunctionlineCreateFcn
factoryParameterizedfunctionsurfaceCreateFcn
factoryPatchCreateFcn
factoryPolaraxesCreateFcn
factoryQuiverCreateFcn
factoryRectangleCreateFcn
factoryRectangleshapeCreateFcn
factoryScatterCreateFcn
factoryStairCreateFcn
factoryStemCreateFcn
factorySurfaceCreateFcn
factoryTextCreateFcn
factoryTextarrowshapeCreateFcn
factoryTextboxshapeCreateFcn
factoryTiledlayoutCreateFcn
factoryUibuttongroupCreateFcn
factoryUicontainerCreateFcn
factoryUicontextmenuCreateFcn
factoryUicontrolCreateFcn
factoryUiflowcontainerCreateFcn
factoryUigridcontainerCreateFcn
factoryUimenuCreateFcn
factoryUipanelCreateFcn
factoryUipushtoolCreateFcn
factoryUisplittoolCreateFcn
factoryUitabCreateFcn
factoryUitabgroupCreateFcn
factoryUitableCreateFcn
factoryUitogglesplittoolCreateFcn
factoryUitoggletoolCreateFcn
factoryUitoolbarCreateFcn
  4 Comments
Justin Dietz
Justin Dietz on 1 Nov 2021
Yeah I'm gonna need some more help with assigning the function. I've tried what was specified in your default property values link. Using its nomenclature, the string that specifies what I want should be 'defaultDataTipCreateFcn', but it tells me that datatip is an invalid class name.
Also, your createFcn link specifies that "Setting the CreateFcn property on an existing component has no effect."
So it would seem that I need to set some kind of 'default' parameter in order for this to work for newly created datatips, but that's precisely what I can't seem to get working properly.
Adam Danz
Adam Danz on 1 Nov 2021
@Justin Dietz, after re-reading your question, I don't think you really want the CreateFcn which is called when the datatip object is created which is why you must define that function within the same line that you define the datatip. I'm going to add a new answer.

Sign in to comment.


Adam Danz
Adam Danz on 1 Nov 2021
  1. > I'm trying to add callback code to a scatterplot that activates when the use clicks on a data point
  2. > I want to set a default value for this callback function so it executes whenever any new datatip is created
  3. > My primary question is how do I assign a callback function that is executed whenever any datatip is created
These are two different questions so the goal is not clear.
In question 1, you want a function that responds to pressing a scatter plot object. That would involve assigning a ButtonDownFcn to the scatter object.
In questions 2 and 3, you want a datatip to appear when you click a scatter object which would prevent use of the ButtonDownFcn (you can't have both).
It sounds like you want a datatip to appear when you click a scatter point and you want some function to be evoked as well. If so, the CreateFcn is not what you're looking for since that is evoked when a datatip object is created which isn't the same as when a datatip object appears after clicking on a point (that's why the CreateFcn must be defined when creating the datatip, otherwise it has no effect). Instead, you want the UpdateFcn of the DataCursorManager or you could use the DataTipTemplate depending on what you want to do. To understand the difference between the two, see Setting precision of datatip text.
There are lots of demos listed here and in the documentation. But I don't think there are default options for these functions, however. If there's a common function you'd like to apply, you could create the function in a separately m-file and then assign the function to all of your functions/scripts.

Massimo Ciacci
Massimo Ciacci on 1 Jul 2023
Edited: Massimo Ciacci on 1 Jul 2023
%% setTips_CallBack.m
% call only when figure created and one line drawn, wo any tips
fh = gcf;
ax_hdl = gca;
% make sure there are NO dta tips yet
% this cursorMode will only work for every new clicked tip
cursorMode = datacursormode(fh);
axChild = get(ax_hdl,'Children');
allCurves = findobj(axChild,'type','line');
hTarget = allCurves(1);
% set format later read back from inside customDataTipCallBack as this:
% output_txt = customDataTipCallBack(src,evt)
% axh = ancestor(evt.Target,'axes');
% fmt_x = axh.UserData.fmt_x;
% fmt_y = axh.UserData.fmt_y;
fmt_x = '%2.2f';
fmt_y = '%2.2f';
chopY = 1e-7;
ax_hdl.UserData.fmt_x = fmt_x;
ax_hdl.UserData.fmt_y = fmt_y;
ax_hdl.UserData.chopY = chopY;
% register callback
set(cursorMode, 'UpdateFcn',@customDataTipCallBack);
% create a tip somewhere (no need)
% % hDatatip = cursorMode.createDatatip(hTarget);
  1 Comment
Massimo Ciacci
Massimo Ciacci on 1 Jul 2023
Edited: Massimo Ciacci on 1 Jul 2023
Don't know why but the text I had written preceding the code is gone... Now I will be shorter.
The code above (setTips_CallBack.m) is is how I register my own callback function.
customDataTipCallBack can be found here:
setTips_CallBack.m comes with it's own test bench: test_setTips_CallBack where you create a plot and then with the mouse add tips using your custom callback.

Sign in to comment.

Categories

Find more on Graphics Object Programming in Help Center and File Exchange

Products


Release

R2020b

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!