The Inbox: Morphic-cmm.1615.mcz

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
3 messages Options
Reply | Threaded
Open this post in threaded view
|

The Inbox: Morphic-cmm.1615.mcz

commits-2
Chris Muller uploaded a new version of Morphic to project The Inbox:
http://source.squeak.org/inbox/Morphic-cmm.1615.mcz

==================== Summary ====================

Name: Morphic-cmm.1615
Author: cmm
Time: 2 January 2020, 3:55:29.150586 pm
UUID: a6947cb4-e842-49ca-a8db-56b7f9f3241a
Ancestors: Morphic-mt.1612

When a text selection cannot fit into its text pane, show its upper-left, rather than its lower-right, so stepping through code in a small window is possible.

=============== Diff against Morphic-mt.1612 ===============

Item was added:
+ ----- Method: MorphicEvent>>isUserInput (in category 'testing') -----
+ isUserInput
+ ^ false!

Item was changed:
  ----- Method: PluggableTextMorph>>handleEdit: (in category 'editor access') -----
  handleEdit: editBlock
  | result |
  textMorph editor selectFrom: selectionInterval first to: selectionInterval last;
  model: model.  "For, eg, evaluateSelection"
  result := textMorph handleEdit: editBlock.   "Update selection after edit"
+ self scrollSelectionIntoView: UserInputEvent new. "Dummy event to control selection scrolling"
- self scrollSelectionIntoView.
  ^ result!

Item was changed:
  ----- Method: PluggableTextMorph>>scrollSelectionIntoView: (in category 'editor access') -----
+ scrollSelectionIntoView: event
- scrollSelectionIntoView: event
  "Scroll my text into view. Due to line composition mechanism, we must never use the right of a character block because the lines last character block right value always comes from a global container and is *not* line specific."
+ self flag: #fixIntervalCache.
+ "mt: We should find a better design for discarding unused text editors in text morphs and restoring them on demand."
-
- self flag: #fixIntervalCache. "mt: We should find a better design for discarding unused text editors in text morphs and restoring them on demand."
  selectionInterval := textMorph editor markIndex to: textMorph editor pointIndex - 1.
+ self scrollToShow:
+ (textMorph editor hasSelection
+ ifTrue: [ textMorph editor startBlock topLeft corner: textMorph editor stopBlock bottomLeft ]
+ ifFalse: [ textMorph editor startBlock withWidth: 1 ]).
+ (event notNil and: [ event isUserInput ]) ifTrue:
+ [ self scrollToShow: (textMorph editor pointBlock withWidth: 1) ].
-
- textMorph editor hasSelection
- ifFalse: [self scrollToShow: (textMorph editor startBlock withWidth: 1)]
- ifTrue: [
- self scrollToShow: (textMorph editor startBlock topLeft corner: textMorph editor stopBlock bottomLeft).
- self scrollToShow: (textMorph editor pointBlock withWidth: 1). "Ensure text cursor visibility."].
-
  ^ true!

Item was changed:
  ----- Method: ScrollPane>>keyStroke: (in category 'event handling') -----
+ keyStroke: aKeyboardEvent
+ "If pane is not empty, let the last submorph handle the event."
+ scroller submorphs ifNotEmpty: [ : subs | subs last keyStroke: aKeyboardEvent ]!
- keyStroke: evt
- "If pane is not empty, pass the event to the last submorph,
-  assuming it is the most appropriate recipient (!!)"
-
- scroller submorphs last keyStroke: evt!

Item was changed:
  ----- Method: ScrollPane>>offsetToShow: (in category 'scrolling') -----
  offsetToShow: aRectangle
  "Calculate the offset necessary to show the rectangle."
 
  | offset scrollRange target |
  self fullBounds. "We need updated bounds."
  offset := scroller offset.
  scrollRange := self hTotalScrollRange @ self vTotalScrollRange.
 
  "Normalize the incoming rectangle."
  target :=
