function MarkupOption(image, div, vectorMode, ieCursor, otherCursor)
{
	this.image = $get(image);
	this.div = $get(div);
	this.vectorMode = vectorMode;
	this.ieCursor = ieCursor;
	this.otherCursor = otherCursor;
	this.mapTool;
};

MarkupTool = function(map, floatingPanelId, imgSave, imgEdit, imgDelete)
{
	this.map = map;
	this.floatingPanelId = floatingPanelId;
	this.imgSave = imgSave;
	this.imgEdit = imgEdit;
	this.imgDelete = imgDelete;
	
    this.snippetLength = 40;
    this.textEmptyPlaceholderString = "Type Text in Highlighted box";
    
	this.floatingPanel = $find(floatingPanelId);
	this.floatingPanel.add_close(Function.createDelegate(this, this._onClosePanel));
	
	//main container for markup formatting options
	this.markupOptions = $get("markupOptions");
	
	//container for saved markup items
	this.markupSavedItemsContainer = $get("markupSavedItemsContainer");
	
	//these are the DOM objects that contain the states of the options
	this.option_linetype = $get("markup_option_linetype");
	this.td_linecolor = $get("tdLineColor");
	this.option_linewidth = $get("markup_option_lineWidth");
	this.option_linetrans = $get("markup_option_linetrans");
	this.option_textSize = $get("markup_option_textSize");
	this.td_fillcolor = $get("tdFillColor");
	this.option_filltrans = $get("markup_option_filltrans");
	this.markupTextArea = $get("markupTextArea");
	this.markupListDiv = $get("markupListDiv");
	
	//these are the DOM objects that act as containers for options
	//this is for toggling visibility of options for various markup types
	this.markupTextOptions = $get("markupTextOptions");
	
	//stroke
	this.markup_row_lineType = $get("markup_row_lineType");
	this.markup_row_lineColor = $get("markup_row_lineColor");
	this.markup_row_lineWidth = $get("markup_row_lineWidth");
	this.markup_row_linetrans = $get("markup_row_linetrans");
	
	//help
	this.warningString = "<br /><br /><b>The markup will not be saved until you press the <img border=0 align=\"middle\" src=\"" + this.imgSave + "\" /> button.</b>";    
    this.startHelpString = "This tool allows you to add custom markup (shapes and text) to the map.<br /><br />Any markup added throug this tool will be shown when the map is exported (eg. to PDF).<br /><br />Start by choosing the kind of markup you would like to add.";
	this.lineHelpString = "Click on the map to add points to your user-defined path.<br /><br />Press the 'DELETE' key to undo your last click.<br /><br />Double-click to complete the path.<br /><br />Points in an completed shape can be moved by dragging the associated vertex to the desired location.<br /><br />Points can be removed from a completed path by mousing over the vertex and hitting the 'DELETE' key."+this.warningString;
    this.circleHelpString = "Click on the map to define the center of the circle.  Without releasing the mouse button, drag the cursor out to the desired radius then release the mouse button."+this.warningString;
    this.textHelpString = "Click on the map to select the point where your text will begin.<br /><br />Click on the highlighted text area above and enter your text.<br /><br />You may move the markup by clicking on another point on the map."+this.warningString;
    this.polyHelpString = "Click on the map to add points to your user-defined shape.<br /><br />Press the 'DELETE' key to undo your last click.<br /><br />Double-click to complete the shape.<br /><br />Points in an completed shape can be moved by dragging the associated vertex to the desired location.<br /><br />Points can be removed from a completed shape by mousing over the vertex and hitting the 'DELETE' key."+this.warningString;
		      
	//fill
	this.markup_row_FillColor = $get("markup_row_FillColor");
	this.markup_row_FillTrans = $get("markup_row_FillTrans");
	
	//save name input
	this.markup_Name_Input = $get("markup_Name_Input");
	this.createTools();
	
	// create a graphics layer to hold the markup
	this.graphicsLayer = new MapsDirect.WebControls.GraphicsLayer("markup");
	this.map.addGraphicsLayer(this.graphicsLayer);
};

