Creating Inline Timepicker with JavaScript and jQuery
February 16th, 2008
Inline editing is not only limited to text and textarea inputs. In this tutorial you will learn how to make inline timepicker with JavaScript. We will be using the usual tools: jQuery and Jeditable.
Before continuing you might be interested in reading introduction to custom input types for Jeditable.
Available methods for creating custom input
When creating custom input type you want to define one or several of following methods. None of them are mandatory.
$.editable.addInputType('example', {
element : function(settings, original) { },
content : function(string, settings, original) { },
buttons : function(settings, original) { },
submit : function(settings, original) { },
plugin : function(settings, original) { },
reset : function(settings, original) { }
});
All methods receive two parameters. Settings is Jeditable settings hash. Original is the original element which was clicked. Method content() also receives third parameter string which is the value input should be set to. Inside all methods this represents the form.
For this example we will be using three methods.
- element(settings, original) should create input element and attach it to form. Form is available inside function as variable this. Input element returned stores the final value to be submitted to server. Finally function should return the newly created element. If you do not provide this method an hidden input will be created by default.
- submit(settings, original) is called before submitting the form. It should set the value of input element returned by element(). This is only needed in special cases such as having multiple selects.
- content(string, settings, original) should set the value of custom input. For example for multiple selects it should set the selected options in each select.
Creating custom input
Throughout the tutorial we will be using following code to trigger Jeditable.
$("#id").editable("http://www.example.com/save.php", {
type : "time",
submit : "OK",
style : "display: inline",
tooltip : "Click to edit..."
});
We will start by adding custom input type called time.
$.editable.addInputType('time', {
});
Right now it does not do much anything. Since no methods are defined plugin will simply call the default methods.
Click time 13:30 to see how code works this far.
Add hour and minute pulldowns
Our timepicker will have two selects. One for hour and one for minutes. To keep minutes select short we will use 15 minute steps. To create these elements, we need to use element() method.
The two loops build the pulldowns. When they are ready the are appended to the form. As you remember, inside all helper methods this represents the form.
$.editable.addInputType('time', {
element : function(settings, original) {
var hourselect = $('<select id="hour_">');
var minselect = $('<select id="min_">');
/* Hour loop */
for (var hour=1; hour <= 24; hour++) {
if (hour < 10) {
hour = '0' + hour;
}
var option = $('<option>').val(hour).append(hour);
hourselect.append(option);
}
$(this).append(hourselect);
/* Minutes loop */
for (var min=0; min <= 45; min = parseInt(min)+15) {
if (min < 10) {
min = '0' + min;
}
var option = $('<option>').val(min).append(min);
minselect.append(option);
}
$(this).append(minselect);
/* Hidden input to store value which is submitted to server. */
var hidden = $('<input type="hidden">');
$(this).append(hidden);
return(hidden);
}
});
Why did we create hidden input in the end? When new value is submitted to server Jeditable expects there is only one input field to read value from. It could be any kind of field such as text or textarea. In this case it is best to use hidden. Later in the code I will show how to write pulldown values to the hidden input.
Note! Element method must return this single input in the end of function.
Click time 13:30 to see how code works this far.
Now selects are created. One problem exists though. Nothing is submitted to server. Our hidden field has empty value.
Sending correct value to server
We need to combine hours and minutes from two pulldowns. This combined value needs to be written to our hidden input. For that we will use submit method. This method is called just before form is submitted.
We read values from both pulldowns and put : character in between. Resulting string is then written into previously created hidden input.
$.editable.addInputType('time', {
element : function(settings, original) {
...
},
submit: function (settings, original) {
var value = $("#hour_").val() + ":" + $("#min_").val();
$("input", this).val(value);
}
});
Hey, what was that $(“input”, this) selector? Especially why is variable this inside selector?
There is optional second parameter for jQuery selectors. It is called context. Without second parameter selector is matched against current HTML page. If it is provided, selector is matched only against contents of second parameter.
Inside all methods this refers to the form Jeditable created. Selector above will search for our hidden input inside created form and not full HTML document.
Click time 13:30 to see how code works this far.
In demo selects are created. Correct value is submitted. One problem still exists. Default value for timepicker always is 24:45.
Setting default values
Content method set inputs default value. If editable time value is 13:30 and we click it, hour pulldown should be 13 and minute pulldown 30.
“13:30” is passed in as parameter called string. Hours and minutes are parsed from this string. Both hour and minute pulldown are then looped. Inside loop correct hour and minute are set as selected.
$.editable.addInputType('time', {
element : function(settings, original) {
...
},
submit: function (settings, original) {
...
},
content : function(string, settings, original) {
var hour = parseInt(string.substr(0,2));
var min = parseInt(string.substr(3,2));
$("#hour_", this).children().each(function() {
if (hour == $(this).val()) {
$(this).attr('selected', 'selected');
}
});
$("#min_", this).children().each(function() {
if (min == $(this).val()) {
$(this).attr('selected', 'selected')
}
});
}
});
Click time 13:30 to see finished inline timepicker.
What now?
Code could still be improved. Various aspects could be configurable. Some poeple might prefer minutes pulldown have five minute interval. Other people might prefer AM/PM time format.
In meanwhile download and experiment with code we just did.

