--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/UISelectionPanel.st Mon Apr 07 17:49:18 1997 +0200
@@ -0,0 +1,1069 @@
+"
+ COPYRIGHT (c) 1997 by eXept Software AG
+ All Rights Reserved
+
+ This software is furnished under a license and may be used
+ only in accordance with the terms of that license and with the
+ inclusion of the above copyright notice. This software may not
+ be provided or otherwise made available to, or used by, any
+ other person. No title to or ownership of the software is
+ hereby transferred.
+"
+
+
+View subclass:#UISelectionPanel
+ instanceVariableNames:'action window tabView labelView inputView selection
+ lastClickPoint specification'
+ classVariableNames:''
+ poolDictionaries:''
+ category:'Interface-UIPainter'
+!
+
+DropObject subclass:#DropSpecification
+ instanceVariableNames:''
+ classVariableNames:''
+ poolDictionaries:''
+ privateIn:UISelectionPanel
+!
+
+!UISelectionPanel class methodsFor:'documentation'!
+
+copyright
+"
+ COPYRIGHT (c) 1997 by eXept Software AG
+ All Rights Reserved
+
+ This software is furnished under a license and may be used
+ only in accordance with the terms of that license and with the
+ inclusion of the above copyright notice. This software may not
+ be provided or otherwise made available to, or used by, any
+ other person. No title to or ownership of the software is
+ hereby transferred.
+"
+
+!
+
+documentation
+"
+ implements a selection panel, keeping widgets which could be placed
+ into the UIPainter by drag & drop.
+
+ [author:]
+ Claus Atzkern
+
+ [see also:]
+ TabView
+ UIPainter
+"
+
+!
+
+examples
+"
+ creates and opens the default panel
+ [exBegin]
+ self defaultPanel.
+ [exEnd]
+
+
+ create a panel with labels and selectors implemented by the receiver
+ which returns a FullSpec.
+ [exBegin]
+ |top slv inset list view idx frame colSelected colUnselected|
+
+ top := StandardSystemView new
+ label:'UI-Selection Panel';
+ extent:450@150.
+
+ view := self origin:0.0 @ 0.0 corner:1.0 @ 1.0 in:top.
+
+ view labels:#( 'Button & Toggles'
+ 'Panels'
+ 'Scroller'
+ )
+ selectors:#( #buttonToggleSpec
+ #scrollerSpec
+ #panelSpec
+ )
+ receiver:self.
+
+ top open.
+ [exEnd]
+"
+! !
+
+!UISelectionPanel class methodsFor:'instance creation'!
+
+defaultPanel
+ |top slv inset list view idx frame colSelected colUnselected|
+
+ top := StandardSystemView new
+ label:'UI-Selection Panel';
+ extent:480@200.
+
+ view := self origin:0.0 @ 0.0 corner:1.0 @ 1.0 in:top.
+
+ view labels:#( 'Button & Toggle'
+ 'Panel'
+ 'Text'
+ 'View'
+ 'Menu & Combo'
+ 'Scroller'
+ )
+ selectors:#( #buttonToggleSpec
+ #panelSpec
+ #textSpec
+ #viewsSpec
+ #menuComboSpec
+ #scrollerSpec
+ )
+ receiver:self.
+
+ top open.
+
+! !
+
+!UISelectionPanel class methodsFor:'default specifications'!
+
+buttonToggleSpec
+ "this window spec was automatically generated by the ST/X UIPainter"
+
+ "do not manually edit this - the painter/builder may not be able to
+ handle the specification if its corrupted."
+
+ "
+ UIPainter new openOnClass:UISelectionPanel andSelector:#buttonToggleSpec
+ UISelectionPanel new openInterface:#buttonToggleSpec
+ "
+
+ <resource: #canvas>
+
+ ^
+
+ #(#FullSpec
+ #'window:'
+ #(#WindowSpec
+ #'name:' 'uIPainterView'
+ #'layout:' #(#LayoutFrame 0 0.0 0 0.0 0 1.0 0 1.0)
+ #'label:' 'unnamed'
+ #'bounds:' #(#Rectangle 0 0 450 100)
+ )
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#ArrowButtonSpec
+ #'name:' 'ArrowButton up'
+ #'layout:' #(#LayoutFrame 16 0 70 0 38 0 92 0)
+ #'translateLabel:' false
+ #'tabable:' false
+ #'hasCharacterOrientedLabel:' false
+ #'isTriggerOnDown:' true
+ #'direction:' #up
+ )
+ #(#ActionButtonSpec
+ #'name:' 'Button'
+ #'layout:' #(#LayoutFrame 16 0 8 0 115 0 30 0)
+ #'label:' 'Button'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' false
+ )
+ #(#RadioButtonSpec
+ #'name:' 'RadioButton'
+ #'layout:' #(#LayoutFrame 16 0.0 39 0 115 0 61 0)
+ #'label:' 'RadioButton'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' true
+ #'showLamp:' true
+ #'lampColor:' #(#Color 100.0 100.0 0.0)
+ )
+ #(#ArrowButtonSpec
+ #'name:' 'ArrowButton down'
+ #'layout:' #(#LayoutFrame 42 0 70 0 64 0 92 0)
+ #'translateLabel:' false
+ #'tabable:' false
+ #'hasCharacterOrientedLabel:' false
+ #'isTriggerOnDown:' true
+ #'direction:' #down
+ )
+ #(#ArrowButtonSpec
+ #'name:' 'ArrowButton left'
+ #'layout:' #(#LayoutFrame 68 0 70 0 90 0 92 0)
+ #'translateLabel:' false
+ #'tabable:' false
+ #'hasCharacterOrientedLabel:' false
+ #'isTriggerOnDown:' true
+ #'direction:' #left
+ )
+ #(#ArrowButtonSpec
+ #'name:' 'ArrowButton right'
+ #'layout:' #(#LayoutFrame 93 0 70 0 115 0 92 0)
+ #'translateLabel:' false
+ #'tabable:' false
+ #'hasCharacterOrientedLabel:' false
+ #'isTriggerOnDown:' true
+ #'direction:' #right
+ )
+ #(#CheckToggleSpec
+ #'name:' 'CheckToggle'
+ #'layout:' #(#LayoutFrame 147 0 70 0 167 0 90 0)
+ #'translateLabel:' false
+ #'tabable:' false
+ #'hasCharacterOrientedLabel:' false
+ #'isTriggerOnDown:' true
+ #'showLamp:' false
+ #'lampColor:' #(#Color 100.0 100.0 0.0)
+ )
+ #(#ToggleSpec
+ #'name:' 'Toggle'
+ #'layout:' #(#LayoutFrame 147 0 8 0 246 0 30 0)
+ #'label:' 'Toggle'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' true
+ #'showLamp:' true
+ #'lampColor:' #(#Color 100.0 100.0 0.0)
+ )
+ #(#CheckBoxSpec
+ #'name:' 'CheckBox'
+ #'layout:' #(#LayoutFrame 145 0 39 0 246 0 61 0)
+ #'tabable:' false
+ #'label:' 'CheckBox'
+ #'translateLabel:' false
+ )
+ )
+ )
+ )
+!
+
+menuComboSpec
+ "this window spec was automatically generated by the ST/X UIPainter"
+
+ "do not manually edit this - the painter/builder may not be able to
+ handle the specification if its corrupted."
+
+ "
+ UIPainter new openOnClass:UISelectionPanel andSelector:#menuComboSpec
+ UISelectionPanel new openInterface:#menuComboSpec
+ "
+
+ <resource: #canvas>
+
+ ^
+
+ #(#FullSpec
+ #'window:'
+ #(#WindowSpec
+ #'name:' 'uIPainterView'
+ #'layout:' #(#LayoutFrame 0 0.0 0 0.0 0 1.0 0 1.0)
+ #'label:' 'unnamed'
+ #'bounds:' #(#Rectangle 0 0 450 100)
+ )
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#ComboBoxSpec
+ #'name:' 'ComboBox'
+ #'layout:' #(#LayoutFrame 14 0 15 0 117 0 35 0)
+ #'immediateAccept:' false
+ #'acceptOnLeave:' true
+ #'acceptOnReturn:' true
+ #'acceptOnTab:' true
+ #'acceptOnLostFocus:' true
+ #'hasBorder:' false
+ )
+ #(#ComboListSpec
+ #'name:' 'ComboList'
+ #'layout:' #(#LayoutFrame 14 0 46 0 117 0 66 0)
+ #'tabable:' false
+ )
+ #(#PopUpListSpec
+ #'name:' 'PopUpList'
+ #'layout:' #(#LayoutFrame 139 0 15 0 242 0 37 0)
+ #'label:' 'PopUpList'
+ #'initiallyInvisible:' false
+ #'translateLabel:' false
+ )
+ )
+ )
+ )
+!
+
+panelSpec
+ "this window spec was automatically generated by the ST/X UIPainter"
+
+ "do not manually edit this - the painter/builder may not be able to
+ handle the specification if its corrupted."
+
+ "
+ UIPainter new openOnClass:UISelectionPanel andSelector:#panelSpec
+ UISelectionPanel new openInterface:#panelSpec
+ "
+
+ <resource: #canvas>
+
+ ^
+
+ #(#FullSpec
+ #'window:'
+ #(#WindowSpec
+ #'name:' 'uIPainterView'
+ #'layout:' #(#LayoutFrame 0 0.0 0 0.0 0 1.0 0 1.0)
+ #'label:' 'unnamed'
+ #'bounds:' #(#Rectangle 0 0 450 100)
+ )
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#HorizontalPanelViewSpec
+ #'name:' 'HorizontalPanelView'
+ #'layout:' #(#LayoutFrame 20 0 17 0 104 0 81 0)
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#ActionButtonSpec
+ #'name:' 'button1'
+ #'label:' 'A'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' false
+ #'extent:' #(#Point 34 23)
+ #'canUIDrag:' false
+ )
+ #(#ActionButtonSpec
+ #'name:' 'button8'
+ #'label:' 'B'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' false
+ #'extent:' #(#Point 32 41)
+ #'canUIDrag:' false
+ )
+ )
+ )
+ #'level:' 0
+ #'horizontalLayout:' #center
+ #'verticalLayout:' #center
+ #'horizontalSpace:' 3
+ #'verticalSpace:' 3
+ )
+ #(#VariableHorizontalPanelSpec
+ #'name:' 'VariableHorizontalPanel'
+ #'layout:' #(#LayoutFrame 128 0 17 0 212 0 81 0)
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#ActionButtonSpec
+ #'name:' 'button2'
+ #'label:' 'A'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' false
+ #'canUIDrag:' false
+ )
+ #(#ActionButtonSpec
+ #'name:' 'button3'
+ #'label:' 'B'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' false
+ #'canUIDrag:' false
+ )
+ )
+ )
+ )
+ #(#VerticalPanelViewSpec
+ #'name:' 'VerticalPanelView'
+ #'layout:' #(#LayoutFrame 236 0 17 0 320 0 81 0)
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#ActionButtonSpec
+ #'name:' 'button4'
+ #'label:' 'A'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' false
+ #'extent:' #(#Point 19 18)
+ #'canUIDrag:' false
+ )
+ #(#ActionButtonSpec
+ #'name:' 'button5'
+ #'label:' 'B'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' false
+ #'extent:' #(#Point 63 30)
+ #'canUIDrag:' false
+ )
+ )
+ )
+ #'level:' 0
+ #'horizontalLayout:' #center
+ #'verticalLayout:' #center
+ #'horizontalSpace:' 3
+ #'verticalSpace:' 3
+ )
+ #(#VariableVerticalPanelSpec
+ #'name:' 'VariableVerticalPanel'
+ #'layout:' #(#LayoutFrame 344 0 17 0 428 0 81 0)
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#ActionButtonSpec
+ #'name:' 'button6'
+ #'label:' 'A'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' false
+ #'canUIDrag:' false
+ )
+ #(#ActionButtonSpec
+ #'name:' 'button7'
+ #'label:' 'B'
+ #'translateLabel:' false
+ #'tabable:' false
+ #'isTriggerOnDown:' false
+ #'canUIDrag:' false
+ )
+ )
+ )
+ )
+ )
+ )
+ )
+!
+
+scrollerSpec
+ "this window spec was automatically generated by the ST/X UIPainter"
+
+ "do not manually edit this - the painter/builder may not be able to
+ handle the specification if its corrupted."
+
+ "
+ UIPainter new openOnClass:UISelectionPanel andSelector:#scrollerSpec
+ UISelectionPanel new openInterface:#scrollerSpec
+ "
+
+ <resource: #canvas>
+
+ ^
+
+ #(#FullSpec
+ #'window:'
+ #(#WindowSpec
+ #'name:' 'uIPainterView'
+ #'layout:' #(#LayoutFrame 0 0.0 0 0.0 0 1.0 0 1.0)
+ #'label:' 'unnamed'
+ #'bounds:' #(#Rectangle 0 0 450 100)
+ )
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#ArbitraryComponentSpec
+ #'name:' 'HorizontalMiniScroller'
+ #'layout:' #(#LayoutFrame 4 0 10 0 105 0 16 0)
+ #'component:' ''
+ #'tabable:' false
+ #'hasHorizontalScrollBar:' false
+ #'hasVerticalScrollBar:' false
+ #'hasBorder:' false
+ )
+ #(#ArbitraryComponentSpec
+ #'name:' 'HorizontalScrollBar'
+ #'layout:' #(#LayoutFrame 4 0 23 0 105 0 42 0)
+ #'component:' ''
+ #'tabable:' false
+ #'hasHorizontalScrollBar:' false
+ #'hasVerticalScrollBar:' false
+ #'hasBorder:' false
+ )
+ #(#ArbitraryComponentSpec
+ #'name:' 'HorizontalScroller'
+ #'layout:' #(#LayoutFrame 4 0 49 0 105 0 66 0)
+ #'component:' ''
+ #'tabable:' false
+ #'hasHorizontalScrollBar:' false
+ #'hasVerticalScrollBar:' false
+ #'hasBorder:' false
+ )
+ #(#ArbitraryComponentSpec
+ #'name:' 'HorizontalSlider'
+ #'layout:' #(#LayoutFrame 4 0 73 0 105 0 90 0)
+ #'tabable:' false
+ #'hasHorizontalScrollBar:' false
+ #'hasVerticalScrollBar:' false
+ #'hasBorder:' false
+ )
+ #(#ArbitraryComponentSpec
+ #'name:' 'MiniScroller'
+ #'layout:' #(#LayoutFrame 137 0 11 0 143 0 90 0)
+ #'component:' ''
+ #'tabable:' false
+ #'hasHorizontalScrollBar:' false
+ #'hasVerticalScrollBar:' false
+ #'hasBorder:' false
+ )
+ #(#ArbitraryComponentSpec
+ #'name:' 'ScrollBar'
+ #'layout:' #(#LayoutFrame 153 0 11 0 172 0 90 0)
+ #'component:' ''
+ #'tabable:' false
+ #'hasHorizontalScrollBar:' false
+ #'hasVerticalScrollBar:' false
+ #'hasBorder:' false
+ )
+ #(#ScrollerSpec
+ #'name:' 'Scroller'
+ #'layout:' #(#LayoutFrame 182 0 11 0 212 0 90 0)
+ )
+ #(#SliderSpec
+ #'name:' 'Slider'
+ #'layout:' #(#LayoutFrame 222 0 11 0 252 0 90 0)
+ )
+ #(#ArbitraryComponentSpec
+ #'name:' 'ThumbWheel'
+ #'layout:' #(#LayoutFrame 270 0 11 0 285 0 90 0)
+ #'component:' ''
+ #'tabable:' false
+ #'hasHorizontalScrollBar:' false
+ #'hasVerticalScrollBar:' false
+ #'hasBorder:' false
+ )
+ )
+ )
+ )
+!
+
+textSpec
+ "this window spec was automatically generated by the ST/X UIPainter"
+
+ "do not manually edit this - the painter/builder may not be able to
+ handle the specification if its corrupted."
+
+ "
+ UIPainter new openOnClass:UISelectionPanel andSelector:#textSpec
+ UISelectionPanel new openInterface:#textSpec
+ "
+
+ <resource: #canvas>
+
+ ^
+
+ #(#FullSpec
+ #'window:'
+ #(#WindowSpec
+ #'name:' 'uIPainterView'
+ #'layout:' #(#LayoutFrame 0 0.0 0 0.0 0 1.0 0 1.0)
+ #'label:' 'unnamed'
+ #'bounds:' #(#Rectangle 0 0 450 100)
+ )
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#InputFieldSpec
+ #'name:' 'EditField'
+ #'layout:' #(#LayoutFrame 13 0 11 0 117 0 29 0)
+ #'immediateAccept:' false
+ #'acceptOnLeave:' true
+ #'acceptOnReturn:' true
+ #'acceptOnTab:' true
+ #'acceptOnLostFocus:' true
+ #'hasBorder:' false
+ )
+ #(#TextEditorSpec
+ #'name:' 'EditTextView'
+ #'layout:' #(#LayoutFrame 171 0 11 0 275 0 91 0)
+ )
+ #(#SequenceViewSpec
+ #'name:' 'SelectionInListView'
+ #'layout:' #(#LayoutFrame 329 0 11 0 433 0 91 0)
+ #'hasHorizontalScrollBar:' true
+ #'hasVerticalScrollBar:' true
+ )
+ #(#LabelSpec
+ #'name:' 'Text Label'
+ #'layout:' #(#LayoutFrame 13 0 41 0 117 0 57 0)
+ #'label:' 'Text Label'
+ #'initiallyInvisible:' false
+ #'translateLabel:' false
+ #'level:' 0
+ #'adjust:' #center
+ #'hasCharacterOrientedLabel:' true
+ )
+ )
+ )
+ )
+!
+
+viewsSpec
+ "this window spec was automatically generated by the ST/X UIPainter"
+
+ "do not manually edit this - the painter/builder may not be able to
+ handle the specification if its corrupted."
+
+ "
+ UIPainter new openOnClass:UISelectionPanel andSelector:#viewsSpec
+ UISelectionPanel new openInterface:#viewsSpec
+ "
+
+ <resource: #canvas>
+
+ ^
+
+ #(#FullSpec
+ #'window:'
+ #(#WindowSpec
+ #'name:' 'uIPainterView'
+ #'layout:' #(#LayoutFrame 0 0.0 0 0.0 0 1.0 0 1.0)
+ #'label:' 'unnamed'
+ #'bounds:' #(#Rectangle 0 0 450 100)
+ )
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#FramedBoxSpec
+ #'name:' 'FramedBox'
+ #'layout:' #(#LayoutFrame 4 0 11 0 109 0 81 0)
+ #'label:' 'FramedBox'
+ #'labelPosition:' #topCenter
+ #'showFrame:' true
+ )
+ #(#ViewSpec
+ #'name:' 'view1'
+ #'layout:' #(#LayoutFrame 118 0 11 0 223 0 81 0)
+ #'component:'
+ #(#SpecCollection
+ #'collection:'
+ #(
+ #(#LabelSpec
+ #'name:' 'label1'
+ #'layout:' #(#Point 3 2)
+ #'label:' 'View'
+ #'initiallyInvisible:' false
+ #'translateLabel:' false
+ #'level:' 0
+ #'adjust:' #center
+ #'hasCharacterOrientedLabel:' true
+ #'canUIDrag:' false
+ )
+ )
+ )
+ )
+ #(#SubCanvasSpec
+ #'name:' 'subCanvas1'
+ #'layout:' #(#LayoutFrame 232 0 11 0 337 0 81 0)
+ )
+ #(#LabelSpec
+ #'name:' 'label2'
+ #'layout:' #(#Point 246 20)
+ #'label:' 'SubCanvas'
+ #'initiallyInvisible:' false
+ #'translateLabel:' false
+ #'level:' 0
+ #'adjust:' #center
+ #'hasCharacterOrientedLabel:' true
+ #'canUIDrag:' false
+ )
+ #(#DividerSpec
+ #'name:' 'Horizontal Seperator'
+ #'layout:' #(#LayoutFrame 373 0 11 0 437 0 28 0)
+ #'orientation:' #horizontal
+ )
+ #(#DividerSpec
+ #'name:' 'Vertical Seperator'
+ #'layout:' #(#LayoutFrame 345 0 11 0 364 0 81 0)
+ #'orientation:' #vertical
+ )
+ )
+ )
+ )
+! !
+
+!UISelectionPanel methodsFor:'accessing'!
+
+labels:labels selectors:selectors receiver:receiver
+ "change specification and tabs
+ "
+ tabView action:[:aNrOrNil||spec|
+ aNrOrNil notNil ifTrue:[
+ spec := receiver perform:(selectors at:aNrOrNil).
+ ].
+ self specification:spec.
+ ].
+ tabView list:labels.
+ self recomputeSizes.
+
+
+!
+
+specification:specOrSpecArray
+ "load a spec
+ "
+ |builder|
+
+ self selection:nil.
+ labelView label:''.
+
+ window subViews copy do:[:aSubView|
+ aSubView ~~ inputView ifTrue:[
+ aSubView == labelView ifTrue:[self halt].
+ aSubView destroy
+ ]
+ ].
+
+ specOrSpecArray notNil ifTrue:[
+ specification := UISpecification from:specOrSpecArray.
+
+ builder := UIBuilder new.
+ specification buildViewFor:builder in:window.
+ window realizeAllSubViews.
+ inputView raise.
+ ]
+! !
+
+!UISelectionPanel methodsFor:'change & update'!
+
+recomputeSizes
+ "recompute sizes dependent on list
+ "
+ |y x extent|
+
+ extent := tabView preferredExtent.
+ x := extent x.
+
+ x <= (self extent x) ifTrue:[
+ y := extent y.
+ ] ifFalse:[
+ y := tabView preferredHeight.
+ ].
+ y := y + 8.
+ tabView bottomInset:(y negated).
+ window topInset:y.
+
+
+!
+
+update:something with:aParameter from:changedObject
+ "tabView might change its size
+ "
+ (something == #preferredHeight and:[changedObject == tabView]) ifFalse:[
+ ^ self
+ ].
+ self recomputeSizes
+
+
+! !
+
+!UISelectionPanel methodsFor:'drag & drop'!
+
+startDrag
+ "start drag of selection
+ "
+ |dragObj spec|
+
+ spec := self findSpecFor:selection.
+
+ spec notNil ifTrue:[
+ spec := self buildSpecFrom:spec.
+
+ self showUnselected.
+ dragObj := DropSpecification for:selection specification:spec.
+ self showSelected.
+
+ DragAndDropManager startDrag:dragObj from:inputView.
+ ]
+
+! !
+
+!UISelectionPanel methodsFor:'event handling'!
+
+buttonMotion:state x:x y:y
+ "start a drag on selection
+ "
+ |obj sensor|
+
+ selection notNil ifTrue:[
+ sensor := self sensor.
+ sensor anyButtonPressed ifTrue:[
+ (lastClickPoint dist:(x@y)) > 10.0 ifTrue:[
+ self startDrag
+ ]
+ ]
+ ] ifFalse:[
+ obj := self findObjectAtX:x y:y.
+
+ obj notNil ifTrue:[
+ labelView label:obj name
+ ]
+ ].
+!
+
+buttonPress:button x:x y:y
+ "change selection
+ "
+ lastClickPoint := Point x:x y:y.
+ self selection:(self findObjectAtX:x y:y).
+
+
+!
+
+doesNotUnderstand:aMessage
+ "any event message not catched; discard message
+ "
+
+
+!
+
+exposeX:x y:y width:w height:h
+ "handle an expose event from device; redraw selection
+ "
+ super exposeX:x y:y width:w height:h.
+ self showSelected.
+
+! !
+
+!UISelectionPanel methodsFor:'initialization'!
+
+initialize
+ |y|
+
+ super initialize.
+ tabView := TabView origin:0.0@0.0 corner:1.0@0.0 in:self.
+ window := NoteBookFrameView origin:0.0@0.0 corner:1.0@1.0 in:self.
+ labelView := Label origin:0.0@1.0 corner:1.0@1.0 in:self.
+ inputView := InputView origin:0.0@0.0 extent:1.0@1.0 in:window.
+
+ y := labelView preferredExtent y.
+ window bottomInset:y.
+ labelView topInset:(y negated).
+
+ inputView eventReceiver:self.
+ inputView enableButtonEvents.
+ inputView enableButtonMotionEvents.
+ inputView enableMotionEvents.
+
+ tabView tabWidget:#Window.
+
+ tabView styleAt:#expandSelection put:6@2.
+ tabView styleAt:#labelBottomInset put:4.
+ tabView styleAt:#lableTopInset put:0.
+ tabView font:(Label defaultFont).
+ tabView addDependent:self.
+
+ window viewBackground:(tabView styleAt:#selectedColor).
+ labelView backgroundColor:(tabView styleAt:#unselectedColor).
+
+! !
+
+!UISelectionPanel methodsFor:'searching'!
+
+buildSpecFrom:aSpec
+ "build spec out of spec
+ "
+ |spec comp coll|
+
+ (aSpec notNil and:[aSpec canUIDrag]) ifFalse:[
+ ^ nil
+ ].
+
+ (aSpec class supportsSubComponents and:[aSpec component notNil]) ifFalse:[
+ ^ aSpec
+ ].
+ comp := aSpec component.
+ spec := aSpec copy.
+ spec component:nil.
+
+ comp canUIDrag ifFalse:[
+ ^ spec
+ ].
+ coll := OrderedCollection new.
+
+ comp do:[:anEntry||spc|
+ (spc := self buildSpecFrom:anEntry) notNil ifTrue:[
+ coll add:spc
+ ]
+ ].
+ coll isEmpty ifTrue:[
+ ^ spec
+ ].
+ comp := comp copy.
+ comp collection:coll.
+ spec component:comp.
+ ^ spec
+!
+
+findObjectAtX:x y:y
+ "find the origin/corner of the currentWidget
+ "
+ |view viewId point|
+
+ point := Point x:x y:y.
+ point := device translatePoint:point from:(inputView id)
+ to:(inputView device rootView id).
+ inputView lower.
+ viewId := device viewIdFromPoint:point in:(window id).
+ view := device viewFromId:viewId.
+ inputView raise.
+
+ (view ~~ window and:[view ~~ inputView]) ifTrue:[
+ (self findSpecFor:view) notNil ifTrue:[
+ ^ view
+ ]
+ ].
+ ^ nil
+
+
+!
+
+findSpecFor:anObject
+ "returns subspec assigned to instance or nil
+ "
+ |name components spec|
+
+ anObject notNil ifTrue:[
+ name := anObject name.
+
+ specification do:[:aSpec|
+ aSpec name = name ifTrue:[
+ aSpec canUIDrag ifTrue:[^ aSpec]
+ ifFalse:[^ nil]
+ ]
+ ]
+ ].
+ ^ nil
+
+! !
+
+!UISelectionPanel methodsFor:'selections'!
+
+handlesOf:aComponent do:aOneArgBlock
+ "evaluate the block on each handle; the argument to the block
+ is a rectangle
+ "
+ aComponent notNil ifTrue:[
+ aOneArgBlock value:(aComponent origin - (4@4) extent:7@7).
+ aOneArgBlock value:(aComponent corner - (4@4) extent:7@7).
+ aOneArgBlock value:(aComponent topRight - (4@4) extent:7@7).
+ aOneArgBlock value:(aComponent bottomLeft - (4@4) extent:7@7).
+ aOneArgBlock value:(aComponent leftCenter - (4@4) extent:7@7).
+ aOneArgBlock value:(aComponent rightCenter - (4@4) extent:7@7).
+ aOneArgBlock value:(aComponent topCenter - (4@4) extent:7@7).
+ aOneArgBlock value:(aComponent bottomCenter - (4@4) extent:7@7).
+ ]
+
+
+!
+
+selection:anObject
+ "selection changed
+ "
+ |spec|
+
+ selection ~~ anObject ifTrue:[
+ self showUnselected.
+ spec := self findSpecFor:anObject.
+
+ spec notNil ifTrue:[
+ selection := anObject.
+ self showSelected
+ ] ifFalse:[
+ selection := nil
+ ].
+
+ selection notNil ifTrue:[
+ labelView label:(selection name)
+ ]
+ ]
+
+!
+
+showSelected
+ "show selected
+ "
+ selection notNil ifTrue:[
+ window clippedByChildren:false.
+
+ self handlesOf:selection do:[:aRectangle|
+ window fillRectangle:aRectangle
+ ].
+ window clippedByChildren:true.
+ ].
+!
+
+showUnselected
+ "show unselected
+ "
+ |r|
+
+ selection isNil ifTrue:[
+ ^ self
+ ].
+
+ window clippedByChildren:false.
+
+ self handlesOf:selection do:[:aRectangle|
+ window clearRectangle:aRectangle
+ ].
+ window clippedByChildren:true.
+
+"must redraw all components which are affected b the handles
+"
+ r := (selection originRelativeTo:window) - (4@4) extent:(selection extent + (4@4)).
+
+ window subViews do:[:aComponent |
+ |absOrg absFrame|
+
+ aComponent ~~ inputView ifTrue:[
+ absOrg := aComponent originRelativeTo:window.
+ absFrame := absOrg extent:(aComponent extent).
+
+ (absFrame intersects:r) ifTrue:[
+ aComponent withAllSubViewsDo:[:aView|
+ aView clear.
+ aView exposeX:0 y:0 width:9999 height:9999.
+ ]
+ ]
+ ]
+ ]
+
+! !
+
+!UISelectionPanel::DropSpecification class methodsFor:'instance creation'!
+
+for:aView specification:aSpec
+ "create drop object for a view derived from a specification
+ "
+ aView topView raise.
+ aView device sync.
+ aView invalidate.
+ aView windowGroup processExposeEvents.
+ DisplayObject := Image fromView:aView grab:false.
+
+ DisplayObject extent ~= aView extent ifTrue:[
+ DisplayObject := Form extent:(aView extent) depth:1.
+ DisplayObject colorMap:(Array with:Color white with:Color black).
+ DisplayObject fill:(Color colorId:0).
+ DisplayObject paint:(Color colorId:1).
+ DisplayObject displayRectangleX:0 y:0 width:aView extent x height:aView extent y.
+ ].
+
+ ^ self new theObject:aSpec
+! !
+
+!UISelectionPanel class methodsFor:'documentation'!
+
+version
+ ^ '$Header$'
+! !