+ aRectangle left @ aRectangle top
- (scroller width < aRectangle width
- ifTrue: [offset x < aRectangle left "Coming from left?"
- ifTrue: [aRectangle right - scroller width]
- ifFalse: [aRectangle left]]
- ifFalse: [aRectangle left])
- @
- (scroller height < aRectangle height
- ifTrue: [offset y < aRectangle top "Coming from top?"
- ifTrue: [aRectangle bottom - scroller height]
- ifFalse: [aRectangle top]]
- ifFalse: [aRectangle top])
  corner:
  (scroller width < aRectangle width
  ifTrue: [offset x + scroller width > aRectangle right "Coming from right?"
  ifTrue: [aRectangle left + scroller width]
  ifFalse: [aRectangle right]]
  ifFalse: [aRectangle right])
  @
  (scroller height < aRectangle height
  ifTrue: [offset y + scroller height > aRectangle bottom "Coming from bottom?"
  ifTrue: [aRectangle top + scroller height]
  ifFalse: [aRectangle bottom]]
  ifFalse: [aRectangle bottom]).
 
  "Vertical Scrolling"
- target top < offset y
- ifTrue: [offset := offset x @ target top].
  target bottom > (offset y + scroller height)
  ifTrue: [offset := offset x @ (target bottom - scroller height)].
+ target top < offset y
+ ifTrue: [offset := offset x @ target top].
 
  "Horizontal Scrolling"
- target left < offset x
- ifTrue: [offset := target left @ offset y].
  target right > (offset x + scroller width)
  ifTrue: [offset := (target right - scroller width) @ offset y].
+ target left < offset x
+ ifTrue: [offset := target left @ offset y].
 
  ^ (offset min: scrollRange - scroller extent) max: 0@0!

Item was changed:
  ----- Method: TextMorphForEditView>>keyStroke: (in category 'event handling') -----
  keyStroke: evt
  | view |
 
  editView deleteBalloon.
  self editor model: editView model.  "For evaluateSelection"
  view := editView.  "Copy into temp for case of a self-mutating doit"
  (acceptOnCR and: [evt keyCharacter = Character cr])
  ifTrue: [^ self editor accept].
 
  view hasUserEdited: false.
  super keyStroke: evt.
+ view scrollSelectionIntoView: evt.
- view scrollSelectionIntoView.
 
  view hasUserEdited
  ifTrue: [ view textEdited: self contents].!

Item was added:
+ ----- Method: UserInputEvent>>isUserInput (in category 'testing') -----
+ isUserInput
+ ^ true!


Reply | Threaded
Open this post in threaded view
|

Re: The Inbox: Morphic-cmm.1615.mcz

marcel.taeumel
Hmm... did you test this with all kinds of scroll panes? Lists, trees, text fields ... I think we can fix that for text fields only.

I also dislike the separation of user-vs-program here. It produces code that is hard to maintain. It also smells like it disagrees with basic information hiding. Hmm....

For the 5.3 release, I would rather change that for debuggers only! :-) Just reverse the pc selection and you will be fine.

Best,
Marcel

Am 02.01.2020 22:55:58 schrieb [hidden email] <[hidden email]>:

Chris Muller uploaded a new version of Morphic to project The Inbox:
http://source.squeak.org/inbox/Morphic-cmm.1615.mcz

==================== Summary ====================

Name: Morphic-cmm.1615
Author: cmm
Time: 2 January 2020, 3:55:29.150586 pm
UUID: a6947cb4-e842-49ca-a8db-56b7f9f3241a
Ancestors: Morphic-mt.1612

When a text selection cannot fit into its text pane, show its upper-left, rather than its lower-right, so stepping through code in a small window is possible.

=============== Diff against Morphic-mt.1612 ===============

Item was added:
+ ----- Method: MorphicEvent>>isUserInput (in category 'testing') -----
+ isUserInput
+ ^ false!