February 18th, 2008 at 12:04 PM
Now, I’ve also written a little “EditInPlace”, could be combined with jQuery or Prototype easily, but works fine without Frameworks …
http://rh-balingen.de/clip_this/eip.htm http://rh-balingen.de/clip_this/eip.zip
(
: roland :)February 20th, 2008 at 02:34 PM
Similar in many respects to my TimePicker jQuery plugin here:
http://plugins.jquery.com/project/timepicker
February 20th, 2008 at 04:58 PM
Jason: I guess you haven’t seen custom inputs example page ?
Timepicker using your plugin was actually the first Jeditable custom input I made. Quite short code too :)
$.editable.addInputType('timepicker', { /* Call before submit hook. */ submit: function (settings, original) { var value = $("#h_").val() + ":" + $("#m_").val() + "" + $("#p_").val(); $("input", this).val(value); }, /* Attach Timepicker plugin to the default hidden input element. */ plugin: function(settings, original) { $("input", this).filter(":hidden").timepicker(); } });November 24th, 2008 at 12:32 AM
Hi Mika,
I cannot get the onblur: “cancel” to work. Can you help please?
I have tried several different ways, but none work, and really I have no clue as to which way to go…
Thanks
November 27th, 2008 at 06:06 PM
Meg: I cannot help if I do not know what the problem is :) Can you put some example code online? Are you trying to use it with Timepicker input?
December 13th, 2008 at 02:42 PM
Hello Mika, first of all, thnx for your work, it appears as very useful to me.
But i’ve encountered the same problem – canceling on blur doesn’t work. My custom input code is like this:
element: function(settings, original) { var types_select = $('<select id="edit_node_type"></select>'); $(types_select).html( $('#node_type').html() ); $(this).append( $(types_select) ); $(this).append($('<textarea id="edit_node"></textarea>')); var hidden = $('<input type="hidden">'); $(this).append(hidden); return(hidden); }, content: function(string, settings, original) { $("#edit_node", this).val(string); var node_type = original['id'].split('_')[0]; switch(node_type) { case 'parag': node_type = '?????'; break; case 'title': node_type = '?????????'; break; case 'ni': node_type = '???????????? ??????'; break; case 'ui': node_type = '?????????????? ??????'; break; } $("#edit_node_type", this).children().each(function() { if (node_type == $(this).val()) $(this).attr('selected', 'selected'); }); }, submit: function (settings, original) { var value = $('#edit_node_type',this).val() + String.fromCharCode(07) + $("#edit_node").val(); $('input', this).val(value); }, plugin: function(settings, original) { $("#edit_node", this).growfield(); }And here’s making div “jeditable”:$(".jeditable").editable("./../save_element.php", { type: 'node_settings', loadurl: './../load_element.php', onblur: 'cancel', cancel: 'Discard', submit: 'Save', indicator: '<img src="./../pic/indicator.gif">', tooltip: 'Dblclick for editing...', event: 'dblclick', style: 'text-indent: 0pt; text-align: left;', callback: function() { //... } });Can u tell me where can be problem?
December 20th, 2008 at 10:44 PM
Define “does not work”. Do you have example page somewhere online?
In any case onblur event can be problematic when you have multiple input elements. Onblur will trigger each time you switch focus between the inputs.
December 23rd, 2008 at 10:07 AM
I think using 24 hrs could be pragmatically incorrect. 00 hrs should help
for (var hour=0; hour <= 23; hour++) { if (hour < 10) { hour = '0' + hour; } var option = $('<option>').val(hour).append(hour); hourselect.append(option); }December 23rd, 2008 at 03:28 PM
Raj: Good catch, thanks. Fixed in Git
December 29th, 2008 at 05:10 PM
If i try change
to
The browser crash… some one know a solution?...
January 11th, 2009 at 08:04 PM
Michael: Works ok with FF3 and Safari. Did not boot Windows to test IE. You can also try something like:
for (var min=0; min <= 59; min = parseInt(min) + 1) {February 6th, 2009 at 12:18 PM
can anyone tell me how i can achieve this with datepicker.
I’ve tried everything and it doesn’t work.
really need help.
Thanks
February 6th, 2009 at 04:33 PM
Eamon: This datepicker you are talking about? Put some code online so I can see how it looks.
February 6th, 2009 at 05:33 PM
My problem is retrieving the value, been at this for 3days, tried many different things. it’e the UI DatePicker.
Thanks;
<script type="text/javascript" src="/site/js/jquery.ui.datepicker.min.js"></script> <link rel="stylesheet" href="/site/css/ui.datepicker.css" type="text/css" media="all" /> $.editable.addInputType('date', { element : function(settings, original) { var input = $('<input>'); $(this).append(input); //$(input).css('opacity', 0.01); return(input); }, plugin : function(settings, original) { var form = this; settings.onblur = 'cancel' $("input", this).datepicker().bind('click', function(){ $("input",this).dpDisplay(); return false; }).bind('dateSelected', function(e, selectedDate, $td) { $(form).submit(); }).bind('dpClosed', function(e, selected) { $(this).blur(); }).trigger('change').click(); } });February 11th, 2009 at 12:12 PM
Hello Mika,
Thank you for the help you provided, unfortunately I’ve had serveral problems and the above did not work.
Since, I have come much closer, when I submit I can get the value out of the DOM however, editable doesn’t set the value.
Here’s the new code
$.editable.addInputType(‘date’, { element : function(settings, original) { form = this; var input = $(‘’); var span = $(‘’); settings.onblur=’submit’; $(input).datepicker ({ dateFormat: ‘dd/mm/yy’, onSelect: function(dateText) { $(span).html(dateText); $(input).val(dateText); $(input).hide(); // jedit(); $(form).submit(); this.blur(); }, onClose: function() { if($(input).val()==’’) { $(this).blur(); this.blur(); } } }); $(this).append(span); $(this).append(input); return $(span); }, submit: function(settings,original) { alert($(‘span’, this).html()); var value = $(‘span’, this).html(); $(‘input’, this).val(value); } });February 27th, 2009 at 05:00 PM
Is there any chance you will update the date picker from jquery to be used?
March 2nd, 2009 at 10:55 PM
Hi,
I like it and using my .asp project. But I have a big problem with this. It’s not compatible with the Turkish characters [iso-8859-9]. I’m using a mysql database and posting the value. Everything is great to here. But I checking the posted value…
Can I fix that?
Thanks and sorry for my english.
Best Regards
March 5th, 2009 at 09:58 AM
Here’s how I did jQuery UI Datepicker with jeditable:
March 10th, 2009 at 02:54 PM
Orhan: I guess Turkish characters are included in UTF-8? I use it in all my projects without problems. IIRC all AJAX requests are UTF-8 so that might be what is causing your problems.
March 10th, 2009 at 02:57 PM
Calle: Excellent. Have you blogged about the datepicker input so I could link to it? Or can I include it in Github?
March 11th, 2009 at 07:53 AM
@Calle: If I choose a different month/year, the inline-text box closes automatically leaving the datepicker window still open. It works fine as long as I choose date within the current month. Have you faced this problem?
March 17th, 2009 at 01:14 AM
Hi Mika, great plugin! But i was wondering: is it possible to seperate the mouseover trigger from the input-Field? like this: there is a userimage and if i move the mouse over it, underneath(!) the userimg a select-box appears where i can choose some value. when i leave the select box, this value should be submitted – is this possible? sincerely, John.
March 17th, 2009 at 07:21 PM
John: Sorry but I did not understand what you are trying to do. You might be after the “onblur” parameter which affect what happens when focus is lost from input field.
You can use values ‘cancel’, ‘submit’, ‘ignore’ or use a function.
April 3rd, 2009 at 06:06 PM
Hi. I am having the same problem as 4. & 6. Look at the final example 4. If you dont click the big ok button but click elsewhere you expect the entry option to disappear. The onblur option doesnt appear to help. Great effort. Thanks.
April 6th, 2009 at 05:16 PM
Yes onblur cancel does not work. Because there are multiple selects previous one would blur when you change the next one.
June 6th, 2009 at 05:06 PM
Hi MIka. I want to customize a little your code. I have jeditable textarea so when i click on text – textarea appears, but i want at the same time toappear fileupload(i have div with display:none) I made bind(‘click’) function to jeditable textarea that appears this div with upload. But when i want to submit or cancel or ‘esc’ this textarea this div should hide also … and there is a problem. I tried to bind click to buttons and function hide() but it works only for submit, cancel didn’t work ;(
Do you have any solution for me ? Please help. Rafa?
PS. Sorry for my bad english.
June 16th, 2009 at 11:53 PM
Hey,
Does anybody have a working example of jeditable with jquery ui datepicker? It just doesn’t seem to work for me.
June 17th, 2009 at 11:07 AM
Rafa: Sorry but I do not understand what you are trying to do. Put some example code online.
Prof: See comment number 18.
June 30th, 2009 at 09:21 PM
I have fallow instructions as post #18, it works fine loading the calendar popup when doing click. but its not doing the submit at selectecDate. it places the date but nothing else, means not doing submit. here is my code:
A. Div block containing the click to edit field:
B. JQuery ready function:
C. The attached jquery.editable.datepicker.js
July 1st, 2009 at 06:33 PM
ok i have half problem solve: now a can do post on selected date, but i can’t change moth on calendar to select previous or next month date it does close the editable box.like doing cancel on blur.
here is my new code:July 1st, 2009 at 09:11 PM
well since i needs ths asap i have change datepicker for timepicker with dates values and it works for me to finish my project. here is the sample code using dropdown date array as a datepicker for jditable:
...and to make it editable with:
I hope this can be usefull :)
July 8th, 2009 at 09:35 PM
Hi, I need a date picker plugin for jeditable. So I’ve started developping this.
Here is my first try, feel free to improve :July 10th, 2009 at 03:15 PM
Nuranto: Looks good. Do you have the source somewhere available for download? I could also include it in contributed folder of Jeditable. If I include it with Jeditable then it should be MIT licensed or dual MIT + GPL licensed.
I do not want to distribute anything GPL only since its viral and I am allergic to GPL :)
July 23rd, 2009 at 03:20 AM
Hello
I have been trying for hours to create 2 linked select forms (dependent selects) with jeditable in the same HTML page with just javascript (i.e. no Ajax, no Put, no Get, no php, this is for a desktop aplication with a webkit ui) like
First select Second select
France -> Paris, Nancy, Belfort Germany -> Munich, Berlin
You can see a live exqmple on this site : http://www.infimum.dk/HTML/multiselect.html
How should I code this with Jeditable ? Best regards, Olivier
July 23rd, 2009 at 07:46 PM
Hi,
I put it here, with MIT license.
http://www.tireuse-a-biere.com/jquery.jeditable.datepicker.js
Here’s an exemple of use, for birthday date for exemple. There’s a lot of possibilities, see datepicker plugin page for more details.
here’s an example of use :$('.editDate').editable('processurl', { indicator : "<img src='imgurl", submitdata: { _method: "post" }, datepicker: { flat: true, date: '09/10/1978', format: 'd/m/Y', view: 'years', current: '09/10/1978', calendars: 1, starts: 1 }, type : 'datepicker', submit : 'Save', cancel : 'Cancel' } );And here’s another plugin, for password changing : http://www.tireuse-a-biere.com/jquery.jeditable.password.js
Example of use, client side :
$('.editPass').editable('processurl', { indicator : "imgurl>", submitdata: { _method: "post" }, type : 'password', currentpass : 'Your current password : ', newpass : 'The new pass : ', separator : '_%^%_', submit : 'Save', cancel : 'Cancel' } );and server side example (php/zf) :
$passes = explode('_%^%_', $value); if(count($passes) != 2) { echo $this->view->_('An error occured, the password has not been changed.'); break; } $current = $passes[0]; $new = $passes[1]; if($pro->pro_pass != md5($current)) { echo $this->view->_('Current password incorrect, the password has not been changed.'); break; } if(!Zend_Validate::is($new , 'StringLength', array('6'))) { echo $this->view->_('New password incorrect (at least 6chars.), the password has not been changed'); break; } $pro->pro_pass = md5($new); $pro->save(); echo $this->view->_('The password has been changed');August 3rd, 2009 at 02:26 PM
Nuranto: Just committed datepicker to GitHub.
October 27th, 2009 at 06:49 AM
I really like this jeditable plugin. Works very well.
I was wondering if anyone has tried to use autosuggest or autocompleter in a jeditable field ?
I am trying to do so, but with my poor skills, I’m going nowhere at the moment.
Cheers,
Jonathan
October 29th, 2009 at 10:29 AM
i want to implement third party plugin, but i dont want to use it for input box, but rather on cancel button. well i want to add class to cancel button, so thought best way to do it, is to make third party plugin. what is your suggestion? and would i just write the plugin from addInputType or would i need to create it differently, if differently then above, then please show me.
November 2nd, 2009 at 03:52 PM
Jonathan: Quick and dirty demo of Jeditable and autocomplete (write something starting with letter a). Demo was done with 5 lines of code:
Demo was done in 5 lines of code:
$.editable.addInputType('autocomplete', { element : $.editable.types.text.element, plugin : function(settings, original) { $('input', this).autocomplete(settings.autocomplete.data); } });Then you can call Jeditable with something like:
$(".autocomplete").editable("http://www.example.com/save.php";, { type : "autocomplete", tooltip : "Click to edit...", onblur : "submit", autocomplete : { data : ["Aberdeen", "Ada", "Adamsville", "Addyston", "Adelphi", "Adena", "Adrian", "Akron"] } });November 2nd, 2009 at 03:55 PM
basit: Just do a custom input type for Jeditable. That should be the easiest way.
November 3rd, 2009 at 05:51 PM
Im really liking this plugin, my quick question is, how can i loop a mysql database to retrieve a list of “categories” then create a list of checkboxes. im new to jQuery so my apologies if this is an easy to answer q.
J
November 5th, 2009 at 07:25 AM
Thanks Mika, this autocomplete works fine :)
November 6th, 2009 at 10:51 AM
James Tanner: It is really a PHP / ASP / Ruby / whatever serverside language you use question. Does not really concern jQuery nor Jeditable.
December 8th, 2009 at 08:34 AM
Hi again Mika, it’s only been a month but I seek another advice/help from you about your great jeditable javascript.
I am trying to have a multiple SELECT dropdown list. To do so, I wanted to duplicate the “select” type already available and change
select: { element : function(settings, original) { var select = $('<select />');to
selectmulti: { element : function(settings, original) { var select = $('<select multiple size="5"/>');The data source is a json encoded array: data : ‘<?php print json_encode($array); ?>‘
Now the problem as you have already guessed is that I only retrieve the last selected value from my multiple select where instead, I am trying to retrieve all selected values (either in an array or separated by a character like a comma).
Would you be able to help me with this one as well ?
Best regards,
Jonathan
January 26th, 2010 at 05:02 PM
Has anyone solved the multi-select list issue that only the last element being returned?