some keyboard navigation, some submenu

This commit is contained in:
Rolux 2010-02-05 10:50:13 +05:30
parent bff58df78f
commit 8277cab528
5 changed files with 197 additions and 74 deletions

View file

@ -55,6 +55,10 @@ Forms
background: -moz-linear-gradient(top, rgb(224, 224, 224), rgb(192, 192, 192)); background: -moz-linear-gradient(top, rgb(224, 224, 224), rgb(192, 192, 192));
background: -webkit-gradient(linear, left top, left bottom, from(rgb(224, 224, 224)), to(rgb(192, 192, 192))); background: -webkit-gradient(linear, left top, left bottom, from(rgb(224, 224, 224)), to(rgb(192, 192, 192)));
} }
.OxThemeClassic .OxButton:focus {
-moz-box-shadow: 0 0 2px rgb(128, 128, 128);
-webkit-box-shadow: 0 2 4px rgb(128, 128, 128);
}
.OxThemeClassic .OxButton:active, .OxThemeClassic .OxButton:active,
.OxThemeClassic .OxRange.OxActive { .OxThemeClassic .OxRange.OxActive {
//background: rgb(160, 160, 160); //background: rgb(160, 160, 160);
@ -112,7 +116,7 @@ Menus
.OxThemeClassic .OxMenu .OxScrollbar.OxSelected { .OxThemeClassic .OxMenu .OxScrollbar.OxSelected {
background: rgba(192, 192, 192, 0.96); background: rgba(192, 192, 192, 0.96);
} }
.OxThemeModern .OxMenu .OxItem.OxDisabled .OxCell { .OxThemeClassic .OxMenu .OxItem.OxDisabled .OxCell {
color: rgb(160, 160, 160); color: rgb(160, 160, 160);
} }

View file

@ -442,22 +442,22 @@ Menus
.OxMenu .OxLine { .OxMenu .OxLine {
height: 1px; height: 1px;
} }
.OxMenu .OxScrollBar { .OxMenu .OxScrollbar {
text-align: center; text-align: center;
cursor: pointer; cursor: pointer;
display: none; display: none;
} }
.OxMenu.OxLarge .OxScrollBar { .OxMenu.OxLarge .OxScrollbar {
height: 16px; height: 16px;
padding-top: 4px; padding-top: 4px;
font-size: 10px; font-size: 10px;
} }
.OxMenu.OxMedium .OxScrollBar { .OxMenu.OxMedium .OxScrollbar {
height: 13px; height: 13px;
padding-top: 3px; padding-top: 3px;
font-size: 8px; font-size: 8px;
} }
.OxMenu.OxSmall .OxScrollBar { .OxMenu.OxSmall .OxScrollbar {
height: 10px; height: 10px;
padding-top: 2px; padding-top: 2px;
font-size: 6px; font-size: 6px;

View file

@ -53,52 +53,52 @@ requires
apple: "\uF8FF", apple: "\uF8FF",
arrow_down: "\u2193", arrow_down: "\u2193",
arrow_left: "\u2190", arrow_left: "\u2190",
"arrow right": "\u2192", arrow_right: "\u2192",
"arrow up": "\u2191", arrow_up: "\u2191",
"backspace": "\u232B", backspace: "\u232B",
"backup": "\u2707", backup: "\u2707",
"ballot": "\u2717", ballot: "\u2717",
"black star": "\u2605", black_star: "\u2605",
"burn": "\u2622", burn: "\u2622",
"caps lock": "\u21EA", caps_lock: "\u21EA",
"check": "\u2713", check: "\u2713",
"CLEAR": "\u2327", clear: "\u2327",
"CLICK": "\uF803", click: "\uF803",
"CLOSE": "\u2715", close: "\u2715",
"COMMAND": "\u2318", command: "\u2318",
"CONTROL": "\u2303", control: "\u2303",
"CUT": "\u2702", cut: "\u2702",
"DELETE": "\u2326", "delete": "\u2326",
"DIAMOND": "\u25C6", diamond: "\u25C6",
"EDIT": "\uF802", edit: "\uF802",
"EJECT": "\u23CF", eject: "\u23CF",
"ESCAPE": "\u238B", escape: "\u238B",
"END": "\u2198", end: "\u2198",
"ENTER": "\u2324", enter: "\u2324",
"FLY": "\u2708", fly: "\u2708",
"GEAR": "\u2699", gear: "\u2699",
"HOME": "\u2196", home: "\u2196",
"INFO": "\u24D8", info: "\u24D8",
"NAVIGATE": "\u2388", navigate: "\u2388",
"OPTION": "\u2387", option: "\u2387",
"PAGE UP": "\u21DE", page_up: "\u21DE",
"PAGE DOWN": "\u21DF", page_down: "\u21DF",
"REDO": "\u21BA", redo: "\u21BA",
"RETURN": "\u21A9", "return": "\u21A9",
"SELECT": "\u21D5", select: "\u21D5",
"SHIFT": "\u21E7", shift: "\u21E7",
"SOUND": "\u266B", sound: "\u266B",
"SPACE": "\u2423", space: "\u2423",
"TAB": "\u21E5", tab: "\u21E5",
"TRASH": "\u267A", trash: "\u267A",
"TRIANGLE DOWN": "\u25BC", triangle_down: "\u25BC",
"TRIANGLE LEFT": "\u25C0", triangle_left: "\u25C0",
triangle_right: "\u25BA", triangle_right: "\u25BA",
"TRIANGLE UP": "\u25B2", triangle_up: "\u25B2",
"UNDO": "\u21BB", undo: "\u21BB",
"VOLTAGE": "\u26A1", voltage: "\u26A1",
"WARNING": "\u26A0", warning: "\u26A0",
"WHITE STAR": "\u2606" white_star: "\u2606"
} }
}, },
$window, $document, $body; $window, $document, $body;
@ -1634,6 +1634,44 @@ requires
}; };
/*
----------------------------------------------------------------------------
Ox.Select
----------------------------------------------------------------------------
*/
Ox.Select = function(options, self) {
var self = self || {},
that = new Ox.Button({}, self)
.defaults({
id: "",
items: []
})
.options(options)
.click(click),
items;
$.each(self.options.items, function(i, item) {
items.push({
checked: false,
group: self.options.id,
title: item.title
})
})
that.$menu = new Ox.Menu({
})
function click() {
}
return that;
}
/* /*
============================================================================ ============================================================================
Menus Menus
@ -1685,18 +1723,27 @@ requires
.addClass("OxContent") .addClass("OxContent")
.appendTo(that.$container); .appendTo(that.$container);
$.each(self.options.items, function(i, item) { $.each(self.options.items, function(i, item) {
var position;
if (item.id) { if (item.id) {
if (!$.isEmptyObject(item.submenu)) {
that.submenus[item.id] = new Ox.Menu(item.submenu);
}
$.extend(item, { $.extend(item, {
menu: that, menu: that,
submenu: that.submenus[item.id] || null
}); });
that.items.push(new Ox.MenuItem($.extend(item, { that.items.push(new Ox.MenuItem($.extend(item, {
position: that.items.length position: position = that.items.length
})).appendTo(that.$content)); })).appendTo(that.$content));
that.$content.append($item); if (item.items) {
that.submenus[item.id] = new Ox.Menu({
element: that.items[position],
id: Ox.toCamelCase(self.options.id + "/" + item.id),
items: item.items,
offset: {
left: 0,
top: -4
},
side: "right",
size: self.options.size
});
}
} else { } else {
that.$content.append(constructSpace()); that.$content.append(constructSpace());
that.$content.append(constructLine()); that.$content.append(constructLine());
@ -1712,6 +1759,8 @@ requires
function clickItem() { function clickItem() {
if (self.options.selected > -1) { if (self.options.selected > -1) {
that.items[self.options.selected].trigger("click"); that.items[self.options.selected].trigger("click");
} else {
that.hideMenu();
} }
} }
@ -1727,7 +1776,7 @@ requires
function constructScrollbar(direction) { function constructScrollbar(direction) {
var interval; var interval;
return $("<div/>", { return $("<div/>", {
addClass: "OxScrollbar Ox" + Ox.toTitleCase(direction), "class": "OxScrollbar Ox" + Ox.toTitleCase(direction),
html: oxui.symbols["triangle_" + direction], html: oxui.symbols["triangle_" + direction],
click: function() { // fixme: do we need to listen to click event? click: function() { // fixme: do we need to listen to click event?
return false; return false;
@ -1777,6 +1826,26 @@ requires
return $("#" + Ox.toCamelCase(options.id + "/" + id)); return $("#" + Ox.toCamelCase(options.id + "/" + id));
} }
function isFirstEnabledItem() {
var ret = true;
$.each(that.items, function(i, item) {
if (i < self.options.selected && !item.options("disabled")) {
return ret = false;
}
});
return ret;
}
function isLastEnabledItem() {
var ret = true;
$.each(that.items, function(i, item) {
if (i > self.options.selected && !item.options("disabled")) {
return ret = false;
}
});
return ret;
}
function scrollMenu(speed) { function scrollMenu(speed) {
var containerHeight = that.$container.height(), var containerHeight = that.$container.height(),
contentHeight = that.$content.height(), contentHeight = that.$content.height(),
@ -1807,20 +1876,24 @@ requires
function selectNextItem() { function selectNextItem() {
var selected = self.options.selected; var selected = self.options.selected;
if (selected < that.items.length - 1) { if (!isLastEnabledItem()) {
if (selected > -1) { if (selected > -1) {
that.items[selected].trigger("mouseleave"); that.items[selected].trigger("mouseleave");
} }
selected++; do {
selected++;
} while (that.items[selected].options("disabled"))
that.items[selected].trigger("mouseenter"); that.items[selected].trigger("mouseenter");
} }
} }
function selectPreviousItem() { function selectPreviousItem() {
var selected = self.options.selected; var selected = self.options.selected;
if (selected > 0) { if (!isFirstEnabledItem()) {
that.items[selected].trigger("mouseleave"); that.items[selected].trigger("mouseleave");
selected--; do {
selected--;
} while (that.items[selected].options("disabled"))
that.items[selected].trigger("mouseenter"); that.items[selected].trigger("mouseenter");
} }
} }
@ -1838,8 +1911,9 @@ requires
if (self.options.selected > -1) { if (self.options.selected > -1) {
that.items[self.options.selected].trigger("mouseleave"); that.items[self.options.selected].trigger("mouseleave");
} }
Ox.Event.unbind("key down", selectNextItem) Ox.Event.unbind("key down", selectNextItem);
Ox.Event.unbind("key up", selectPreviousItem) Ox.Event.unbind("key up", selectPreviousItem);
Ox.Event.unbind("key.escape", that.hideMenu);
Ox.Event.unbind("key.enter", clickItem); Ox.Event.unbind("key.enter", clickItem);
$document.unbind("click", that.hideMenu); $document.unbind("click", that.hideMenu);
}; };
@ -1861,9 +1935,10 @@ requires
that.$container.height(maxHeight - itemHeight); that.$container.height(maxHeight - itemHeight);
that.$scrollbars.down.show(); that.$scrollbars.down.show();
} }
Ox.print("binding...") Ox.print("binding...");
Ox.Event.bind("key.down", selectNextItem); Ox.Event.bind("key.down", selectNextItem);
Ox.Event.bind("key.up", selectPreviousItem); Ox.Event.bind("key.up", selectPreviousItem);
Ox.Event.bind("key.escape", that.hideMenu);
Ox.Event.bind("key.enter", clickItem); Ox.Event.bind("key.enter", clickItem);
setTimeout(function() { setTimeout(function() {
$document.bind("click", that.hideMenu); $document.bind("click", that.hideMenu);
@ -1890,10 +1965,10 @@ requires
group: "", group: "",
icon: "", icon: "",
id: "", id: "",
items: [],
keyboard: "", keyboard: "",
menu: null, // fixme: is passing the menu to 100s of menu items really memory-neutral? menu: null, // fixme: is passing the menu to 100s of menu items really memory-neutral?
position: 0, position: 0,
submenu: null,
title: [], title: [],
}) })
.options($.extend(options, { .options($.extend(options, {
@ -1908,7 +1983,7 @@ requires
.data("group", self.options.group) // fixme: why? .data("group", self.options.group) // fixme: why?
.mouseenter(mouseenter) .mouseenter(mouseenter)
.mouseleave(mouseleave) .mouseleave(mouseleave)
.mousemove(mouseenter); // in case selection has goes elsewhere via keyboard .mousemove(mousemove); // in case selection has goes elsewhere via keyboard
// construct // construct
that.append( that.append(
@ -1943,11 +2018,11 @@ requires
) )
.append( .append(
$("<td>", { $("<td>", {
"class": "OxCell Ox" + (self.options.submenu ? "Submenu" : "Key"), "class": "OxCell Ox" + (self.options.items.length ? "Submenu" : "Key"),
html: self.options.submenu ? oxui.symbols.triangle_right : html: self.options.items.length ? oxui.symbols.triangle_right :
oxui.symbols[self.options.keyboard.key] || self.options.keyboard.key oxui.symbols[self.options.keyboard.key] || self.options.keyboard.key
}) })
) );
function click() { function click() {
if (!that.hasClass("OxDisabled") && !self.options.submenu) { if (!that.hasClass("OxDisabled") && !self.options.submenu) {
@ -1968,13 +2043,19 @@ requires
} }
} }
function isSelected() {
return self.options.position == self.options.menu.options("selected");
}
function mouseenter() { function mouseenter() {
if (!that.is(".OxDisabled") && !that.is(".OxSelected")) { if (!self.options.disabled && !isSelected()) {
$.each(self.options.menu.submenus, function(id, submenu) { $.each(self.options.menu.submenus, function(id, submenu) {
submenu.hideMenu(); submenu.hideMenu();
}); });
$(".OxMenu .OxItem[id!=" + self.options.id + "]").removeClass("selected"); if (self.options.menu.options("selected") > -1) {
self.options.submenu && self.options.submenu.showMenu(); // fixme: do we want to switch to this style? self.options.menu.items[self.options.menu.options("selected")].trigger("mouseleave");
}
self.options.items.length && self.options.menu.submenus[self.options.id].showMenu(); // fixme: do we want to switch to this style?
that.addClass("OxSelected"); that.addClass("OxSelected");
self.options.menu.options({ self.options.menu.options({
selected: self.options.position selected: self.options.position
@ -1983,7 +2064,7 @@ requires
} }
function mouseleave() { function mouseleave() {
if (!that.hasClass("OxDisabled") && !self.options.submenu) { if (!self.options.disabled && !self.options.submenu) {
that.removeClass("OxSelected"); that.removeClass("OxSelected");
self.options.menu.options({ self.options.menu.options({
selected: -1 selected: -1
@ -1991,6 +2072,15 @@ requires
} }
} }
function mousemove() {
var selected = self.options.menu.options("selected");
if (!self.options.disabled && !isSelected()) {
self.options.menu.items[self.options.menu.options("selected")]
.trigger("mouseleave");
mouseenter();
}
}
function parseKeyboard(str) { function parseKeyboard(str) {
var modifiers = str.split(' '), var modifiers = str.split(' '),
key = modifiers.pop(); key = modifiers.pop();

BIN
demos/.DS_Store vendored

Binary file not shown.

View file

@ -39,6 +39,7 @@ $(function() {
}, },
{ {
checked: false, checked: false,
disabled: true,
group: "123", group: "123",
id: "fifth", id: "fifth",
title: "Fifth" title: "Fifth"
@ -48,10 +49,38 @@ $(function() {
group: "123", group: "123",
id: "sixth", id: "sixth",
title: "Sixth" title: "Sixth"
},
{},
{
id: "more",
items: [
{
checked: true,
group: "789",
id: "seventh",
title: "Seventh"
},
{
checked: false,
group: "789",
id: "eighth",
title: "Eighth"
},
{
checked: false,
group: "789",
id: "ninth",
title: "Ninth"
},
],
title: "More",
} }
] ]
}); });
button.click(menu.toggleMenu) button.click(function() {
$(this).focus();
menu.toggleMenu();
});
Ox.Event.bind("OxClickMenu", function(event, data) { Ox.Event.bind("OxClickMenu", function(event, data) {
button.options({ button.options({
value: data.value value: data.value