One of my consulting clients asked me last week if I knew an easy way to integrate a range (dual-knob) slider control in Matlab GUI. Today’s post is an expansion of the answer I provided him, which I though might interest other Matlab users.

- Matlab vs. Java sliders
- Using JSlider
- Range (dual-knob) sliders
- AppDesigner – Matlab’s new GUI
- Conclusions and some personal musings

### Matlab vs. Java sliders

As funny as it may sound, Matlab’s so-called “slider” control (`uicontrol('Style','slider')`

) is actually implemented as a scroll-bar, rather than the more natural JSlider. I believe that this is due to a design decision that occurred sometime in the 1990’s (sliders were not as prevalent then as they are nowadays). This was never corrected, probably for backward-compatibility reasons. So to this day, Matlab’s so-called “slider” is actually a scroll-bar, and we do not [yet] have a real slider control in standard Matlab, apparently since the ‘slider’ * uicontrol* style is already in use. Spoiler alert: this

*will*change soon — keep reading.

It gets worse: for some reason Matlab’s implementation of the so-called “slider” uses a Windows95 look-and-feel that makes the control look antique in today’s GUI standards. Using Java Swing’s standard JScrollBar control would at least have made it appear more consistent with the other Matlab controls, which are all based more closely on Java Swing:

% Standard Matlab "slider" uicontrol('style','slider', 'position',[10,10,200,20]); % Standard Java JScrollBar jScrollbar = javax.swing.JScrollBar; jScrollbar.setOrientation(jScrollbar.HORIZONTAL); javacomponent(jScrollbar,[10,40,200,20]); % Standard Java JSlider (20px high if no ticks/labels, otherwise use 45px) jSlider = javax.swing.JSlider; javacomponent(jSlider,[10,70,200,45]);

I advise users of the current Matlab GUI to use `JScrollBar`

or `JSlider`

, rather than Matlab’s standard “slider” * uicontrol*. The rest of today’s post will discuss the

`JSlider`

variant.### Using JSlider

As shown above, we can use the * javacomponent* function to display any Java component in a Matlab container (such as

*or figure). We can easily modify the slider’s appearance using its internal properties:*

**uipanel**set(jSlider, 'Value',84, 'MajorTickSpacing',20, 'PaintLabels',true); % with labels, no ticks

set(jSlider, 'Value',22, 'PaintLabels',false, 'PaintTicks',true); % with ticks, no labels

jSlider.setPaintLabels(true); % or: jSlider.setPaintLabels(1); % with both ticks and labels

[jhSlider, hContainer] = javacomponent(jSlider,[10,10,100,40]); set(jSlider, 'Value',72, 'Orientation',jSlider.VERTICAL, 'MinorTickSpacing',5); set(hContainer,'position',[10,10,40,100]); %note container size change

We can query the current slider value via its **Value** property:

>> value = get(jSlider,'Value'); % or: value = jSlider.getValue; value = 29

We can easily attach Matlab callback functions to slider value-change events:

>> hjSlider = handle(jSlider, 'CallbackProperties') hjSlider = javahandle_withcallbacks.javax.swing.JSlider >> hjSlider.StateChangedCallback = @(hjSlider,eventData) disp(get(hjSlider,'Value')); >> set(hjSlider, 'StateChangedCallback', @myCallback); %alternative

As you can see, standard Java controls (such as `JSlider`

here) are very simple to customize and use in Matlab GUI. I have shown more complex customizations elsewhere in this blog, as well as in my Matlab-Java programming book.

Note that `JSlider`

(and Java sliders in general) only supports integer values, so if you need floating-point values you’d either need to find some other Java Swing component somewhere that supports what you need, or do the scaling yourself with some text label. I recently created a Matlab class wrapper for a client that does exactly that: the underlying component was a Java slider and the labels were updated to display floating-point values, dynamically updated based on the Matlab class object’s properties. It only took a short morning to create a fully-functional generic slider class that works quite well.

