Skip to content

The block argument of #whenDoubleClickDo: sent to an event handler of a list presentor is not evaluated #1839

@koendehondt

Description

@koendehondt

Context: Pharo 13. Also present in Pharo 14.

This bug should be fixed in Pharo 13.

Bug

Consider this small Spec application with a list presenter:

SpPresenter << #DoubleClickBug
	slots: { #list };
	package: 'Bug'

initializePresenters

	list := self newList
		items: { 1 . 2. 3 };
		yourself

defaultLayout

	^ SpBoxLayout newTopToBottom
		add: list;
		yourself

initializeWindow: aWindowPresenter

	super initializeWindow: aWindowPresenter.
	aWindowPresenter whenOpenedDo: [
		list eventHandler whenDoubleClickDo: [ :event | list selectedItem inspect ] ]

After evaluating DoubleClickBug new open, this window opens:

Image

Now, double-click any item in the list. We expect that an inspector opens on the double-clicked number. But it does not.

Note that the same bug is present when double-clicking items in a tree. I tried that. Probably the bug is also present in tables, but I did not check that.

Investigation

While several Morph subclasses implement #doubleClick: and most send a super send, FTTableMorph>>#doubleClick: does not do a super send. That is the reason that the double click handler is not invoked, because that is what Morph>>#doubleClick: indirectly does:

doubleClick: evt
	"Handle a double-click event. This message is only sent to clients that request it by sending #waitForClicksOrDrag:event: to the initiating hand in their mouseDown: method. This default implementation does nothing."
	"We should not double click if not on the same element"
	(self containsPoint: evt position) ifFalse: [ ^self ].
	^ self eventHandler ifNotNil:
		[self eventHandler doubleClick: evt fromMorph: self]

Solution

The solution is to add a super send to FTTableMorph>>#doubleClick:, like this (see the addition of the last line):

doubleClick: event

	(self selectionModeStrategy selectableIndexContainingPoint:
		 event cursorPoint) ifNotNil: [ :firstClickedIndex |
		| pdcEvent |
		pdcEvent := event asPseudoDoubleClickEvent.
		(self selectionModeStrategy selectableIndexContainingPoint:
			 pdcEvent secondEvent position) ifNotNil: [ :secondClickedIndex |
			firstClickedIndex = secondClickedIndex
				ifFalse: [
					self selectionStrategy
						selectIndex: secondClickedIndex
						event: pdcEvent secondEvent ]
				ifTrue: [
					self selectedIndexes
						detect: [ :i | i = secondClickedIndex ]
						ifNone: [
							self selectionStrategy
								selectIndex: secondClickedIndex
								event: pdcEvent secondEvent ].
					self doAnnounce:
						(FTStrongSelectionChanged index: secondClickedIndex event: event).
					super doubleClick: event ] ] ]

Then double clicking any item in the list opens an inspector on the corresponding number.

@estebanlm If you agree with my analysis, I am happy to create a PR with the fix, including tests to describe the behavior.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions