How to pre-set cursor or selection for default answer in input dialog - matlab

If one creates an inputdialog with inputdlg and a default answer, it looks like that:
Which callback command do I need to make it look like that?
The documentation is missing a lot here. It's a kind of "luxury service" for the customer ;)
But I think it would be nice, if it's easy to implement.
This question is actually solved, as I found out that there are convenient functions like uigetfile and uiputfile for my particular case. But the general case of my questions remains unsolved or at least I haven't tested the java approach.

I'm afraid using the builtin inputdlg without changes this is not possible.
At least there's not 'hidden' feature allowing for this.
You'd need access to the underlying java TextField object for that purpose.
You could copy inputdlg to some new place and make your own version of it.
In combination with the findjobj utility the desired functionality in principle exists.
http://www.mathworks.com/matlabcentral/fileexchange/14317-findjobj-find-java-handles-of-matlab-graphic-objects
Things could look like this then:
% create the edit-field:
h = uicontrol('style', 'edit',...);
% get the underlying java object
% this should be a javahandle to a JTextField
jtextfield = findjobj(h);
% set start/end of the selection as desired:
jtextfield.setSelectionStart(startPos);
jtextfield.setSelectionEnd(endPos);

Related

Function Fields Feature in Matlab

mapminmax is a builtin Matlab function. I am trying to implement something that does autocomplete for functions/subfunctions like this.
I've done a quick search but haven't really come up with what it's called. mapminmax is the only function I know of that implements this feature. It looks like a field of a function (like how a field of a struct).
I've used edit mapminmax to see the insides of Matlab's function but I haven't found anything leading to how this is possible. getParamStructFromArgs looks like it might be able to explain what this is, but it looks like it's related to NNs.
Question: What is this feature called and is there any documentation on this?
Looks like what #hypfco said was right. This "feature" is related to Matlab's package system. I'm sure there's a way to do it by creating a package, but for those who don't want to create such a package there's a simple way of doing this.
If you have a function such as untitled.m, you can create a folder called +untitled in your Matlab directory.
Function's .m file
+Function folder
Then when you do untitled. and press tab in the console, you'll get the following pop-up.
If anyone's got a way to do this inside the .m file, I'll accept that answer instead.

How to capture key press in Matlab uipanel