### Range (dual-knob) sliders

This brings me to my client’s query that I mentioned at the beginning of this post: `JSlider`

only contains a single knob. Is it possible to integrate a range (dual-knob) slider?

My initial response was to simply google for “Java range slider“. This returns numerous different controls, both open-source and commercial, that we can download and integrate in Matlab. All it takes is to download the **.class, *.zip* or **.jar* file that contains the component, add it to Matlab Java classpath using the * javaaddpath* function, and then use the

*to display it, just as we did with*

**javacomponent**`JSlider`

above.This is simple enough, but then I thought of an even simpler solution, namely to use JIDE’s library of commercial-grade controls that is pre-bundled in Matlab. Surely enough, a quick search in JIDE’s enormous catalog yielded its `RangeSlider`

component, which extends `JSlider`

with a dual knob. `RangeSlider`

‘s appearance has changed somewhat across Matlab releases (or actually, JIDE releases, as they are integrated within the corresponding Matlab releases), but its basic functionality remained unchanged:

jRangeSlider = com.jidesoft.swing.RangeSlider(0,100,20,70); % min,max,low,high jRangeSlider = javacomponent(jRangeSlider, [0,0,200,80], gcf); set(jRangeSlider, 'MajorTickSpacing',25, 'MinorTickSpacing',5, 'PaintTicks',true, 'PaintLabels',true, ... 'Background',java.awt.Color.white, 'StateChangedCallback',@myCallbackFunc);

We can move the two knobs relative to each other. We can also move the entire range (i.e., both knobs at once), by either dragging the square on top of the right knob (R2010b), or by dragging the space between the two knobs (R2014b).

The benefit of JIDE controls is that they are pre-bundled in every Matlab installation and deployed MCR. There is no need to download anything, nor to use * javaaddpath*. All the richness of JIDE’s commercial-grade libraries (at least those libraries used in Matlab, which is plenty) is automatically available to us within Matlab, just as easily as the standard Java Swing controls. MathWorks has already paid a small fortune to integrate JIDE’s libraries in Matlab, and we can use it free of charge within Matlab GUIs. This is a great (and sadly undocumented) advantage of Matlab GUI. Matlab GUI programmers who wish to enrich their GUI are strongly encourages to take the time to review the long list of controls provide by JIDE in Matlab. I’ve posted quite a few articles on using JIDE components in Matlab – feel free to take a look and see the richness that JIDE can bring to your GUI. Additional material can be found in my Matlab-Java programming book.

In the specific case of `RangeSlider`

, this control is part of the JIDE Common Layer that JideSoft open-sourced a few years ago. This means that we can download the latest version of this library and use it in Matlab, in case it has some new component that is still not available in our version of Matlab. For example, Matlab R2014b includes JIDE version 3.4.1, released by JideSoft on May 2012 – the latest version (3.6.9, released last week) includes numerous fixes and improvements that were integrated in the past 3 years:

>> com.jidesoft.utils.Lm.getProductVersion ans = 3.4.1

Note that JIDE’s online documentation (PDF, javadoc, webpage) always refers to the latest version. To use the latest Common-layer library in Matlab, simply download it and replace Matlab’s pre-bundled *<matlabroot>/java/jarext/jide/jide-common.jar* file. Be careful with changing Matlab’s installation files (such as this one), as there is always a risk that some Matlab functionality might break. So always keep a copy of the original file, in case you need to revert your changes. Alternatively, place the *jide-common.jar* file in some other user folder and use it in Matlab on an as-needed basis using * javaaddpath* and

*.*

**javarmpath**Using the latest commercial (non-open-sourced) JIDE libraries, such as *jide-grids.jar*, *jide-components.jar* or *jide-charts.jar*, is only possible if you purchase them from JideSoft. But as noted, we can freely use the older bundled libraries in our Matlab GUIs without paying JideSoft anything.

