@spidunno/desmos-types 1.13.2 → 1.13.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +154 -4
- package/internals/generated/objects.d.ts +5 -5
- package/internals/graph-sketches.d.ts +631 -0
- package/internals/grapher2d.d.ts +591 -0
- package/internals/index.d.ts +2 -0
- package/internals/list-model.d.ts +36 -31
- package/package.json +3 -2
package/README.md
CHANGED
|
@@ -6,11 +6,11 @@ the graphing calculator, geometry tool, 3D calculator, and the four-function and
|
|
|
6
6
|
## Install
|
|
7
7
|
|
|
8
8
|
```sh
|
|
9
|
-
npm install --save-dev @spidunno/desmos-types@~1.13.
|
|
9
|
+
npm install --save-dev @spidunno/desmos-types@~1.13.4
|
|
10
10
|
```
|
|
11
11
|
|
|
12
12
|
The package's major and minor version match the Desmos API version it describes; patch releases
|
|
13
|
-
are fixes to the types. Use a tilde range (`~1.13.
|
|
13
|
+
are fixes to the types. Use a tilde range (`~1.13.4`), not npm's default caret (`^`), so you only
|
|
14
14
|
get type fixes for the API version you load.
|
|
15
15
|
|
|
16
16
|
## Usage
|
|
@@ -134,7 +134,7 @@ Everything here is internal to Desmos and changes between builds, even within v1
|
|
|
134
134
|
|
|
135
135
|
| Layer | Files | Source |
|
|
136
136
|
| --- | --- | --- |
|
|
137
|
-
| Generated | `internals/generated/objects.d.ts` | The bundle loaded in jsdom;
|
|
137
|
+
| Generated | `internals/generated/objects.d.ts` | The bundle loaded in jsdom; 60 internal objects walked |
|
|
138
138
|
| Generated | `internals/generated/actions.d.ts` | Every `dispatch({ type })` call site and `switch (action.type)` reducer, found with acorn. Each of the 341 actions is attributed to the reducer(s) that handle it, giving three unions: `Action` (graph controller), `MathFieldAction` and `BasicCalculatorAction` |
|
|
139
139
|
| Generated | `internals/generated/views.d.ts` | Props and instance members of the 13 `Private.Fragile` views, from live instances (about 1,400 views rendered), call sites and prop reads, following `{...props}` forwarding into inner views |
|
|
140
140
|
| Hand-written | `internals/*.d.ts` | Precise types for the parts mods use, checked against the bundle source |
|
|
@@ -143,7 +143,9 @@ In the generated layer, property types come from observed values. A method's ret
|
|
|
143
143
|
static analysis of its source (nothing returned → `void`, only booleans returned → `boolean`), or from
|
|
144
144
|
calling side-effect-free getters such as `get*` and `is*`. Anything that couldn't be determined is
|
|
145
145
|
`unknown`, and parameters are `unknown` because the bundle is minified. Action payload field names are
|
|
146
|
-
reliable, but their value types are often inferred from the field name.
|
|
146
|
+
reliable, but their value types are often inferred from the field name. A property is optional if it
|
|
147
|
+
held `undefined` or was added after the calculator loaded (for example, by the first animation frame
|
|
148
|
+
or a UI interaction).
|
|
147
149
|
|
|
148
150
|
The hand-written interfaces *extend* the generated ones (`Internals.Controller extends
|
|
149
151
|
Generated.Controller`, and so on). TypeScript therefore checks every hand-written type against what
|
|
@@ -158,6 +160,18 @@ What's hand-typed:
|
|
|
158
160
|
`ImageModel` and `TickerModel` as a discriminated union (`ItemModel`), plus `ListModel`.
|
|
159
161
|
- **Actions:** `Action` is the full union. About 25 common actions have checked payloads, and
|
|
160
162
|
`ActionOfType<'set-item-latex'>` picks one.
|
|
163
|
+
- **Graph sketches** (`controller.grapher2d.graphSketches`): one `GraphSketch` per graphed
|
|
164
|
+
expression, holding `GraphBranch`es as a union over the 20 branch modes the 2D grapher
|
|
165
|
+
draws (`BranchModes` names them). Each mode's `segments` layout is typed: flat `[x, y, …]`
|
|
166
|
+
for most curves, `[y, x, …]` for `x = f(y)`, `[θ, r, …]` for polar, `[x, y]` tuples for
|
|
167
|
+
points, and fixed tuples like `[cx, cy, r]` for geometry objects. Also covered: points of
|
|
168
|
+
interest (`POI`, `POITypes`), sketch labels, movable points and the grapher's sketch methods.
|
|
169
|
+
A fixture of 60 real sketches (`test/fixtures/graph-sketches.ts`) is type-checked against
|
|
170
|
+
these types.
|
|
171
|
+
- **The rest of `grapher2d`:** the projection (math ↔ pixel conversion, with linear and log axes),
|
|
172
|
+
`Viewport`, the viewport controller (jump, animate, zoom, pan), `GrapherSettings` (every graph
|
|
173
|
+
and drawing setting, with typed `observe` / `getProperty` / `setProperty`), the `'redraw'`
|
|
174
|
+
event, draw layers, graph images, screenshots and grapher state.
|
|
161
175
|
- **Dispatcher:** `register`, `unregister`, `waitFor`, generic over the action type.
|
|
162
176
|
- **Other controllers:** each math field (`mathField.controller`) and each basic calculator
|
|
163
177
|
(`calculator.controller`) has its own controller and dispatcher. Keystrokes in a math field are
|
|
@@ -184,14 +198,150 @@ What's hand-typed:
|
|
|
184
198
|
`getReconciledExpressionProps`, `currentLanguage`, `manageFocusHelper` / `mathquillFocusHelper`,
|
|
185
199
|
and `List`.
|
|
186
200
|
|
|
201
|
+
### Graph sketches
|
|
202
|
+
|
|
203
|
+
`controller.grapher2d.graphSketches` holds what the 2D grapher draws, keyed by expression id. Each
|
|
204
|
+
sketch has `branches`, and each branch has a numeric `branchMode` that tells you what it is and
|
|
205
|
+
how to read its `segments`. One expression often produces several branches: one per list element,
|
|
206
|
+
boundary curves plus a fill for an inequality, an outline plus a fill for a polygon.
|
|
207
|
+
|
|
208
|
+
The examples below are plain JavaScript, so you can paste them into the browser console. On
|
|
209
|
+
desmos.com the calculator is the global `Calc`; in your own page it's whatever you called
|
|
210
|
+
`Desmos.GraphingCalculator(...)`. desmos.com runs the same v1.13 line, but it is redeployed
|
|
211
|
+
continuously, so an internal field can change before these types are regenerated.
|
|
212
|
+
|
|
213
|
+
```js
|
|
214
|
+
// Every branch of every sketch, with its mode
|
|
215
|
+
for (const [id, sketch] of Object.entries(Calc.controller.grapher2d.graphSketches)) {
|
|
216
|
+
console.log(id, sketch.branches.map((b) => b.branchMode));
|
|
217
|
+
}
|
|
218
|
+
```
|
|
219
|
+
|
|
220
|
+
#### Branch modes
|
|
221
|
+
|
|
222
|
+
| Mode | Name | Drawn for | `segments` | Other notable fields |
|
|
223
|
+
| ---: | --- | --- | --- | --- |
|
|
224
|
+
| 1 | X | `x = f(y)`, `x` inequalities | flat `[y0, x0, y1, x1, …]` (**y first**) | `operator`, `compiled`, `poi` |
|
|
225
|
+
| 2 | Y | `y = f(x)`, `y` inequalities, distributions, solvable implicit equations | flat `[x0, y0, x1, y1, …]` | `operator`, `compiled`, `poi`, `boundingBox` |
|
|
226
|
+
| 3 | XYPOINT | points, point lists, dot plots | arrays of `[x, y]` | `labels`, `pointSize`, `pointOpacity`, `showLabel` |
|
|
227
|
+
| 4 | XYPOINT_MOVABLE | draggable points | arrays of `[x, y]` | `movablePointInfo` |
|
|
228
|
+
| 5 | PARAMETRIC | parametrics, point-list and table lines, polygon outlines, box plots | flat `[x0, y0, …]` | `compiled`, `tableId` |
|
|
229
|
+
| 6 | POLAR | `r = f(θ)`, polar inequalities | flat `[θ0, r0, θ1, r1, …]` (**polar**) | `sampledDomain` |
|
|
230
|
+
| 7 | POLYGONFILL | inequality shading, polygon and parametric fills, histogram bars | flat `[x0, y0, …]` polygons (empty for inequality shading) | `fillOpacity` |
|
|
231
|
+
| 8 | IMPLICIT | implicit curves | flat `[x0, y0, …]` | `compiled` |
|
|
232
|
+
| 15 | ERROR | an expression that failed while graphing | `[]` | `error` (`{ key, vars }`) |
|
|
233
|
+
| 17 | SEGMENT | `segment` | `[x1, y1, x2, y2]` | `arrowMode` |
|
|
234
|
+
| 18 | LINE | `line` | `[x1, y1, x2, y2]`: two points on the line | `arrowMode` |
|
|
235
|
+
| 19 | RAY | `ray` | `[startX, startY, throughX, throughY]` | `arrowMode` |
|
|
236
|
+
| 20 | CIRCLE | `circle` | `[cx, cy, r]` | |
|
|
237
|
+
| 21 | ARC | `arc` | `[cx, cy, r, startAngle, endAngle]` | |
|
|
238
|
+
| 22 | LABEL | label of a segment, polygon or angle | placement data | `labels` (text), `objectType` (17, 16 or 23) |
|
|
239
|
+
| 23 | ANGLE_MARKER | `angle`, `directedangle` | `[vx, vy, startAngle, angle, directed]` | |
|
|
240
|
+
| 24 | VECTOR | `vector` | `[tailX, tailY, headX, headY]` | `arrowMode` |
|
|
241
|
+
| 25 | COMPLEX_NUMBER | complex numbers in complex mode | arrays of `[re, im]` | like XYPOINT |
|
|
242
|
+
| 26 | COMPLEX_NUMBER_MOVABLE | draggable complex numbers | arrays of `[re, im]` | `movablePointInfo` |
|
|
243
|
+
| 27 | IMAGE | images | `[]` | `dimensions` (`x`, `y`, `width`, `height`, `radianAngle`, `opacity`) |
|
|
244
|
+
|
|
245
|
+
Modes 17–24 only appear in the geometry tool. Angles are in radians. In each row, `segments` is a
|
|
246
|
+
list of these: a curve broken at discontinuities has several flat arrays, and a list of circles has
|
|
247
|
+
several `[cx, cy, r]` entries. In TypeScript, hovering `branchMode` shows this table, and comparing
|
|
248
|
+
it to a number (`branch.branchMode === 20`) narrows the branch to that mode's type.
|
|
249
|
+
|
|
250
|
+
#### Points of interest
|
|
251
|
+
|
|
252
|
+
`sketch.getPOI()` returns the points of interest the grapher shows when an expression is selected.
|
|
253
|
+
`poi.type` is:
|
|
254
|
+
|
|
255
|
+
| Type | Meaning | Comes from |
|
|
256
|
+
| ---: | --- | --- |
|
|
257
|
+
| 1001 | intersection | `X` / `Y` branches |
|
|
258
|
+
| 1002 | zero (root) | `X` / `Y` branches |
|
|
259
|
+
| 1003 | axis intercept | `X` / `Y` branches |
|
|
260
|
+
| 1004 | extremum | `X` / `Y` branches |
|
|
261
|
+
| 1006 | plotted point without a visible label | point branches |
|
|
262
|
+
| 1008 | labeled point, or a geometry label's anchor | point branches, labels |
|
|
263
|
+
|
|
264
|
+
#### Examples
|
|
265
|
+
|
|
266
|
+
```js
|
|
267
|
+
const sketches = Calc.controller.grapher2d.graphSketches;
|
|
268
|
+
|
|
269
|
+
// Turn any curve branch into a list of {x, y} points, handling the modes
|
|
270
|
+
// whose coordinates aren't (x, y)
|
|
271
|
+
function curvePoints(branch) {
|
|
272
|
+
const points = [];
|
|
273
|
+
for (const flat of branch.segments) {
|
|
274
|
+
for (let i = 0; i < flat.length; i += 2) {
|
|
275
|
+
const [a, b] = [flat[i], flat[i + 1]];
|
|
276
|
+
if (branch.branchMode === 1) points.push({ x: b, y: a }); // x = f(y): (y, x)
|
|
277
|
+
else if (branch.branchMode === 6) points.push({ x: b * Math.cos(a), y: b * Math.sin(a) }); // polar: (θ, r)
|
|
278
|
+
else points.push({ x: a, y: b });
|
|
279
|
+
}
|
|
280
|
+
}
|
|
281
|
+
return points;
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
// Circles in the geometry tool
|
|
285
|
+
for (const sketch of Object.values(sketches)) {
|
|
286
|
+
for (const branch of sketch.branches) {
|
|
287
|
+
if (branch.branchMode === 20) {
|
|
288
|
+
for (const [cx, cy, r] of branch.segments) console.log(`circle at (${cx}, ${cy}), radius ${r}`);
|
|
289
|
+
}
|
|
290
|
+
}
|
|
291
|
+
}
|
|
292
|
+
|
|
293
|
+
// Extrema of the expression with id "1"
|
|
294
|
+
sketches['1']?.getPOI().filter((poi) => poi.type === 1004).map((poi) => [poi.x, poi.y]);
|
|
295
|
+
|
|
296
|
+
// Draggable points, with table row info for table columns
|
|
297
|
+
sketches['1']?.getMovablePoints().map((p) => ({ x: p.x, y: p.y, row: p.tableInfo?.rowIndex }));
|
|
298
|
+
```
|
|
299
|
+
|
|
300
|
+
### Projection, viewport and settings
|
|
301
|
+
|
|
302
|
+
`grapher2d.getProjection()` converts between math coordinates and pixels (CSS pixels from the
|
|
303
|
+
graph paper's top-left, y down). The projection is replaced whenever you pan, zoom or resize, so
|
|
304
|
+
get a fresh one each time instead of keeping it.
|
|
305
|
+
|
|
306
|
+
```js
|
|
307
|
+
const g = Calc.controller.grapher2d;
|
|
308
|
+
|
|
309
|
+
// Math ↔ pixels
|
|
310
|
+
const p = g.getProjection();
|
|
311
|
+
p.map_pt({ x: 0, y: 0 }); // where the origin is on screen
|
|
312
|
+
p.reverse_map_pt({ x: 100, y: 100 }); // the math point under pixel (100, 100)
|
|
313
|
+
p.mathToPixels.dangerouslyGetXScaleFactor(); // pixels per unit (throws on a log axis)
|
|
314
|
+
|
|
315
|
+
// The viewport
|
|
316
|
+
g.getCurrentViewport(); // { xmin, xmax, ymin, ymax }
|
|
317
|
+
g.viewportController.animateToViewport({ xmin: -5, xmax: 5, ymin: -5, ymax: 5 });
|
|
318
|
+
g.viewportController.zoom('in'); // 'in' | 'out' | 'square' | 'default'
|
|
319
|
+
|
|
320
|
+
// Settings: graph settings plus drawing settings like labelSize and graphLineWidth
|
|
321
|
+
g.settings.observe('showGrid.myMod', (name, settings) => console.log(name, settings.showGrid));
|
|
322
|
+
g.settings.setProperty('showGrid', false);
|
|
323
|
+
g.settings.unobserve('.myMod'); // remove every observer in the myMod namespace
|
|
324
|
+
|
|
325
|
+
// Run code after each redraw (the callback gets the redraw time in ms)
|
|
326
|
+
g.events.observeEvent('redraw.myMod', (event, ms) => console.log(`redrew in ${ms}ms`));
|
|
327
|
+
g.events.unobserveEvent('.myMod');
|
|
328
|
+
```
|
|
329
|
+
|
|
330
|
+
Moving the viewport this way doesn't add an undo step. Call
|
|
331
|
+
`g.debounceUserRequestedViewportChange()` afterwards if you want one.
|
|
332
|
+
|
|
187
333
|
### Regenerating for a new bundle
|
|
188
334
|
|
|
189
335
|
```sh
|
|
190
336
|
curl -o calculator.js "https://www.desmos.com/api/v1.13/calculator.js?apiKey=YOUR_API_KEY"
|
|
191
337
|
npm run generate:internals -- calculator.js
|
|
338
|
+
npm run snapshot:sketches -- calculator.js
|
|
192
339
|
npm test
|
|
193
340
|
```
|
|
194
341
|
|
|
342
|
+
`snapshot:sketches` re-renders real graph sketches into `test/fixtures/graph-sketches.ts`. If a
|
|
343
|
+
branch shape changed, `npm test` reports which field of which branch mode no longer matches.
|
|
344
|
+
|
|
195
345
|
The generator executes the bundle inside jsdom, so only run it on a bundle from desmos.com.
|
|
196
346
|
If `npm test` fails afterwards, the bundle changed in a way that contradicts a hand-written type.
|
|
197
347
|
The error names the field.
|
|
@@ -18,7 +18,7 @@ declare namespace Desmos.Internals.Generated {
|
|
|
18
18
|
bugsnagContext: string;
|
|
19
19
|
cachedGeoTokenDepths: Record<string, Array<Record<string, unknown>>>;
|
|
20
20
|
canShowKeyboardShortcuts: boolean;
|
|
21
|
-
checkSlowAnalysis
|
|
21
|
+
checkSlowAnalysis?: boolean;
|
|
22
22
|
clipboardHandlers: Record<string, (arg0?: any) => unknown>;
|
|
23
23
|
cooperativeGestureHint?: unknown;
|
|
24
24
|
cooperativeGestureHintTimeout?: unknown;
|
|
@@ -51,7 +51,7 @@ declare namespace Desmos.Internals.Generated {
|
|
|
51
51
|
isExpressionReplaceStrValidForReplace: boolean;
|
|
52
52
|
isExpressionSearchStrValidForReplace: boolean;
|
|
53
53
|
lastCursorContext?: unknown;
|
|
54
|
-
lastFrameTime
|
|
54
|
+
lastFrameTime?: number;
|
|
55
55
|
lastInfiniteScrollFirstDOM: HTMLDivElement;
|
|
56
56
|
lastInfiniteScrollLastDOM: HTMLDivElement;
|
|
57
57
|
lastParsableObjects: { abstract_item_2: Record<string, unknown>; abstract_item_3: Record<string, unknown>; abstract_item_4: Record<string, unknown>; abstract_item_5: Record<string, unknown>; abstract_item_6: Record<string, unknown>; abstract_item_7: { type: string; id: string; center: string; angle: string; width: string; height: string; opacity: string; mask: string; clickableInfo: Record<string, unknown>; description: string; draggable: boolean; moduleId?: unknown; guid: string; index: number; color: string; shouldGraph: boolean; showPoints: boolean }; abstract_item_8: { type: string; id: string; columns: Array<Record<string, unknown>>; regression?: unknown }; dcg_ticker_guid_internal: { type: string; id: string; handlerLatex: string; minStepLatex: string; shouldGraph: boolean }; dcg_viewport_statement_id_internal: { type: string; id: string; viewport: Record<string, unknown> } };
|
|
@@ -66,7 +66,7 @@ declare namespace Desmos.Internals.Generated {
|
|
|
66
66
|
pinchZoom: number;
|
|
67
67
|
progressUpdateLegendHidden: boolean;
|
|
68
68
|
raw(arg0?: unknown, arg1?: unknown): unknown;
|
|
69
|
-
requestedEvaluatorRestart
|
|
69
|
+
requestedEvaluatorRestart?: boolean;
|
|
70
70
|
rootElt: HTMLDivElement;
|
|
71
71
|
s(arg0?: unknown, arg1?: unknown): unknown;
|
|
72
72
|
sendActionToIframeConnect(): void;
|
|
@@ -1024,7 +1024,7 @@ declare namespace Desmos.Internals.Generated {
|
|
|
1024
1024
|
imageLayer: Grapher2DImageLayer;
|
|
1025
1025
|
isVisible: boolean;
|
|
1026
1026
|
lastActiveToken: { selected?: unknown; hovered?: unknown };
|
|
1027
|
-
lastTickViewport
|
|
1027
|
+
lastTickViewport?: Grapher2DLastTickViewport;
|
|
1028
1028
|
markLabelsDirty(): unknown;
|
|
1029
1029
|
movablePointsLayer: Grapher2DMovablePointsLayer;
|
|
1030
1030
|
poiController: Grapher2DPoiController;
|
|
@@ -1120,7 +1120,7 @@ declare namespace Desmos.Internals.Generated {
|
|
|
1120
1120
|
graphLineWidth: number;
|
|
1121
1121
|
guid: string;
|
|
1122
1122
|
hideCustomColors: boolean;
|
|
1123
|
-
highlight?:
|
|
1123
|
+
highlight?: boolean;
|
|
1124
1124
|
highlightPropertyMultipliers: Record<string, number[]>;
|
|
1125
1125
|
includeFunctionParametersInRandomSeed: boolean;
|
|
1126
1126
|
labelHangingColor: string;
|