Requirements:
1. two layers (one layer with the workarounds and the other with the menu code)
2. three empty movieclips with the linkage names: subButtonSymbol, mainButtonSymbol and popUpMenuSymbol
3. one xml-file named xmlMenuTree
that’s it. Click on read more to see the code.
btw: by now it’s just a beta version. If you recognize any mistakes or things that could be improved I would be thankful if you’d write me a mail.
download fla
download xml
show example
Workarounds:
// :: GET_NEXT_DEPTH :: //
MovieClip.prototype.getNextDepth = function(){
var t = -Infinity;
for(var i in this){
if(this[i].getDepth() != null && this[i]._parent == this){
t = Math.max(t, this[i].getDepth());
}
}
return (t > -1) ? ++t: 0;
}
// :: GET_TEXT_EXTENT :: //
_global.TextFormat2 = TextFormat;
TextFormat = function(){
super();
delete this.getTextExtent;
}
TextFormat.prototype = new TextFormat2();
TextFormat.prototype.getTextExtent2 = TextFormat.prototype.getTextExtent;
TextFormat.prototype.getTextExtent = function ( the_str ) {
// create temporary textfield
_root.createTextField(”getTextExtentTemp_txt“, 1000000, 1, 1, 10, 10);
// local reference to text field
var temp_txt = _root [ “getTextExtentTemp_txt” ];
// set the text format
temp_txt.setNewTextFormat( this );
// populate textfield with string
temp_txt.text = the_str;
// get dimensions
var w = temp_txt.textWidth;
var h = temp_txt.textHeight;
// wrap in object
var textExtent = { width: w, height: h };
// remove the textfield
temp_txt.removeTextField();
// return dimensions object
return textExtent;
}
ASSetPropFlags(_global,”TextFormat,TextFormat2“,131);
// :: CREATE_TEXT_FIELD :: //
MovieClip.prototype.createTextField2 = MovieClip.prototype.createTextField;
MovieClip.prototype.createTextField = function(name, depth, x, y, w, h){
this.createTextField2(name, depth, x, y, w, h);
return this[name];
}
Code:
MovieClip.prototype.useHandCursor = false;
// :: POP_UP_MENU_CLASS :: //
PopUpMenuClass = function(){
this._x = 0;
this._y = 0;
this.width = Stage.width;
this.height = 20;
this.xmlFile = “xmlMenuTree.xml“;
this.init();
}
PopUpMenuClass.prototype = new MovieClip();
PopUpMenuClass.prototype.init = function(){
this.loadXMLFile();
this.drawBackground();
}
PopUpMenuClass.prototype.loadXMLFile = function(){
var xml = new XML();
xml.master = this;
xml.ignoreWhite = true;
xml.onLoad = function(success){
if(success){
this.master.menuTree_arr = this.master.handleXMLData(this.firstChild.childNodes);
this.master.createMainMenu();
}
}
xml.load(this.xmlFile);
}
PopUpMenuClass.prototype.handleXMLData = function(child){
var menuTree_arr = new Array();
for(var i=0; i < child.length; i++){
var temp_obj = new Object();
temp_obj.title = child[i].attributes.title;
temp_obj.func = child[i].attributes.func;
temp_obj.link = child[i].attributes.link;
temp_obj.symbol = child[i].attributes.symbol;
if(child[i].childNodes.length > 0){
temp_obj.subMenu = this.handleXMLData(child[i].childNodes);
}
menuTree_arr.push(temp_obj);
}
return menuTree_arr;
}
PopUpMenuClass.prototype.drawBackground = function(){
this.createEmptyMovieClip(”background_mc“, this.getNextDepth());
with(this.background_mc){
beginFill(0xD4D0C8, 100);
lineStyle(1, 0×404040, 100);
moveTo(0, this.height);
lineTo(this.width, this.height);
lineStyle(0, 0×404040, 0);
lineTo(this.width, 0);
lineTo(0, 0);
lineTo(0, this.height);
endFill();
}
}
PopUpMenuClass.prototype.createMainMenu = function(){
for(var i=0; i<this.menuTree_arr.length; i++){
this.attachMovie(”mainButtonSymbol“, “mainButton“+i, this.getNextDepth());
this[”mainButton“+i].master = this;
with(this[”mainButton“+i]){
_x = this[”mainButton“+(i-1)]._x+this[”mainButton“+(i-1)]._width+2;
_y = 2;
}
this[”mainButton“+i].init(this.menuTree_arr[i]);
}
}
PopUpMenuClass.prototype.createSubMenu = function(x, y, subMenu_arr, target){
target.createEmptyMovieClip(”subMenu“, target.getNextDepth());
with(target.subMenu){
_x = x;
_y = y;
}
var tF = new TextFormat();
tF.bold = true;
tF.font = “Tahoma“;
tF.size = 12;
for(var i=0; i < subMenu_arr.length; i++){
var size;
var textWidth = tF.getTextExtent(subMenu_arr[i].title).width;
if(textWidth>size){
size = textWidth;
}
}
for(var i=0; i < subMenu_arr.length; i++){
target.subMenu.attachMovie(”subButtonSymbol“, “subButton“+i, target.subMenu.getNextDepth());
target.subMenu[”subButton“+i].master = [this, target.subMenu];
target.subMenu[”subButton“+i].width = size;
with(target.subMenu[”subButton“+i]){
_x = 1;
_y = target.subMenu[”subButton“+(i-1)]._y+target.subMenu[”subButton“+(i-1)]._height;
}
target.subMenu[”subButton“+i].init(subMenu_arr[i]);
}
var height = target.subMenu._height-1;
var width = target.subMenu._width+2;
with(target.subMenu){
clear();
beginFill(0xD4D0C8, 100);
lineStyle(1, 0xFFFFFF, 100);
moveTo(width, -1);
lineTo(0, -1);
lineTo(0, height);
lineStyle(1, 0×404040, 100);
lineTo(width, height);
lineTo(width, -1);
endFill();
}
}
PopUpMenuClass.prototype.removeSubMenu = function(target){
target.subMenu.removeMovieClip();
for(var i in target){
if(typeof target[i] == “movieclip“){
target[i].setToDefault();
}
}
}
PopUpMenuClass.prototype.onMouseDown = function(){
if(this.hitTest(_root._xmouse, _root._ymouse, true) == false){
this.removeSubMenu(this);
}
}
// :: BUTTON_CLASS :: //
ButtonClass = function(){};
ButtonClass.prototype = new MovieClip();
ButtonClass.prototype.init = function(dataObj){
this.title = dataObj.title;
this.func = dataObj.func;
this.link = dataObj.link;
this.symbol = dataObj.symbol;
this.subMenu = dataObj.subMenu;
this.defineTextFormat();
this.defineColors();
this.defineSize();
this.setSymbol();
this.draw();
this.createTitle();
}
ButtonClass.prototype.setSymbol = function(){
this.attachMovie(this.symbol, “symbol_mc“, this.getNextDepth());
this.symbol_mc._x = 2;
this.symbol_mc._y = this.height/2;
this.width += this.symbol_mc._width+this.symbol_mc._x;
}
// :: MAIN_BUTTON_CLASS :: //
MainButtonClass = function(){};
MainButtonClass.prototype = new ButtonClass();
MainButtonClass.prototype.init = function(dataObj){
this.type = “main“;
super.init(dataObj);
}
MainButtonClass.prototype.defineTextFormat = function(){
this.tF = new TextFormat();
this.tF.bold = true;
this.tF.font = “Tahoma“;
this.tF.size = 12;
}
MainButtonClass.prototype.defineColors = function(){
this.background_color = 0xD4D0C8;
this.line1_color = 0xFFFFFF;
this.line2_color = 0×404040;
}
MainButtonClass.prototype.defineSize = function(){
this.textSize = this.tF.getTextExtent(this.title);
this.width = this.textSize.width+4;
this.height = 16;
}
MainButtonClass.prototype.draw = function(status){
with(this){
clear();
beginFill(this.background_color, 100);
if(status == “pressed“) lineStyle(1, this.line2_color, 100);
else if(status == “active“) lineStyle(1, this.line1_color, 100);
moveTo(this.width, 0);
lineTo(0, 0);
lineTo(0, this.height);
if(status == “pressed“) lineStyle(1, this.line1_color, 100);
else if(status == “active“) lineStyle(1, this.line2_color, 100);
lineTo(this.width, this.height);
lineTo(this.width, 0);
endFill();
}
}
MainButtonClass.prototype.createTitle = function(){
this.createTextField(”title_txt“, this.getNextDepth(), 0, 0, 0, 0);
this.title_txt._x = this.symbol_mc._x+this.symbol_mc._width;
this.title_txt._y = (this.height-this.textSize.height)/2-2;
this.title_txt.autoSize = “left“;
this.title_txt.selectable = false;
this.title_txt.htmlText = this.title;
this.title_txt.setTextFormat(this.tF);
}
MainButtonClass.prototype.openSubMenu = function(){
this.master.createSubMenu(this._x, this._y+this.height+3, this.subMenu, this.master);
}
MainButtonClass.prototype.closeSubMenu = function(){
this.master.removeSubMenu(this.master);
}
MainButtonClass.prototype.setToDefault = function(){
this.draw();
this.pressed = false;
}
MainButtonClass.prototype.onRollOver = function(){
if(!this.pressed){
if(this.master.subMenu != undefined
&& this.subMenu != undefined){
this.closeSubMenu();
this.openSubMenu();
this.draw(”pressed“);
this.pressed = !this.pressed;
} else {
this.draw(”active“);
}
}
}
MainButtonClass.prototype.onRollOut = function(){
if(!this.pressed){
this.draw();
}
}
MainButtonClass.prototype.onPress = function(){
if(!this.pressed){
this.closeSubMenu();
if(this.subMenu != undefined){
this.openSubMenu();
}
this.draw(”pressed“);
this.pressed = !this.pressed;
} else {
this.closeSubMenu();
this.draw();
}
}
// :: SUB_BUTTON_CLASS :: //
SubButtonClass = function(){};
SubButtonClass.prototype = new ButtonClass();
SubButtonClass.prototype.init = function(dataObj){
this.type = “sub“;
super.init(dataObj);
}
SubButtonClass.prototype.defineTextFormat = function(){
this.tFStatic = new TextFormat();
this.tFStatic.bold = true;
this.tFStatic.font = “Tahoma“;
this.tFStatic.color = 0×000000;
this.tFStatic.size = 12;
this.tFActive = new TextFormat();
this.tFActive.color = 0xFFFFFF;
}
SubButtonClass.prototype.defineColors = function(){
this.backgroundStatic_color = 0xD4D0C8;
this.backgroundActive_color = 0×0A246A;
}
SubButtonClass.prototype.defineSize = function(){
this.textSize = this.tFStatic.getTextExtent(this.title);
this.width = this.width+20;
this.height = 16;
}
SubButtonClass.prototype.draw = function(status){
with(this){
clear();
status == “active” ? beginFill(this.backgroundActive_color, 100) : beginFill(this.backgroundStatic_color, 100);
moveTo(this.width+w, 0);
lineTo(0, 0);
lineTo(0, this.height);
lineTo(this.width+w, this.height);
lineTo(this.width+w, 0);
endFill();
}
if(this.subMenu != undefined){
with(this){
status == “active” ? beginFill(0xFFFFFF, 100) : beginFill(0×000000, 100);
moveTo(this.width-4, this.height/2);
lineTo(this.width-10, this.height/2-5);
lineTo(this.width-10, this.height/2+5);
lineTo(this.width-4, this.height/2);
}
}
}
SubButtonClass.prototype.createTitle = function(){
this.createTextField(”title_txt“, this.getNextDepth(), 0, 0, 0, 0);
this.title_txt._x = this.symbol_mc._width+this.symbol_mc._x+2;
this.title_txt._y = (this.height-this.textSize.height)/2-2;
this.title_txt.autoSize = “left“;
this.title_txt.selectable = false;
this.title_txt.htmlText = this.title;
this.title_txt.setTextFormat(this.tFStatic);
}
SubButtonClass.prototype.openSubMenu = function(){
this.master[0].createSubMenu(this._x+this.width, this._y, this.subMenu, this.master[1]);
}
SubButtonClass.prototype.closeSubMenu = function(){
this.master[0].removeSubMenu(this.master[1]);
}
SubButtonClass.prototype.setToDefault = function(){
this.draw();
this.pressed = false;
this.title_txt.setTextFormat(this.tFStatic);
}
SubButtonClass.prototype.onRollOver = function(){
this.closeSubMenu();
if(this.subMenu != undefined){
this.openSubMenu();
}
this.draw(”active“);
this.title_txt.setTextFormat(this.tFActive);
}
// example
Object.registerClass(”popUpMenuSymbol“, popUpMenuClass);
Object.registerClass(”mainButtonSymbol“, mainButtonClass);
Object.registerClass(”subButtonSymbol“, subButtonClass);
this.attachMovie(”popUpMenuSymbol“, “popUpMenuCon_mc“, this.getNextDepth());