** Disclaimer**: I am an engineer, not a lawyer. What I said above is my personal opinion; it is not legal advice. If you are unsure about licensing of JIDE components in your programs, contact MathWorks or JideSoft.

### AppDesigner – Matlab’s new GUI

Last autumn, with little fanfare, MathWorks released the App Designer toolbox, which can be freely downloaded from the File Exchange. This is not just another File Exchange utility. It is in fact an official MathWorks Technical Preview that is both functional by itself, and also provides very interesting insight of Matlab’s upcoming new GUI. MathWorks have not announced exactly when this new AppDesigner will replace the aging GUIDE in Matlab. But the fact that AppDesigner is an actual working product in the public domain since late 2014, and that MathWorks has officially endorsed it as a “Technical Preview”, mean that this day is close.

In the new AppDesigner, sliders finally appear modern, complete with all sorts of customizable properties:

Java controls still provide more customizability than Matlab, even in the new AppDesigner, but the functionality gap is now significantly reduced. This provides the flexibility of modern easy-to-create/maintain GUIs for users who do not need to preserve backward-compatibility with existing GUIs or extra customizabilty enabled by Java, while preserving the functionality for those who do.

Java components and even standard Matlab * uicontrol*s cannot be added to an AppDesigner window because it is not a standard Java

`JFrame`

window. The new App window has its own set of controls, separate from *(topic for a separate blog post someday). However, we can always keep using*

**uicontrols***and*

**javacomponent***in plain-ol’ figures, as before, side-by-side with the new AppDesigned windows. The new App window can be created using the new*

**uicontrol***function, whereas the existing*

**appwindow***function creates a standard figure window (basically a Java*

**figure**`JFrame`

) that accepts *and*

**javacomponent***. Maybe one day I’ll find out if there’s a way to combine these two seemingly disparate sets of GUIs. In the meantime I’m content that there’s a new way to create Matlab GUIs that has not previously existed.*

**uicontrol**AppDesigner is a very nice addition for Matlab GUI builders, and it will get even better with time. Having looked at some of the internals, I’m drooling over the potential improvements. MathWorks has invested quite a bit in this new product, so I’m confident that many of these improvements will find their way into AppDesigner in the upcoming releases. I just hope it will remain a free utility and will not turn into an addon toolbox when officially released (I have not seen any mention about this either way, so it’s still an open question; I’ll clarify this point here when I learn something). For the time being, AppDesigner is free to use.

MathWorks is actively looking for ways to improve AppDesigner, so if you find any functionality that is missing or buggy, please provide feedback:

### Conclusions and some personal musings

Matlab itself has kept its Desktop GUI relatively modern, and integrates advanced JIDE GUI controls internally. But until AppDesigner came about, Matlab application builders were not provided with similarly modern documented GUI components and design tools, in keeping with the times.

It is indeed possible, as I’ve repeatedly claimed in this blog, to create professional-looking GUIs in Matlab. However, this currently requires using undocumented features and Java controls.

In Matlab’s upcoming AppDesigner, making professional-looking Matlab GUIs will be easier, with sleek new controls, user-friendly visual layout, and easy-to-maintain class-based code. I still find the tech-preview to be lacking in some respects, and not integrated with the existing GUI functionality. Still, the fact that MathWorks has gone out of its way to provide a Technical Preview of its upcoming new GUI, despite its normal reluctance to provide a technical development roadmap, shows a commitment to improving Matlab’s user-facing front-end. This makes me optimistic that most shortcomings will be solved by the time AppDesigner is officially released, hopefully soon.

Until this happens, and possibly even later, we can significantly improve Matlab’s standard GUI using Java in standard figure windows. Interested readers can find out more information about integrating Java controls in Matlab GUI in my book “* Undocumented Secrets of MATLAB-Java Programming*” (CRC Press, 2011, ISBN 978-1439869031). If you already have this book, please be kind enough to post your feedback on it on Amazon (link), for the benefit of others.