var markupGlobalCounter = 0;

MarkupTool.prototype = 
{	  
    createTools: function()
    {
        //this.tools = null;
        this.tools = new Object();
	    this.tools["line"] = new MarkupOption("markupPolylineImage", "markupOptions", "line", "hand", "pointer");
	    this.tools["line"].mapTool = $create(MapsDirect.WebControls.Tools.Line, {map: this.map}, null, null, null);
	    this.tools["poly"] = new MarkupOption("markupPolygonImage", "markupOptions", "poly", "crosshair", "pointer");
	    this.tools["poly"].mapTool = $create(MapsDirect.WebControls.Tools.Polygon, {map: this.map}, null, null, null);
	    this.tools["circle"] = new MarkupOption("markupCircleImage", "markupOptions", "circle", "hand", "pointer");
	    this.tools["circle"].mapTool = $create(MapsDirect.WebControls.Tools.Circle, {map: this.map}, null, null, null);
	    this.tools["textPoint"] = new MarkupOption("markupTextImage", "markupOptions", "textPoint", "hand", "pointer");
	    this.tools["textPoint"].mapTool = $create(MapsDirect.WebControls.Tools.Point, {map: this.map, isTextTool: true}, null, null, null);
	    this.tools["textPoint"].mapTool.isTextTool = true;
	    
	    this.defaultTool = "line";
	    this.activeTool = this.tools[this.defaultTool];
	    this.segments = null;
    },
    
    unset_AllTools: function()
    {
        if (this.graphicsLayer.currentEditItem) {
            this.graphicsLayer.removeEditor(this.graphicsLayer.currentEditItem);
        }
        
        for(var key in this.tools) {
			this.tools[key].image.style.border = "1px solid #FFFFFF";		
			//alert('clearing ' + this.tools[key].mapTool.get_geometry().id);					
			this.tools[key].mapTool.graphic.geometry.clear();
			//alert('clear');
	        this.tools[key].mapTool.graphic.geometry.showVertices = false;
		}
		
		this.markupOptions.style.display = "none";
    },
    
    bindFormatControlsToItem: function(item)
    {
        //alert(this.activeToolName);
        switch(this.activeToolName)
	    {
	        case "poly":
	            //stroke
	            this.option_linetype.selectedIndex = getIndex(this.option_linetype, item.style.strokeType); 
	        	this.option_linewidth.selectedIndex = getIndex(this.option_linewidth, item.style.strokeWidth); 
	            this.option_linetrans.selectedIndex = getIndex(this.option_linetrans, 100-(item.style.strokeOpacity*100)); 
	            this.td_linecolor.bgColor = item.style.strokeColor;
	            
	            //fill
	            this.option_filltrans.selectedIndex = getIndex(this.option_filltrans, 100-(item.style.fillOpacity*100)); 
	            this.td_fillcolor.bgColor = item.style.fillColor;
	            break;
	            
	        case "line":
	            this.option_linetype.selectedIndex = getIndex(this.option_linetype, item.style.strokeType); 
	            this.option_linetrans.selectedIndex = getIndex(this.option_linetrans, 100-(item.style.strokeOpacity*100)); 
	            this.option_linewidth.selectedIndex = getIndex(this.option_linewidth, item.style.strokeWidth); 
	            this.td_linecolor.bgColor = item.style.strokeColor;
	            break;   
	    }
    },
    
	set_tool: function(tool, existingGraphic)
	{
	    this.usingText = false;
	    this.unset_AllTools();
		
		this.activeTool = this.tools[tool];
		this.activeToolName = tool;
		
		this.activeTool.image.style.border = "1px solid #919B9C";
		this.activeTool.div.style.display = "block";
		
		this.map.set_tool(this.activeTool.mapTool);	 
		
		var type;
		switch(tool)
	    {
			case "textPoint":
			    type = "text";
			    this.usingText = true;
			    
			    //help
				this.floatingPanel.get_helpPanel().innerHTML = this.textHelpString;	
				
			    this.markup_row_lineColor.style.display = "";
			    	            
			    //hide stroke options
			    this.markup_row_lineType.style.display = "none";
	            this.markup_row_lineWidth.style.display = "none";
	            this.markup_row_linetrans.style.display = "none";
			    
			    //hide fill options
		        this.markup_row_FillColor.style.display = "none";
		        this.markup_row_FillTrans.style.display = "none";
		        
		        //show text options
		        this.markupTextOptions.style.display = "";
	            this.activeTool.mapTool.add_click(Function.createDelegate(this, this.set_text));
				break;
			case "circle":
				type = "circle";
				
				//help
				this.floatingPanel.get_helpPanel().innerHTML = this.circleHelpString;	
				
			    //show stroke options
			    this.markup_row_lineType.style.display = "";
	            this.markup_row_lineWidth.style.display = "";
	            this.markup_row_linetrans.style.display = "";
	            
			    //show fill options
			    this.markup_row_FillColor.style.display = "";
			    this.markup_row_FillTrans.style.display = "";
			    
			    //hide text options
			    this.markupTextOptions.style.display = "none";
			    break;
			case "poly":
				type = "polygon";
				
				//help
				this.floatingPanel.get_helpPanel().innerHTML = this.polyHelpString;	
				
			    //show stroke options
			    this.markup_row_lineType.style.display = "";
	            this.markup_row_lineWidth.style.display = "";
	            this.markup_row_linetrans.style.display = "";
	            
			    //show fill options
			    this.markup_row_FillColor.style.display = "";
			    this.markup_row_FillTrans.style.display = "";
			    
			    //hide text options
			    this.markupTextOptions.style.display = "none";
			    break;
			case "line":
				type = "line";
				
				//help
				this.floatingPanel.get_helpPanel().innerHTML = this.lineHelpString;	
				
			    //show stroke options
			    this.markup_row_lineType.style.display = "";
	            this.markup_row_lineWidth.style.display = "";
	            this.markup_row_linetrans.style.display = "";
	            
			    //hide fill options
			    this.markup_row_FillColor.style.display = "none";
			    this.markup_row_FillTrans.style.display = "none";
			    
			    //hide text options
			    this.markupTextOptions.style.display = "none";
			    break;
			default:
			    this.markup_row_FillColor.style.display = "";	
		}
		this.markup_Name_Input.value = type + "_" + markupGlobalCounter;
		
	    if (existingGraphic) {
	        this.bindFormatControlsToItem(existingGraphic);
	    } else {
	        this.set_allVectorStyles();	
	    }
	    
	    Sys.Debug.trace("setting tool...");
	},
	
    save: function()
    {
        var _me;
        
        if (!this.activeTool) {
            _me = markup;
        } else {
            _me = this;
        }
        
        var originalGraphic = _me.activeTool.mapTool.graphic;
        _me.graphicsLayer.removeEditor(originalGraphic);
                
        var savedGraphic = new MapsDirect.Vector.Graphic();
        savedGraphic.geometry = new clone(originalGraphic.geometry);
	    savedGraphic.style = new clone(originalGraphic.style);
	    savedGraphic.displayName = this.markup_Name_Input.value;
	    //savedGraphic.toolType = _me.activeTool.
	    var text = originalGraphic.textString;
	    savedGraphic.textString = text;
	    savedGraphic.saved = true;
	    savedGraphic.toolName = this.activeToolName;	    
	    originalGraphic.textString = "";
	    
	    
	    //alert("************* " + Object.getTypeName(newGraphic.geometry));
	    this.graphicsLayer.addItem(savedGraphic, true);
        
        this.graphicsLayer.erase(this.activeTool.mapTool.graphic);
		this.activeTool.mapTool.graphic.geometry.clear();
		
		//this.graphicsLayer.editItem(newGraphic);
		 
        this.bindTableOfSavedVectorObjects();
        this.set_allVectorStyles();
        
        markupGlobalCounter++;
        var type = Object.getTypeName(savedGraphic.geometry).split(".");
        this.markup_Name_Input.value = type[2] + "_" + markupGlobalCounter;
        this.markupTextArea.value = "";
    },
    
    bindTableOfSavedVectorObjects: function()
    {
        var counter=0;
        var outString = "<table>\n";
        var textStringSnippet = "";
        
         //render list of saved items...
        for(var key in this.graphicsLayer.items) {
			Sys.Debug.trace("***** " + key);
			//alert(this.graphicsLayer.items[key].textString);
            var textString = this.graphicsLayer.items[key].textString;
            var displayName = this.graphicsLayer.items[key].displayName;
            
            if (textString && textString.length>0) {
                textStringSnippet = this.graphicsLayer.items[key].textString.substring(0,this.snippetLength);
                if (textString.length > this.snippetLength) {
                    textStringSnippet = textStringSnippet + "...";
                    //alert("yes");
                }
            } else {
                textStringSnippet = "";
            }
                
            //Sys.Debug.trace("createTableOfSavedVectorObjects()" + key + "..." + this.map.vectorObjects[key].isMarkup);
            if (this.graphicsLayer.items[key].saved) {
                try {
                    //alert("key..."+this.map.vectorObjects[key].isMarkup);
                    outString += "<tr>";
                    
                    if (this.graphicsLayer.items[key].geometry.allowEdit == true) {
                    //if (true) { 
                        outString += "<td><img onmousedown=\"markup.editItemByKey('" + key + "')\" style=\"cursor: pointer;\" alt\"Edit\" src='" + this.imgEdit + "' /></td>";
                    } else {
                        outString += "<td></td>";
                    }
                    outString += "<td><img onmousedown=\"markup.deleteItemByKey('" + key + "')\" style=\"cursor: pointer;\" alt\"Delete\" src='" + this.imgDelete + "' /></td>";
                    //outString += "<td><img style=\"cursor: hand;\" src='./images/contextMenuZoomTo.gif' /></td>";
                    outString += "<td>";
                    outString += displayName;
                    outString += "</td>";
                    outString += "<td>";
                    outString += "&nbsp;&nbsp;<i>"+textStringSnippet+"</i>";
                    outString += "</td>";
                    outString += "</tr>";
                    counter++;
                } catch (ex) {
                    alert('Error encountered while generating a table row for markUp item with key ' + key);
                }
            }
	    }
	    outString += "</table>";
        this.markupListDiv.innerHTML = outString;
        
        //alert(counter);
        if (counter>0) {
            this.markupSavedItemsContainer.style.display="";
        } else {
            this.markupSavedItemsContainer.style.display="none";
        }
    },
    
    deleteItemByKey: function(key)
    {
		this.graphicsLayer.removeItem(this.graphicsLayer.items[key]);
        this.bindTableOfSavedVectorObjects();
    },
    
    editItemByKey: function(key)
    {
		this.graphicsLayer.erase(this.activeTool.mapTool.graphic);
		this.activeTool.mapTool.graphic.geometry.clear();
		
        this.set_tool(this.graphicsLayer.items[key].toolName, this.graphicsLayer.items[key]);
        
        if (this.graphicsLayer.items[key].geometry.allowEdit == true) {
            this.graphicsLayer.editItem(this.graphicsLayer.items[key]);
        }
        //this.activeTool.mapTool.graphic = this.graphicsLayer.items[key];
        		
        this.bindTableOfSavedVectorObjects();
    },
    
	show: function()
	{
	    //help
		this.floatingPanel.get_helpPanel().innerHTML = this.startHelpString;	
				
		floatingPanelManager.closeAll();		
		floatingPanelManager.open(this.floatingPanelId);
		this.unset_AllTools();
		this.bindTableOfSavedVectorObjects();
		
	},

    set_allVectorStyles: function()
    {
        this.set_lineType(this.option_linetype.value);
        this.set_lineWidth(this.option_linewidth.value);
        this.set_lineColor(this.td_linecolor.bgColor);
        //alert("line color set to " + this.td_linecolor.bgColor);
        this.set_lineTransparency(this.option_linetrans.value);
        
        this.set_fillColor(this.td_fillcolor.bgColor);
        this.set_fillTransparency(this.option_filltrans.value);
        
        if (this.usingText) {
            this.set_textSize(this.option_textSize.value);
        }
    },
    
    setAttribute: function(name, value){
		if(this.graphicsLayer.editor != null){
			eval("this.graphicsLayer.editor.graphic.style."+name+" = value;");
			this.graphicsLayer.draw(this.graphicsLayer.editor.graphic);
		}else{
			eval("this.activeTool.mapTool.graphic.style."+name+" = value;");
			this.graphicsLayer.draw(this.activeTool.mapTool.graphic);
		}
    },
    
    set_lineColor: function(value){
		var _me;
		if (!this.activeTool) {
            _me = markup;
        } else {
            _me = this;
        }
		_me.setAttribute("strokeColor", value);
    },
    
    set_fillColor: function(value){
		var _me;
		if (!this.activeTool) {
            _me = markup;
        } else {
            _me = this;
        }
		_me.setAttribute("fillColor", value);
    },
    
    set_lineType: function(value){   
		var _me;
		if (!this.activeTool) {
            _me = markup;
        } else {
            _me = this;
        }
		_me.setAttribute("strokeType", value);
    },
    
    set_lineWidth: function(value){
		var _me;
		if (!this.activeTool) {
            _me = markup;
        } else {
            _me = this;
        }
		_me.setAttribute("strokeWidth", value);
    },
    
    set_lineTransparency: function(value){
        var opacityPercent = 100-value;
        var opacityRatio = opacityPercent/100;
        var _me;
		if (!this.activeTool) {
            _me = markup;
        } else {
            _me = this;
        }
		_me.setAttribute("strokeOpacity", opacityRatio);
    },
    
    set_fillTransparency: function(value){
        var opacityPercent = 100-value;
        var opacityRatio = opacityPercent/100;
         var _me;
		if (!this.activeTool) {
            _me = markup;
        } else {
            _me = this;
        }
		_me.setAttribute("fillOpacity", opacityRatio);
    },
    
    set_text: function()
    {
        if (!this.usingText) return;
        //Sys.Debug.trace("this.activeTool.mapTool.get_geometry().text has been set to "+ this.activeTool.mapTool.get_geometry().textString);
        this.activeTool.mapTool.graphic.textString = this.markupTextArea.value;//.replace('\n','<br/>');
        if (this.activeTool.mapTool.graphic.textString.length < 1) {
            this.activeTool.mapTool.graphic.textString = this.textEmptyPlaceholderString;
            this.markupTextArea.style.backgroundColor="#FFFF66";
        } else {
            this.markupTextArea.style.backgroundColor="";
        }
       
        this.set_allVectorStyles();
        this.graphicsLayer.draw(this.activeTool.mapTool.graphic);
    },
    
    set_textSize: function(value)
    {
        if (!this.usingText) return;
        
        this.activeTool.mapTool.graphic.style.textSize = value;
        
        if (this.activeTool.mapTool.graphic.textString)
            this.graphicsLayer.draw(this.activeTool.mapTool.graphic);
    },
	
//	_drawText: function()
//	{
//	    //alert("drawText()");
//	    this.set_allVectorStyles();	
//	    var geometry = this.activeTool.mapTool.get_geometry();
//	    alert(geometry.textString); 
//	    geometry.get_renderer().drawText(geometry);
//	},
	
    _onClosePanel: function()
    {
        //alert("clearing...");
        this.graphicsLayer.removeEditor();
        this.map.clear_tool();
        //alert("clear");
    }
};
if(typeof(Sys)!=='undefined')Sys.Application.notifyScriptLoaded();