Ok here you are. It works by using toc.excludelayers. At the beginning all layers are in the exclude. Then when a user wants to add a layer I actually remove it from the exclude list I have. To remove from the TOC I add it back to the list of excluded layers. The Visibility check boxes in both TOCs do stay synced, order is also synced when using the base code (my application gets around this but be careful if you do not want this) .
First I made a copy of MapSwitcherWidget and called it MapSwitcherWidget2. I then had to change a few other files to allow the drag and drop mostly. Overall very few changes to the original code.
There is still test code in here commented out. If I missed anything or questions just let me know.
------------------------------
Drag and Drop Code (and other code parts are seen here also)
in MapSwitcherWidget2.mxml
private function dragDropHandler(event:DragEvent):void
{
/*Alert.show(event.dragSource.dataForFormat('text') as String);*/
if (templist.getItemIndex(event.dragSource.dataForFormat('text')) != -1)
{
templist.removeItemAt(templist.getItemIndex(event.dragSource.dataForFormat('text')));
}
}
private function dragEnterHandler(event:Event):void
{
var dropTarget:Button=Button(event.currentTarget);
// Accept the drop.
DragManager.acceptDragDrop(dropTarget);
}
/* drop on the toc button itself because of the autohide - i later took out the autohide and then moved this to the border container*/
<s:HGroup id="mapLayersContainer" gap="9">
<s:Button id="opLayersButton"
height="100%"
label="{opLayerListButtonLabel}"
rollOut="startHideTimer()"
rollOver="opLayerListButton_rollOverHandler(event)"
visible="false"
dragEnter="dragEnterHandler(event)"
dragDrop="dragDropHandler(event)"/>
in TocItemRenderer.as
protected function onCheckBoxMouseMove(event:MouseEvent):void
{
// Get the drag initiator component from the event object.
var dragInitiator:CheckBoxIndeterminate=CheckBoxIndeterminate(event.currentTarget);
// Get the color of the drag initiator component.
// Create a DragSource object.
var ds:DragSource = new DragSource();
ds.addData(event.currentTarget.owner.data.label, 'text');
// Call the DragManager doDrag() method to start the drag.
DragManager.doDrag(dragInitiator, ds, event);
}
** just added one line here for a mouse move listener
override protected function createChildren():void
{
super.createChildren();
// Create a checkbox child component for toggling layer visibility.
if (!_checkbox)
{
_checkbox = new CheckBoxIndeterminate();
_checkbox.addEventListener(MouseEvent.CLICK, onCheckBoxClick);
_checkbox.addEventListener(MouseEvent.DOUBLE_CLICK, onCheckBoxDoubleClick);
_checkbox.addEventListener(MouseEvent.MOUSE_DOWN, onCheckBoxMouseDown);
_checkbox.addEventListener(MouseEvent.MOUSE_UP, onCheckBoxMouseUp);
_checkbox.addEventListener(MouseEvent.MOUSE_MOVE, onCheckBoxMouseMove);
addChild(_checkbox);
}
if (!_layerMenuImage)
{
_layerMenuImage = new Image();
_layerMenuImage.source = contextCls;
_layerMenuImage.height = 11;
_layerMenuImage.width = 11;
_layerMenuImage.setStyle("verticalAlign", "middle");
_layerMenuImage.buttonMode = true;
addChild(_layerMenuImage);
this._layerMenuImage.addEventListener(MouseEvent.CLICK, onLayerMenuImageClick);
this._layerMenuImage.addEventListener(MouseEvent.DOUBLE_CLICK, onLayerMenuImageDoubleClick);
}
}
Changed this so it used the text instead of the checkbox for the drag. The drop handler is where it ignores draggin the checkbox or down arrow (these can be dragged but then you have to change the code to get the name of the layer).
protected function onTOCItemMouseMove(event:MouseEvent):void
{
// Get the drag initiator component from the event object.
var dragInitiator:TocItemRenderer=TocItemRenderer(event.currentTarget);
// Get the color of the drag initiator component.
if ('text' in event.target)
{
// Create a DragSource object.
var ds:DragSource = new DragSource();
ds.addData(event.target.text, 'text');
// Call the DragManager doDrag() method to start the drag.
DragManager.doDrag(dragInitiator, ds, event);
}
}
public function TocItemRenderer()
{
super();
addEventListener(MouseEvent.CLICK, itemClickHandler);
addEventListener(MouseEvent.MOUSE_MOVE, onTOCItemMouseMove);
}
---------------------
Remove Layer Code
Added in MapSwitcherWidget
/* Added by me */
In the initTOC function
/* Added for remove button */
AppEvent.addListener("removefromtoc", removeFromWorkingTOC);
/* Added by me */
private function removeFromWorkingTOC(event:AppEvent):void
{
templist.addItem(event.data);
}
In TOCLayerMenu.mxml
(or anywhere you put the button)
/* added by me */
public function removeFromListLabel_clickHandler(event:MouseEvent):void
{
AppEvent.dispatch("removefromtoc", _layer.id);
}
--------------------
Save Layers TOC (same code is shown in Drag and Drop also
/* Added by me */
public var myFileReference2:FileReference = new FileReference();
protected function SaveTOC_clickHandler(event:MouseEvent):void
{
var myFileReference:FileReference = new FileReference();
myFileReference.save(templist, "filename.txt");
}
/* Added by me */
protected function LoadTOC_clickHandler(event:MouseEvent):void
{
myFileReference2.browse([new FileFilter("TXT File", "*.txt")]);
myFileReference2.addEventListener(Event.SELECT, onFileSelected);
}
/* Added by me */
protected function onFileSelected(e:Event):void {
myFileReference2.addEventListener(Event.COMPLETE, onFileLoaded);
myFileReference2.load();
}
/* Added by me */
protected function onFileLoaded(e:Event):void {
var tempArrayC:ArrayCollection = new ArrayCollection(myFileReference2.data.toString().split(','));
templist = tempArrayC;
toc2.excludeLayers = templist;
}
private function mapLayerAddHandler2(event:Event):void
{
/*Alert.show(templist.getItemIndex(event.currentTarget.id)as String);*/
/*Alert.show(templist[0]);*/
if (templist.getItemIndex(event.currentTarget.id) != -1)
{
templist.removeItemAt(templist.getItemIndex(event.currentTarget.id));
}
/*event.currentTarget.id*/
/*toc2.excludeLayers = templist;*/
/*toc2.map = map; /*
toc2.isMapServiceOnly = false; //gotta get this from the config file
toc2.excludeLayers = getExcludeLayers();
toc2.basemapLayers = getBasemapLayers();
toc2.excludeGraphicsLayers = true;
if (expandLayerItems)
{
toc2.expandLayerItems();
} */
}
<s:VGroup top="100">
<s:Label id="SaveTOC"
text="Save TOC to File.."
click="SaveTOC_clickHandler(event)"/>
<s:Label id="LoadTOC"
text="Load TOC from File.."
click="LoadTOC_clickHandler(event)"/>
</s:VGroup>
-------------------------