var create = function(el) {
return document.createElement(el);
}
function buildMainMenu(menuData, target) {
var ul = create('ul');
for (idx in menuData) {
var mnu = menuData[idx];
var li = create('li');
li.innerHTML = mnu.text;
mnu.parent = null;
if (mnu.children && mnu.children instanceof Array) {
(function() {
var children = mnu.children;
$(li).data('parent', null);
$(li).bind('click', function(e) {
var par = this;
buildSubMenu(children, par, target);
});
})();
}
else {
(function() {
var action = mnu.action;
$(li).click(function(e) {
action();
});
})();
}
ul.appendChild(li);
}
target.appendChild(ul);
}
function buildSubMenu(menuData, target, container) {
var ul = create('ul');
for (idx in menuData) {
var mnu = menuData[idx];
var li = create('li');
li.innerHTML = mnu.text;
mnu.parent = $(target).data('parent');
if (mnu.children) {
(function() {
var children = mnu.children;
$(li).data('parent', mnu);
$(li).bind('click', function(e) {
var par = this;
buildSubMenu(children, par, target);
});
})();
}
else {
(function() {
var action = mnu.action;
$(li).click(function(e) {
action();
cleanUpMenu();
$('.invisible').remove();
});
})();
}
ul.appendChild(li);
}
var depth = findLevel(target);
var div, d;
d = document.getElementById('mnulvl' + depth);
div = d == null ? (function() {
var k = create('div');
k.id = 'mnulvl' + depth;
return k;
})() : (function() {
if ($(d).children().size()) {
removeLinked(d);
}
$(d).children().remove();
return d;
})();
div.appendChild(ul);
div.className = "menucard";
if (depth == 0) {
var spc = (function() {
var d = document.getElementById(container.id + '_invisible');
if (d) return d;
else {
var k = create('div');
k.id = container.id + '_invisible';
k.className = 'invisible';
$(k).click(function(e) {
cleanUpMenu();
$(this).remove();
});
if ($.support.opacity) k.style.opacity = '0.4';
else k.style.filter = 'alpha(opacity=40)';
return k;
}
})();
document.body.appendChild(spc);
var b = getBounds(target, depth);
div.style.top = (b.top + b.height + 5) + 'px';
div.style.left = b.left + 'px';
}
else {
var b = getBounds(target, depth);
div.style.top = b.top + 'px';
div.style.left = (b.left + b.width + 5) + 'px';
$(target).closest('div').data('linked', div);
}
document.body.appendChild(div);
}
function findLevel(el) {
var mnu = $(el).data('parent');
var i = 0;
while (mnu != null) {
i++;
mnu = mnu.parent;
}
return i;
}
function getBounds(el, depth) {
var b = {};
b['left'] = 0;
b['top'] = 0;
b['width'] = el.offsetWidth;
b['height'] = el.offsetHeight;
do {
b['left'] += el.offsetLeft;
b['top'] += el.offsetTop;
el = el.parentNode;
} while (el != document.body);
return b;
}
function cleanUpMenu() {
$('div.menucard').each(function() {
$(this).remove();
});
}
function removeLinked(div) {
$($(div).data('linked')).each(function() {
removeLinked($(this));
}).remove();
}
var menu = [
{
text: 'File',
children: [
{
text: 'Say Hello',
action: function() {
alert("hello");
}}
]},
{
text: 'Edit',
children: [
{
text: 'Change',
children: [
{
text: 'Change Link 1',
action: function() {
document.getElementById('link1').innerHTML = 'Yahoo';
alert('Changed Link 1');
}},
{
text: 'Change Link 2',
action: function() {
document.getElementById('link2').innerHTML = 'google';
alert('Changed Link 2');
}}
]}
]},
{
text: 'Help',
children: [
{
text: 'About',
action: function() {
alert('menu sample v1.0');
}}
]}
];
$(function() {
var target = document.getElementById('menu');
buildMainMenu(menu, target);
});
<div id="menu"></div>
<div id="container">
<h1>Menu Demo Sample</h1>
<ul>
<li><a id="link1" href="www.yahoo.com">Sample Link1</a></li>
<li><a id="link2" href="www.google.com">Sample Link2</a></li>
</ul>
</div>
*{font-family: Arial, Verdana;}
#menu {position:fixed; top:0; left:0; right:0; height:16px;
background-color:#339999; color:#ffffff;
padding:3px; font-size:10pt; }
#menu ul { padding:0px; margin: 0px; }
#menu ul li { display: inline; margin-left:3px; margin-right:3px;
padding-left:3px; padding-right:3px;
border:1px solid transparent;}
#menu ul li:hover { background-color:#40BFBF; border:1px solid white; cursor:pointer;}
.menucard { background-color:#339999; position:fixed; width:125px; color:white; font-size:8pt; z-index:110;}
.menucard ul {list-style-type:none; margin:0px; padding:0px; }
.menucard ul li {padding:3px; border:1px solid transparent; }
.menucard ul li:hover {border:1px solid white; background-color:#40BFBF; cursor:pointer;}
.invisible {position:fixed; top:18px;
background-color:#E7CCFF; left:0px; right:0px;
bottom:0px; z-index:100;}
#container { margin-top: 25px; margin-left:25px; }