How can one capture keyboard entry inside a uipanel, i.e. when anything in the panel has focus? I've found that uipanel does not have the KeyPressFcn property. I've read this post from Undocumented Matlab about Java callbacks, but I also can't get KeyPressedCallback to work. For example, if I try to this:
set(h_panel, 'KeyPressFcn', #(src, event)key_press(obj, src, event));
I get this error:
The name 'KeyPressFcn' is not an accessible property for an instance of class 'uicontrol'.
The same thing occurs if I try KeyPressedCallback. I'm afraid I'll have to resort to some sort of hack involving the parent figure, which I would like to avoid if possible.
KeyPressedCallback is a property of the underlying Java object, not the original Matlab uicontrol object. To access the underlying Java control of a Matlab uicontrol, you need to use the findjobj utility, as I believe that I explained in my blog post that you referenced (you probably missed that crucial step):
jPanel = findjobj(hPanel);
jPanel.KeyPressedCallback = #myMatlabCallbackFunc;
Note that Matlab panels only became Java-based objects in HG2 (R2014b, see here). So on R2014a and earlier Matlab releases you will not be able to use this technique, only on one of the newer releases.
I don't see any callback properties that you can use or events to which you can attach a listener.
>> events(h_panel)
Events for class matlab.ui.container.Panel:
ObjectBeingDestroyed
LocationChanged
SizeChanged
ButtonDown
Reset
PropertyAdded
PropertyRemoved
Just the mouse event (ButtonDown) and the ButtonDownFcn callback. Perhaps there are other tricks. Ask Yair Altman!
Ultimately, I have found there are two reasonable solutions to this problem, both involving what I originally described as "some sort of hack involving the parent figure". Both of them require some sort of concept of an "active" panel or object within the figure in question.
Solution 1
Rely on the last-clicked object to direct keyboard input in the figure to that object. Use ButtonDownFcn for every object in the figure that needs keyboard input. In the callback, store the handle of the object in the appdata of the figure as the "active" object. (Something like setappdata(h_fig, 'active_obj', h_obj.) Then set KeyPressFcn in the figure to a function that will get that handle out of the appdata and branch accordingly.
Solution 2
Use some sort of keypress scheme to decide which object to direct further input to. This works well if you have a number of similar objects that merely need disambiguation. For example, set the KeyPressFcn of the figure to a function that uses keys 1-9 to indicate the correspondingly numbered object. Direct further keyboard input to that object or a related function.
Neither method is perfect, and I wish there was a way to avoid going through the figure, but in practice these aren't very complicated to implement. I'm actually using both simultaneously.

Custom classes data tooltips in Matlab editor

Does any one would know a way of overriding the data tooltip that is shown when hovering over a variable when we are in the Matlab editor ? I have a custom class that is relatively simple and its content could be shown easily in the tool tip, but Matlab insists on saying it is a 1x1 CustomClass, which is nice and all, but it would be more useful if we could make it to show the content of the object in a nice way. Right now, I have to type the name of the variable in the cmd window e.g. when debugging instead of a short hover on the variable name. Nitpicky, but I'd find it interesting ^^
I've tried to dig a bit using undocumented leads on data tooltips, e.g. http://undocumentedmatlab.com/blog/accessing-the-matlab-editor/
http://undocumentedmatlab.com/blog/spicing-up-matlab-uicontrol-tooltips/
But I don't have the final answer, anyone has any ideas ?
The tooltip seems to get its string by using the disp method. Override disp on your class. In the method body, construct your desired string however you want and then call disp on it. In R2012a at least this works for the debugger tooltip.
Note that you'll need to do a clear classes after editing the class to get MATLAB to recognize the overridden disp.

Matlab function signature changes

Let us say that I have a Matlab function and I change its signature (i.e. add parameter). As Matlab does not 'compile' is there an easy way to determine which other functions do not use the right signature (i.e. submits the additional parameter). I do not want to determine this at runtime (i.e. get an error message) or have to do text searches. Hope this makes sense. Any feedback would be very much appreciated. Many thanks.
If I understand you correctly, you want to change a function's signature and find all functions/scripts/classes that call it in the "old" way, and change it to the "new" way.
You also indicated you don't want to do it at runtime, or do text searches, but there is no way to detect "incorrect" calls at "parse-time", so I'm afraid these demands leave no option at all to detect old function calls...
What I would do in that case is temporarily add a few lines to the new function:
function myFunc(param1, param2, newParam) % <-- the NEW signature
if nargin == 2
clc, error('old call detected.'); end
and then run the main script/function/whatever in which this function resides. You'll get one error for each time something calls the function incorrectly, along with the error stack in the Matlab command window.
It is then a matter of clicking on the link in the bottom of the error stack, correct the function call, and repeat from the top until no more errors occur.
Don't forget to remove these lines when you're done, or better, replace the word error with warning just to capture anything that was missed.
Better yet: if you're on linux, a text search would be a matter of
$ grep -l 'myFunc(.*,.*); *.m'
which will list all the files having the "incorrect" call. That's not too difficult I'd say...You can probably do a similar thing with the standard windows search, but I can't test that right now.
This is more or less what the dependency report was invented for. Using that tool, you can find what functions/scripts call your altered function. Then it is just a question of manually inspecting every occurrence.
However, I'd advise to make your changes to the function signature such that backwards compatibility is maintained. You can do so by specifying default values for new parameters and/or issuing a warning in those scenarios. That way, your code will run, and you will get run-time hints of deprecated code (which is more or less a necessary evil in interpreted/dynamic languages).
For many dynamic languages (and MATLAB specifically) it is generally impossible to fully inspect the code without the interpreter executing the code. Just imagine the following piece of code:
x = magic(10);
In general, you'd say that the magic function is called. However, magic could map to a totally different function. This could be done in ways that are invisible to a static analysis tool (such as the dependency report): e.g. eval('magic = 1:100;');.
The only way is to go through your whole code base, either inspecting every occurrence manually (which can be found easily with a text search) or by running a test that fully covers your code base.
edit:
There is however a way to access intermediate outputs of the MATLAB parser. This can be accessed using the undocumented and unsupported mtree function (which can be called like this: t = mtree(file, '-file'); for every file in your code base). Using the resulting structure you might be able to find calls with a certain amount of parameters.

Limiting string length in a Edit Box on Matlab user interfaces

I inserted an Edit box in a Matlab user interface and I would like to limit the number of characters that an user can type. There is no obvious property on the Edit box (such as "max characters"). I tried to use the callback function, verifying if the current string size on the edit box was bigger than a limit I set and truncating the first characters, however the callback only acted when I clicked outside the edit box and then inside again.
Do you have any idea of how to do this?
Thanks in advance.
EDITED
As suggested by Amro, I tried placing a verification code inside the KeyPressFcn callback of the edit box. I typed the following code:
function prefix_edit_KeyPressFcn(hObject, eventdata, handles)
text = get(hObject, 'String');
if length(text) > 15
set(hObject, 'String', text(1:15));
end
The problem is that the edit box string is only changed when I type something, press Enter and then try to type something again. It seems that the KeyPressFcn is only called after pressing Enter (as mentioned in the forum post that Amro suggested).
The solution proposed in the forum seems too complicated, for such a simple task. Surely there has to be a more elegant way...
Instead of using KeyPressFcn, implement the aforementioned callback function on the KeyTypedCallback property of the underlying Java component, which can be found using the findjobj utility.
Note: do NOT use the underlying Java component's document's lineLimit attribute, since this is a blind alley - a remnant of old Java versions that are not used by Matlab.
You could set your own Document object, but the callback way is simpler I think.
Try to put your logic inside the KeyPressFcn callback function. There is an old newsgroup thread discussing a similar solution.