]>
Commit | Line | Data |
---|---|---|
4d328268 DI |
1 | /** |
2 | * @license MIT | |
3 | */ | |
4 | ||
5 | import { CharMeasure } from './CharMeasure'; | |
6 | ||
0dc3dd03 | 7 | export function getCoordsRelativeToElement(event: MouseEvent, element: HTMLElement): [number, number] { |
70e35de5 | 8 | // Ignore browsers that don't support MouseEvent.pageX |
4d328268 DI |
9 | if (event.pageX == null) { |
10 | return null; | |
11 | } | |
12 | ||
13 | let x = event.pageX; | |
14 | let y = event.pageY; | |
4d328268 | 15 | |
70e35de5 DI |
16 | // Converts the coordinates from being relative to the document to being |
17 | // relative to the terminal. | |
0dc3dd03 DI |
18 | while (element && element !== self.document.documentElement) { |
19 | x -= element.offsetLeft; | |
20 | y -= element.offsetTop; | |
21 | element = 'offsetParent' in element ? <HTMLElement>element.offsetParent : <HTMLElement>element.parentElement; | |
4d328268 | 22 | } |
0dc3dd03 DI |
23 | return [x, y]; |
24 | } | |
25 | ||
26 | /** | |
27 | * Gets coordinates within the terminal for a particular mouse event. The result | |
28 | * is returned as an array in the form [x, y] instead of an object as it's a | |
29 | * little faster and this function is used in some low level code. | |
30 | * @param event The mouse event. | |
31 | * @param rowContainer The terminal's row container. | |
32 | * @param charMeasure The char measure object used to determine character sizes. | |
b05814e6 DI |
33 | * @param colCount The number of columns in the terminal. |
34 | * @param rowCount The number of rows n the terminal. | |
35 | * @param isSelection Whether the request is for the selection or not. This will | |
36 | * apply an offset to the x value such that the left half of the cell will | |
37 | * select that cell and the right half will select the next cell. | |
0dc3dd03 | 38 | */ |
b05814e6 | 39 | export function getCoords(event: MouseEvent, rowContainer: HTMLElement, charMeasure: CharMeasure, colCount: number, rowCount: number, isSelection?: boolean): [number, number] { |
e56f710c DI |
40 | // Coordinates cannot be measured if charMeasure has not been initialized |
41 | if (!charMeasure.width || !charMeasure.height) { | |
42 | return null; | |
43 | } | |
44 | ||
0dc3dd03 | 45 | const coords = getCoordsRelativeToElement(event, rowContainer); |
e56f710c DI |
46 | if (!coords) { |
47 | return null; | |
48 | } | |
4d328268 | 49 | |
b05814e6 DI |
50 | // Convert to cols/rows. |
51 | coords[0] = Math.ceil((coords[0] + (isSelection ? charMeasure.width / 2 : 0)) / charMeasure.width); | |
0dc3dd03 | 52 | coords[1] = Math.ceil(coords[1] / charMeasure.height); |
4d328268 | 53 | |
0dc3dd03 DI |
54 | // Ensure coordinates are within the terminal viewport. |
55 | coords[0] = Math.min(Math.max(coords[0], 1), colCount + 1); | |
56 | coords[1] = Math.min(Math.max(coords[1], 1), rowCount + 1); | |
57 | ||
58 | return coords; | |
4d328268 DI |
59 | } |
60 | ||
c323e0ad DI |
61 | /** |
62 | * Gets coordinates within the terminal for a particular mouse event, wrapping | |
63 | * them to the bounds of the terminal and adding 32 to both the x and y values | |
64 | * as expected by xterm. | |
65 | * @param event The mouse event. | |
66 | * @param rowContainer The terminal's row container. | |
67 | * @param charMeasure The char measure object used to determine character sizes. | |
68 | * @param colCount The number of columns in the terminal. | |
69 | * @param rowCount The number of rows in the terminal. | |
70 | */ | |
4d328268 | 71 | export function getRawByteCoords(event: MouseEvent, rowContainer: HTMLElement, charMeasure: CharMeasure, colCount: number, rowCount: number): { x: number, y: number } { |
0dc3dd03 | 72 | const coords = getCoords(event, rowContainer, charMeasure, colCount, rowCount); |
4d328268 DI |
73 | let x = coords[0]; |
74 | let y = coords[1]; | |
75 | ||
70e35de5 | 76 | // xterm sends raw bytes and starts at 32 (SP) for each. |
4d328268 DI |
77 | x += 32; |
78 | y += 32; | |
79 | ||
80 | return { x, y }; | |
81 | } |