several undos
authortz
Tue, 21 Jul 1998 18:50:23 +0200
changeset 995 cd84d6f8c449
parent 994 5727c2484ecd
child 996 f3674765d8fb
several undos
ImageEditView.st
ImgEditV.st
--- a/ImageEditView.st	Tue Jul 21 13:26:39 1998 +0200
+++ b/ImageEditView.st	Tue Jul 21 18:50:23 1998 +0200
@@ -12,9 +12,9 @@
 
 ImageView subclass:#ImageEditView
 	instanceVariableNames:'magnification selectColors imageReaderClass resourceClass
-		resourceSelector mouseKeyColorMode undoImage modified
-		masterApplication editMode'
-	classVariableNames:'Clipboard GridMagnification'
+		resourceSelector mouseKeyColorMode undoImages modified
+		masterApplication editMode lastPastePoint'
+	classVariableNames:'Clipboard ClipboardMagnification GridMagnification MaxUndos'
 	poolDictionaries:''
 	category:'Views-Misc'
 !
@@ -64,7 +64,8 @@
         magnification := aPoint asPoint.
         self scrollToTopLeft.
         self contentsChanged.
-        self invalidate
+        self invalidate.
+        ClipboardMagnification := nil.
     ]
 !
 
@@ -137,6 +138,11 @@
 selectedColor: aColor
 
     selectColors at: mouseKeyColorMode put: aColor
+!
+
+undoImages
+
+   ^undoImages
 ! !
 
 !ImageEditView methodsFor:'drawing'!
@@ -307,32 +313,40 @@
     state ~~ 0
     ifTrue:
     [
-        self selectedColor notNil & image notNil & (self imageContainsPoint: x@y) & (editMode = 'point')
+        (self selectedColor notNil and: [(self imageContainsPoint: x@y) and: [editMode = 'point']])
             ifTrue: [^self pointAt: x@y]
+    ].
+    (state == 0 and: [editMode = 'paste'])
+    ifTrue:
+    [
+        (self selectedColor notNil and: [self imageContainsPastePoint: x@y]) 
+            ifTrue:  [self drawPasteRectangleAt: x@y]
+            ifFalse: [Cursor stop show. self releasePasteDrawing]
     ]
 !
 
 buttonPress:button x:x y:y
 
     self drawCursorAt: x@y.
-    self selectedColor notNil & image notNil & (self imageContainsPoint: x@y)
+    (self selectedColor notNil and: [self imageContainsPoint: x@y])
     ifTrue:
     [   
         |mouseButtonColorToolBar|
         mouseKeyColorMode := button.
         mouseButtonColorToolBar := masterApplication builder componentAt: #MouseButtonColorToolBar.
-        undoImage := image copy.
+        self makeUndo.
         masterApplication valueOfCanUndo value: true.
         (mouseButtonColorToolBar itemAt: mouseKeyColorMode) toggleIndication.
         mouseButtonColorToolBar do: [:i| i updateIndicators].
         self perform: (editMode, 'At:') asSymbol with: x@y
     ]
+
 !
 
 buttonRelease:button x:x y:y
 
     self drawCursorAt: x@y.
