some improvements to lists (editable, sortable)

This commit is contained in:
rlx 2011-01-11 06:17:45 +00:00
parent 53fb84425e
commit c29a8c9fda
2 changed files with 233 additions and 43 deletions

View file

@ -22,6 +22,10 @@ div, input, textarea {
font-family: Lucida Grande, Segoe UI, DejaVu Sans, Arial;
font-size: 11px;
}
img {
-moz-user-drag: none;
-webkit-user-drag: none;
}
td {
padding: 0;
}
@ -243,6 +247,16 @@ input.OxMedium {
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
}
input.OxMedium.OxRounded {
padding: 0 6px 0 6px;
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
}
input.OxMedium.OxSquare {
padding: 0 2px 0 2px;
-moz-border-radius: 0;
-webkit-border-radius: 0;
}
input.OxSmall {
height: 10px;
padding: 0 4px 0 4px;
@ -422,12 +436,18 @@ OxInput
*/
div.OxInput {
height: 16px;
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
}
div.OxInput.OxMedium {
height: 16px;
}
div.OxInput.OxRounded {
-moz-border-radius: 8px;
-webkit-border-radius: 8px;
}
div.OxInput.OxSquare {
-moz-border-radius: 0;
-webkit-border-radius: 0;
}
div.OxInput > .OxInputLabel {
float: left;
padding: 0 6px 0 6px;
@ -763,11 +783,6 @@ Lists
//-webkit-user-select: text;
}
.OxTextList .OxCell {
float: left;
height: 12px;
padding: 2px 4px 2px 4px;
}
.OxTextList .OxBar {
//z-index: 10;
//-moz-box-shadow: 2px 2px 4px rgba(0, 0, 0, 0.75);
@ -879,6 +894,10 @@ Lists
overflow: hidden;
white-space: nowrap;
}
.OxTextList .OxBody .OxItem .OxCell.OxEdit {
height: 16px;
padding: 0;
}
.OxTextList .OxBody .OxItem .OxCell > img {
width: 16px;
height: 16px;

View file

@ -225,7 +225,7 @@ requires
that.api.api(function(result) {
$.each(result.data.actions, function(i, action) {
that.api[action] = function(data, callback) {
if (arguments.length == 1) {
if (arguments.length == 1 && Ox.isFunction(data)) {
callback = data;
data = {};
}
@ -702,7 +702,7 @@ requires
function callback(data) {
delete requests[options.id];
Ox.length(requests) == 0 && $body.trigger('requestStop');
options.callback(data); // fixme: doesn't work if callback hasn't been passed
options.callback && options.callback(data);
}
function debug(request) {
@ -2554,6 +2554,7 @@ requires
overlap: 'none',
placeholder: '',
serialize: null,
style: 'rounded',
textAlign: 'left',
type: 'text',
validate: null,
@ -2561,7 +2562,7 @@ requires
width: 128
})
.options(options)
.addClass('OxInput OxMedium')
.addClass('OxInput OxMedium Ox' + Ox.toTitleCase(self.options.style))
.bindEvent($.extend(self.options.type == 'textarea' ? {} : {
key_enter: submit
}, {
@ -2658,7 +2659,7 @@ requires
}
self.$input = $('<input>')
.addClass('OxInput OxMedium')
.addClass('OxInput OxMedium Ox' + Ox.toTitleCase(self.options.style))
.attr({
disabled: self.options.disabled ? 'disabled' : '',
type: self.options.type == 'password' ? 'password' : 'text'
@ -2676,7 +2677,9 @@ requires
if (self.hasPasswordPlaceholder) {
self.$input.hide();
self.$placeholder = $('<input>')
.addClass('OxInput OxMedium OxPlaceholder')
.addClass('OxInput OxMedium Ox' +
Ox.toTitleCase(self.options.style) +
' OxPlaceholder')
.attr({
type: 'text'
})
@ -2942,6 +2945,7 @@ requires
$document.unbind('keydown', keypress);
$document.unbind('keypress', keypress);
}
//that.triggerEvent('blur', {});
}
function cancel() {
@ -3029,10 +3033,11 @@ requires
}
function getInputWidth() {
return self.options.width - 14 -
return self.options.width -
(self.options.arrows ? 32 : 0) -
(self.options.clear ? 16 : 0) -
(self.options.label ? self.options.labelWidth : 0);
(self.options.label ? self.options.labelWidth : 0) -
(self.options.style == 'rounded' ? 14 : 6);
}
function keypress(event) {
@ -3150,6 +3155,7 @@ requires
that.focus = function() {
self.$input.focus();
cursor(0, self.$input.val().length);
return that;
};
that.value = function() {
@ -5781,6 +5787,7 @@ requires
that = new Ox.Element({}, self)
.defaults({
centerSelection: false,
draggable: true,
id: '',
item: function() {},
keys: [],
@ -5802,6 +5809,7 @@ requires
that.$element = new Ox.List({
centered: self.options.centered,
construct: constructItem,
draggable: self.options.draggable,
id: self.options.id,
itemHeight: self.itemHeight,
itemWidth: self.itemWidth,
@ -5834,9 +5842,9 @@ requires
{height: 8, width: 5},
ratio = data.width / data.height;
return new Ox.IconItem($.extend(data, {
height: self.options.size / (ratio <= 1 ? 1 : ratio),
height: Math.round(self.options.size / (ratio <= 1 ? 1 : ratio)),
size: self.options.size,
width: self.options.size * (ratio >= 1 ? 1 : ratio)
width: Math.round(self.options.size * (ratio >= 1 ? 1 : ratio))
}));
}
@ -5890,7 +5898,7 @@ requires
Ox.IconItem = function(options, self) {
Ox.print('IconItem', options, self)
//Ox.print('IconItem', options, self)
var self = self || {},
that = new Ox.Element({}, self)
@ -6051,6 +6059,7 @@ requires
.defaults({
centered: false,
construct: function() {},
draggable: false,
format: [],
itemHeight: 16,
itemWidth: 16,
@ -6062,20 +6071,22 @@ requires
request: function() {}, // (data, callback), without data returns {items, size etc.}
selected: [],
sort: [],
sortable: false,
type: 'text',
unique: ''
})
.options(options || {})
.scroll(scroll);
that.$content.mousedown(mousedown);
that.$content.mousedown(mousedown).mouseup(mouseup);
$.extend(self, {
$items: [],
$pages: [],
clickTimeout: 0,
dragTimeout: 0,
format: {},
ids: {},
ids: [],
itemMargin: self.options.type == 'text' ? 0 : 8, // 2 x 4 px margin ... fixme: the 2x should be computed later
keyboardEvents: {
key_end: scrollToFirst,
@ -6104,11 +6115,19 @@ requires
key_control_shift_a: selectNone
});
}
self.keyboardEvents['key_' + (self.options.orientation == 'vertical' ? 'up' : 'left')] = selectPrevious;
self.keyboardEvents['key_' + (self.options.orientation == 'vertical' ? 'down' : 'right')] = selectNext;
self.keyboardEvents[
'key_' + (self.options.orientation == 'vertical' ? 'up' : 'left')
] = selectPrevious;
self.keyboardEvents[
'key_' + (self.options.orientation == 'vertical' ? 'down' : 'right')
] = selectNext;
if (self.options.max == -1) {
self.keyboardEvents['key_' + (self.options.orientation == 'vertical' ? 'shift_up' : 'shift_left')] = addPreviousToSelection;
self.keyboardEvents['key_' + (self.options.orientation == 'vertical' ? 'shift_down' : 'shift_right')] = addNextToSelection;
self.keyboardEvents[
'key_' + (self.options.orientation == 'vertical' ? 'shift_up' : 'shift_left')
] = addPreviousToSelection;
self.keyboardEvents[
'key_' + (self.options.orientation == 'vertical' ? 'shift_down' : 'shift_right')
] = addNextToSelection;
}
if (self.options.orientation == 'both') {
$.extend(self.keyboardEvents, {
@ -6125,6 +6144,13 @@ requires
0, 60, 60, 60, 60, 60, 60, 63, 64, 63, 60, 66, 60, 65, 70, 60, 64, 68, 72, 76, 60
];
}
if (self.options.draggable) {
that.bind({
dragstart: function(e) {
Ox.print('DRAGSTART', e);
}
});
}
updateQuery(self.options.selected);
that.bindEvent(self.keyboardEvents);
@ -6249,6 +6275,90 @@ requires
}
}
function dragItem(pos, e) {
var $item = self.$items[pos],
id = self.ids[pos],
startPos = pos,
startY = e.clientY,
stopPos = startPos,
offsets = $.map(self.$items, function($item, pos) {
return (pos - startPos) * 16 - e.offsetY + 8;
});
Ox.print('dragItem', e);
Ox.print(e.offsetY, offsets)
$item.addClass('OxDrag') // fixme: why does the class not work?
.css({
cursor: 'move',
opacity: 0.5
});
$window.mousemove(function(e) {
var clientY = e.clientY - that.offset()['top'],
offset = clientY % 16,
position = Ox.limit(parseInt(clientY / 16), 0, self.$items.length - 1);
if (position < pos) {
stopPos = position + (offset > 8 ? 1 : 0);
} else if (position > pos) {
stopPos = position - (offset <= 8 ? 1 : 0);
}
if (stopPos != pos) {
moveItem(pos, stopPos);
pos = stopPos;
}
});
$window.one('mouseup', function() {
dropItem(id, pos);
$window.unbind('mousemove');
});
}
function moveItem(startPos, stopPos) {
var $item = self.$items[startPos],
insert = startPos < stopPos ? 'insertAfter' : 'insertBefore';
$item.detach()[insert](self.$items[stopPos].$element); // fixme: why do we need .$element here?
Ox.print('moveItem', startPos, stopPos, insert, self.ids);
var $item = self.$items.splice(startPos, 1)[0];
id = self.ids.splice(startPos, 1)[0];
self.$items.splice(stopPos, 0, $item);
self.ids.splice(stopPos, 0, id);
self.$items.forEach(function($item, pos) {
$item.data({position: pos});
});
self.selected = [stopPos];
Ox.print('ids', self.ids);
}
function dropItem(id, pos) {
var $item = self.$items[pos];
$item.removeClass('OxDrag')
.css({
cursor: 'pointer',
opacity: 1
});
that.triggerEvent('sort', {
ids: self.ids
});
/*
Ox.print('dropColumn', id, pos)
var startPos = getColumnPositionById(id),
stopPos = pos,
$title = that.$titles.splice(startPos, 1)[0],
column = self.visibleColumns.splice(startPos, 1)[0],
width = self.columnWidths.splice(startPos, 1)[0];
self.visibleColumns.splice(stopPos, 0, column);
self.columnWidths.splice(stopPos, 0, width);
that.$head.$content.empty();
constructHead();
Ox.print('s.vC', self.visibleColumns)
$('.OxColumn' + Ox.toTitleCase(id)).css({
opacity: 1
});
that.$titles[stopPos].removeClass('OxDrag').css({
cursor: 'pointer'
});
that.$body.clearCache();
*/
}
function emptyFirstPage() {
Ox.print('emptyFirstPage', self.$pages);
self.$pages[0] && self.$pages[0].find('.OxEmpty').remove();
@ -6485,11 +6595,12 @@ requires
self.$items[pos] = new Ox.ListItem({
construct: self.options.construct,
data: v,
draggable: self.options.draggable,
format: self.options.format,
id: v[self.options.unique],
position: pos
});
self.ids[pos] = v[self.options.unique];
self.ids[pos] = v[self.options.unique]; // fixme: why not use self.$items[pos].options('id')?
if (isSelected(pos)) {
Ox.print('pos', pos, 'isSelected')
self.$items[pos].addClass('OxSelected');
@ -6523,7 +6634,7 @@ requires
}
function mousedown(e) {
Ox.print('click')
Ox.print('mousedown')
var $item = findItem(e),
pos,
deselectTimeout = false;
@ -6554,6 +6665,14 @@ requires
select(pos);
}
}, 250);
if (self.options.sortable) {
self.dragTimeout = setTimeout(function() {
if (self.dragTimeout) {
dragItem(pos, e);
self.dragTimeout = 0;
}
}, 250);
}
} else {
// dblclick
clearTimeout(self.clickTimeout);
@ -6565,6 +6684,14 @@ requires
}
}
function mouseup(e) {
Ox.print('mouseup')
if (self.dragTimeout) {
clearTimeout(self.dragTimeout);
self.dragTimeout = 0;
}
}
function open() {
that.triggerEvent('open', {
ids: getSelectedIds()
@ -6895,6 +7022,8 @@ requires
self.preview = false;
};
that.findItem = findItem; // fixme: not pretty, exporting for TextList, to make edit work
that.reload = function() {
Ox.print('---------------- list reload, page', self.page)
var page = self.page;
@ -6966,6 +7095,7 @@ requires
.defaults({
construct: function() {},
data: {},
draggable: false,
format: [],
id: '',
position: 0
@ -6990,6 +7120,7 @@ requires
that.$element = self.options.construct(self.data)
.addClass('OxItem')
.attr({
draggable: self.options.draggable,
id: self.options.id
})
.data('position', self.options.position);
@ -7112,6 +7243,7 @@ requires
request: self.options.request,
selected: self.options.selected,
sort: self.options.sort,
sortable: self.options.sortable,
type: 'text',
unique: self.unique
}, $.extend({}, self)) // pass event handler
@ -7127,6 +7259,9 @@ requires
that.$head && that.$head.scrollLeft(scrollLeft);
}
})
.bind({
mousedown: mousedown
})
.bindEvent({
select: function(event, data) {
self.options.selected = data.ids;
@ -7186,6 +7321,54 @@ requires
}
}
function mousedown(e) {
var $cell = $(e.target),
$input,
$item = that.$body.findItem(e),
columnId,
columnIndex,
html, width;
if ($item && $item.hasClass('OxSelected')) {
columnId = $cell.attr('class')
.split('OxColumn')[1].split(' ')[0].toLowerCase();
columnIndex = getColumnIndexById(columnId);
if (self.options.columns[columnIndex].editable) {
html = $cell.html();
width = self.options.columns[columnIndex].width;
$cell.empty()
.addClass('OxEdit')
.css({
width: width + 'px'
});
$input = Ox.Input({
style: 'square',
value: html,
width: width
})
.bindEvent({
blur: submit,
submit: submit
})
.appendTo($cell)
.focus();
}
}
function submit() {
var value = $input.value();
$cell.empty()
.removeClass('OxEdit')
.css({
width: (width - 8) + 'px'
})
.html(value)
that.triggerEvent('edit', {
id: $item.attr('id'),
key: columnId,
value: value
});
}
}
function clickColumn(id) {
Ox.print('clickColumn', id);
var i = getColumnIndexById(id),
@ -7355,25 +7538,12 @@ requires
}
function getColumnIndexById(id) {
var pos = -1;
$.each(self.options.columns, function(i, v) {
if (v.id == id) {
pos = i;
return false;
}
});
return pos;
// fixme: use ox.js function
return Ox.getPositionById(self.options.columns, id);
}
function getColumnPositionById(id) {
var pos = -1;
$.each(self.visibleColumns, function(i, v) {
if (v.id == id) {
pos = i;
return false;
}
});
return pos;
return Ox.getPositionById(self.visibleColumns, id);
}
function getItemWidth() {
@ -7400,8 +7570,8 @@ requires
var $v = $(v);
$v.children(startClassName).detach()[insert]($v.children(stopClassName));
});
column = self.visibleColumns.splice(startPos, 1)[0],
width = self.columnWidths.splice(startPos, 1)[0];
var column = self.visibleColumns.splice(startPos, 1)[0],
width = self.columnWidths.splice(startPos, 1)[0];
self.visibleColumns.splice(stopPos, 0, column);
self.columnWidths.splice(stopPos, 0, width);
}
@ -8965,6 +9135,7 @@ requires
title: [],
})
.options($.extend(options, {
foo: Ox.print(options, self.defaults.keyboard),
keyboard: parseKeyboard(options.keyboard || self.defaults.keyboard),
title: Ox.makeArray(options.title || self.defaults.title)
}))