fixed mouseup + click events order when clicked on empty area of stage. close #1954

This commit is contained in:
Anton Lavrevov 2025-08-17 00:26:36 +09:00
parent 79cb4a080f
commit c621b39f99
2 changed files with 39 additions and 3 deletions

View File

@ -677,7 +677,7 @@ export class Stage extends Container<Layer> {
const clickStartShape = this[eventType + 'ClickStartShape']; const clickStartShape = this[eventType + 'ClickStartShape'];
const clickEndShape = this[eventType + 'ClickEndShape']; const clickEndShape = this[eventType + 'ClickEndShape'];
const processedShapesIds = {}; const processedShapesIds = {};
let triggeredOnShape = false; let skipPointerUpTrigger = false;
this._changedPointerPositions.forEach((pos) => { this._changedPointerPositions.forEach((pos) => {
const shape = (PointerEvents.getCapturedShape(pos.id) || const shape = (PointerEvents.getCapturedShape(pos.id) ||
this.getIntersection(pos)) as Shape; this.getIntersection(pos)) as Shape;
@ -708,7 +708,7 @@ export class Stage extends Container<Layer> {
}, Konva.dblClickWindow); }, Konva.dblClickWindow);
if (shape && shape.isListening()) { if (shape && shape.isListening()) {
triggeredOnShape = true; skipPointerUpTrigger = true;
this[eventType + 'ClickEndShape'] = shape; this[eventType + 'ClickEndShape'] = shape;
shape._fireAndBubble(events.pointerup, { ...event }); shape._fireAndBubble(events.pointerup, { ...event });
@ -727,6 +727,16 @@ export class Stage extends Container<Layer> {
} else { } else {
this[eventType + 'ClickEndShape'] = null; this[eventType + 'ClickEndShape'] = null;
if (!skipPointerUpTrigger) {
this._fire(events.pointerup, {
evt: evt,
target: this,
currentTarget: this,
pointerId: this._changedPointerPositions[0].id,
});
skipPointerUpTrigger = true;
}
if (Konva['_' + eventType + 'ListenClick']) { if (Konva['_' + eventType + 'ListenClick']) {
this._fire(events.pointerclick, { this._fire(events.pointerclick, {
evt: evt, evt: evt,
@ -747,7 +757,7 @@ export class Stage extends Container<Layer> {
} }
}); });
if (!triggeredOnShape) { if (!skipPointerUpTrigger) {
this._fire(events.pointerup, { this._fire(events.pointerup, {
evt: evt, evt: evt,
target: this, target: this,

View File

@ -900,6 +900,32 @@ describe('Stage', function () {
assert.equal(dblicks, 1, 'first dbclick registered'); assert.equal(dblicks, 1, 'first dbclick registered');
}); });
it('stage mouseup should fire before click on empty area', function () {
if (isNode) {
return;
}
var stage = addStage();
var layer = new Konva.Layer();
stage.add(layer);
var order: string[] = [];
stage.on('mousedown', function () {
order.push('down');
});
stage.on('mouseup', function () {
order.push('up');
});
stage.on('click', function () {
order.push('click');
});
simulateMouseDown(stage, { x: 10, y: 10 });
simulateMouseUp(stage, { x: 10, y: 10 });
assert.deepEqual(order, ['down', 'up', 'click']);
});
it('can listen taps on empty areas', function () { it('can listen taps on empty areas', function () {
var stage = addStage(); var stage = addStage();
var layer = new Konva.Layer(); var layer = new Konva.Layer();