Yair

Swing and even the SwingX extensions from Oracle never included a dial for some reason.

For open-source JSliders, some readers might like the GJDial that was used in some of the Project Waterloo internal GUIs.

It’s a simple, self-contained, subclass of JSlider that presents visually as a dial instead of a slider and supports both single and multi-turn operation. That can be handy when you need fine control but want to pack the GUI into a small screen area.

Hopefully, TMW will include dials in the new AppDesigner.

Indeed, dials and knobs galore (details):

Yair

These look great. Do they supply a “multi-turn” dial: value from first turn from zero = 0:10, second = 10:20 etc?. It’s not obvious from the screenshots that they do.

That is what I needed to scroll through a lengthy strip-chart without jumping several seconds at a time because of the number of pixels used by a JSlider. Do others among your readers have a need for that behaviour?

If so, shout now: TMW read this blog and it should not be too difficult to implement.

ML

@Malcolm – is this what you mean?

If so, then I haven’t seen this functionality in AppDesigner…

I believe MathWorks would be working on stability and compatibility for their first release, rather than adding new features such as this. But we can definitely ask for them to be added to the dev queue. The best way to do this is to use the feedback form integrated in AppDesigner, since this will enter some backoffice system that is monitored and tracked. Relying on them to monitor this blog is risky, since it’s not tracked or monitored in the same way.

Yair

Exactly that. I deleted a reference to a “10-turn potentiometer” in the OP because I wasn’t sure how many readers would be long enough in the tooth to recognise one.

M

You can spot many of the new dials and gauges from the forthcoming app designer in the new Simulink HMI widgets section of R2015a. I believe all of the new controls are going to be web enabled.

How do you change the tick labels? I’m trying to use the JSlider for a time range and so I want the labels to be datestr(x,13) output of the times. Can’t seem to figure it out myself.

Thanks!

http://undocumentedmatlab.com/blog/javacomponent#comment-80247

Hello Yair,

I started using the Java sliders in Matlab yesterday and they work great (thanks for the texbook as well as the tutorials)! I do not have much experience with Java though, and can’t seem to get mouse callbacks to work with it. Your example above works great, but breaks when I try to implement it using guidata within a function. Basically I’m trying to get the value of the slider when the slider moves, but want this to be saved as a handle. Here is my code so far:

Here is the error I get when I run the code in MATLAB:

I’d appreciate any suggestions. Thanks!

@Vidya – the

*CallbackDataproperties are automatically populated by Matlab whenever the corresponding*Callbackis called, and then this callback-data is passed on to the callback function as an input parameter. Therefore, it is not surprising that you cannot programmatically modify the contents of any*CallbackDataproperty. You can only change*Callback, and in this specific caseMouseDraggedCallback.Still, I do not see why you would want to set a

MouseDraggedCallback: do you plan for your GUI users to interactively drag the entire slider control within your GUI??? If you are only trying to trap changes to the slider’s knob, then you should setStateChangedCallbackinstead, as I explained in the main article.@Yair

“do you plan for your GUI users to interactively drag the entire slider control within your GUI???”

Sort of. I would like to save the (final) value of the slider position. That is, export it, for example to a text file. I was hoping to do this by updating the handle structure using guidata. This is proving to be difficult.

“If you are only trying to trap changes to the slider’s knob, then you should set StateChangedCallback instead, as I explained in the main article.”

This works, but only shows the current value of the slider in the command window. How can I save this information onto the workspace, or export the final value of the slider? Thanks.

@Vidya – you really need to learn how to use Matlab callbacks. Instead of calling

to output the latest slider value to the console, you can set the callback to any Matlab function that does whatever you wish, such as storing the data in your handles struct or saving it somewhere or whatever. This is standard basic Matlab programming, it has nothing at all to do with Java. There’s plenty of documentation on using Matlab callbacks that you could (and should) use.disp@Yair – Yes, you are correct. Just figured out how.

