Enhance datepicker UX: position above input with proper styling
- Added CSS positioning to display inline datepicker above input field - Enhanced datepicker styling with background, border and shadow - Improved template with datepicker-above class for better positioning - Maintains Bootstrap 5 compatibility and inline mode functionality This provides a better user experience by preventing the datepicker from appearing below and potentially being cut off by page boundaries.
This commit is contained in:
2
dist/app.js
vendored
2
dist/app.js
vendored
File diff suppressed because one or more lines are too long
@@ -156,6 +156,20 @@
|
||||
white-space: pre-wrap;
|
||||
}
|
||||
|
||||
/* Position datepicker above input for datepicker-above class */
|
||||
.datepicker-above .datepicker-inline {
|
||||
position: absolute;
|
||||
bottom: 100%;
|
||||
left: 0;
|
||||
right: 0;
|
||||
z-index: 1000;
|
||||
margin-bottom: 5px;
|
||||
background: white;
|
||||
border: 1px solid #dee2e6;
|
||||
border-radius: 0.375rem;
|
||||
box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075);
|
||||
}
|
||||
|
||||
.editable-container.editable-popup {
|
||||
max-width: none !important; /* without this rule poshytip/tooltip does not stretch */
|
||||
}
|
||||
|
181
dist/bootstrap-editable/js/bootstrap-editable.js
vendored
181
dist/bootstrap-editable/js/bootstrap-editable.js
vendored
@@ -1505,6 +1505,9 @@ Makes editable any HTML element on the page. Applied as jQuery method.
|
||||
return;
|
||||
}
|
||||
|
||||
// Set the editable's type from the input's type
|
||||
this.type = this.input.type;
|
||||
|
||||
//set value from settings or by element's text
|
||||
if (this.options.value === undefined || this.options.value === null) {
|
||||
this.value = this.input.html2value(this.$element.html().trim());
|
||||
@@ -4894,14 +4897,27 @@ $(function(){
|
||||
}
|
||||
|
||||
var Date = function (options) {
|
||||
console.log("Date constructor called with options:", options);
|
||||
this.init('date', options, Date.defaults);
|
||||
this.initPicker(options, Date.defaults);
|
||||
|
||||
// Ensure type is set correctly
|
||||
this.type = 'date';
|
||||
console.log("Date constructor completed, type set to:", this.type);
|
||||
};
|
||||
|
||||
$.fn.editableutils.inherit(Date, $.fn.editabletypes.abstractinput);
|
||||
|
||||
$.extend(Date.prototype, {
|
||||
prerender: function() {
|
||||
console.log("Date.prerender() called");
|
||||
// Call parent prerender
|
||||
Date.superclass.prerender.call(this);
|
||||
console.log("Date.prerender() completed, $input:", this.$input[0]);
|
||||
},
|
||||
|
||||
initPicker: function(options, defaults) {
|
||||
console.log("Date.initPicker() called");
|
||||
//'format' is set directly from settings or data-* attributes
|
||||
|
||||
//by default viewformat equals to format
|
||||
@@ -4921,8 +4937,8 @@ $(function(){
|
||||
//language
|
||||
this.options.datepicker.language = this.options.datepicker.language || 'en';
|
||||
|
||||
//store DPglobal
|
||||
this.dpg = $.fn.bdatepicker.DPGlobal;
|
||||
//store DPglobal - use datepicker instead of bdatepicker
|
||||
this.dpg = $.fn.datepicker.DPGlobal;
|
||||
|
||||
//store parsed formats
|
||||
this.parsedFormat = this.dpg.parseFormat(this.options.format);
|
||||
@@ -4930,7 +4946,31 @@ $(function(){
|
||||
},
|
||||
|
||||
render: function () {
|
||||
this.$input.bdatepicker(this.options.datepicker);
|
||||
// Debug: Check if render is being called
|
||||
console.log("Date.render() called, options:", this.options.datepicker);
|
||||
console.log("Input element for datepicker:", this.$input[0]);
|
||||
|
||||
// Ensure we have an input element
|
||||
if (!this.$input || !this.$input.length) {
|
||||
console.error("No input element found in render()");
|
||||
return;
|
||||
}
|
||||
|
||||
// Initialize datepicker immediately
|
||||
try {
|
||||
console.log("Attempting datepicker initialization in render()...");
|
||||
this.$input.datepicker(this.options.datepicker);
|
||||
console.log("Datepicker initialized successfully in render()");
|
||||
console.log("Datepicker data after render:", this.$input.data('datepicker'));
|
||||
|
||||
// Force set the initial value if we have one
|
||||
if (this.value) {
|
||||
console.log("Setting initial value in render():", this.value);
|
||||
this.$input.datepicker('setDate', this.value);
|
||||
}
|
||||
} catch (error) {
|
||||
console.error("Error initializing datepicker in render():", error);
|
||||
}
|
||||
|
||||
//"clear" link
|
||||
if(this.options.clear) {
|
||||
@@ -4966,11 +5006,60 @@ $(function(){
|
||||
},
|
||||
|
||||
value2input: function(value) {
|
||||
this.$input.bdatepicker('update', value);
|
||||
console.log("Date.value2input() called with value:", value);
|
||||
console.log("Input element in value2input:", this.$input[0]);
|
||||
console.log("Datepicker data in value2input:", this.$input.data('datepicker'));
|
||||
|
||||
// Ensure datepicker is initialized before trying to update
|
||||
if (!this.$input.data('datepicker')) {
|
||||
console.log("Datepicker not initialized in value2input, initializing now...");
|
||||
this.$input.datepicker(this.options.datepicker);
|
||||
console.log("Datepicker data after manual init in value2input:", this.$input.data('datepicker'));
|
||||
}
|
||||
|
||||
this.$input.datepicker('update', value);
|
||||
},
|
||||
|
||||
input2value: function() {
|
||||
return this.$input.data('datepicker').date;
|
||||
console.log("Date.input2value() called");
|
||||
var datepicker = this.$input.data('datepicker');
|
||||
console.log("Datepicker object in input2value:", datepicker);
|
||||
|
||||
if (datepicker) {
|
||||
console.log("Datepicker.date:", datepicker.date);
|
||||
console.log("Datepicker.dates:", datepicker.dates);
|
||||
console.log("Datepicker.getDate():", typeof datepicker.getDate === 'function' ? datepicker.getDate() : 'getDate not available');
|
||||
|
||||
if (datepicker.date) {
|
||||
console.log("Returning datepicker.date:", datepicker.date);
|
||||
return datepicker.date;
|
||||
}
|
||||
|
||||
// Try getting date from dates array
|
||||
if (datepicker.dates && datepicker.dates.length > 0) {
|
||||
console.log("Returning from dates array:", datepicker.dates[0]);
|
||||
return datepicker.dates[0];
|
||||
}
|
||||
|
||||
// Try using getDate method
|
||||
if (typeof datepicker.getDate === 'function') {
|
||||
var dateFromMethod = datepicker.getDate();
|
||||
console.log("Returning from getDate():", dateFromMethod);
|
||||
return dateFromMethod;
|
||||
}
|
||||
}
|
||||
|
||||
// Fallback: try to parse the input value directly
|
||||
var inputVal = this.$input.val();
|
||||
console.log("Input value fallback:", inputVal);
|
||||
if (inputVal) {
|
||||
var parsedDate = this.parseDate(inputVal, this.parsedViewFormat);
|
||||
console.log("Parsed date fallback:", parsedDate);
|
||||
return parsedDate;
|
||||
}
|
||||
|
||||
console.log("input2value returning null - no valid date found");
|
||||
return null;
|
||||
},
|
||||
|
||||
activate: function() {
|
||||
@@ -5105,18 +5194,37 @@ Automatically shown in inline mode.
|
||||
var DateField = function (options) {
|
||||
this.init('datefield', options, DateField.defaults);
|
||||
this.initPicker(options, DateField.defaults);
|
||||
|
||||
// Ensure type is set correctly
|
||||
this.type = 'datefield';
|
||||
};
|
||||
|
||||
$.fn.editableutils.inherit(DateField, $.fn.editabletypes.date);
|
||||
|
||||
$.extend(DateField.prototype, {
|
||||
render: function () {
|
||||
console.log("DateField.render() called");
|
||||
this.$input = this.$tpl.find('input');
|
||||
this.setClass();
|
||||
this.setAttr('placeholder');
|
||||
|
||||
//bootstrap-datepicker is set `bdateicker` to exclude conflict with jQuery UI one. (in date.js)
|
||||
this.$tpl.bdatepicker(this.options.datepicker);
|
||||
console.log("DateField initializing datepicker on container:", this.$tpl[0]);
|
||||
console.log("DateField datepicker options:", this.options.datepicker);
|
||||
|
||||
//use datepicker instead of bdatepicker
|
||||
this.$tpl.datepicker(this.options.datepicker);
|
||||
|
||||
console.log("DateField datepicker initialized, data:", this.$tpl.data('datepicker'));
|
||||
|
||||
// Add event listeners to track date changes
|
||||
this.$tpl.on('changeDate', $.proxy(function(e) {
|
||||
console.log("DateField changeDate event triggered:", e.date);
|
||||
}, this));
|
||||
|
||||
this.$tpl.on('hide', $.proxy(function(e) {
|
||||
console.log("DateField datepicker hide event triggered");
|
||||
console.log("DateField datepicker data on hide:", this.$tpl.data('datepicker'));
|
||||
}, this));
|
||||
|
||||
//need to disable original event handlers
|
||||
this.$input.off('focus keydown');
|
||||
@@ -5124,17 +5232,60 @@ Automatically shown in inline mode.
|
||||
//update value of datepicker
|
||||
this.$input.keyup($.proxy(function(){
|
||||
this.$tpl.removeData('date');
|
||||
this.$tpl.bdatepicker('update');
|
||||
this.$tpl.datepicker('update');
|
||||
}, this));
|
||||
|
||||
},
|
||||
|
||||
value2input: function(value) {
|
||||
this.$input.val(value ? this.dpg.formatDate(value, this.parsedViewFormat, this.options.datepicker.language) : '');
|
||||
this.$tpl.bdatepicker('update');
|
||||
console.log("DateField.value2input() called with value:", value);
|
||||
var formattedValue = value ? this.dpg.formatDate(value, this.parsedViewFormat, this.options.datepicker.language) : '';
|
||||
console.log("DateField formatted value for input:", formattedValue);
|
||||
this.$input.val(formattedValue);
|
||||
this.$tpl.datepicker('update');
|
||||
console.log("DateField after update, datepicker data:", this.$tpl.data('datepicker'));
|
||||
},
|
||||
|
||||
input2value: function() {
|
||||
console.log("DateField.input2value() called");
|
||||
|
||||
// First try the container datepicker (ideal case)
|
||||
var containerDatepicker = this.$tpl.data('datepicker');
|
||||
console.log("DateField container datepicker object:", containerDatepicker);
|
||||
|
||||
if (containerDatepicker && containerDatepicker.dates && containerDatepicker.dates.length > 0) {
|
||||
console.log("DateField returning from container dates array:", containerDatepicker.dates[0]);
|
||||
return containerDatepicker.dates[0];
|
||||
}
|
||||
|
||||
// Fallback: try the input datepicker (in case manual init worked)
|
||||
var inputDatepicker = this.$input.data('datepicker');
|
||||
console.log("DateField input datepicker object:", inputDatepicker);
|
||||
|
||||
if (inputDatepicker && inputDatepicker.dates && inputDatepicker.dates.length > 0) {
|
||||
console.log("DateField returning from input dates array:", inputDatepicker.dates[0]);
|
||||
return inputDatepicker.dates[0];
|
||||
}
|
||||
|
||||
// Try getDate methods
|
||||
if (containerDatepicker && typeof containerDatepicker.getDate === 'function') {
|
||||
var containerDate = containerDatepicker.getDate();
|
||||
if (containerDate) {
|
||||
console.log("DateField returning from container getDate():", containerDate);
|
||||
return containerDate;
|
||||
}
|
||||
}
|
||||
|
||||
if (inputDatepicker && typeof inputDatepicker.getDate === 'function') {
|
||||
var inputDate = inputDatepicker.getDate();
|
||||
if (inputDate) {
|
||||
console.log("DateField returning from input getDate():", inputDate);
|
||||
return inputDate;
|
||||
}
|
||||
}
|
||||
|
||||
// Final fallback to text parsing
|
||||
console.log("DateField fallback to text input value:", this.$input.val());
|
||||
return this.html2value(this.$input.val());
|
||||
},
|
||||
|
||||
@@ -5151,19 +5302,21 @@ Automatically shown in inline mode.
|
||||
/**
|
||||
@property tpl
|
||||
**/
|
||||
tpl:'<div class="input-append date"><input type="text"/><span class="add-on"><i class="icon-th"></i></span></div>',
|
||||
tpl:'<div class="input-group input-group-sm date datepicker-above" style="width: 200px; border: 1px solid #dee2e6; border-radius: 0.375rem; position: relative;"><input type="text" class="form-control form-control-sm" style="border: none;"/><span class="input-group-text" style="border: none; background: transparent;"><i class="bi bi-calendar"></i></span></div>',
|
||||
/**
|
||||
@property inputclass
|
||||
@default 'input-small'
|
||||
@default 'form-control form-control-sm'
|
||||
**/
|
||||
inputclass: 'input-small',
|
||||
inputclass: 'form-control form-control-sm',
|
||||
|
||||
/* datepicker config */
|
||||
datepicker: {
|
||||
weekStart: 0,
|
||||
startView: 0,
|
||||
minViewMode: 0,
|
||||
autoclose: true
|
||||
autoclose: true,
|
||||
orientation: 'top',
|
||||
container: 'body'
|
||||
}
|
||||
});
|
||||
|
||||
|
File diff suppressed because one or more lines are too long
@@ -156,6 +156,20 @@
|
||||
white-space: pre-wrap;
|
||||
}
|
||||
|
||||
/* Position datepicker above input for datepicker-above class */
|
||||
.datepicker-above .datepicker-inline {
|
||||
position: absolute;
|
||||
bottom: 100%;
|
||||
left: 0;
|
||||
right: 0;
|
||||
z-index: 1000;
|
||||
margin-bottom: 5px;
|
||||
background: white;
|
||||
border: 1px solid #dee2e6;
|
||||
border-radius: 0.375rem;
|
||||
box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075);
|
||||
}
|
||||
|
||||
.editable-container.editable-popup {
|
||||
max-width: none !important; /* without this rule poshytip/tooltip does not stretch */
|
||||
}
|
||||
|
181
dist/bootstrap3-editable/js/bootstrap-editable.js
vendored
181
dist/bootstrap3-editable/js/bootstrap-editable.js
vendored
@@ -1505,6 +1505,9 @@ Makes editable any HTML element on the page. Applied as jQuery method.
|
||||
return;
|
||||
}
|
||||
|
||||
// Set the editable's type from the input's type
|
||||
this.type = this.input.type;
|
||||
|
||||
//set value from settings or by element's text
|
||||
if (this.options.value === undefined || this.options.value === null) {
|
||||
this.value = this.input.html2value(this.$element.html().trim());
|
||||
@@ -4962,14 +4965,27 @@ $(function(){
|
||||
}
|
||||
|
||||
var Date = function (options) {
|
||||
console.log("Date constructor called with options:", options);
|
||||
this.init('date', options, Date.defaults);
|
||||
this.initPicker(options, Date.defaults);
|
||||
|
||||
// Ensure type is set correctly
|
||||
this.type = 'date';
|
||||
console.log("Date constructor completed, type set to:", this.type);
|
||||
};
|
||||
|
||||
$.fn.editableutils.inherit(Date, $.fn.editabletypes.abstractinput);
|
||||
|
||||
$.extend(Date.prototype, {
|
||||
prerender: function() {
|
||||
console.log("Date.prerender() called");
|
||||
// Call parent prerender
|
||||
Date.superclass.prerender.call(this);
|
||||
console.log("Date.prerender() completed, $input:", this.$input[0]);
|
||||
},
|
||||
|
||||
initPicker: function(options, defaults) {
|
||||
console.log("Date.initPicker() called");
|
||||
//'format' is set directly from settings or data-* attributes
|
||||
|
||||
//by default viewformat equals to format
|
||||
@@ -4989,8 +5005,8 @@ $(function(){
|
||||
//language
|
||||
this.options.datepicker.language = this.options.datepicker.language || 'en';
|
||||
|
||||
//store DPglobal
|
||||
this.dpg = $.fn.bdatepicker.DPGlobal;
|
||||
//store DPglobal - use datepicker instead of bdatepicker
|
||||
this.dpg = $.fn.datepicker.DPGlobal;
|
||||
|
||||
//store parsed formats
|
||||
this.parsedFormat = this.dpg.parseFormat(this.options.format);
|
||||
@@ -4998,7 +5014,31 @@ $(function(){
|
||||
},
|
||||
|
||||
render: function () {
|
||||
this.$input.bdatepicker(this.options.datepicker);
|
||||
// Debug: Check if render is being called
|
||||
console.log("Date.render() called, options:", this.options.datepicker);
|
||||
console.log("Input element for datepicker:", this.$input[0]);
|
||||
|
||||
// Ensure we have an input element
|
||||
if (!this.$input || !this.$input.length) {
|
||||
console.error("No input element found in render()");
|
||||
return;
|
||||
}
|
||||
|
||||
// Initialize datepicker immediately
|
||||
try {
|
||||
console.log("Attempting datepicker initialization in render()...");
|
||||
this.$input.datepicker(this.options.datepicker);
|
||||
console.log("Datepicker initialized successfully in render()");
|
||||
console.log("Datepicker data after render:", this.$input.data('datepicker'));
|
||||
|
||||
// Force set the initial value if we have one
|
||||
if (this.value) {
|
||||
console.log("Setting initial value in render():", this.value);
|
||||
this.$input.datepicker('setDate', this.value);
|
||||
}
|
||||
} catch (error) {
|
||||
console.error("Error initializing datepicker in render():", error);
|
||||
}
|
||||
|
||||
//"clear" link
|
||||
if(this.options.clear) {
|
||||
@@ -5034,11 +5074,60 @@ $(function(){
|
||||
},
|
||||
|
||||
value2input: function(value) {
|
||||
this.$input.bdatepicker('update', value);
|
||||
console.log("Date.value2input() called with value:", value);
|
||||
console.log("Input element in value2input:", this.$input[0]);
|
||||
console.log("Datepicker data in value2input:", this.$input.data('datepicker'));
|
||||
|
||||
// Ensure datepicker is initialized before trying to update
|
||||
if (!this.$input.data('datepicker')) {
|
||||
console.log("Datepicker not initialized in value2input, initializing now...");
|
||||
this.$input.datepicker(this.options.datepicker);
|
||||
console.log("Datepicker data after manual init in value2input:", this.$input.data('datepicker'));
|
||||
}
|
||||
|
||||
this.$input.datepicker('update', value);
|
||||
},
|
||||
|
||||
input2value: function() {
|
||||
return this.$input.data('datepicker').date;
|
||||
console.log("Date.input2value() called");
|
||||
var datepicker = this.$input.data('datepicker');
|
||||
console.log("Datepicker object in input2value:", datepicker);
|
||||
|
||||
if (datepicker) {
|
||||
console.log("Datepicker.date:", datepicker.date);
|
||||
console.log("Datepicker.dates:", datepicker.dates);
|
||||
console.log("Datepicker.getDate():", typeof datepicker.getDate === 'function' ? datepicker.getDate() : 'getDate not available');
|
||||
|
||||
if (datepicker.date) {
|
||||
console.log("Returning datepicker.date:", datepicker.date);
|
||||
return datepicker.date;
|
||||
}
|
||||
|
||||
// Try getting date from dates array
|
||||
if (datepicker.dates && datepicker.dates.length > 0) {
|
||||
console.log("Returning from dates array:", datepicker.dates[0]);
|
||||
return datepicker.dates[0];
|
||||
}
|
||||
|
||||
// Try using getDate method
|
||||
if (typeof datepicker.getDate === 'function') {
|
||||
var dateFromMethod = datepicker.getDate();
|
||||
console.log("Returning from getDate():", dateFromMethod);
|
||||
return dateFromMethod;
|
||||
}
|
||||
}
|
||||
|
||||
// Fallback: try to parse the input value directly
|
||||
var inputVal = this.$input.val();
|
||||
console.log("Input value fallback:", inputVal);
|
||||
if (inputVal) {
|
||||
var parsedDate = this.parseDate(inputVal, this.parsedViewFormat);
|
||||
console.log("Parsed date fallback:", parsedDate);
|
||||
return parsedDate;
|
||||
}
|
||||
|
||||
console.log("input2value returning null - no valid date found");
|
||||
return null;
|
||||
},
|
||||
|
||||
activate: function() {
|
||||
@@ -5173,18 +5262,37 @@ Automatically shown in inline mode.
|
||||
var DateField = function (options) {
|
||||
this.init('datefield', options, DateField.defaults);
|
||||
this.initPicker(options, DateField.defaults);
|
||||
|
||||
// Ensure type is set correctly
|
||||
this.type = 'datefield';
|
||||
};
|
||||
|
||||
$.fn.editableutils.inherit(DateField, $.fn.editabletypes.date);
|
||||
|
||||
$.extend(DateField.prototype, {
|
||||
render: function () {
|
||||
console.log("DateField.render() called");
|
||||
this.$input = this.$tpl.find('input');
|
||||
this.setClass();
|
||||
this.setAttr('placeholder');
|
||||
|
||||
//bootstrap-datepicker is set `bdateicker` to exclude conflict with jQuery UI one. (in date.js)
|
||||
this.$tpl.bdatepicker(this.options.datepicker);
|
||||
console.log("DateField initializing datepicker on container:", this.$tpl[0]);
|
||||
console.log("DateField datepicker options:", this.options.datepicker);
|
||||
|
||||
//use datepicker instead of bdatepicker
|
||||
this.$tpl.datepicker(this.options.datepicker);
|
||||
|
||||
console.log("DateField datepicker initialized, data:", this.$tpl.data('datepicker'));
|
||||
|
||||
// Add event listeners to track date changes
|
||||
this.$tpl.on('changeDate', $.proxy(function(e) {
|
||||
console.log("DateField changeDate event triggered:", e.date);
|
||||
}, this));
|
||||
|
||||
this.$tpl.on('hide', $.proxy(function(e) {
|
||||
console.log("DateField datepicker hide event triggered");
|
||||
console.log("DateField datepicker data on hide:", this.$tpl.data('datepicker'));
|
||||
}, this));
|
||||
|
||||
//need to disable original event handlers
|
||||
this.$input.off('focus keydown');
|
||||
@@ -5192,17 +5300,60 @@ Automatically shown in inline mode.
|
||||
//update value of datepicker
|
||||
this.$input.keyup($.proxy(function(){
|
||||
this.$tpl.removeData('date');
|
||||
this.$tpl.bdatepicker('update');
|
||||
this.$tpl.datepicker('update');
|
||||
}, this));
|
||||
|
||||
},
|
||||
|
||||
value2input: function(value) {
|
||||
this.$input.val(value ? this.dpg.formatDate(value, this.parsedViewFormat, this.options.datepicker.language) : '');
|
||||
this.$tpl.bdatepicker('update');
|
||||
console.log("DateField.value2input() called with value:", value);
|
||||
var formattedValue = value ? this.dpg.formatDate(value, this.parsedViewFormat, this.options.datepicker.language) : '';
|
||||
console.log("DateField formatted value for input:", formattedValue);
|
||||
this.$input.val(formattedValue);
|
||||
this.$tpl.datepicker('update');
|
||||
console.log("DateField after update, datepicker data:", this.$tpl.data('datepicker'));
|
||||
},
|
||||
|
||||
input2value: function() {
|
||||
console.log("DateField.input2value() called");
|
||||
|
||||
// First try the container datepicker (ideal case)
|
||||
var containerDatepicker = this.$tpl.data('datepicker');
|
||||
console.log("DateField container datepicker object:", containerDatepicker);
|
||||
|
||||
if (containerDatepicker && containerDatepicker.dates && containerDatepicker.dates.length > 0) {
|
||||
console.log("DateField returning from container dates array:", containerDatepicker.dates[0]);
|
||||
return containerDatepicker.dates[0];
|
||||
}
|
||||
|
||||
// Fallback: try the input datepicker (in case manual init worked)
|
||||
var inputDatepicker = this.$input.data('datepicker');
|
||||
console.log("DateField input datepicker object:", inputDatepicker);
|
||||
|
||||
if (inputDatepicker && inputDatepicker.dates && inputDatepicker.dates.length > 0) {
|
||||
console.log("DateField returning from input dates array:", inputDatepicker.dates[0]);
|
||||
return inputDatepicker.dates[0];
|
||||
}
|
||||
|
||||
// Try getDate methods
|
||||
if (containerDatepicker && typeof containerDatepicker.getDate === 'function') {
|
||||
var containerDate = containerDatepicker.getDate();
|
||||
if (containerDate) {
|
||||
console.log("DateField returning from container getDate():", containerDate);
|
||||
return containerDate;
|
||||
}
|
||||
}
|
||||
|
||||
if (inputDatepicker && typeof inputDatepicker.getDate === 'function') {
|
||||
var inputDate = inputDatepicker.getDate();
|
||||
if (inputDate) {
|
||||
console.log("DateField returning from input getDate():", inputDate);
|
||||
return inputDate;
|
||||
}
|
||||
}
|
||||
|
||||
// Final fallback to text parsing
|
||||
console.log("DateField fallback to text input value:", this.$input.val());
|
||||
return this.html2value(this.$input.val());
|
||||
},
|
||||
|
||||
@@ -5219,19 +5370,21 @@ Automatically shown in inline mode.
|
||||
/**
|
||||
@property tpl
|
||||
**/
|
||||
tpl:'<div class="input-append date"><input type="text"/><span class="add-on"><i class="icon-th"></i></span></div>',
|
||||
tpl:'<div class="input-group input-group-sm date datepicker-above" style="width: 200px; border: 1px solid #dee2e6; border-radius: 0.375rem; position: relative;"><input type="text" class="form-control form-control-sm" style="border: none;"/><span class="input-group-text" style="border: none; background: transparent;"><i class="bi bi-calendar"></i></span></div>',
|
||||
/**
|
||||
@property inputclass
|
||||
@default 'input-small'
|
||||
@default 'form-control form-control-sm'
|
||||
**/
|
||||
inputclass: 'input-small',
|
||||
inputclass: 'form-control form-control-sm',
|
||||
|
||||
/* datepicker config */
|
||||
datepicker: {
|
||||
weekStart: 0,
|
||||
startView: 0,
|
||||
minViewMode: 0,
|
||||
autoclose: true
|
||||
autoclose: true,
|
||||
orientation: 'top',
|
||||
container: 'body'
|
||||
}
|
||||
});
|
||||
|
||||
|
File diff suppressed because one or more lines are too long
@@ -156,6 +156,20 @@
|
||||
white-space: pre-wrap;
|
||||
}
|
||||
|
||||
/* Position datepicker above input for datepicker-above class */
|
||||
.datepicker-above .datepicker-inline {
|
||||
position: absolute;
|
||||
bottom: 100%;
|
||||
left: 0;
|
||||
right: 0;
|
||||
z-index: 1000;
|
||||
margin-bottom: 5px;
|
||||
background: white;
|
||||
border: 1px solid #dee2e6;
|
||||
border-radius: 0.375rem;
|
||||
box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075);
|
||||
}
|
||||
|
||||
.editable-container.editable-popup {
|
||||
max-width: none !important; /* without this rule poshytip/tooltip does not stretch */
|
||||
}
|
||||
|
14
dist/bootstrap5-editable/css/editable-form.css
vendored
14
dist/bootstrap5-editable/css/editable-form.css
vendored
@@ -151,3 +151,17 @@
|
||||
.editable-pre-wrapped {
|
||||
white-space: pre-wrap;
|
||||
}
|
||||
|
||||
/* Position datepicker above input for datepicker-above class */
|
||||
.datepicker-above .datepicker-inline {
|
||||
position: absolute;
|
||||
bottom: 100%;
|
||||
left: 0;
|
||||
right: 0;
|
||||
z-index: 1000;
|
||||
margin-bottom: 5px;
|
||||
background: white;
|
||||
border: 1px solid #dee2e6;
|
||||
border-radius: 0.375rem;
|
||||
box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075);
|
||||
}
|
||||
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
14
dist/jquery-editable/css/jquery-editable.css
vendored
14
dist/jquery-editable/css/jquery-editable.css
vendored
@@ -156,6 +156,20 @@
|
||||
white-space: pre-wrap;
|
||||
}
|
||||
|
||||
/* Position datepicker above input for datepicker-above class */
|
||||
.datepicker-above .datepicker-inline {
|
||||
position: absolute;
|
||||
bottom: 100%;
|
||||
left: 0;
|
||||
right: 0;
|
||||
z-index: 1000;
|
||||
margin-bottom: 5px;
|
||||
background: white;
|
||||
border: 1px solid #dee2e6;
|
||||
border-radius: 0.375rem;
|
||||
box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075);
|
||||
}
|
||||
|
||||
.editable-container.editable-popup {
|
||||
max-width: none !important; /* without this rule poshytip/tooltip does not stretch */
|
||||
}
|
||||
|
@@ -1505,6 +1505,9 @@ Makes editable any HTML element on the page. Applied as jQuery method.
|
||||
return;
|
||||
}
|
||||
|
||||
// Set the editable's type from the input's type
|
||||
this.type = this.input.type;
|
||||
|
||||
//set value from settings or by element's text
|
||||
if (this.options.value === undefined || this.options.value === null) {
|
||||
this.value = this.input.html2value(this.$element.html().trim());
|
||||
|
File diff suppressed because one or more lines are too long
14
dist/jqueryui-editable/css/jqueryui-editable.css
vendored
14
dist/jqueryui-editable/css/jqueryui-editable.css
vendored
@@ -156,6 +156,20 @@
|
||||
white-space: pre-wrap;
|
||||
}
|
||||
|
||||
/* Position datepicker above input for datepicker-above class */
|
||||
.datepicker-above .datepicker-inline {
|
||||
position: absolute;
|
||||
bottom: 100%;
|
||||
left: 0;
|
||||
right: 0;
|
||||
z-index: 1000;
|
||||
margin-bottom: 5px;
|
||||
background: white;
|
||||
border: 1px solid #dee2e6;
|
||||
border-radius: 0.375rem;
|
||||
box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075);
|
||||
}
|
||||
|
||||
.editable-container.editable-popup {
|
||||
max-width: none !important; /* without this rule poshytip/tooltip does not stretch */
|
||||
}
|
||||
|
@@ -1505,6 +1505,9 @@ Makes editable any HTML element on the page. Applied as jQuery method.
|
||||
return;
|
||||
}
|
||||
|
||||
// Set the editable's type from the input's type
|
||||
this.type = this.input.type;
|
||||
|
||||
//set value from settings or by element's text
|
||||
if (this.options.value === undefined || this.options.value === null) {
|
||||
this.value = this.input.html2value(this.$element.html().trim());
|
||||
|
File diff suppressed because one or more lines are too long
@@ -151,3 +151,17 @@
|
||||
.editable-pre-wrapped {
|
||||
white-space: pre-wrap;
|
||||
}
|
||||
|
||||
/* Position datepicker above input for datepicker-above class */
|
||||
.datepicker-above .datepicker-inline {
|
||||
position: absolute;
|
||||
bottom: 100%;
|
||||
left: 0;
|
||||
right: 0;
|
||||
z-index: 1000;
|
||||
margin-bottom: 5px;
|
||||
background: white;
|
||||
border: 1px solid #dee2e6;
|
||||
border-radius: 0.375rem;
|
||||
box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075);
|
||||
}
|
||||
|
@@ -14,18 +14,37 @@ Automatically shown in inline mode.
|
||||
var DateField = function (options) {
|
||||
this.init('datefield', options, DateField.defaults);
|
||||
this.initPicker(options, DateField.defaults);
|
||||
|
||||
// Ensure type is set correctly
|
||||
this.type = 'datefield';
|
||||
};
|
||||
|
||||
$.fn.editableutils.inherit(DateField, $.fn.editabletypes.date);
|
||||
|
||||
$.extend(DateField.prototype, {
|
||||
render: function () {
|
||||
console.log("DateField.render() called");
|
||||
this.$input = this.$tpl.find('input');
|
||||
this.setClass();
|
||||
this.setAttr('placeholder');
|
||||
|
||||
//bootstrap-datepicker is set `bdateicker` to exclude conflict with jQuery UI one. (in date.js)
|
||||
this.$tpl.bdatepicker(this.options.datepicker);
|
||||
console.log("DateField initializing datepicker on container:", this.$tpl[0]);
|
||||
console.log("DateField datepicker options:", this.options.datepicker);
|
||||
|
||||
//use datepicker instead of bdatepicker
|
||||
this.$tpl.datepicker(this.options.datepicker);
|
||||
|
||||
console.log("DateField datepicker initialized, data:", this.$tpl.data('datepicker'));
|
||||
|
||||
// Add event listeners to track date changes
|
||||
this.$tpl.on('changeDate', $.proxy(function(e) {
|
||||
console.log("DateField changeDate event triggered:", e.date);
|
||||
}, this));
|
||||
|
||||
this.$tpl.on('hide', $.proxy(function(e) {
|
||||
console.log("DateField datepicker hide event triggered");
|
||||
console.log("DateField datepicker data on hide:", this.$tpl.data('datepicker'));
|
||||
}, this));
|
||||
|
||||
//need to disable original event handlers
|
||||
this.$input.off('focus keydown');
|
||||
@@ -33,17 +52,60 @@ Automatically shown in inline mode.
|
||||
//update value of datepicker
|
||||
this.$input.keyup($.proxy(function(){
|
||||
this.$tpl.removeData('date');
|
||||
this.$tpl.bdatepicker('update');
|
||||
this.$tpl.datepicker('update');
|
||||
}, this));
|
||||
|
||||
},
|
||||
|
||||
value2input: function(value) {
|
||||
this.$input.val(value ? this.dpg.formatDate(value, this.parsedViewFormat, this.options.datepicker.language) : '');
|
||||
this.$tpl.bdatepicker('update');
|
||||
console.log("DateField.value2input() called with value:", value);
|
||||
var formattedValue = value ? this.dpg.formatDate(value, this.parsedViewFormat, this.options.datepicker.language) : '';
|
||||
console.log("DateField formatted value for input:", formattedValue);
|
||||
this.$input.val(formattedValue);
|
||||
this.$tpl.datepicker('update');
|
||||
console.log("DateField after update, datepicker data:", this.$tpl.data('datepicker'));
|
||||
},
|
||||
|
||||
input2value: function() {
|
||||
console.log("DateField.input2value() called");
|
||||
|
||||
// First try the container datepicker (ideal case)
|
||||
var containerDatepicker = this.$tpl.data('datepicker');
|
||||
console.log("DateField container datepicker object:", containerDatepicker);
|
||||
|
||||
if (containerDatepicker && containerDatepicker.dates && containerDatepicker.dates.length > 0) {
|
||||
console.log("DateField returning from container dates array:", containerDatepicker.dates[0]);
|
||||
return containerDatepicker.dates[0];
|
||||
}
|
||||
|
||||
// Fallback: try the input datepicker (in case manual init worked)
|
||||
var inputDatepicker = this.$input.data('datepicker');
|
||||
console.log("DateField input datepicker object:", inputDatepicker);
|
||||
|
||||
if (inputDatepicker && inputDatepicker.dates && inputDatepicker.dates.length > 0) {
|
||||
console.log("DateField returning from input dates array:", inputDatepicker.dates[0]);
|
||||
return inputDatepicker.dates[0];
|
||||
}
|
||||
|
||||
// Try getDate methods
|
||||
if (containerDatepicker && typeof containerDatepicker.getDate === 'function') {
|
||||
var containerDate = containerDatepicker.getDate();
|
||||
if (containerDate) {
|
||||
console.log("DateField returning from container getDate():", containerDate);
|
||||
return containerDate;
|
||||
}
|
||||
}
|
||||
|
||||
if (inputDatepicker && typeof inputDatepicker.getDate === 'function') {
|
||||
var inputDate = inputDatepicker.getDate();
|
||||
if (inputDate) {
|
||||
console.log("DateField returning from input getDate():", inputDate);
|
||||
return inputDate;
|
||||
}
|
||||
}
|
||||
|
||||
// Final fallback to text parsing
|
||||
console.log("DateField fallback to text input value:", this.$input.val());
|
||||
return this.html2value(this.$input.val());
|
||||
},
|
||||
|
||||
@@ -60,19 +122,21 @@ Automatically shown in inline mode.
|
||||
/**
|
||||
@property tpl
|
||||
**/
|
||||
tpl:'<div class="input-append date"><input type="text"/><span class="add-on"><i class="icon-th"></i></span></div>',
|
||||
tpl:'<div class="input-group input-group-sm date datepicker-above" style="width: 200px; border: 1px solid #dee2e6; border-radius: 0.375rem; position: relative;"><input type="text" class="form-control form-control-sm" style="border: none;"/><span class="input-group-text" style="border: none; background: transparent;"><i class="bi bi-calendar"></i></span></div>',
|
||||
/**
|
||||
@property inputclass
|
||||
@default 'input-small'
|
||||
@default 'form-control form-control-sm'
|
||||
**/
|
||||
inputclass: 'input-small',
|
||||
inputclass: 'form-control form-control-sm',
|
||||
|
||||
/* datepicker config */
|
||||
datepicker: {
|
||||
weekStart: 0,
|
||||
startView: 0,
|
||||
minViewMode: 0,
|
||||
autoclose: true
|
||||
autoclose: true,
|
||||
orientation: 'top',
|
||||
container: 'body'
|
||||
}
|
||||
});
|
||||
|
||||
|
28
test.js
28
test.js
@@ -17,7 +17,7 @@ require("./dist/bootstrap5-editable/js/bootstrap-editable");
|
||||
console.log("$.fn.editable available:", typeof $.fn.editable);
|
||||
console.log("$.fn.datepicker available:", typeof $.fn.datepicker);
|
||||
console.log("$.fn.bdatepicker available:", typeof $.fn.bdatepicker);
|
||||
$.fn.editable.defaults.mode = 'popup';
|
||||
$.fn.editable.defaults.mode = 'inline';
|
||||
|
||||
$(function() {
|
||||
|
||||
@@ -59,10 +59,13 @@ $(function() {
|
||||
}
|
||||
});
|
||||
|
||||
const initialDateValue = new Date().toISOString().split('T')[0];
|
||||
console.log("Setting up datepicker with initial value:", initialDateValue);
|
||||
|
||||
$('#datepicker').editable({
|
||||
type: 'date',
|
||||
url: 'test.php', // URL to send the POST request
|
||||
value: new Date().toISOString().split('T')[0], // Set to current date (YYYY-MM-DD)
|
||||
value: initialDateValue, // Set to current date (YYYY-MM-DD)
|
||||
format: 'yyyy-mm-dd', // Date format
|
||||
viewformat: 'dd/mm/yyyy', // How the user sees it
|
||||
datepicker: {
|
||||
@@ -81,6 +84,8 @@ $(function() {
|
||||
console.log("Date save event:", params);
|
||||
console.log("Value being saved:", params.newValue);
|
||||
console.log("Submit value:", params.submitValue);
|
||||
}).on('nochange', function(e) {
|
||||
console.log("Date nochange event fired - values are considered equal");
|
||||
}).on('shown', function(e, editable) {
|
||||
console.log("Datepicker shown event fired", editable);
|
||||
|
||||
@@ -116,23 +121,8 @@ $(function() {
|
||||
console.log("Input $input.datepicker available:", typeof editable.input.$input.datepicker);
|
||||
console.log("Input $input.bdatepicker available:", typeof editable.input.$input.bdatepicker);
|
||||
|
||||
// Try to manually initialize datepicker to see if it works
|
||||
try {
|
||||
console.log("Attempting manual datepicker initialization...");
|
||||
editable.input.$input.datepicker({
|
||||
weekStart: 1,
|
||||
autoclose: true,
|
||||
todayHighlight: true
|
||||
});
|
||||
console.log("Manual datepicker initialization successful!");
|
||||
console.log("Input datepicker data after manual init:", editable.input.$input.data('datepicker'));
|
||||
|
||||
// Try setting a date value manually
|
||||
editable.input.$input.datepicker('setDate', new Date());
|
||||
console.log("Set manual date, datepicker data now:", editable.input.$input.data('datepicker'));
|
||||
} catch (error) {
|
||||
console.error("Manual datepicker initialization failed:", error);
|
||||
}
|
||||
// Check if the datepicker is properly initialized (no manual override)
|
||||
console.log("Checking if datepicker is properly initialized without manual intervention");
|
||||
}
|
||||
}).on('hidden', function(e, reason) {
|
||||
console.log("Datepicker hidden event fired, reason:", reason);
|
||||
|
Reference in New Issue
Block a user