Item was changed:
----- Method: PluggableTextMorph>>handleEdit: (in category 'editor access') -----
handleEdit: editBlock
| result |
textMorph editor selectFrom: selectionInterval first to: selectionInterval last;
model: model. "For, eg, evaluateSelection"
result := textMorph handleEdit: editBlock. "Update selection after edit"
+ self scrollSelectionIntoView: UserInputEvent new. "Dummy event to control selection scrolling"
- self scrollSelectionIntoView.
^ result!

Item was changed:
----- Method: PluggableTextMorph>>scrollSelectionIntoView: (in category 'editor access') -----
+ scrollSelectionIntoView: event
- scrollSelectionIntoView: event
"Scroll my text into view. Due to line composition mechanism, we must never use the right of a character block because the lines last character block right value always comes from a global container and is *not* line specific."
+ self flag: #fixIntervalCache.
+ "mt: We should find a better design for discarding unused text editors in text morphs and restoring them on demand."
-
- self flag: #fixIntervalCache. "mt: We should find a better design for discarding unused text editors in text morphs and restoring them on demand."
selectionInterval := textMorph editor markIndex to: textMorph editor pointIndex - 1.
+ self scrollToShow:
+ (textMorph editor hasSelection
+ ifTrue: [ textMorph editor startBlock topLeft corner: textMorph editor stopBlock bottomLeft ]
+ ifFalse: [ textMorph editor startBlock withWidth: 1 ]).
+ (event notNil and: [ event isUserInput ]) ifTrue:
+ [ self scrollToShow: (textMorph editor pointBlock withWidth: 1) ].
-
- textMorph editor hasSelection
- ifFalse: [self scrollToShow: (textMorph editor startBlock withWidth: 1)]
- ifTrue: [
- self scrollToShow: (textMorph editor startBlock topLeft corner: textMorph editor stopBlock bottomLeft).
- self scrollToShow: (textMorph editor pointBlock withWidth: 1). "Ensure text cursor visibility."].
-
^ true!

Item was changed:
----- Method: ScrollPane>>keyStroke: (in category 'event handling') -----
+ keyStroke: aKeyboardEvent
+ "If pane is not empty, let the last submorph handle the event."
+ scroller submorphs ifNotEmpty: [ : subs | subs last keyStroke: aKeyboardEvent ]!
- keyStroke: evt
- "If pane is not empty, pass the event to the last submorph,
-  assuming it is the most appropriate recipient (!!)"
-
- scroller submorphs last keyStroke: evt!

Item was changed:
----- Method: ScrollPane>>offsetToShow: (in category 'scrolling') -----
offsetToShow: aRectangle
"Calculate the offset necessary to show the rectangle."

| offset scrollRange target |
self fullBounds. "We need updated bounds."
offset := scroller offset.
scrollRange := self hTotalScrollRange @ self vTotalScrollRange.

"Normalize the incoming rectangle."
target :=
+ aRectangle left @ aRectangle top
- (scroller width < arectangle="">
- ifTrue: [offset x < arectangle="" left="" "coming="" from="">
- ifTrue: [aRectangle right - scroller width]
- ifFalse: [aRectangle left]]
- ifFalse: [aRectangle left])
- @
- (scroller height < arectangle="">
- ifTrue: [offset y < arectangle="" top="" "coming="" from="">
- ifTrue: [aRectangle bottom - scroller height]
- ifFalse: [aRectangle top]]
- ifFalse: [aRectangle top])
corner:
(scroller width < arectangle="">
ifTrue: [offset x + scroller width > aRectangle right "Coming from right?"
ifTrue: [aRectangle left + scroller width]
ifFalse: [aRectangle right]]
ifFalse: [aRectangle right])
@
(scroller height < arectangle="">
ifTrue: [offset y + scroller height > aRectangle bottom "Coming from bottom?"
ifTrue: [aRectangle top + scroller height]
ifFalse: [aRectangle bottom]]
ifFalse: [aRectangle bottom]).

"Vertical Scrolling"
- target top < offset="">
- ifTrue: [offset := offset x @ target top].
target bottom > (offset y + scroller height)
ifTrue: [offset := offset x @ (target bottom - scroller height)].
+ target top < offset="">
+ ifTrue: [offset := offset x @ target top].