-    self selectedColor notNil & image notNil & (self imageContainsPoint: x@y)
+    (self selectedColor notNil and: [self imageContainsPoint: x@y])
     ifTrue:
     [   
         image restored.
@@ -345,7 +359,10 @@
     super pointerLeave: state.
 
     self drawLabel: self imageInfoString.
-    Cursor normal show
+    Cursor normal show.
+
+    editMode = 'paste' ifTrue: [self releasePasteDrawing]
+
 ! !
 
 !ImageEditView methodsFor:'image editing'!
@@ -365,6 +382,7 @@
 
     |choosedBox|
     choosedBox := self drawRectangleStartingAt: aPoint emphasis: #inverseFilledBox.
+    ClipboardMagnification := nil.
     Clipboard := image subImageIn: (choosedBox origin//magnification extent: (choosedBox extent//magnification)).
     self redraw: (choosedBox expandedBy: 1)    
 
@@ -404,12 +422,14 @@
 
 flipHorizontal
 
+    self makeUndo.
     self image: image copy flipHorizontal
 
 !
 
 flipVertical
 
+    self makeUndo.
     self image: image copy flipVertical
 
 !
@@ -426,26 +446,35 @@
     (box accepted and: [(newSize := Object readFromString: box contents onError:nil) notNil])
     ifTrue:
     [
+        self makeUndo.
         self image: (image magnifiedBy: newSize/image extent)
     ]
 !
 
 negativeImage
 
+    self makeUndo.
     self image: image copy negative
-
 !
 
 pasteAt: aPoint
 
+    ClipboardMagnification isNil ifTrue: [^self].
+
     Object errorSignal handle:
     [:ex|
-        self warn: 'Pasting at selected point failed!!\' withCRs, 'Exceed of paste extent or mismatch of color maps.'. 
+        self undo.
+        self warn: 'Pasting at selected point failed!!\' withCRs, 'An increase of image depth could help.'. 
     ] 
     do:
     [   
-        |imagePoint copiedImage imageBox presentClr|
-        imagePoint := aPoint//magnification.
+        |choosedBox imagePoint copiedImage imageBox presentClr|
+
+
+        choosedBox := self drawRectangleStartingAt: aPoint emphasis: #inverseFilledBox.
+
+        imagePoint := choosedBox origin//magnification.
+
         copiedImage := Clipboard copy.
 
         1 to: copiedImage colorMap size do: 
@@ -506,6 +535,7 @@
         ].
 
         newImage copyFrom:image x:0 y:0 toX:0 y:0 width: (image width min:newSize x) height: (image height min:newSize y).
+        self makeUndo.
         self image: newImage.
     ]
 !
@@ -527,6 +557,7 @@
         ] 
         do:
         [   
+            self makeUndo.
             self image: (image hardRotated: rotation)
         ]
     ]
@@ -534,13 +565,14 @@
 
 undo
 
-    undoImage notNil
+    undoImages notEmpty
     ifTrue:
     [           
-        modified := false.
-        self image: undoImage.
+        modified := false. 
+        self image: undoImages removeLast.
+        masterApplication listOfColors contents: image colorMap.
         masterApplication findColorMapMode.
-        masterApplication valueOfCanUndo value: false.
+        undoImages isEmpty ifTrue: [masterApplication valueOfCanUndo value: false].
         self invalidate
     ]
 ! !
@@ -611,6 +643,36 @@
     ]
 !
 
+drawPasteRectangleAt: aPoint
+
+    |currentPoint gridCorrection extent|
+
+    magnification > GridMagnification ifFalse: [gridCorrection := 0] ifTrue: [gridCorrection := 1].
+    currentPoint := aPoint//magnification*magnification + 1. 
+
+    currentPoint ~= lastPastePoint
+    ifTrue:
+    [             
+        ClipboardMagnification isNil ifTrue: [ClipboardMagnification := (Clipboard magnifiedBy: magnification) onDevice: image device].   
+
+        extent       := ClipboardMagnification extent.
+        self redraw: ((lastPastePoint ? currentPoint) extent: extent).
+
+        (extent x > 200 or: [extent y > 200])
+        ifTrue:
+        [
+            self xoring: [self fillRectangle: (currentPoint extent: extent)]
+        ]
+        ifFalse:
+        [
+            self displayDeviceForm: ClipboardMagnification x: currentPoint x y: currentPoint y
+        ]
+    ]. 
+    lastPastePoint := currentPoint.
+
+
+!
+
 drawRectangleStartingAt: aPoint emphasis: emphasis
 
     |currentPoint currentExtent firstPoint lastCurrentPoint gridCorrection p whichQuarter|
@@ -618,7 +680,7 @@
     magnification > GridMagnification ifFalse: [gridCorrection := 0] ifTrue: [gridCorrection := 1].
     [device anyButtonPressed]
     whileTrue:
