Christoph Thiede uploaded a new version of Morphic to project The Inbox: http://source.squeak.org/inbox/Morphic-ct.2125.mcz
==================== Summary ====================
Name: Morphic-ct.2125 Author: ct Time: 27 August 2023, 4:39:22.523324 pm UUID: 610cd311-cf21-c844-a7da-678a093aee91 Ancestors: Morphic-ct.2124
Revises #insertTextReplacement proposal for PluggableTextMorph by moving the insertion logic to TextEditor. Indeed an ancestor of Morphic-ct.2124.
=============== Diff against Morphic-ct.2124 ===============
Item was changed: ----- Method: PluggableTextMorph>>insertText:from:to:invisibly: (in category 'transcript') ----- insertText: newText from: start to: stop invisibly: invisibly
+ invisibly + ifTrue: [ + textMorph editor insertText: newText from: start to: stop invisibly: invisibly. + textMorph selectionChanged. + textMorph updateFromParagraph. + self rememberSelectionInterval] + ifFalse: [self handleEdit: [ + textMorph editor insertText: newText from: start to: stop invisibly: invisibly]]. - | priorSelection priorHadUnacceptedEdits | - priorSelection := self selectionInterval. - self selectInvisiblyFrom: start to: stop. - priorHadUnacceptedEdits := self hasUnacceptedEdits. - textMorph editor restoreEmphasisHereAfter: [ - textMorph editor setEmphasisHere. - self replaceSelectionWith: newText]. - - invisibly ifFalse: [^ self]. - - "cover all our tracks" - self hasUnacceptedEdits: priorHadUnacceptedEdits. - - "Restore previous selection. Also update it if behind insertion." - priorSelection start >= start ifTrue: [ - priorSelection := priorSelection start + newText size - (stop - start) - 1 to: priorSelection stop]. - priorSelection stop >= start ifTrue: [ - priorSelection := priorSelection start to: priorSelection stop + newText size - (stop - start) - 1]. - self selectInvisiblyFrom: priorSelection start to: priorSelection stop. - textMorph selectionChanged. - textMorph updateFromParagraph. - self rememberSelectionInterval. - self flag: #todo. "Also preserve scroll position (which is NOT identical to the selection), so that insertions at the beginning do not interrupt the user further down in the text. This is rarely visible to the user, but should ultimately be done."!
Item was added: + ----- Method: TextEditor>>insertText:from:to:invisibly: (in category 'accessing') ----- + insertText: newText from: start to: stop invisibly: invisibly + + | priorSelection | + priorSelection := self selectionInterval. + self selectInvisiblyFrom: start to: stop. + + self restoreEmphasisHereAfter: [ + self setEmphasisHere. + self replaceSelectionWith: newText invisibly: invisibly]. + + invisibly ifFalse: [^ self]. + + "Restore previous selection. Also update it if behind insertion." + priorSelection start >= start ifTrue: [ + priorSelection := priorSelection start + newText size - (stop - start) - 1 to: priorSelection stop]. + priorSelection stop >= start ifTrue: [ + priorSelection := priorSelection start to: priorSelection stop + newText size - (stop - start) - 1]. + self selectInvisiblyFrom: priorSelection start to: priorSelection stop.!
Item was changed: ----- Method: TextEditor>>replaceSelectionWith: (in category 'undo') ----- replaceSelectionWith: aText - "Remember the selection text in UndoSelection. - Deselect, and replace the selection text by aText. - Remember the resulting selectionInterval in UndoInterval and PriorInterval. - Set up undo to use UndoReplace."
+ ^ self replaceSelectionWith: aText invisibly: false! - self openTypeIn. - self zapSelectionWith: aText. - self closeTypeIn.!
Item was added: + ----- Method: TextEditor>>replaceSelectionWith:invisibly: (in category 'undo') ----- + replaceSelectionWith: aText invisibly: invisibly + "Remember the selection text in UndoSelection. + Deselect, and replace the selection text by aText. + Remember the resulting selectionInterval in UndoInterval and PriorInterval. + Set up undo to use UndoReplace. + Unless invisibly, notify the text morph about the change." + + self openTypeIn. + self zapSelectionWith: aText invisibly: invisibly. + self closeTypeIn.!
Item was changed: ----- Method: TextEditor>>zapSelectionWith: (in category 'mvc compatibility') ----- zapSelectionWith: replacement
+ ^ self zapSelectionWith: replacement invisibly: false! - | start stop rep | - morph readOnly ifTrue: [^ self]. - start := self startIndex. - stop := self stopIndex. - (replacement isEmpty and: [stop > start]) ifTrue: [ - "If deleting, then set emphasisHere from 1st character of the deletion" - emphasisHere := (self text attributesAt: start) select: [:att | att mayBeExtended]]. - (start = stop and: [ replacement isEmpty ]) ifFalse: [ - morph plainTextOnly - ifTrue: [ - "We support TextAlignment but nothing else. Rely on emphasisHere." - rep := Text string: replacement asString attributes: emphasisHere ] - ifFalse: [ replacement isText - ifTrue: [ rep := replacement] - ifFalse: [ rep := Text string: replacement attributes: emphasisHere ] ]. - - self text replaceFrom: start to: stop - 1 with: rep. - paragraph - recomposeFrom: start - to: start + rep size - 1 - delta: rep size - (stop-start). - self markIndex: start pointIndex: start + rep size. - otherInterval := self selectionInterval]. - - self userHasEdited " -- note text now dirty"!
Item was added: + ----- Method: TextEditor>>zapSelectionWith:invisibly: (in category 'mvc compatibility') ----- + zapSelectionWith: replacement invisibly: invisibly + + | start stop rep | + morph readOnly ifTrue: [^ self]. + start := self startIndex. + stop := self stopIndex. + (replacement isEmpty and: [stop > start]) ifTrue: [ + "If deleting, then set emphasisHere from 1st character of the deletion" + emphasisHere := (self text attributesAt: start) select: [:att | att mayBeExtended]]. + (start = stop and: [ replacement isEmpty ]) ifFalse: [ + morph plainTextOnly + ifTrue: [ + "We support TextAlignment but nothing else. Rely on emphasisHere." + rep := Text string: replacement asString attributes: emphasisHere ] + ifFalse: [ replacement isText + ifTrue: [ rep := replacement] + ifFalse: [ rep := Text string: replacement attributes: emphasisHere ] ]. + + self text replaceFrom: start to: stop - 1 with: rep. + paragraph + recomposeFrom: start + to: start + rep size - 1 + delta: rep size - (stop-start). + self markIndex: start pointIndex: start + rep size. + otherInterval := self selectionInterval]. + + invisibly ifFalse: [ + self userHasEdited " -- note text now dirty"].!
Hi Christoph --
Hmm... -0.5 :-)
Is there really a need for expanding the #replaceSelectionWith: and #zapSelectionWith: interfaces with that "invisibly:" option? I would just handle that in that new #insertText:from:to:invisibly:. Hmm...
Yet, if you think this is okay, go ahead and merge it. Please double-check (conceptual) compatibility with text undo.
Best, Marcel
Am 27.08.2023 16:39:48 schrieb commits@source.squeak.org commits@source.squeak.org: Christoph Thiede uploaded a new version of Morphic to project The Inbox: http://source.squeak.org/inbox/Morphic-ct.2125.mcz
==================== Summary ====================
Name: Morphic-ct.2125 Author: ct Time: 27 August 2023, 4:39:22.523324 pm UUID: 610cd311-cf21-c844-a7da-678a093aee91 Ancestors: Morphic-ct.2124
Revises #insertTextReplacement proposal for PluggableTextMorph by moving the insertion logic to TextEditor. Indeed an ancestor of Morphic-ct.2124.
=============== Diff against Morphic-ct.2124 ===============
Item was changed: ----- Method: PluggableTextMorph>>insertText:from:to:invisibly: (in category 'transcript') ----- insertText: newText from: start to: stop invisibly: invisibly
+ invisibly + ifTrue: [ + textMorph editor insertText: newText from: start to: stop invisibly: invisibly. + textMorph selectionChanged. + textMorph updateFromParagraph. + self rememberSelectionInterval] + ifFalse: [self handleEdit: [ + textMorph editor insertText: newText from: start to: stop invisibly: invisibly]]. - | priorSelection priorHadUnacceptedEdits | - priorSelection := self selectionInterval. - self selectInvisiblyFrom: start to: stop.
- priorHadUnacceptedEdits := self hasUnacceptedEdits. - textMorph editor restoreEmphasisHereAfter: [ - textMorph editor setEmphasisHere. - self replaceSelectionWith: newText]. - - invisibly ifFalse: [^ self]. - - "cover all our tracks" - self hasUnacceptedEdits: priorHadUnacceptedEdits. - - "Restore previous selection. Also update it if behind insertion." - priorSelection start >= start ifTrue: [ - priorSelection := priorSelection start + newText size - (stop - start) - 1 to: priorSelection stop]. - priorSelection stop >= start ifTrue: [ - priorSelection := priorSelection start to: priorSelection stop + newText size - (stop - start) - 1]. - self selectInvisiblyFrom: priorSelection start to: priorSelection stop. - textMorph selectionChanged. - textMorph updateFromParagraph. - self rememberSelectionInterval. - self flag: #todo. "Also preserve scroll position (which is NOT identical to the selection), so that insertions at the beginning do not interrupt the user further down in the text. This is rarely visible to the user, but should ultimately be done."!
Item was added: + ----- Method: TextEditor>>insertText:from:to:invisibly: (in category 'accessing') ----- + insertText: newText from: start to: stop invisibly: invisibly + + | priorSelection | + priorSelection := self selectionInterval. + self selectInvisiblyFrom: start to: stop. + + self restoreEmphasisHereAfter: [ + self setEmphasisHere. + self replaceSelectionWith: newText invisibly: invisibly]. + + invisibly ifFalse: [^ self]. + + "Restore previous selection. Also update it if behind insertion." + priorSelection start >= start ifTrue: [ + priorSelection := priorSelection start + newText size - (stop - start) - 1 to: priorSelection stop]. + priorSelection stop >= start ifTrue: [ + priorSelection := priorSelection start to: priorSelection stop + newText size - (stop - start) - 1]. + self selectInvisiblyFrom: priorSelection start to: priorSelection stop.!
Item was changed: ----- Method: TextEditor>>replaceSelectionWith: (in category 'undo') ----- replaceSelectionWith: aText - "Remember the selection text in UndoSelection. - Deselect, and replace the selection text by aText. - Remember the resulting selectionInterval in UndoInterval and PriorInterval. - Set up undo to use UndoReplace."
+ ^ self replaceSelectionWith: aText invisibly: false! - self openTypeIn. - self zapSelectionWith: aText. - self closeTypeIn.!
Item was added: + ----- Method: TextEditor>>replaceSelectionWith:invisibly: (in category 'undo') ----- + replaceSelectionWith: aText invisibly: invisibly + "Remember the selection text in UndoSelection. + Deselect, and replace the selection text by aText. + Remember the resulting selectionInterval in UndoInterval and PriorInterval. + Set up undo to use UndoReplace. + Unless invisibly, notify the text morph about the change." + + self openTypeIn. + self zapSelectionWith: aText invisibly: invisibly. + self closeTypeIn.!
Item was changed: ----- Method: TextEditor>>zapSelectionWith: (in category 'mvc compatibility') ----- zapSelectionWith: replacement
+ ^ self zapSelectionWith: replacement invisibly: false! - | start stop rep | - morph readOnly ifTrue: [^ self]. - start := self startIndex. - stop := self stopIndex. - (replacement isEmpty and: [stop > start]) ifTrue: [ - "If deleting, then set emphasisHere from 1st character of the deletion" - emphasisHere := (self text attributesAt: start) select: [:att | att mayBeExtended]]. - (start = stop and: [ replacement isEmpty ]) ifFalse: [ - morph plainTextOnly - ifTrue: [ - "We support TextAlignment but nothing else. Rely on emphasisHere." - rep := Text string: replacement asString attributes: emphasisHere ] - ifFalse: [ replacement isText - ifTrue: [ rep := replacement] - ifFalse: [ rep := Text string: replacement attributes: emphasisHere ] ]. - - self text replaceFrom: start to: stop - 1 with: rep. - paragraph - recomposeFrom: start - to: start + rep size - 1 - delta: rep size - (stop-start). - self markIndex: start pointIndex: start + rep size. - otherInterval := self selectionInterval]. - - self userHasEdited " -- note text now dirty"!
Item was added: + ----- Method: TextEditor>>zapSelectionWith:invisibly: (in category 'mvc compatibility') ----- + zapSelectionWith: replacement invisibly: invisibly + + | start stop rep | + morph readOnly ifTrue: [^ self]. + start := self startIndex. + stop := self stopIndex. + (replacement isEmpty and: [stop > start]) ifTrue: [ + "If deleting, then set emphasisHere from 1st character of the deletion" + emphasisHere := (self text attributesAt: start) select: [:att | att mayBeExtended]]. + (start = stop and: [ replacement isEmpty ]) ifFalse: [ + morph plainTextOnly + ifTrue: [ + "We support TextAlignment but nothing else. Rely on emphasisHere." + rep := Text string: replacement asString attributes: emphasisHere ] + ifFalse: [ replacement isText + ifTrue: [ rep := replacement] + ifFalse: [ rep := Text string: replacement attributes: emphasisHere ] ]. + + self text replaceFrom: start to: stop - 1 with: rep. + paragraph + recomposeFrom: start + to: start + rep size - 1 + delta: rep size - (stop-start). + self markIndex: start pointIndex: start + rep size. + otherInterval := self selectionInterval]. + + invisibly ifFalse: [ + self userHasEdited " -- note text now dirty"].!
Hi Marcel,
thanks for the feedback! How would Morphic-ct.2127 look to you? :-)
Best, Christoph
--- Sent from Squeak Inbox Talk
On 2023-08-28T17:22:58+02:00, marcel.taeumel@hpi.de wrote:
Hi Christoph --
Hmm... -0.5 :-)
Is there really a need for expanding the #replaceSelectionWith: and #zapSelectionWith: interfaces with that "invisibly:" option? I would just handle that in that new #insertText:from:to:invisibly:. Hmm...
Yet, if you think this is okay, go ahead and merge it. Please double-check (conceptual) compatibility with text undo.
Best, Marcel
Am 27.08.2023 16:39:48 schrieb commits(a)source.squeak.org <commits(a)source.squeak.org>: Christoph Thiede uploaded a new version of Morphic to project The Inbox: http://source.squeak.org/inbox/Morphic-ct.2125.mcz
==================== Summary ====================
Name: Morphic-ct.2125 Author: ct Time: 27 August 2023, 4:39:22.523324 pm UUID: 610cd311-cf21-c844-a7da-678a093aee91 Ancestors: Morphic-ct.2124
Revises #insertTextReplacement proposal for PluggableTextMorph by moving the insertion logic to TextEditor. Indeed an ancestor of Morphic-ct.2124.
=============== Diff against Morphic-ct.2124 ===============
Item was changed: ----- Method: PluggableTextMorph>>insertText:from:to:invisibly: (in category 'transcript') ----- insertText: newText from: start to: stop invisibly: invisibly
- invisibly
- ifTrue: [
- textMorph editor insertText: newText from: start to: stop invisibly: invisibly.
- textMorph selectionChanged.
- textMorph updateFromParagraph.
- self rememberSelectionInterval]
- ifFalse: [self handleEdit: [
- textMorph editor insertText: newText from: start to: stop invisibly: invisibly]].
| priorSelection priorHadUnacceptedEdits |
priorSelection := self selectionInterval.
self selectInvisiblyFrom: start to: stop.
priorHadUnacceptedEdits := self hasUnacceptedEdits.
textMorph editor restoreEmphasisHereAfter: [
textMorph editor setEmphasisHere.
self replaceSelectionWith: newText].
invisibly ifFalse: [^ self].
"cover all our tracks"
self hasUnacceptedEdits: priorHadUnacceptedEdits.
"Restore previous selection. Also update it if behind insertion."
priorSelection start >= start ifTrue: [
priorSelection := priorSelection start + newText size - (stop - start) - 1 to: priorSelection stop].
priorSelection stop >= start ifTrue: [
priorSelection := priorSelection start to: priorSelection stop + newText size - (stop - start) - 1].
self selectInvisiblyFrom: priorSelection start to: priorSelection stop.
textMorph selectionChanged.
textMorph updateFromParagraph.
self rememberSelectionInterval.
self flag: #todo. "Also preserve scroll position (which is NOT identical to the selection), so that insertions at the beginning do not interrupt the user further down in the text. This is rarely visible to the user, but should ultimately be done."!
Item was added:
- ----- Method: TextEditor>>insertText:from:to:invisibly: (in category 'accessing') -----
- insertText: newText from: start to: stop invisibly: invisibly
- | priorSelection |
- priorSelection := self selectionInterval.
- self selectInvisiblyFrom: start to: stop.
- self restoreEmphasisHereAfter: [
- self setEmphasisHere.
- self replaceSelectionWith: newText invisibly: invisibly].
- invisibly ifFalse: [^ self].
- "Restore previous selection. Also update it if behind insertion."
- priorSelection start >= start ifTrue: [
- priorSelection := priorSelection start + newText size - (stop - start) - 1 to: priorSelection stop].
- priorSelection stop >= start ifTrue: [
- priorSelection := priorSelection start to: priorSelection stop + newText size - (stop - start) - 1].
- self selectInvisiblyFrom: priorSelection start to: priorSelection stop.!
Item was changed: ----- Method: TextEditor>>replaceSelectionWith: (in category 'undo') ----- replaceSelectionWith: aText
- "Remember the selection text in UndoSelection.
- Deselect, and replace the selection text by aText.
- Remember the resulting selectionInterval in UndoInterval and PriorInterval.
- Set up undo to use UndoReplace."
- ^ self replaceSelectionWith: aText invisibly: false!
- self openTypeIn.
- self zapSelectionWith: aText.
- self closeTypeIn.!
Item was added:
- ----- Method: TextEditor>>replaceSelectionWith:invisibly: (in category 'undo') -----
- replaceSelectionWith: aText invisibly: invisibly
- "Remember the selection text in UndoSelection.
- Deselect, and replace the selection text by aText.
- Remember the resulting selectionInterval in UndoInterval and PriorInterval.
- Set up undo to use UndoReplace.
- Unless invisibly, notify the text morph about the change."
- self openTypeIn.
- self zapSelectionWith: aText invisibly: invisibly.
- self closeTypeIn.!
Item was changed: ----- Method: TextEditor>>zapSelectionWith: (in category 'mvc compatibility') ----- zapSelectionWith: replacement
- ^ self zapSelectionWith: replacement invisibly: false!
- | start stop rep |
- morph readOnly ifTrue: [^ self].
- start := self startIndex.
- stop := self stopIndex.
- (replacement isEmpty and: [stop > start]) ifTrue: [
- "If deleting, then set emphasisHere from 1st character of the deletion"
- emphasisHere := (self text attributesAt: start) select: [:att | att mayBeExtended]].
- (start = stop and: [ replacement isEmpty ]) ifFalse: [
- morph plainTextOnly
- ifTrue: [
- "We support TextAlignment but nothing else. Rely on emphasisHere."
- rep := Text string: replacement asString attributes: emphasisHere ]
- ifFalse: [ replacement isText
- ifTrue: [ rep := replacement]
- ifFalse: [ rep := Text string: replacement attributes: emphasisHere ] ].
- self text replaceFrom: start to: stop - 1 with: rep.
- paragraph
- recomposeFrom: start
- to: start + rep size - 1
- delta: rep size - (stop-start).
- self markIndex: start pointIndex: start + rep size.
- otherInterval := self selectionInterval].
- self userHasEdited " -- note text now dirty"!
Item was added:
- ----- Method: TextEditor>>zapSelectionWith:invisibly: (in category 'mvc compatibility') -----
- zapSelectionWith: replacement invisibly: invisibly
- | start stop rep |
- morph readOnly ifTrue: [^ self].
- start := self startIndex.
- stop := self stopIndex.
- (replacement isEmpty and: [stop > start]) ifTrue: [
- "If deleting, then set emphasisHere from 1st character of the deletion"
- emphasisHere := (self text attributesAt: start) select: [:att | att mayBeExtended]].
- (start = stop and: [ replacement isEmpty ]) ifFalse: [
- morph plainTextOnly
- ifTrue: [
- "We support TextAlignment but nothing else. Rely on emphasisHere."
- rep := Text string: replacement asString attributes: emphasisHere ]
- ifFalse: [ replacement isText
- ifTrue: [ rep := replacement]
- ifFalse: [ rep := Text string: replacement attributes: emphasisHere ] ].
- self text replaceFrom: start to: stop - 1 with: rep.
- paragraph
- recomposeFrom: start
- to: start + rep size - 1
- delta: rep size - (stop-start).
- self markIndex: start pointIndex: start + rep size.
- otherInterval := self selectionInterval].
- invisibly ifFalse: [
- self userHasEdited " -- note text now dirty"].!
squeak-dev@lists.squeakfoundation.org