"Horizontal Scrolling"
- target left < offset="">
- ifTrue: [offset := target left @ offset y].
target right > (offset x + scroller width)
ifTrue: [offset := (target right - scroller width) @ offset y].
+ target left < offset="">
+ ifTrue: [offset := target left @ offset y].

^ (offset min: scrollRange - scroller extent) max: 0@0!

Item was changed:
----- Method: TextMorphForEditView>>keyStroke: (in category 'event handling') -----
keyStroke: evt
| view |

editView deleteBalloon.
self editor model: editView model. "For evaluateSelection"
view := editView. "Copy into temp for case of a self-mutating doit"
(acceptOnCR and: [evt keyCharacter = Character cr])
ifTrue: [^ self editor accept].

view hasUserEdited: false.
super keyStroke: evt.
+ view scrollSelectionIntoView: evt.
- view scrollSelectionIntoView.

view hasUserEdited
ifTrue: [ view textEdited: self contents].!

Item was added:
+ ----- Method: UserInputEvent>>isUserInput (in category 'testing') -----
+ isUserInput
+ ^ true!




Reply | Threaded
Open this post in threaded view
|

Re: The Inbox: Morphic-cmm.1615.mcz

marcel.taeumel
With Tools-mt.929, I put a simple workaround for this into Trunk.

This topic needs further discussion as it adresses multiple concerns.

Best,
Marcel

Am 06.01.2020 10:56:15 schrieb Marcel Taeumel <[hidden email]>:

Hmm... did you test this with all kinds of scroll panes? Lists, trees, text fields ... I think we can fix that for text fields only.

I also dislike the separation of user-vs-program here. It produces code that is hard to maintain. It also smells like it disagrees with basic information hiding. Hmm....

For the 5.3 release, I would rather change that for debuggers only! :-) Just reverse the pc selection and you will be fine.

Best,
Marcel

Am 02.01.2020 22:55:58 schrieb [hidden email] <[hidden email]>:

Chris Muller uploaded a new version of Morphic to project The Inbox:
http://source.squeak.org/inbox/Morphic-cmm.1615.mcz

==================== Summary ====================

Name: Morphic-cmm.1615
Author: cmm
Time: 2 January 2020, 3:55:29.150586 pm
UUID: a6947cb4-e842-49ca-a8db-56b7f9f3241a
Ancestors: Morphic-mt.1612

When a text selection cannot fit into its text pane, show its upper-left, rather than its lower-right, so stepping through code in a small window is possible.

=============== Diff against Morphic-mt.1612 ===============

Item was added:
+ ----- Method: MorphicEvent>>isUserInput (in category 'testing') -----
+ isUserInput
+ ^ false!

Item was changed:
----- Method: PluggableTextMorph>>handleEdit: (in category 'editor access') -----
handleEdit: editBlock
| result |
textMorph editor selectFrom: selectionInterval first to: selectionInterval last;
model: model. "For, eg, evaluateSelection"
result := textMorph handleEdit: editBlock. "Update selection after edit"
+ self scrollSelectionIntoView: UserInputEvent new. "Dummy event to control selection scrolling"
- self scrollSelectionIntoView.
^ result!

Item was changed:
----- Method: PluggableTextMorph>>scrollSelectionIntoView: (in category 'editor access') -----
+ scrollSelectionIntoView: event
- scrollSelectionIntoView: event
"Scroll my text into view. Due to line composition mechanism, we must never use the right of a character block because the lines last character block right value always comes from a global container and is *not* line specific."
+ self flag: #fixIntervalCache.
+ "mt: We should find a better design for discarding unused text editors in text morphs and restoring them on demand."
-
- self flag: #fixIntervalCache. "mt: We should find a better design for discarding unused text editors in text morphs and restoring them on demand."
selectionInterval := textMorph editor markIndex to: textMorph editor pointIndex - 1.
+ self scrollToShow:
+ (textMorph editor hasSelection
+ ifTrue: [ textMorph editor startBlock topLeft corner: textMorph editor stopBlock bottomLeft ]
+ ifFalse: [ textMorph editor startBlock withWidth: 1 ]).
+ (event notNil and: [ event isUserInput ]) ifTrue:
+ [ self scrollToShow: (textMorph editor pointBlock withWidth: 1) ].
-
- textMorph editor hasSelection
- ifFalse: [self scrollToShow: (textMorph editor startBlock withWidth: 1)]
- ifTrue: [
- self scrollToShow: (textMorph editor startBlock topLeft corner: textMorph editor stopBlock bottomLeft).
- self scrollToShow: (textMorph editor pointBlock withWidth: 1). "Ensure text cursor visibility."].
-
^ true!

