rn-studio 0.2.1 → 0.3.1
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/bin/rn-studio-init.js +173 -0
- package/bin/rn-studio-server.js +143 -15
- package/dist/StudioProvider.d.ts +5 -18
- package/dist/StudioProvider.d.ts.map +1 -1
- package/dist/StudioProvider.js +190 -41
- package/dist/StudioProvider.js.map +1 -1
- package/dist/ast/AstEngine.d.ts.map +1 -1
- package/dist/ast/AstEngine.js +17 -0
- package/dist/ast/AstEngine.js.map +1 -1
- package/dist/ast/PreviewState.d.ts +41 -0
- package/dist/ast/PreviewState.d.ts.map +1 -0
- package/dist/ast/PreviewState.js +159 -0
- package/dist/ast/PreviewState.js.map +1 -0
- package/dist/ast/UndoStack.d.ts +18 -0
- package/dist/ast/UndoStack.d.ts.map +1 -0
- package/dist/ast/UndoStack.js +105 -0
- package/dist/ast/UndoStack.js.map +1 -0
- package/dist/components/AddPropertyModal.d.ts +19 -0
- package/dist/components/AddPropertyModal.d.ts.map +1 -0
- package/dist/components/AddPropertyModal.js +174 -0
- package/dist/components/AddPropertyModal.js.map +1 -0
- package/dist/components/InspectorPanel.js +101 -6
- package/dist/components/InspectorPanel.js.map +1 -1
- package/dist/components/SelectionOverlay.d.ts.map +1 -1
- package/dist/components/SelectionOverlay.js +5 -0
- package/dist/components/SelectionOverlay.js.map +1 -1
- package/dist/components/StyleEditor.d.ts +5 -3
- package/dist/components/StyleEditor.d.ts.map +1 -1
- package/dist/components/StyleEditor.js +45 -11
- package/dist/components/StyleEditor.js.map +1 -1
- package/dist/data/styleProperties.d.ts +26 -0
- package/dist/data/styleProperties.d.ts.map +1 -0
- package/dist/data/styleProperties.js +142 -0
- package/dist/data/styleProperties.js.map +1 -0
- package/dist/types.d.ts +37 -0
- package/dist/types.d.ts.map +1 -1
- package/dist/utils/autoScroll.d.ts +15 -0
- package/dist/utils/autoScroll.d.ts.map +1 -0
- package/dist/utils/autoScroll.js +132 -0
- package/dist/utils/autoScroll.js.map +1 -0
- package/dist/utils/findFiberBySource.d.ts +17 -0
- package/dist/utils/findFiberBySource.d.ts.map +1 -0
- package/dist/utils/findFiberBySource.js +76 -0
- package/dist/utils/findFiberBySource.js.map +1 -0
- package/dist/utils/persistence.d.ts +12 -0
- package/dist/utils/persistence.d.ts.map +1 -0
- package/dist/utils/persistence.js +44 -0
- package/dist/utils/persistence.js.map +1 -0
- package/package.json +3 -2
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.findFiberBySource = findFiberBySource;
|
|
4
|
+
/* eslint-disable @typescript-eslint/no-explicit-any */
|
|
5
|
+
function matchesSource(props, target) {
|
|
6
|
+
if (!props || typeof props !== 'object')
|
|
7
|
+
return false;
|
|
8
|
+
if (props.__rnStudioSource &&
|
|
9
|
+
props.__rnStudioSource.file === target.file &&
|
|
10
|
+
props.__rnStudioSource.line === target.line) {
|
|
11
|
+
return true;
|
|
12
|
+
}
|
|
13
|
+
if (props.__source &&
|
|
14
|
+
props.__source.fileName === target.file &&
|
|
15
|
+
props.__source.lineNumber === target.line) {
|
|
16
|
+
return true;
|
|
17
|
+
}
|
|
18
|
+
return false;
|
|
19
|
+
}
|
|
20
|
+
function walkFiber(fiber, target) {
|
|
21
|
+
if (!fiber)
|
|
22
|
+
return null;
|
|
23
|
+
const queue = [fiber];
|
|
24
|
+
let safety = 0;
|
|
25
|
+
while (queue.length && safety < 10000) {
|
|
26
|
+
safety++;
|
|
27
|
+
const node = queue.shift();
|
|
28
|
+
if (!node)
|
|
29
|
+
continue;
|
|
30
|
+
if (matchesSource(node.memoizedProps, target))
|
|
31
|
+
return node;
|
|
32
|
+
if (node.child)
|
|
33
|
+
queue.push(node.child);
|
|
34
|
+
if (node.sibling)
|
|
35
|
+
queue.push(node.sibling);
|
|
36
|
+
}
|
|
37
|
+
return null;
|
|
38
|
+
}
|
|
39
|
+
/**
|
|
40
|
+
* Public entry point. Returns the first matching fiber or null. Safe
|
|
41
|
+
* to call even if React DevTools isn't installed.
|
|
42
|
+
*/
|
|
43
|
+
function findFiberBySource(target) {
|
|
44
|
+
const hook = globalThis.__REACT_DEVTOOLS_GLOBAL_HOOK__;
|
|
45
|
+
if (!hook || !hook.renderers)
|
|
46
|
+
return null;
|
|
47
|
+
try {
|
|
48
|
+
const renderers = Array.from(hook.renderers.values());
|
|
49
|
+
for (const renderer of renderers) {
|
|
50
|
+
// Fiber roots may be exposed via `getFiberRoots(rendererID)` or a
|
|
51
|
+
// Set stored on the renderer itself; defensively handle both.
|
|
52
|
+
const rendererID = [...hook.renderers.keys()].find((k) => hook.renderers.get(k) === renderer);
|
|
53
|
+
let roots = null;
|
|
54
|
+
if (typeof hook.getFiberRoots === 'function' && rendererID != null) {
|
|
55
|
+
roots = hook.getFiberRoots(rendererID);
|
|
56
|
+
}
|
|
57
|
+
if (!roots && renderer.getFiberRoots) {
|
|
58
|
+
roots = renderer.getFiberRoots();
|
|
59
|
+
}
|
|
60
|
+
if (!roots)
|
|
61
|
+
continue;
|
|
62
|
+
for (const root of roots) {
|
|
63
|
+
const fiberRoot = root.current || root;
|
|
64
|
+
const found = walkFiber(fiberRoot, target);
|
|
65
|
+
if (found)
|
|
66
|
+
return found;
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
catch {
|
|
71
|
+
// DevTools hook internals shift between RN versions; swallow any
|
|
72
|
+
// reflection errors — re-selection is best-effort.
|
|
73
|
+
}
|
|
74
|
+
return null;
|
|
75
|
+
}
|
|
76
|
+
//# sourceMappingURL=findFiberBySource.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"findFiberBySource.js","sourceRoot":"","sources":["../../src/utils/findFiberBySource.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* persistence
|
|
3
|
+
*
|
|
4
|
+
* Lightweight AsyncStorage wrapper for persisting the last-selected
|
|
5
|
+
* component source across full JS reloads (Cmd+R). Falls back to a
|
|
6
|
+
* no-op in environments where AsyncStorage isn't installed.
|
|
7
|
+
*/
|
|
8
|
+
import type { SourceLocation } from '../types';
|
|
9
|
+
export declare function saveLastSelection(source: SourceLocation): Promise<void>;
|
|
10
|
+
export declare function loadLastSelection(): Promise<SourceLocation | null>;
|
|
11
|
+
export declare function clearLastSelection(): Promise<void>;
|
|
12
|
+
//# sourceMappingURL=persistence.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"persistence.d.ts","sourceRoot":"","sources":["../../src/utils/persistence.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,UAAU,CAAC;AAU/C,wBAAsB,iBAAiB,CAAC,MAAM,EAAE,cAAc,GAAG,OAAO,CAAC,IAAI,CAAC,CAK7E;AAED,wBAAsB,iBAAiB,IAAI,OAAO,CAAC,cAAc,GAAG,IAAI,CAAC,CAWxE;AAED,wBAAsB,kBAAkB,IAAI,OAAO,CAAC,IAAI,CAAC,CAKxD"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.saveLastSelection = saveLastSelection;
|
|
4
|
+
exports.loadLastSelection = loadLastSelection;
|
|
5
|
+
exports.clearLastSelection = clearLastSelection;
|
|
6
|
+
/* eslint-disable @typescript-eslint/no-var-requires */
|
|
7
|
+
let AsyncStorage = null;
|
|
8
|
+
try {
|
|
9
|
+
AsyncStorage = require('@react-native-async-storage/async-storage').default;
|
|
10
|
+
}
|
|
11
|
+
catch { }
|
|
12
|
+
const KEY = '@rn-studio/last-selection';
|
|
13
|
+
async function saveLastSelection(source) {
|
|
14
|
+
if (!AsyncStorage)
|
|
15
|
+
return;
|
|
16
|
+
try {
|
|
17
|
+
await AsyncStorage.setItem(KEY, JSON.stringify(source));
|
|
18
|
+
}
|
|
19
|
+
catch { }
|
|
20
|
+
}
|
|
21
|
+
async function loadLastSelection() {
|
|
22
|
+
if (!AsyncStorage)
|
|
23
|
+
return null;
|
|
24
|
+
try {
|
|
25
|
+
const raw = await AsyncStorage.getItem(KEY);
|
|
26
|
+
if (!raw)
|
|
27
|
+
return null;
|
|
28
|
+
const parsed = JSON.parse(raw);
|
|
29
|
+
if (parsed && parsed.file && typeof parsed.line === 'number') {
|
|
30
|
+
return parsed;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
catch { }
|
|
34
|
+
return null;
|
|
35
|
+
}
|
|
36
|
+
async function clearLastSelection() {
|
|
37
|
+
if (!AsyncStorage)
|
|
38
|
+
return;
|
|
39
|
+
try {
|
|
40
|
+
await AsyncStorage.removeItem(KEY);
|
|
41
|
+
}
|
|
42
|
+
catch { }
|
|
43
|
+
}
|
|
44
|
+
//# sourceMappingURL=persistence.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"persistence.js","sourceRoot":"","sources":["../../src/utils/persistence.ts"],"names":[],"mappings":";;AAiBA,8CAKC;AAED,8CAWC;AAED,gDAKC;AAjCD,uDAAuD;AACvD,IAAI,YAAY,GAAQ,IAAI,CAAC;AAC7B,IAAI,CAAC;IACH,YAAY,GAAG,OAAO,CAAC,2CAA2C,CAAC,CAAC,OAAO,CAAC;AAC9E,CAAC;AAAC,MAAM,CAAC,CAAA,CAAC;AAEV,MAAM,GAAG,GAAG,2BAA2B,CAAC;AAEjC,KAAK,UAAU,iBAAiB,CAAC,MAAsB;IAC5D,IAAI,CAAC,YAAY;QAAE,OAAO;IAC1B,IAAI,CAAC;QACH,MAAM,YAAY,CAAC,OAAO,CAAC,GAAG,EAAE,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC;IAC1D,CAAC;IAAC,MAAM,CAAC,CAAA,CAAC;AACZ,CAAC;AAEM,KAAK,UAAU,iBAAiB;IACrC,IAAI,CAAC,YAAY;QAAE,OAAO,IAAI,CAAC;IAC/B,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,MAAM,YAAY,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;QAC5C,IAAI,CAAC,GAAG;YAAE,OAAO,IAAI,CAAC;QACtB,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;QAC/B,IAAI,MAAM,IAAI,MAAM,CAAC,IAAI,IAAI,OAAO,MAAM,CAAC,IAAI,KAAK,QAAQ,EAAE,CAAC;YAC7D,OAAO,MAAwB,CAAC;QAClC,CAAC;IACH,CAAC;IAAC,MAAM,CAAC,CAAA,CAAC;IACV,OAAO,IAAI,CAAC;AACd,CAAC;AAEM,KAAK,UAAU,kBAAkB;IACtC,IAAI,CAAC,YAAY;QAAE,OAAO;IAC1B,IAAI,CAAC;QACH,MAAM,YAAY,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;IACrC,CAAC;IAAC,MAAM,CAAC,CAAA,CAAC;AACZ,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "rn-studio",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.3.1",
|
|
4
4
|
"description": "Live UI editor for React Native — inspect and edit components directly in your emulator",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -11,7 +11,8 @@
|
|
|
11
11
|
"README.md"
|
|
12
12
|
],
|
|
13
13
|
"bin": {
|
|
14
|
-
"rn-studio-server": "./bin/rn-studio-server.js"
|
|
14
|
+
"rn-studio-server": "./bin/rn-studio-server.js",
|
|
15
|
+
"rn-studio-init": "./bin/rn-studio-init.js"
|
|
15
16
|
},
|
|
16
17
|
"scripts": {
|
|
17
18
|
"build": "tsc",
|