text x-clear button and new $tpl property in inputs, need tests

This commit is contained in:
vitalets 2013-01-05 16:23:58 +04:00
parent f6a7b26e1f
commit 5edc4bbfcb
15 changed files with 173 additions and 84 deletions

@ -88,4 +88,33 @@
font-size: 0.9em;
text-decoration: none;
text-align: right;
}
}
.editable-clear-x {
background: url('../img/clear.png') center center no-repeat;
display: block;
width: 13px;
height: 13px;
position: absolute;
right: 7px;
opacity: 0.6;
z-index: 100;
}
.editable-clear-x:hover {
opacity: 1;
}
/*
.editable-clear-x1 {
background: url('../img/clear.png') center center no-repeat;
display: inline-block;
zoom: 1;
*display: inline;
width: 13px;
height: 13px;
vertical-align: middle;
position: relative;
margin-left: -20px;
}
*/

@ -64,8 +64,8 @@ Editableform is linked with one of input types, e.g. 'text', 'select' etc.
//render input
$.when(this.input.render())
.then($.proxy(function () {
//input
this.$form.find('div.editable-input').append(this.input.$input);
//insert input in form
this.$form.find('div.editable-input').append(this.input.$tpl);
//automatically submit inputs when no buttons shown
if(!this.options.showbuttons) {
@ -73,9 +73,9 @@ Editableform is linked with one of input types, e.g. 'text', 'select' etc.
}
//"clear" link
if(this.input.$clear) {
this.$form.find('div.editable-input').append($('<div class="editable-clear">').append(this.input.$clear));
}
// if(this.input.$clear) {
// this.$form.find('div.editable-input').append($('<div class="editable-clear">').append(this.input.$clear));
// }
//append form to container
this.$div.append(this.$form);
@ -83,6 +83,11 @@ Editableform is linked with one of input types, e.g. 'text', 'select' etc.
//attach 'cancel' handler
this.$form.find('.editable-cancel').click($.proxy(this.cancel, this));
//call postrender to perform actions, required when input is in DOM
if(this.input.postrender) {
this.input.postrender();
}
if(this.input.error) {
this.error(this.input.error);
this.$form.find('.editable-submit').attr('disabled', true);

BIN
src/img/clear.png Normal file

Binary file not shown.

After

(image error) Size: 509 B

@ -153,11 +153,11 @@ $(function(){
});
Address.defaults = $.extend({}, $.fn.editabletypes.abstractinput.defaults, {
tpl: '<div><label><span>City: </span><input type="text" name="city" class="input-small"></label></div>'+
'<div><label><span>Street: </span><input type="text" name="street" class="input-small"></label></div>'+
'<div><label><span>Building: </span><input type="text" name="building" class="input-mini"></label></div>',
tpl: '<div class="editable-address"><label><span>City: </span><input type="text" name="city" class="input-small"></label></div>'+
'<div class="editable-address"><label><span>Street: </span><input type="text" name="street" class="input-small"></label></div>'+
'<div class="editable-address"><label><span>Building: </span><input type="text" name="building" class="input-mini"></label></div>',
inputclass: 'editable-address'
inputclass: ''
});
$.fn.editabletypes.address = Address;

@ -20,9 +20,10 @@ To create your own input you can inherit from this class.
**/
init: function(type, options, defaults) {
this.type = type;
this.options = $.extend({}, defaults, options);
this.$input = null;
this.$clear = null;
this.options = $.extend({}, defaults, options);
this.$tpl = null; //whole tpl as jquery object
this.$input = null; //input as jquery object
this.$clear = null; //clear button
this.error = null;
},
@ -32,14 +33,8 @@ To create your own input you can inherit from this class.
@method render()
**/
render: function() {
this.$input = $(this.options.tpl);
if(this.options.inputclass) {
this.$input.addClass(this.options.inputclass);
}
if (this.options.placeholder) {
this.$input.attr('placeholder', this.options.placeholder);
}
this.$tpl = $(this.options.tpl);
this.$input = this.$tpl;
},
/**

@ -44,8 +44,13 @@ $(function(){
}))
.append($('<span>').text(' '+this.sourceData[i].text));
$('<div>').append($label).appendTo(this.$input);
$('<div>').append($label).appendTo(this.$tpl);
}
this.$input = this.$tpl.find('input[type="checkbox"]');
if(this.options.inputclass) {
this.$input.addClass(this.options.inputclass);
}
},
value2str: function(value) {
@ -66,10 +71,9 @@ $(function(){
//set checked on required checkboxes
value2input: function(value) {
var $checks = this.$input.find('input[type="checkbox"]');
$checks.removeAttr('checked');
this.$input.removeAttr('checked');
if($.isArray(value) && value.length) {
$checks.each(function(i, el) {
this.$input.each(function(i, el) {
var $el = $(el);
// cannot use $.inArray as it performs strict comparison
$.each(value, function(j, val){
@ -85,7 +89,7 @@ $(function(){
input2value: function() {
var checked = [];
this.$input.find('input:checked').each(function(i, el) {
this.$input.filter(':checked').each(function(i, el) {
checked.push($(el).val());
});
return checked;
@ -105,11 +109,11 @@ $(function(){
},
activate: function() {
this.$input.find('input[type="checkbox"]').first().focus();
this.$input.first().focus();
},
autosubmit: function() {
this.$input.find('input[type="checkbox"]').on('keydown', function(e){
this.$input.on('keydown', function(e){
if (e.which === 13) {
$(this).closest('form').submit();
}
@ -122,14 +126,14 @@ $(function(){
@property tpl
@default <div></div>
**/
tpl:'<div></div>',
tpl:'<div class="editable-checklist"></div>',
/**
@property inputclass
@type string
@default editable-checklist
@default
**/
inputclass: 'editable-checklist',
inputclass: '',
/**
Separator of values when reading from 'data-value' string

@ -60,14 +60,19 @@ $(function(){
render: function () {
Date.superclass.render.call(this);
this.$input.datepicker(this.options.datepicker);
},
postrender: function() {
//"clear" link
if(this.options.clear) {
this.$clear = $('<a href="#"></a>').html(this.options.clear).click($.proxy(function(e){
e.preventDefault();
e.stopPropagation();
this.clear();
}, this));
}
this.$tpl.parent().append($('<div class="editable-clear">').append(this.$clear));
}
},
value2html: function(value, element) {
@ -123,12 +128,12 @@ $(function(){
@property tpl
@default <div></div>
**/
tpl:'<div></div>',
tpl:'<div class="editable-date well"></div>',
/**
@property inputclass
@default editable-date well
@default
**/
inputclass: 'editable-date well',
inputclass: '',
/**
Format used for sending value to server. Also applied when converting date from <code>data-value</code> attribute.<br>
Possible tokens are: <code>d, dd, m, mm, yy, yyyy</code>

@ -14,44 +14,41 @@ Automatically shown in inline mode.
$.extend(DateField.prototype, {
render: function () {
this.$input = $(this.options.tpl);
this.$field = this.$input.find('input');
this.$tpl = $(this.options.tpl);
this.$input = this.$tpl.find('input');
if(this.options.inputclass) {
this.$field.addClass(this.options.inputclass);
this.$input.addClass(this.options.inputclass);
}
if (this.options.placeholder) {
this.$field.attr('placeholder', this.options.placeholder);
this.$input.attr('placeholder', this.options.placeholder);
}
this.$input.datepicker(this.options.datepicker);
this.$tpl.datepicker(this.options.datepicker);
//need to disable original event handlers
this.$field.off('focus keydown');
this.$input.off('focus keydown');
//update value of datepicker
this.$field.keyup($.proxy(function(){
this.$input.removeData('date');
this.$input.datepicker('update');
this.$input.keyup($.proxy(function(){
this.$tpl.removeData('date');
this.$tpl.datepicker('update');
}, this));
},
value2input: function(value) {
this.$field.val(value ? this.dpg.formatDate(value, this.parsedViewFormat, this.options.datepicker.language) : '');
this.$input.datepicker('update');
this.$input.val(value ? this.dpg.formatDate(value, this.parsedViewFormat, this.options.datepicker.language) : '');
this.$tpl.datepicker('update');
},
input2value: function() {
return this.html2value(this.$field.val());
return this.html2value(this.$input.val());
},
activate: function() {
if(this.$field.is(':visible')) {
this.$field.focus();
$.fn.editableutils.setCursorPosition(this.$field.get(0), this.$field.val().length);
}
$.fn.editabletypes.text.prototype.activate.call(this);
},
autosubmit: function() {
@ -64,12 +61,12 @@ Automatically shown in inline mode.
@property tpl
@default
**/
tpl:'<div class="input-append date"><input class="input-small" type="text"/><span class="add-on"><i class="icon-th"></i></span></div>',
tpl:'<div class="input-append date"><input type="text"/><span class="add-on"><i class="icon-th"></i></span></div>',
/**
@property inputclass
@default ''
@default 'input-small'
**/
inputclass: '',
inputclass: 'input-small',
/* datepicker config */
datepicker: {

@ -52,15 +52,20 @@ $(function(){
render: function () {
DateUI.superclass.render.call(this);
this.$input.datepicker(this.options.datepicker);
},
postrender: function() {
//"clear" link
if(this.options.clear) {
this.$clear = $('<a href="#"></a>').html(this.options.clear).click($.proxy(function(e){
e.preventDefault();
e.stopPropagation();
this.clear();
}, this));
this.$tpl.parent().append($('<div class="editable-clear">').append(this.$clear));
}
},
},
value2html: function(value, element) {
var text = $.datepicker.formatDate(this.options.viewformat, value);
@ -134,12 +139,12 @@ $(function(){
@property tpl
@default <div></div>
**/
tpl:'<div></div>',
tpl:'<div class="editable-date"></div>',
/**
@property inputclass
@default 'editable-date'
@default ''
**/
inputclass: 'editable-date',
inputclass: '',
/**
Format used for sending value to server. Also applied when converting date from <code>data-value</code> attribute.<br>
Full list of tokens: http://docs.jquery.com/UI/Datepicker/formatDate

@ -14,9 +14,9 @@ Automatically shown in inline mode.
$.extend(DateUIField.prototype, {
render: function () {
$.fn.editabletypes.dateui.superclass.render.call(this);
this.$field = this.$input.find('input');
this.$field.datepicker(this.options.datepicker);
this.$tpl = $(this.options.tpl);
this.$input = this.$tpl.find('input');
this.$input.datepicker(this.options.datepicker);
/*
if(this.options.clear) {
@ -30,18 +30,15 @@ Automatically shown in inline mode.
},
value2input: function(value) {
this.$field.val($.datepicker.formatDate(this.options.viewformat, value));
this.$input.val($.datepicker.formatDate(this.options.viewformat, value));
},
input2value: function() {
return this.html2value(this.$field.val());
return this.html2value(this.$input.val());
},
activate: function() {
if(this.$field.is(':visible')) {
this.$field.focus();
$.fn.editableutils.setCursorPosition(this.$field.get(0), this.$field.val().length);
}
$.fn.editabletypes.text.prototype.activate.call(this);
},
autosubmit: function() {

@ -155,29 +155,29 @@ Range (inherit from number)
$.fn.editableutils.inherit(Range, $.fn.editabletypes.number);
$.extend(Range.prototype, {
render: function () {
this.$input = $(this.options.tpl);
var $slider = this.$input.filter('input');
this.$tpl = $(this.options.tpl);
this.$input = this.$tpl.filter('input');
if(this.options.inputclass) {
$slider.addClass(this.options.inputclass);
this.$input.addClass(this.options.inputclass);
}
if (this.options.min !== null) {
$slider.attr('min', this.options.min);
this.$input.attr('min', this.options.min);
}
if (this.options.max !== null) {
$slider.attr('max', this.options.max);
this.$input.attr('max', this.options.max);
}
if (this.options.step !== null) {
$slider.attr('step', this.options.step);
this.$input.attr('step', this.options.step);
}
$slider.on('input', function(){
this.$input.on('input', function(){
$(this).siblings('output').text($(this).val());
});
},
activate: function() {
this.$input.filter('input').focus();
this.$input.focus();
}
});
Range.defaults = $.extend({}, $.fn.editabletypes.number.defaults, {

@ -14,8 +14,9 @@ List - abstract class for inputs that have source option loaded from js array or
$.extend(List.prototype, {
render: function () {
List.superclass.render.call(this);
var deferred = $.Deferred();
this.$tpl = $(this.options.tpl);
this.$input = this.$tpl; //will be set in renderList
this.error = null;
this.sourceData = null;
this.prependData = null;

@ -35,9 +35,13 @@ $(function(){
}
for(var i=0; i<this.sourceData.length; i++) {
this.$input.append($('<option>', {value: this.sourceData[i].value}).text(this.sourceData[i].text));
this.$tpl.append($('<option>', {value: this.sourceData[i].value}).text(this.sourceData[i].text));
}
if(this.options.inputclass) {
this.$input.addClass(this.options.inputclass);
}
//enter submit
this.$input.on('keydown.editable', function (e) {
if (e.which === 13) {

@ -23,11 +23,56 @@ $(function(){
$.fn.editableutils.inherit(Text, $.fn.editabletypes.abstractinput);
$.extend(Text.prototype, {
render: function() {
Text.superclass.render.call(this);
if (this.options.clear) {
this.$clear = $('<span class="editable-clear-x"></span>');
this.$tpl = $('<div style="position: relative">')
.append(this.$input)
.append(this.$clear);
}
if(this.options.inputclass) {
this.$input.addClass(this.options.inputclass);
}
if (this.options.placeholder) {
this.$input.attr('placeholder', this.options.placeholder);
}
},
postrender: function() {
if (this.options.clear) {
var h = this.$input.parent().height() || 20;
this.$clear.css('top', (h - this.$clear.outerHeight()) / 2);
this.$input.keyup($.proxy(this.toggleClear, this));
this.$clear.click($.proxy(function(){
this.$clear.hide();
this.$input.val('').focus();
}, this));
}
},
activate: function() {
if(this.$input.is(':visible')) {
this.$input.focus();
$.fn.editableutils.setCursorPosition(this.$input.get(0), this.$input.val().length);
if(this.options.clear) {
this.toggleClear();
}
}
},
//show / hide clear button
toggleClear: function() {
if(!this.options.clear) return;
if(this.$input.val()) {
this.$clear.show();
} else {
this.$clear.hide();
}
}
});
@ -44,7 +89,12 @@ $(function(){
@type string
@default null
**/
placeholder: null
placeholder: null,
/**
Whether to show clear button / link or not
**/
clear: true
});
$.fn.editabletypes.text = Text;

@ -67,10 +67,7 @@ $(function(){
},
activate: function() {
if(this.$input.is(':visible')) {
$.fn.editableutils.setCursorPosition(this.$input.get(0), this.$input.val().length);
this.$input.focus();
}
$.fn.editabletypes.text.prototype.activate.call(this);
}
});