I came across a timepicker solution on this Stack Overflow answer that I really liked. However, I encountered difficulties trying to implement it in a project where input elements are dynamically created. It seemed like the timepicker required specific handling of the object returned by the constructor. I wanted it to function more like the jQuery-UI datepicker, so I attempted to create a JavaScript class before diving into creating a jQuery plugin:
function MyTimePicker(inputelement) {
// store the timepicker object
this.mytimepicker = new TimePicker(inputelement);
// display the selected time in the element
this.mytimepicker.on('change', function (evt) {
var value = (evt.hour || '00') + ':' + (evt.minute || '00');
evt.element.value = value;
});
}
I tried using this class on three different input elements:
var dummy1;
var dummy2;
var dummy3;
window.onload = function () {
dummy1 = new MyTimePicker(jQuery('#time2').get(0));
dummy2 = new MyTimePicker(jQuery('#time3').get(0));
dummy3 = new MyTimePicker(jQuery('#time4').get(0));
};
Unfortunately, it didn't work as expected. The timepicker popup appeared when clicking on each input element, but the 'on(change)' event was never triggered, so the selected time was not displayed in the input field.
This could be due to my lack of experience with JavaScript objects or perhaps an issue with the timepicker itself.
Update: I made some improvements by setting up a proper prototype. Here is the complete code for standalone testing:
<!DOCTYPE html>
<html>
<head>
<title>Timepicker class, standalone, by Jonatas Walker</title>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.1/jquery.min.js"></script>
<link href="//cdn.jsdelivr.net/timepicker.js/latest/timepicker.min.css" rel="stylesheet">
<script src="//cdn.jsdelivr.net/timepicker.js/latest/timepicker.min.js"></script>
</head>
<body>
<div id="arrayoftimes">
<input id="time2" type="time" placeholder="Time HH:MM"><br />
<input id="time3" type="time" placeholder="Time HH:MM"><br />
<input id="time4" type="time" placeholder="Time HH:MM"><br />
</div>
<script>
// Javascript Class. this disturbs the above reference application of TimePicker. It probably is not re-entrant.
//constructor
function MyTimePicker(selector) {
this.mytimepicker;
this.init(selector);
}
//prototype
MyTimePicker.prototype = {
init: function (selector) {
var inputelement = jQuery(selector).get(0);
this.mytimepicker = new TimePicker(inputelement);
// show picked time in the element
this.mytimepicker.on('change', function (evt) {
var value = (evt.hour || '00') + ':' + (evt.minute || '00');
evt.element.value = value;
});
}
};
</script>
<script>
var dummy1;
var dummy2;
var dummy3;
window.onload = function () {
dummy1 = new MyTimePicker('#time2');
dummy2 = new MyTimePicker('#time3');
dummy3 = new MyTimePicker('#time4');
};
</script>
</body>
</html>
Now the first input element functions correctly, but the selected time value is being populated in all three input fields. The other two inputs trigger the timepicker dialog, but the chosen value doesn't appear.
In the browser console, after selecting a time, I noticed two errors from the timepicker.js file: TypeError: active is undefined.
This might suggest that the timepicker's internal code isn't re-entrant in nature?
Or maybe I'm misunderstanding something about object-oriented JavaScript?
Update:
I suspect there may be a bug in timepicker.js. I will update here once I identify and address it.