5 Responses to “Windows Style Menu”
hy simon !
i have tried your xml-menue, it´s fantastic !!!
but please, can you tell me how i can set a link in the xml-file.
such as: http:www.domain.net
i have tried averything, but it don´t works.
thx for being helpful !!!
gtx, mario
Hi Mario!
Sorry for the delay but just recognized your comment. Add the following to the Button-Class:
ButtonClass.prototype.onRelease = function(){
if(this.func == “getURL”){
var linkArray = this.link.split(”,”);
this.getURL(linkArray[0], linkArray[1]);
}
}
And then copy the following into the xml-file:
Should work now.
Simon
Damn. He absorbed the few lines aftern And then copy… .
So here’s another try. The value of the func var must be getURL and the value of the link var must look like the following: http://www.flashforum.de, _blank.
I love your menu.. but i get this error in flash MX…
”
**Warning** Scene=Szene 1, layer=Script:, frame=1:Line 18: Case-insensitive identifier ‘xml’ will obscure built-in object ‘XML’.
var xml = new XML();
Total ActionScript Errors: 1 Reported Errors: 1
”
what’s wrong?
Jorge
Hi Jorge.
There’s nothing wrong. It’s just a warning. It occurs because I used a case-insensitive identifier. That means that the term ‘xml’ shouldn’t be used as identifier because it overlaps with the XML-Class (same name only one time big and the other small letters).
To get rid of that error just rename xml with something like myXML or so.