Example program - drag and drop for listboxes
Drag and drop is supported between controls on a form that support object notation such as list boxes, trees and grid cells. The selection and dragging is handled entirely in the client. The program can specify using the DragStyle enumerated property whether a control will allow dragging off and or whether it can be a target of a drop When dropped onto a control whose style allows it, a Drop() event fires allowing the program perform the transfer if it deems fit. When the Drop() event handler is executing it has access to the DragSourceControl and DragSourceItem object properties defining the source control and item. Also available are DragTargetControl and DragTargetItem object properties defining the target control and item. The event handler can also check the keyboard shift state at the time of the drop by inspecting the DragKey property.
This example shows dragging between a pair of list boxes with the program enforcing a check that the drop target is suitable. There are two pair of boxes, one for fruit and one for vegetables whose .DragStyle property is set to &.DragBoth allowing them to be both a source and a target. The check in 'DoListDrag() compares the .id properties of the acceptable target and the actual target and only moves the item if they agree so that fruit cannot be moved to vegetables list and vice versa. The fifth 'Off limits' list box has its .DragStyle set to &.DragNone so it cannot accept a drop or allow its contents to be dragged. This does not require a server event and is managed entirely by the client.
// Drag and drop between list boxes DEFFORM Form1()={.form,.form$,.Style=0x50c000c4,.Width=238,.Height=189,.Text$="Drag",.Id=1024},\ {.ok,.button$,.Style=0x50010001,.Left=186,.Top=6,.Width=50,.Height=14,.Text$="OK",.__Anchor=5,.Id=1},\ {.cancel,.button$,.Style=0x50010000,.Left=186,.Top=23,.Width=50,.Height=14,.Text$="Cancel",.__Anchor=5,.Id=2},\ {.listFruit1,.listbox$,.Style=0x50a10183,.Left=7,.Top=15,.Width=73,.Height=54,.Id=1000,.DragStyle=4},\ {.ListFruit2,.listbox$,.Style=0x50a10183,.Left=87,.Top=15,.Width=73,.Height=54,.Id=1001,.DragStyle=4},\ {.frameControl1,.groupbox$,.Style=0x50000007,.Left=1,.Top=2,.Width=165,.Height=73,.Text$="Fruit",.Id=1002},\ {.listVeg1,.listbox$,.Style=0x50a10183,.Left=7,.Top=98,.Width=73,.Height=54,.Id=1003,.DragStyle=4},\ {.ListVeg2,.listbox$,.Style=0x50a10183,.Left=86,.Top=98,.Width=73,.Height=54,.Id=1004,.DragStyle=4},\ {.frameControl2,.groupbox$,.Style=0x50000007,.Left=1,.Top=82,.Width=165,.Height=73,.Text$="Vegetables",.Id=1005},\ {.lblControl1,.static$,.Style=0x50000000,.Left=6,.Top=164,.Width=158,.Height=34,.Text$="Drag items between lists. Items may only be dragged to a list of the same type",.Id=1006,.Font=.Bold},\ {.offlimits,.listbox$,.Style=0x50a10183,.Left=179,.Top=98,.Width=52,.Height=54,.Id=1007,.DragStyle=1},\ {.frameControl3,.groupbox$,.Name$="OffLimits",.Style=0x50000007,.Left=175,.Top=82,.Width=59,.Height=73,.Text$="Off Limits",.Id=1008} DEFEVENT Form1.Enter() // prime the list boxes with some fruit and veg\ .listFruit1.Add("Apple") .listFruit1.Add("Orange") .listFruit1.Add("Banana") .listFruit1.Add("Pear") .listVeg1.Add("Potato") .listVeg1.Add("Turnip") .listVeg1.Add("Carrot") .listVeg1.Add("Cabbage") .offlimits.Add("Not draggable") END EVENT DEFEVENT Form1.listFruit1.Drop() 'DoListDrag(OBJECT .ListFruit2) END EVENT DEFEVENT Form1.ListFruit2.Drop() 'DoListDrag(OBJECT .listFruit1) END EVENT DEFEVENT Form1.listVeg1.Drop() 'DoListDrag(OBJECT .ListVeg2) END EVENT DEFEVENT Form1.ListVeg2.Drop() 'DoListDrag(OBJECT .listVeg1) END EVENT FORM END Form1 Form1.Open() $END DEFSUB 'MoveListItem(OBJECT SourceItem, OBJECT DestList) REM Add list item to destination listbox, then remove it from the source listbox DestList.Add(SourceItem.Text$) SourceItem.Delete() END SUB DEFSUB 'DoListDrag(OBJECT ValidSource) REM Check the source control is valid before moving list item LOCAL DIM OBJECT SourceControl, OBJECT TargetControl OBJECT SourceItem = ..DragSourceItem OBJECT SourceControl = ..DragSourceControl OBJECT TargetControl = ..DragTargetControl IF (SourceControl.Id == ValidSource.Id) 'MoveListItem(OBJECT SourceItem, OBJECT TargetControl) END IF END SUB