Hi Yair,

Regarding the new HG2 system: it seems that TMW have sealed all the graphic classes and widgets from sub-classing. They have also concealed (by

`pcode`

) the implementation, so that the old HG1 approach ofcopy-the-original-code-and-redesign-for-your-needsdoesn’t work anymore. Since sub-classing may be instrumental in many cases providing simple and powerful solutions, I have several questions:1. Are you familiar with any ways to overcome this issue? If so, can you dedicate it a post?

2. Do you know, whether TMW are planning to open their graphics classes sometime in the future?

3. If both answers are negative, can you post something like “

A layman’s guide to creating own Matlab graphics classes” ?With thanks and appreciation —

In Matlab2007 I’m trying to use the JSlider but I keep getting a “Warning: Transform Fcn…” error every time the GUI repaints. I cannot find a way to get rid of this warning. I’ve tried finding a way to define the Transform Fcn (whatever that is) so no avail. I’ve also tried suppressing the warning by doing:

and it doesn’t like the lastwarn() command. I’m stuck.

@Christina – sounds like something’s funky with your Java. Java warnings cannot be suppressed. You have a very old Matlab release so try upgrading to a newer release.

Hi Yair,

any chance you know if the values passed by these new knobs can change on the fly according to the mouse, without having to land on a specific step on the knob first?

Thanks!

@Panos – perhaps you mean this?

http://undocumentedmatlab.com/blog/continuous-slider-callback

Dear Yair,

really interesing way of integrating sliders. Yet, I dont get how I insert the Java double knob slider exactly. I tried putting it into a panel of my guide created GUI (replacing gcf with handles.myslider) but I cant get position right, as well as resizing does not work… Any ideas how to fix that?

Thanks a bunch.

Ravi

@Ravi – read my article on

. If you still need assistance then email me for a short consultancy.javacomponentDear Yair,

I have a problem that I appreciate if you could help me to resolve it.

I am using “JSlider” and I was wondering if there is a way to partially disable the slider to take some values? In my case, the default range for the slider is set to be 0-100, with predefined minor and major ticks, I want to not allow for the slider to take values less than 50 under some conditions! i.e., I want the range 0-50 to be disabled, is this doable?

Thanks

Sog

@Sog – you can do this by creating a slider data custom model in Java code. Alternatively, you can have your Matlab callback check the new value and reset it to an allowed value in case it is outside the valid range.

Yair,

Thanks for your article.

The RangeSlider is great except I’d like to use it for very small fractional values. For example: I want to set range of zero to 0.001. The component isn’t happy with naively setting the range I’d like. I *could* just set the range from 0 to 1 and do my own scaling but then I’d have to shut off the labels & put some text indicating something like “*10^-3″… and… before you know it… things look ugly.

Am I missing something?

Thanks!

Dan

@Dan – RangeSlider (and JSlider in general) only supports integer values, so you’d either need to find some other Java Swing component somewhere that supports what you need, or do the scaling yourself with some text label.

How can I update/refresh the ‘foreground’ property ?

I’m able to change that property but visually it always stays black Tick Labels won’t change.

Nevertheless, with your ‘findjobj’ GUI the foreground color is affecting and refreshing.

@Yair

*Update*

I was able to change change the foreground using only the static color name (number does not work) from some weird reason.

Do you know why? and how can I change it to any numeric color ?

@Amir – you need to learn how to specify Java Colors:

* http://docs.oracle.com/javase/7/docs/api/java/awt/Color.html

* http://www.otherwise.com/Lessons/ColorsInJava.html

Thanks for the great tutorial

I had two questions:

1. How can I change the default [0-100] range?

2. Is there a way to implement this in GUIDE-based GUI’s?

@Soroush – the

`JSlider`

