16

Is it possible to change top and left positions (get current values and change them) of jQuery UI datepicker. Please note that i need to change position, not set margin as it is in other examples.

Kin
  • 4,466
  • 13
  • 54
  • 106

5 Answers5

32

Sure it is. As there's always only one datepicker active, you can select active datepicker with:

var $datepicker = $('#ui-datepicker-div');

and change its position:

$datepicker.css({
    top: 10,
    left: 10
});

EDIT

Whoah, tricky one. If you set top or left position in beforeShow, it gets overriden again by datepicker plugin. You have to put css changes in a setTimeout:

$("#datepicker").datepicker({
    beforeShow: function (input, inst) {
        setTimeout(function () {
            inst.dpDiv.css({
                top: 100,
                left: 200
            });
        }, 0);
    }
});

DEMO: http://jsfiddle.net/BWfwf/4/

Explanation about setTimeout(function () {}, 0): Why is setTimeout(fn, 0) sometimes useful?

Community
  • 1
  • 1
iappwebdev
  • 5,880
  • 1
  • 30
  • 47
  • I need to set it on initialization – Kin Feb 28 '13 at 09:16
  • 1
    thanks, but i did in my way because there is no good solution: ` jQuery.extend(jQuery.datepicker,{_checkOffset: function(inst, offset, isFixed){offset.top = offset.top - 402; offset.left = offset.left - 240; return offset;}});` – Kin Feb 28 '13 at 09:43
  • 1
    in some cases you might want to use relative positioning in the css(), like this: top: '+=5px', left: '-=120px' – szajmon Aug 25 '13 at 23:53
  • Finally found what I was looking for after all the searching. Now my datepicker is always shown below my input element. Excellent! +100. – reaper_unique Sep 24 '13 at 07:11
3

If you get really stuck you can edit your jquery-ui-[version].custom.js. The function that controls the position where the calender will appear is:

_findPos: function(obj) { var position, inst = this._getInst(obj), isRTL = this._get(inst, "isRTL");

    while (obj && (obj.type === "hidden" || obj.nodeType !== 1 || $.expr.filters.hidden(obj))) {
        obj = obj[isRTL ? "previousSibling" : "nextSibling"];
    }

    position = $(obj).offset();
    return [position.left, position.top];
},

I have some custom code that uses a CSS3 transformation to zoom the page in or out based on its width. This throws out the screen coordinates that the calendar widget relies on. I added some custom code to the _findPos to detect and handle the zoom level. Modified code looks like this:

_findPos: function(obj) {
    var position,
        inst = this._getInst(obj),
        isRTL = this._get(inst, "isRTL");

    while (obj && (obj.type === "hidden" || obj.nodeType !== 1 || $.expr.filters.hidden(obj))) {
        obj = obj[isRTL ? "previousSibling" : "nextSibling"];
    }

    position = $(obj).offset();
    /* Custom Code for Zoom */
    var zoomLevel = 1;
    var minW = 1024;
    if ($(window).width() > minW)
               { zoomLevel = $(window).width() / minW;}
    return [position.left, position.top/zoomLevel];
},
2

May be an old question, but ran into the problem myself just today and could not get other suggestions to work. Fixed it alternatively (using .click(function(){}) and wanted to add my two cents.

I have an input field with the id sDate which, when clicked, displays the datepicker.

What I did to solve the problem was add a click routine to the #sDate field.

$('#sDate').click(function(){  //CHANGE sDate TO THE ID OF YOUR INPUT FIELD 
    var pTop = '10px';  //CHANGE TO WHATEVER VALUE YOU WANT FOR TOP POSITIONING
    var pLeft = '10px';  //CHANGE TO WHATEVER VALUE YOU WANT FOR LEFT POSITIONING
    $('#ui-datepicker-div').css({'left':pLeft, 'top':pTop});
});
IIIOXIII
  • 980
  • 3
  • 15
  • 30
0

your solution works provided you run it after calling the datepicker in the code, I tried calling it before but it didn't work, so I tried to understand how it worked for you.

I have adapted the datepicker in the context of an input field which is fixed at the top of the page to scroll. The datepicker was lost ... Here is my example code for adaptation in a context of datepicker which becomes dynamically fixed:

Example found on w3schools.com: https://www.w3schools.com/howto/howto_js_sticky_header.asp

HTML:

  <div class="padding-16 center" id="resa_nav">
      <div style="margin: 24px 0 0;">
            <label for="date_selector"
            class="text-gray">Choose a date</label>
            &nbsp;
            <input type="text" id="date_selector" name="date_selector" class="padding-small">
       </div>
   </div>

CSS:

.sticky {
position: fixed;
top: 0;
width: inherit;
background: white;
box-shadow: 0px 0px 7px 4px #69696969;
}

JS:

// init datepicker
$('#date_selector').datepicker();

// When the user scrolls the page, execute myFunction
window.onscroll = function() { myFunction() };

// Get the header
var header = document.getElementById('resa_nav');

// Get the offset position of the navbar
var sticky = header.offsetTop;

// Add the sticky class to the header when you reach its scroll position. Remove "sticky" when you leave the scroll position
function myFunction() {

        if (window.pageYOffset > sticky) {

                // set block sticky
                header.classList.add('sticky');

                // adjust datepicker position
                // attach a namespace for unbind click later in "non-sticky" context
                $('#date_selector').on('click.sticked', function(){

                        var top = '10px';
                        var left = '10px';

                        $('#ui-datepicker-div').css({'left': left, 'top': top});
                });

        }
        else {

                // remove sticky
                header.classList.remove('sticky');

                // unbind the second event 'click' for retrieve the 
                // default of settings in "non-sticky" context
                $('#date_selector').off('click.sticked');
      }
}
// END FUNCTION

hope to help!

0

just add css as below for datepicker

.datepicker {
    top: -150px; 
    /* adjust value as per requirement. if not work try with addin !important*/
}
Yogesh
  • 715
  • 1
  • 7
  • 20