-    [   
+    [  
         currentPoint := (0@0) max: (image extent * magnification min: (p := self translation negated + (device translatePoint: self sensor mousePoint from:device rootView id to:self id))).
         currentPoint := currentPoint//magnification*magnification.
         currentExtent := (firstPoint - currentPoint) abs.
@@ -634,7 +696,7 @@
             (currentExtent//magnification) printString, ')'.
 
         currentPoint ~= lastCurrentPoint ifTrue:
-        [          
+        [   
             emphasis = #inverseFilledBox
             ifTrue:
             [
@@ -660,7 +722,7 @@
                 extent := currentExtent - gridCorrection.
                 lineWidthY := extent y min: magnification y.
                 lineWidthX := extent x min: magnification x.
-                (lineWidthY > 0) & (lineWidthX > 0)
+                (lineWidthY > 0 and: [lineWidthX > 0])
                 ifTrue:
                 [
                     self fillRectangle: (origin extent: (extent x@lineWidthY)).
@@ -680,7 +742,7 @@
             ].
         ]. 
         lastCurrentPoint := currentPoint.
-    ].
+    ].                  
 
     ^((0@0) max: (firstPoint min: currentPoint)) extent: (firstPoint - currentPoint) abs
 ! !
@@ -696,11 +758,10 @@
         ifTrue:
         [
             |fileName|
-            undoImage := image.
             masterApplication notNil 
             ifTrue: 
             [
-                undoImage notNil ifTrue: [masterApplication valueOfCanUndo value: true].
+                undoImages notEmpty ifTrue: [masterApplication valueOfCanUndo value: true].
                 masterApplication imagePreView image: anImage
             ].
             image notNil
@@ -736,6 +797,7 @@
         (imageFromFile := Image fromFile: aFileName) notNil
         ifTrue:
         [
+            self releaseUndos.
             self image: imageFromFile. 
             imageReaderClass := ImageReader allSubclasses
                 detect: [:cls| cls isValidImageFile: aFileName]
@@ -773,6 +835,7 @@
     [aClass class implements: resourceSelector])
     ifTrue:
     [ 
+        self releaseUndos.
         ^self image: (aClass perform: resourceSelector) copy
     ]
     ifFalse:
@@ -790,12 +853,15 @@
     super initialize.
 
     self enableMotionEvents.
+
     GridMagnification := GridMagnification ? (8@8).
-    magnification := GridMagnification + 2.
-    modified := false.
+    MaxUndos          := MaxUndos ? 3.
+    undoImages        := OrderedCollection new: MaxUndos.
+    magnification     := GridMagnification + 2.
+    modified          := false.
     mouseKeyColorMode := 1.
-    resourceClass := resourceSelector := ''.
-    selectColors := Array with: nil with: nil.
+    resourceClass     := resourceSelector := ''.
+    selectColors      := Array with: nil with: nil.
 ! !
 
 !ImageEditView methodsFor:'printing & storing'!
@@ -813,6 +879,17 @@
 
 !
 
+makeUndo
+
+    image notNil
+    ifTrue:
+    [       
+        MaxUndos <= undoImages size
+            ifTrue:  [undoImages contents: (undoImages copyFrom: 2 to: MaxUndos)].
+        undoImages add: image copy
+    ]
+!
+
 print
 
     image notNil 
@@ -1003,6 +1080,13 @@
     ^(image height * magnification y) rounded
 !
 
+imageContainsPastePoint: aPoint
+
+    ^image notNil and: 
+        [Clipboard notNil and:
+        [((0@0 corner:(image extent) "- 1" - Clipboard extent) containsPoint: (((aPoint - margin + 1) / magnification) floor))]]
+!
+
 imageContainsPoint: aPoint
 
     ^image notNil and:
@@ -1034,10 +1118,26 @@
 
 destroy
 
-    Clipboard := undoImage := nil.
+    ClipboardMagnification := Clipboard.
 
     super destroy
 
+!
+
+releasePasteDrawing
+
+    (lastPastePoint notNil and: [ClipboardMagnification notNil]) 
+    ifTrue: 
+    [ 
+        self redraw: (lastPastePoint extent: (ClipboardMagnification extent)). 
+    ].
+    lastPastePoint := ClipboardMagnification := nil
+!
+
+releaseUndos
+
+    undoImages removeAll.
+    masterApplication valueOfCanUndo value: false.
 ! !
 
 !ImageEditView methodsFor:'testing'!
@@ -1060,5 +1160,5 @@
 !ImageEditView class methodsFor:'documentation'!
 
 version
-    ^ '$Header: /cvs/stx/stx/libwidg2/ImageEditView.st,v 1.77 1998-07-21 11:26:39 tz Exp $'
+    ^ '$Header: /cvs/stx/stx/libwidg2/ImageEditView.st,v 1.78 1998-07-21 16:50:23 tz Exp $'
 ! !
--- a/ImgEditV.st	Tue Jul 21 13:26:39 1998 +0200
+++ b/ImgEditV.st	Tue Jul 21 18:50:23 1998 +0200
@@ -12,9 +12,9 @@
 
 ImageView subclass:#ImageEditView
 	instanceVariableNames:'magnification selectColors imageReaderClass resourceClass
-		resourceSelector mouseKeyColorMode undoImage modified
-		masterApplication editMode'
-	classVariableNames:'Clipboard GridMagnification'
+		resourceSelector mouseKeyColorMode undoImages modified
+		masterApplication editMode lastPastePoint'
+	classVariableNames:'Clipboard ClipboardMagnification GridMagnification MaxUndos'
 	poolDictionaries:''
 	category:'Views-Misc'
 !
@@ -64,7 +64,8 @@
         magnification := aPoint asPoint.
         self scrollToTopLeft.
         self contentsChanged.
-        self invalidate
+        self invalidate.
+        ClipboardMagnification := nil.
     ]
 !
 
@@ -137,6 +138,11 @@
 selectedColor: aColor
 
     selectColors at: mouseKeyColorMode put: aColor
+!
+
+undoImages
+
+   ^undoImages
 ! !
 
 !ImageEditView methodsFor:'drawing'!
@@ -307,32 +313,40 @@
     state ~~ 0
     ifTrue:
     [
-        self selectedColor notNil & image notNil & (self imageContainsPoint: x@y) & (editMode = 'point')
+        (self selectedColor notNil and: [(self imageContainsPoint: x@y) and: [editMode = 'point']])
             ifTrue: [^self pointAt: x@y]
+    ].
+    (state == 0 and: [editMode = 'paste'])
+    ifTrue:
+    [
+        (self selectedColor notNil and: [self imageContainsPastePoint: x@y]) 
+            ifTrue:  [self drawPasteRectangleAt: x@y]
+            ifFalse: [Cursor stop show. self releasePasteDrawing]
     ]
 !
 
 buttonPress:button x:x y:y
 
     self drawCursorAt: x@y.
-    self selectedColor notNil & image notNil & (self imageContainsPoint: x@y)
+    (self selectedColor notNil and: [self imageContainsPoint: x@y])
     ifTrue:
     [   
         |mouseButtonColorToolBar|
         mouseKeyColorMode := button.
         mouseButtonColorToolBar := masterApplication builder componentAt: #MouseButtonColorToolBar.
-        undoImage := image copy.
+        self makeUndo.
         masterApplication valueOfCanUndo value: true.
         (mouseButtonColorToolBar itemAt: mouseKeyColorMode) toggleIndication.
         mouseButtonColorToolBar do: [:i| i updateIndicators].
         self perform: (editMode, 'At:') asSymbol with: x@y
     ]
+
 !
 
 buttonRelease:button x:x y:y
 
     self drawCursorAt: x@y.
-    self selectedColor notNil & image notNil & (self imageContainsPoint: x@y)
+    (self selectedColor notNil and: [self imageContainsPoint: x@y])
     ifTrue:
     [   
         image restored.
@@ -345,7 +359,10 @@
     super pointerLeave: state.
 
     self drawLabel: self imageInfoString.
-    Cursor normal show
+    Cursor normal show.
+
+    editMode = 'paste' ifTrue: [self releasePasteDrawing]
+
 ! !
 
 !ImageEditView methodsFor:'image editing'!
@@ -365,6 +382,7 @@
 
     |choosedBox|
     choosedBox := self drawRectangleStartingAt: aPoint emphasis: #inverseFilledBox.
+    ClipboardMagnification := nil.
     Clipboard := image subImageIn: (choosedBox origin//magnification extent: (choosedBox extent//magnification)).
     self redraw: (choosedBox expandedBy: 1)    
 
@@ -404,12 +422,14 @@
 
 flipHorizontal
 
+    self makeUndo.
     self image: image copy flipHorizontal
 
 !
 
 flipVertical
 
+    self makeUndo.
     self image: image copy flipVertical
 
 !
@@ -426,26 +446,35 @@
     (box accepted and: [(newSize := Object readFromString: box contents onError:nil) notNil])
     ifTrue:
     [
+        self makeUndo.
         self image: (image magnifiedBy: newSize/image extent)
     ]
 !
 
 negativeImage
 
+    self makeUndo.
     self image: image copy negative
-
 !
 
 pasteAt: aPoint
 
+    ClipboardMagnification isNil ifTrue: [^self].
+
     Object errorSignal handle:
     [:ex|
-        self warn: 'Pasting at selected point failed!!\' withCRs, 'Exceed of paste extent or mismatch of color maps.'. 
+        self undo.
+        self warn: 'Pasting at selected point failed!!\' withCRs, 'An increase of image depth could help.'. 
     ] 
     do:
     [   
-        |imagePoint copiedImage imageBox presentClr|
-        imagePoint := aPoint//magnification.
+        |choosedBox imagePoint copiedImage imageBox presentClr|
+
+
+        choosedBox := self drawRectangleStartingAt: aPoint emphasis: #inverseFilledBox.
+
+        imagePoint := choosedBox origin//magnification.
+
         copiedImage := Clipboard copy.
 
         1 to: copiedImage colorMap size do: 
@@ -506,6 +535,7 @@
         ].
 
         newImage copyFrom:image x:0 y:0 toX:0 y:0 width: (image width min:newSize x) height: (image height min:newSize y).
+        self makeUndo.
         self image: newImage.
     ]
 !
@@ -527,6 +557,7 @@
         ] 
         do:
         [   
+            self makeUndo.
             self image: (image hardRotated: rotation)
         ]
     ]
@@ -534,13 +565,14 @@
 
 undo
 
-    undoImage notNil
+    undoImages notEmpty
     ifTrue:
     [           
-        modified := false.
-        self image: undoImage.
+        modified := false. 
+        self image: undoImages removeLast.
+        masterApplication listOfColors contents: image colorMap.
         masterApplication findColorMapMode.
-        masterApplication valueOfCanUndo value: false.
+        undoImages isEmpty ifTrue: [masterApplication valueOfCanUndo value: false].
         self invalidate
     ]
 ! !
@@ -611,6 +643,36 @@
     ]
 !
 
+drawPasteRectangleAt: aPoint
+
+    |currentPoint gridCorrection extent|
+
+    magnification > GridMagnification ifFalse: [gridCorrection := 0] ifTrue: [gridCorrection := 1].
+    currentPoint := aPoint//magnification*magnification + 1. 
+
+    currentPoint ~= lastPastePoint
+    ifTrue:
+    [             
+        ClipboardMagnification isNil ifTrue: [ClipboardMagnification := (Clipboard magnifiedBy: magnification) onDevice: image device].   
+
+        extent       := ClipboardMagnification extent.
+        self redraw: ((lastPastePoint ? currentPoint) extent: extent).
+
+        (extent x > 200 or: [extent y > 200])
+        ifTrue:
+        [
+            self xoring: [self fillRectangle: (currentPoint extent: extent)]
+        ]
+        ifFalse:
+        [
+            self displayDeviceForm: ClipboardMagnification x: currentPoint x y: currentPoint y
+        ]
+    ]. 
+    lastPastePoint := currentPoint.
+
+
+!
+
 drawRectangleStartingAt: aPoint emphasis: emphasis
 
     |currentPoint currentExtent firstPoint lastCurrentPoint gridCorrection p whichQuarter|
@@ -618,7 +680,7 @@
     magnification > GridMagnification ifFalse: [gridCorrection := 0] ifTrue: [gridCorrection := 1].
     [device anyButtonPressed]
     whileTrue:
-    [   
+    [  
         currentPoint := (0@0) max: (image extent * magnification min: (p := self translation negated + (device translatePoint: self sensor mousePoint from:device rootView id to:self id))).
         currentPoint := currentPoint//magnification*magnification.
         currentExtent := (firstPoint - currentPoint) abs.
@@ -634,7 +696,7 @@
             (currentExtent//magnification) printString, ')'.
 
         currentPoint ~= lastCurrentPoint ifTrue:
-        [          
+        [   
             emphasis = #inverseFilledBox
             ifTrue:
             [
@@ -660,7 +722,7 @@
                 extent := currentExtent - gridCorrection.
                 lineWidthY := extent y min: magnification y.
                 lineWidthX := extent x min: magnification x.
-                (lineWidthY > 0) & (lineWidthX > 0)
+                (lineWidthY > 0 and: [lineWidthX > 0])
                 ifTrue:
                 [
                     self fillRectangle: (origin extent: (extent x@lineWidthY)).
@@ -680,7 +742,7 @@
             ].
         ]. 
         lastCurrentPoint := currentPoint.
-    ].
+    ].                  
 
     ^((0@0) max: (firstPoint min: currentPoint)) extent: (firstPoint - currentPoint) abs
 ! !
@@ -696,11 +758,10 @@
         ifTrue:
         [
             |fileName|
-            undoImage := image.
             masterApplication notNil 
             ifTrue: 
             [
-                undoImage notNil ifTrue: [masterApplication valueOfCanUndo value: true].
+                undoImages notEmpty ifTrue: [masterApplication valueOfCanUndo value: true].
                 masterApplication imagePreView image: anImage
             ].
             image notNil
@@ -736,6 +797,7 @@
         (imageFromFile := Image fromFile: aFileName) notNil
         ifTrue:
         [
+            self releaseUndos.
             self image: imageFromFile. 
             imageReaderClass := ImageReader allSubclasses
                 detect: [:cls| cls isValidImageFile: aFileName]
@@ -773,6 +835,7 @@
     [aClass class implements: resourceSelector])
     ifTrue:
     [ 
+        self releaseUndos.
         ^self image: (aClass perform: resourceSelector) copy
     ]
     ifFalse:
@@ -790,12 +853,15 @@
     super initialize.
 
     self enableMotionEvents.
+
     GridMagnification := GridMagnification ? (8@8).
-    magnification := GridMagnification + 2.
-    modified := false.
+    MaxUndos          := MaxUndos ? 3.
+    undoImages        := OrderedCollection new: MaxUndos.
+    magnification     := GridMagnification + 2.
+    modified          := false.
     mouseKeyColorMode := 1.
-    resourceClass := resourceSelector := ''.
-    selectColors := Array with: nil with: nil.
+    resourceClass     := resourceSelector := ''.
+    selectColors      := Array with: nil with: nil.
 ! !
 
 !ImageEditView methodsFor:'printing & storing'!
@@ -813,6 +879,17 @@
 
 !
 
+makeUndo
+
+    image notNil
+    ifTrue:
+    [       
+        MaxUndos <= undoImages size
+            ifTrue:  [undoImages contents: (undoImages copyFrom: 2 to: MaxUndos)].
+        undoImages add: image copy
+    ]
+!
+
 print
 
     image notNil 
@@ -1003,6 +1080,13 @@
     ^(image height * magnification y) rounded
 !
 
+imageContainsPastePoint: aPoint
+
+    ^image notNil and: 
+        [Clipboard notNil and:
+        [((0@0 corner:(image extent) "- 1" - Clipboard extent) containsPoint: (((aPoint - margin + 1) / magnification) floor))]]
+!
+
 imageContainsPoint: aPoint
 
     ^image notNil and:
@@ -1034,10 +1118,26 @@
 
 destroy
 
-    Clipboard := undoImage := nil.
+    ClipboardMagnification := Clipboard.
 
     super destroy
 
+!
+
+releasePasteDrawing
+
+    (lastPastePoint notNil and: [ClipboardMagnification notNil]) 
+    ifTrue: 
+    [ 
+        self redraw: (lastPastePoint extent: (ClipboardMagnification extent)). 
+    ].
+    lastPastePoint := ClipboardMagnification := nil
+!
+
+releaseUndos
+
+    undoImages removeAll.
+    masterApplication valueOfCanUndo value: false.
 ! !
 
 !ImageEditView methodsFor:'testing'!
@@ -1060,5 +1160,5 @@
 !ImageEditView class methodsFor:'documentation'!
 
 version
-    ^ '$Header: /cvs/stx/stx/libwidg2/Attic/ImgEditV.st,v 1.77 1998-07-21 11:26:39 tz Exp $'
+    ^ '$Header: /cvs/stx/stx/libwidg2/Attic/ImgEditV.st,v 1.78 1998-07-21 16:50:23 tz Exp $'
 ! !