Skip to content

Commit 65877d4

Browse files
authored
Merge pull request #1788 from gou4shi1/fix-get-mouse-coord
getCoordsRelativeToElement: use getBoundingClientRect and clientX/Y.
2 parents f34c3d5 + 48629e7 commit 65877d4

File tree

3 files changed

+14
-41
lines changed

3 files changed

+14
-41
lines changed

src/Types.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -245,7 +245,7 @@ export interface ILinkifierAccessor {
245245
}
246246

247247
export interface IMouseHelper {
248-
getCoords(event: { pageX: number, pageY: number }, element: HTMLElement, charMeasure: ICharMeasure, colCount: number, rowCount: number, isSelection?: boolean): [number, number];
248+
getCoords(event: { clientX: number, clientY: number }, element: HTMLElement, charMeasure: ICharMeasure, colCount: number, rowCount: number, isSelection?: boolean): [number, number];
249249
getRawByteCoords(event: MouseEvent, element: HTMLElement, charMeasure: ICharMeasure, colCount: number, rowCount: number): { x: number, y: number };
250250
}
251251

src/utils/MouseHelper.test.ts

Lines changed: 7 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -37,34 +37,28 @@ describe('MouseHelper.getCoords', () => {
3737
describe('when charMeasure is not initialized', () => {
3838
it('should return null', () => {
3939
charMeasure = new MockCharMeasure();
40-
assert.equal(mouseHelper.getCoords({ pageX: 0, pageY: 0 }, document.createElement('div'), charMeasure, 10, 10), null);
41-
});
42-
});
43-
44-
describe('when pageX/pageY are not supported', () => {
45-
it('should return null', () => {
46-
assert.equal(mouseHelper.getCoords({ pageX: undefined, pageY: undefined }, document.createElement('div'), charMeasure, 10, 10), null);
40+
assert.equal(mouseHelper.getCoords({ clientX: 0, clientY: 0 }, document.createElement('div'), charMeasure, 10, 10), null);
4741
});
4842
});
4943

5044
it('should return the cell that was clicked', () => {
5145
let coords: [number, number];
52-
coords = mouseHelper.getCoords({ pageX: CHAR_WIDTH / 2, pageY: CHAR_HEIGHT / 2 }, document.createElement('div'), charMeasure, 10, 10);
46+
coords = mouseHelper.getCoords({ clientX: CHAR_WIDTH / 2, clientY: CHAR_HEIGHT / 2 }, document.createElement('div'), charMeasure, 10, 10);
5347
assert.deepEqual(coords, [1, 1]);
54-
coords = mouseHelper.getCoords({ pageX: CHAR_WIDTH, pageY: CHAR_HEIGHT }, document.createElement('div'), charMeasure, 10, 10);
48+
coords = mouseHelper.getCoords({ clientX: CHAR_WIDTH, clientY: CHAR_HEIGHT }, document.createElement('div'), charMeasure, 10, 10);
5549
assert.deepEqual(coords, [1, 1]);
56-
coords = mouseHelper.getCoords({ pageX: CHAR_WIDTH, pageY: CHAR_HEIGHT + 1 }, document.createElement('div'), charMeasure, 10, 10);
50+
coords = mouseHelper.getCoords({ clientX: CHAR_WIDTH, clientY: CHAR_HEIGHT + 1 }, document.createElement('div'), charMeasure, 10, 10);
5751
assert.deepEqual(coords, [1, 2]);
58-
coords = mouseHelper.getCoords({ pageX: CHAR_WIDTH + 1, pageY: CHAR_HEIGHT }, document.createElement('div'), charMeasure, 10, 10);
52+
coords = mouseHelper.getCoords({ clientX: CHAR_WIDTH + 1, clientY: CHAR_HEIGHT }, document.createElement('div'), charMeasure, 10, 10);
5953
assert.deepEqual(coords, [2, 1]);
6054
});
6155

6256
it('should ensure the coordinates are returned within the terminal bounds', () => {
6357
let coords: [number, number];
64-
coords = mouseHelper.getCoords({ pageX: -1, pageY: -1 }, document.createElement('div'), charMeasure, 10, 10);
58+
coords = mouseHelper.getCoords({ clientX: -1, clientY: -1 }, document.createElement('div'), charMeasure, 10, 10);
6559
assert.deepEqual(coords, [1, 1]);
6660
// Event are double the cols/rows
67-
coords = mouseHelper.getCoords({ pageX: CHAR_WIDTH * 20, pageY: CHAR_HEIGHT * 20 }, document.createElement('div'), charMeasure, 10, 10);
61+
coords = mouseHelper.getCoords({ clientX: CHAR_WIDTH * 20, clientY: CHAR_HEIGHT * 20 }, document.createElement('div'), charMeasure, 10, 10);
6862
assert.deepEqual(coords, [10, 10], 'coordinates should never come back as larger than the terminal');
6963
});
7064
});

src/utils/MouseHelper.ts

Lines changed: 6 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -3,40 +3,19 @@
33
* @license MIT
44
*/
55

6-
import { ICharMeasure } from '../Types';
6+
import { ICharMeasure, IMouseHelper } from '../Types';
77
import { IRenderer } from '../renderer/Types';
88

9-
export class MouseHelper {
9+
export class MouseHelper implements IMouseHelper {
1010
constructor(private _renderer: IRenderer) {}
1111

1212
public setRenderer(renderer: IRenderer): void {
1313
this._renderer = renderer;
1414
}
1515

16-
public static getCoordsRelativeToElement(event: {pageX: number, pageY: number}, element: HTMLElement): [number, number] {
17-
// Ignore browsers that don't support MouseEvent.pageX
18-
if (event.pageX === null || event.pageX === undefined) {
19-
return null;
20-
}
21-
22-
const originalElement = element;
23-
let x = event.pageX;
24-
let y = event.pageY;
25-
26-
// Converts the coordinates from being relative to the document to being
27-
// relative to the terminal.
28-
while (element) {
29-
x -= element.offsetLeft;
30-
y -= element.offsetTop;
31-
element = <HTMLElement>element.offsetParent;
32-
}
33-
element = originalElement;
34-
while (element && element !== element.ownerDocument.body) {
35-
x += element.scrollLeft;
36-
y += element.scrollTop;
37-
element = <HTMLElement>element.parentElement;
38-
}
39-
return [x, y];
16+
public static getCoordsRelativeToElement(event: {clientX: number, clientY: number}, element: HTMLElement): [number, number] {
17+
const rect = element.getBoundingClientRect();
18+
return [event.clientX - rect.left, event.clientY - rect.top];
4019
}
4120

4221
/**
@@ -52,7 +31,7 @@ export class MouseHelper {
5231
* apply an offset to the x value such that the left half of the cell will
5332
* select that cell and the right half will select the next cell.
5433
*/
55-
public getCoords(event: {pageX: number, pageY: number}, element: HTMLElement, charMeasure: ICharMeasure, colCount: number, rowCount: number, isSelection?: boolean): [number, number] {
34+
public getCoords(event: {clientX: number, clientY: number}, element: HTMLElement, charMeasure: ICharMeasure, colCount: number, rowCount: number, isSelection?: boolean): [number, number] {
5635
// Coordinates cannot be measured if charMeasure has not been initialized
5736
if (!charMeasure.width || !charMeasure.height) {
5837
return null;

0 commit comments

Comments
 (0)