object, just like any other object in Java and Matlab, has properties that you can set, includingMaximumandMinimum. Use the builtinfunction to see the available property values, andgetto modify them.setCan some body help me know how this slider can be used for decimal scale? I found that if we set the minimum and maximum as 0 & 1 it’s not working

It took me a while to realize that Java sliders only support integer values. You note that in one of the replies to a comment, but it would be very helpful to put that significant difference from Matlab sliders into the body of this document – thanks.

@Richard – I really don’t think that this is a very big deal: you can keep the slider’s int values and just display custom labels that map to real-world floating-point values (or string labels for that matter). I recently created a Matlab class wrapper for a consulting client, which maps between Matlab double values and the

`JSlider`

‘s int values – the underlying`JSlider`

component’s labels were dynamically updated to display floating-point values, based on the Matlab class object’s properties. It only took a short morning to create a fully-functional generic slider class that works quite well. It looks and behaves just like a native Matlab component, with double-precision labels.Hi, I was wondering how to set the slider as a child of the MATLAB figure. This will allow the figure WindowKeyPressFcn work while the slider has the focus. Apparently I cannot simply set the slider’s ‘Parent’ property because it is not a MATLAB object.

Thank you very much.

Sliders in figure-based (not web-based) UI are Java objects whose parent is a dedicated Matlab container that is automatically created when you use the

function. It is this container whosejavacomponentParentproperty you can then set to be either a figure or another container (such as aoruipanel). Of course, you can set the parent directly in the call touitab, as the 3rd input argument.javacomponentHi Yair,

Great tutorial!

From the day I saw it, I’m looking for ways to use those JSliders in any way I can! They look amazing!

I wonder if there is a way to create triple knob slider…?

I mean 2 knobs to specify a range (like in

`com.jidesoft.swing.RangeSlider`

) and another knob to specify a value somewhere in between those (or outside of those).I need this for a project I’ve started recently. The alternative is to use 2 different sliders, but it would be much cooler to have both slides together!

I found this link: http://threerings.github.io/tripleplay/apidocs/index.html?tripleplay/ui/Slider.html but I have no idea how to use it, or even if it is relevant or possible in any way in matlab…

Thanks,

Koby

@Koby – in general, you need to download the JAR/ZIP file(s) that contain this class (and all other classes on which it depends) from the website that you found, then add this file(s) to your Java classpath in Matlab using the

function, and finally create an object from the new class and display it onscreen just as I explained in the main post above.javaaddpathDear Yair,

Thank you for all the wonderful tips!

The sliders work as advertised, but I would like to be able to add a jSlider to an already existing GUI created using the GUIDE. More specifically, since the GUI is resizable, I would like make it so that upon creation, the slider be attached to a particular panel, so that the proportions are preserved window is being resized. Is there a way to do that? Thanks in advance.

@Misha – you can add the relevant code snippets (with the

call) to yourjavacomponent*_OutputFcn()function that is created by GUIDE in your main m-file. Pass the panel’s handle as the 3rd input arg to. See my post onjavacomponentfor details.javacomponentHi Yair,

I wonder if it is possible to change the position of a jslider after initialized at the constructor to a different value?

I couldn’t find any ‘Position’ property in it’s handler, like standard matlab UI elements have…

Thanks,

Koby

@Koby – you can change

`hContainer`

‘sPositionandUnitsjust like any other Matlab UI control.Yair,

Any idea what kind of object the sliders on the MATLAB colormap editor

`colormapeditor`

are? Of course`findjobj(colormapeditor)`

didn’t work because there’s no (apparent) handle returned by colormapeditor. I am interested in using several sliders in a similar manner.@Peter – as Ctrl-Shift-F1 indicates, the slider object is not a slider at all but rather a custom Java component created by MathWorks, namely

`com.mathworks.page.cmapeditor.CMEditView`

. You can take a look at the Matlab source-code for(incolormap%matlabroot%/toolbox/matlab/graph3d/colormapeditor.m) for additional details that might help you reuse this component.