jSpinner time picker model editing
Asked Answered
D

2

5

I have jSpinner using for time picking. Problem 1: User can edited hour minutes and second seperator ":" and can write extra digits like "123" Problem 2: model get always current time. I want "00:00:00" When i write this in code instead "hh:mm:ss" user can't edit the values.

My Code is;

spinner1 = new javax.swing.JSpinner();
SpinnerDateModel spinnermodel = new SpinnerDateModel();
spinnermodel.setCalendarField(Calendar.MINUTE);
spinner1 .setModel(spinnermodel);
spinner1 .setEditor(new JSpinner.DateEditor(spinner1 , "hh:mm:ss"));

Any help appreciated. Thanks.

Deary answered 22/2, 2014 at 20:40 Comment(5)
Can you explain why the first problem is an issue? The second problem can be fixed by using something like Calendar and setting the hour, minute and seconds fields to 0 and setting the spinners value to the result Date returned by Calendar#getTimeCrossstaff
Problem1 issue because; spinner shows 00:00:00 if user delete 1 of ":" i cant get true format from the user. This must be a time picker. User interacts with only hours minutes and seconds and dont delete any character or add new character.Deary
Take a look at this, which is time field I've been tinckering with for awhileCrossstaff
@Crossstaff Thanks to you for reference. I investigate it but really painful :) your code is very professional.Deary
We had lots of issues with the spinner and user ability requirements that it was just simpler to create a need field/component. It still needs some tweaking, but the basic idea/intend is thereCrossstaff
H
7

Problem 1: User can edited hour minutes and second seperator ":" and can write extra digits like "123"

You can use the editor's formatter to accomplish this through getTextField() method:

JSpinner.DateEditor editor = new JSpinner.DateEditor(spinner, "HH:mm:ss");
DateFormatter formatter = (DateFormatter)editor.getTextField().getFormatter();
formatter.setAllowsInvalid(false); // this makes what you want
formatter.setOverwriteMode(true);

The text field is in fact a JFormattedTextField with a DateFormatter as formatter. Take a look to How to Use Formatted Text Fields for a better understanding on how to work with this component.

Note the pattern used when the editor is created. It's "HH:mm:ss" because of your 2nd requirement.

Problem 2: model get always current time. I want "00:00:00"

You need to provide to your spinner with an initial date at 12 PM (24 hours) which will be translated in "00:00:00":

Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.HOUR_OF_DAY, 24);
calendar.set(Calendar.MINUTE, 0);
calendar.set(Calendar.SECOND, 0);

SpinnerDateModel model = new SpinnerDateModel();
model.setValue(calendar.getTime());

JSpinner spinner = new JSpinner(model);

Example

Here is a quite simple example to test what I've said. Hope it be helpful.

import java.util.Calendar;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JSpinner;
import javax.swing.SpinnerDateModel;
import javax.swing.SwingUtilities;
import javax.swing.text.DateFormatter;

public class Demo {

    private void createAndShowGUI() {

        Calendar calendar = Calendar.getInstance();
        calendar.set(Calendar.HOUR_OF_DAY, 24); // 24 == 12 PM == 00:00:00
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);

        SpinnerDateModel model = new SpinnerDateModel();
        model.setValue(calendar.getTime());

        JSpinner spinner = new JSpinner(model);

        JSpinner.DateEditor editor = new JSpinner.DateEditor(spinner, "HH:mm:ss");
        DateFormatter formatter = (DateFormatter)editor.getTextField().getFormatter();
        formatter.setAllowsInvalid(false); // this makes what you want
        formatter.setOverwriteMode(true);

        spinner.setEditor(editor);

        JPanel content = new JPanel();
        content.add(spinner);

        JFrame frame = new JFrame("Demo");
        frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
        frame.getContentPane().add(content);
        frame.pack();
        frame.setLocationRelativeTo(null);
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {                
                new Demo().createAndShowGUI();
            }
        });
    }    
}

Edit

When user try manually write hours or minutes (not using arrows) some logical problem ocures i think. Example i write 12 but spinner shows 21.

First off sorry I didn't note that before. This creepy behaviour happens because formatter's overwrite mode property is set to false somewhere during JSpinner.DateEditor's initialization (but couldn't find where). This property is true by default according to javadoc. To solve this you only need to add this line (I've also edited my code above):

formatter.setOverwriteMode(true);
Horseman answered 22/2, 2014 at 21:15 Comment(3)
Thank you very much for the Demo. When user try manually write hours or minutes (not using arrows) some logical problem ocures i think. Example i write 12 but spinner shows 21. And any way dont react minutes changes to hours ?Deary
@BlackWhite please see my edit. Hope it works this time (it does for me at least). I think it also solves this: "And any way dont react minutes changes to hours ?"Horseman
Yes this is work. Still Minutes changes after 59 to 0 hours increase 1 time also seconds to minutes. Anyway not a big problem. Thanks for the solution.Deary
B
2

The JSpinner class was not specifically designed to be used as a time picker, so it can be difficult to customize its behavior. The TimePicker class in the LGoodDatePicker library could be a better alternative for this usage.

You mentioned wanting to display the minutes and seconds in your format. The TimePicker format can be customized using the java.time DateTimeFormatter class.

Project Home page: https://github.com/LGoodDatePicker/LGoodDatePicker .

Screenshots of the components and the demo application are pasted below.

DateTimePicker screenshot Demo screenshot

Baumgartner answered 15/3, 2016 at 20:46 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.