Item was changed:
----- Method: ScrollPane>>keyStroke: (in category 'event handling') -----
+ keyStroke: aKeyboardEvent
+ "If pane is not empty, let the last submorph handle the event."
+ scroller submorphs ifNotEmpty: [ : subs | subs last keyStroke: aKeyboardEvent ]!
- keyStroke: evt
- "If pane is not empty, pass the event to the last submorph,
-  assuming it is the most appropriate recipient (!!)"
-
- scroller submorphs last keyStroke: evt!

Item was changed:
----- Method: ScrollPane>>offsetToShow: (in category 'scrolling') -----
offsetToShow: aRectangle
"Calculate the offset necessary to show the rectangle."

| offset scrollRange target |
self fullBounds. "We need updated bounds."
offset := scroller offset.
scrollRange := self hTotalScrollRange @ self vTotalScrollRange.

"Normalize the incoming rectangle."
target :=
+ aRectangle left @ aRectangle top
- (scroller width < arectangle="">
- ifTrue: [offset x < arectangle="" left="" "coming="" from="">
- ifTrue: [aRectangle right - scroller width]
- ifFalse: [aRectangle left]]
- ifFalse: [aRectangle left])
- @
- (scroller height < arectangle="">
- ifTrue: [offset y < arectangle="" top="" "coming="" from="">
- ifTrue: [aRectangle bottom - scroller height]
- ifFalse: [aRectangle top]]
- ifFalse: [aRectangle top])
corner:
(scroller width < arectangle="">
ifTrue: [offset x + scroller width > aRectangle right "Coming from right?"
ifTrue: [aRectangle left + scroller width]
ifFalse: [aRectangle right]]
ifFalse: [aRectangle right])
@
(scroller height < arectangle="">
ifTrue: [offset y + scroller height > aRectangle bottom "Coming from bottom?"
ifTrue: [aRectangle top + scroller height]
ifFalse: [aRectangle bottom]]
ifFalse: [aRectangle bottom]).

"Vertical Scrolling"
- target top < offset="">
- ifTrue: [offset := offset x @ target top].
target bottom > (offset y + scroller height)
ifTrue: [offset := offset x @ (target bottom - scroller height)].
+ target top < offset="">
+ ifTrue: [offset := offset x @ target top].

"Horizontal Scrolling"
- target left < offset="">
- ifTrue: [offset := target left @ offset y].
target right > (offset x + scroller width)
ifTrue: [offset := (target right - scroller width) @ offset y].
+ target left < offset="">
+ ifTrue: [offset := target left @ offset y].

^ (offset min: scrollRange - scroller extent) max: 0@0!

Item was changed:
----- Method: TextMorphForEditView>>keyStroke: (in category 'event handling') -----
keyStroke: evt
| view |

editView deleteBalloon.
self editor model: editView model. "For evaluateSelection"
view := editView. "Copy into temp for case of a self-mutating doit"
(acceptOnCR and: [evt keyCharacter = Character cr])
ifTrue: [^ self editor accept].

view hasUserEdited: false.
super keyStroke: evt.
+ view scrollSelectionIntoView: evt.
- view scrollSelectionIntoView.

view hasUserEdited
ifTrue: [ view textEdited: self contents].!

Item was added:
+ ----- Method: UserInputEvent>>isUserInput (in category 'testing') -----
+ isUserInput
+ ^ true!