@vskin/sdk 0.1.0 → 0.2.0
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 +5 -0
- package/dist/{chunk-KADQENVR.js → chunk-Y4CYVADH.js} +32 -7
- package/dist/chunk-Y4CYVADH.js.map +1 -0
- package/dist/embed.js +30 -4
- package/dist/embed.js.map +1 -1
- package/dist/index.cjs +30 -4
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +2 -2
- package/dist/index.d.ts +2 -2
- package/dist/index.js +2 -2
- package/dist/{interfaces-OatKvSe8.d.cts → interfaces-iOmXANSI.d.cts} +11 -3
- package/dist/{interfaces-OatKvSe8.d.ts → interfaces-iOmXANSI.d.ts} +11 -3
- package/dist/react.cjs +21 -4
- package/dist/react.cjs.map +1 -1
- package/dist/react.d.cts +1 -1
- package/dist/react.d.ts +1 -1
- package/dist/react.js +1 -1
- package/package.json +1 -1
- package/dist/chunk-KADQENVR.js.map +0 -1
package/dist/index.cjs
CHANGED
|
@@ -105,8 +105,15 @@ var EErrorCode = /* @__PURE__ */ ((EErrorCode2) => {
|
|
|
105
105
|
EErrorCode2["NOT_READY"] = "not_ready";
|
|
106
106
|
EErrorCode2["RATE_LIMITED"] = "rate_limited";
|
|
107
107
|
EErrorCode2["INTERNAL"] = "internal";
|
|
108
|
+
EErrorCode2["REFUSED"] = "refused";
|
|
108
109
|
return EErrorCode2;
|
|
109
110
|
})(EErrorCode || {});
|
|
111
|
+
var ERefusalFamily = /* @__PURE__ */ ((ERefusalFamily2) => {
|
|
112
|
+
ERefusalFamily2["SETUP"] = "setup";
|
|
113
|
+
ERefusalFamily2["CUT_OFF"] = "cut_off";
|
|
114
|
+
ERefusalFamily2["OUTAGE"] = "outage";
|
|
115
|
+
return ERefusalFamily2;
|
|
116
|
+
})(ERefusalFamily || {});
|
|
110
117
|
var EViewerEvent = /* @__PURE__ */ ((EViewerEvent2) => {
|
|
111
118
|
EViewerEvent2["READY"] = "ready";
|
|
112
119
|
EViewerEvent2["ERROR"] = "error";
|
|
@@ -123,6 +130,7 @@ var EViewerEvent = /* @__PURE__ */ ((EViewerEvent2) => {
|
|
|
123
130
|
EViewerEvent2["PLACEMENT_START"] = "placementstart";
|
|
124
131
|
EViewerEvent2["PLACEMENT_MOVE"] = "placementmove";
|
|
125
132
|
EViewerEvent2["PLACEMENT_END"] = "placementend";
|
|
133
|
+
EViewerEvent2["REFUSED"] = "refused";
|
|
126
134
|
return EViewerEvent2;
|
|
127
135
|
})(EViewerEvent || {});
|
|
128
136
|
|
|
@@ -345,13 +353,15 @@ var performHandshake = ({
|
|
|
345
353
|
transport,
|
|
346
354
|
iframe,
|
|
347
355
|
mirror,
|
|
348
|
-
onGiveUp
|
|
356
|
+
onGiveUp,
|
|
357
|
+
subscribeRefusal
|
|
349
358
|
}) => new Promise((resolve, reject) => {
|
|
350
359
|
let settled = false;
|
|
351
360
|
const beginAt = Date.now();
|
|
352
361
|
const settle = () => {
|
|
353
362
|
settled = true;
|
|
354
363
|
iframe.removeEventListener("load", attempt);
|
|
364
|
+
unsubscribeRefusal();
|
|
355
365
|
};
|
|
356
366
|
const attempt = () => {
|
|
357
367
|
if (settled) return;
|
|
@@ -360,7 +370,7 @@ var performHandshake = ({
|
|
|
360
370
|
onGiveUp();
|
|
361
371
|
return reject({
|
|
362
372
|
code: "invalid_key" /* INVALID_KEY */,
|
|
363
|
-
message: "the viewer never answered: the
|
|
373
|
+
message: "the viewer never answered: the render service is unreachable, or the frame was blocked before the page could boot"
|
|
364
374
|
});
|
|
365
375
|
}
|
|
366
376
|
transport.send({
|
|
@@ -376,6 +386,15 @@ var performHandshake = ({
|
|
|
376
386
|
resolve();
|
|
377
387
|
}).catch(() => setTimeout(attempt, HELLO_RETRY_MS));
|
|
378
388
|
};
|
|
389
|
+
const unsubscribeRefusal = subscribeRefusal(({ family }) => {
|
|
390
|
+
if (settled) return;
|
|
391
|
+
settle();
|
|
392
|
+
reject({
|
|
393
|
+
code: "refused" /* REFUSED */,
|
|
394
|
+
family,
|
|
395
|
+
message: "the embed server refused this viewer; its family says whose problem it is"
|
|
396
|
+
});
|
|
397
|
+
});
|
|
379
398
|
iframe.addEventListener("load", attempt);
|
|
380
399
|
setTimeout(attempt, HELLO_RETRY_MS);
|
|
381
400
|
});
|
|
@@ -410,6 +429,10 @@ var createViewer = ({
|
|
|
410
429
|
let destroyed = false;
|
|
411
430
|
let greeted = false;
|
|
412
431
|
let greetingAgain = false;
|
|
432
|
+
const subscribeRefusal = (handler) => hub.on(
|
|
433
|
+
"refused" /* REFUSED */,
|
|
434
|
+
(payload) => handler(payload)
|
|
435
|
+
);
|
|
413
436
|
const greetAgain = () => {
|
|
414
437
|
if (!greeted || greetingAgain || destroyed) return;
|
|
415
438
|
greetingAgain = true;
|
|
@@ -420,7 +443,8 @@ var createViewer = ({
|
|
|
420
443
|
mirror,
|
|
421
444
|
// A reload that never answers leaves the viewer as it is: the frame is the
|
|
422
445
|
// integrator's to keep or drop, and an error says so.
|
|
423
|
-
onGiveUp: () => void 0
|
|
446
|
+
onGiveUp: () => void 0,
|
|
447
|
+
subscribeRefusal
|
|
424
448
|
}).then(
|
|
425
449
|
() => hub.dispatch({
|
|
426
450
|
name: "reconnect" /* RECONNECT */,
|
|
@@ -461,7 +485,8 @@ var createViewer = ({
|
|
|
461
485
|
transport,
|
|
462
486
|
iframe,
|
|
463
487
|
mirror,
|
|
464
|
-
onGiveUp: destroy
|
|
488
|
+
onGiveUp: destroy,
|
|
489
|
+
subscribeRefusal
|
|
465
490
|
}).then(() => {
|
|
466
491
|
greeted = true;
|
|
467
492
|
return viewer;
|
|
@@ -476,6 +501,7 @@ exports.EErrorCode = EErrorCode;
|
|
|
476
501
|
exports.EFacing = EFacing;
|
|
477
502
|
exports.EFeature = EFeature;
|
|
478
503
|
exports.EHandedness = EHandedness;
|
|
504
|
+
exports.ERefusalFamily = ERefusalFamily;
|
|
479
505
|
exports.ESubject = ESubject;
|
|
480
506
|
exports.EView = EView;
|
|
481
507
|
exports.EViewerEvent = EViewerEvent;
|
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/lib/constants.ts","../src/contract/interfaces.ts","../src/lib/helpers/buildEmbedUrl.ts","../src/protocol/interfaces.ts","../src/lib/helpers/buildViewerHandle.ts","../src/lib/helpers/createEmbedIframe.ts","../src/lib/helpers/createViewerEventHub.ts","../src/lib/helpers/createCommandId.ts","../src/protocol/constants.ts","../src/lib/helpers/createViewerTransport.ts","../src/lib/helpers/performHandshake.ts","../src/lib/createViewer.ts","../src/lib/buildInspectLink.ts"],"names":["EView","EBackgroundType","EFacing","EHandedness","ESubject","EFeature","EErrorCode","EViewerEvent"],"mappings":"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","file":"index.cjs","sourcesContent":["// Where the viewer lives when the integration does not say otherwise.\nexport const DEFAULT_BASE_URL = 'https://render.vskin.gg';\n\n// The embed page answers the handshake as soon as its bridge is up — retried because the page\n// boots asynchronously behind the iframe's load event.\nexport const HELLO_RETRY_MS = 300;\nexport const HELLO_TIMEOUT_MS = 15000;\n\n// A command that never comes back (the page died, the network broke) must not hang a client's\n// await forever.\nexport const COMMAND_TIMEOUT_MS = 30000;\n\n// The command Steam itself serves in its inventory and market payloads. The space is\n// percent-encoded on purpose: a literal space truncates the steam:// command.\nexport const CS2_INSPECT_LINK_PREFIX =\n 'steam://run/730//+csgo_econ_action_preview%20';\n","// The viewer's public vocabulary: domain words only, no abbreviation, one options object per\n// method, enums whose values ARE the strings a plain-JavaScript consumer writes.\n\nexport enum EView {\n FREE = 'free',\n FIRST_PERSON = 'firstPerson',\n THIRD_PERSON = 'thirdPerson',\n}\n\n// The background is a VALUE, not a boolean: `none` composites the canvas straight onto your\n// page (put your own background behind the viewer), `environment` shows the map's own decor.\nexport enum EBackgroundType {\n NONE = 'none',\n ENVIRONMENT = 'environment',\n}\n\nexport type Background = {\n type: EBackgroundType;\n};\n\nexport enum EFacing {\n FRONT = 'front',\n BACK = 'back',\n}\n\nexport enum EHandedness {\n RIGHT = 'right',\n LEFT = 'left',\n}\n\n// Which of the two picked items the free view presents when a weapon and a pair of gloves are\n// both on stage.\nexport enum ESubject {\n WEAPON = 'weapon',\n GLOVES = 'gloves',\n}\n\n// The weapon as you describe it — identity, roll, marks — in the market's own words (`seed`\n// and `float`). The viewer owns the road to it: a seed or float alone re-rolls in place, a\n// name alone re-engraves the plate, a new identity re-mounts.\nexport type Weapon = {\n // The inspect certificate (hex), the market door: it carries identity, roll and cosmetics.\n cert?: string;\n // The manual door: the item's definition and finish indices.\n defIndex?: number;\n paintIndex?: number;\n seed?: number;\n float?: number;\n stattrak?: boolean;\n kills?: number;\n name?: string;\n};\n\nexport type Gloves = {\n cert?: string;\n defIndex?: number;\n paintIndex?: number;\n seed?: number;\n float?: number;\n};\n\nexport type Agent = {\n // The inspect certificate (hex): a character travels by cert too, patches included.\n cert?: string;\n defIndex?: number;\n};\n\nexport type Sticker = {\n id: number;\n slot: number;\n wear?: number;\n rotation?: number;\n offsetX?: number;\n offsetY?: number;\n};\n\nexport type Charm = {\n id: number;\n pattern?: number;\n // The display-case family: the sticker sealed inside the slab, by its id.\n wrappedSticker?: number;\n // The charm's placement, as a DELTA from the weapon's default hook in the weapon's model\n // space (Source inches) — the same numbers a free-placement drag settles on. Absent = the\n // authored hook. The state mirror's `charmAnchor` publishes the composed ABSOLUTE.\n offsetX?: number;\n offsetY?: number;\n offsetZ?: number;\n};\n\nexport type Patch = {\n id: number;\n slot: number;\n};\n\n// First-person dials in the GAME's units: `fov` is viewmodel_fov degrees, offsets are\n// viewmodel_offset inches. A new dial is a new FIELD here, never a new method.\nexport type FirstPersonSettings = {\n fov?: number;\n offsetX?: number;\n offsetY?: number;\n offsetZ?: number;\n handedness?: EHandedness;\n};\n\n// The camera's flight target. A sticker is named by its STABLE uid (a certificate may repeat a\n// slot, so a slot is not an identity); the state mirror publishes each sticker's uid.\nexport type FocusTarget =\n | { kind: 'sticker'; uid: string }\n | { kind: 'charm' }\n | { kind: 'patch'; slot: number }\n | null;\n\n// What the free-placement mode is armed on: while armed, pressing that cosmetic in the canvas\n// MOVES it instead of orbiting the item. Null disarms.\nexport type PlacementTarget =\n { kind: 'sticker'; slot: number } | { kind: 'charm' } | null;\n\n// One capability, two layers already intersected for you: `entitled` is what the plan bought\n// (stable for the session), `available` folds in what the current scene can serve (moving;\n// `capabilitieschange` fires when it does).\nexport type Capability = {\n entitled: boolean;\n available: boolean;\n};\n\nexport enum EFeature {\n SELECT_WEAPON = 'selectWeapon',\n SELECT_GLOVES = 'selectGloves',\n SELECT_AGENT = 'selectAgent',\n SELECT_ENVIRONMENT = 'selectEnvironment',\n EDIT_SEED = 'editSeed',\n EDIT_FLOAT = 'editFloat',\n EDIT_STATTRAK = 'editStattrak',\n EDIT_NAMETAG = 'editNametag',\n SELECT_STICKER = 'selectSticker',\n SELECT_CHARM = 'selectCharm',\n SELECT_PATCH = 'selectPatch',\n EDIT_STICKERS = 'editStickers',\n EDIT_CHARMS = 'editCharms',\n PLACE_STICKERS = 'placeStickers',\n PLACE_CHARM = 'placeCharm',\n SCREENSHOT = 'screenshot',\n INSPECT_LINK = 'inspectLink',\n SUBJECT_CONTROLS = 'subjectControls',\n WEAPON_ANIMATIONS = 'weaponAnimations',\n AGENT_ANIMATIONS = 'agentAnimations',\n}\n\nexport type ViewerCapabilities = {\n views: Record<EView, Capability>;\n features: Record<EFeature, Capability>;\n};\n\n// One animation the scene can play, with the one fact you need to offer it honestly: a\n// looping clip is a toggle, a one-shot replays.\nexport type AnimationEntry = {\n name: string;\n loop: boolean;\n};\n\n// The synchronous mirror: the last known truth, re-published whole on every `change` event.\n// Read it without ever awaiting.\nexport type ViewerState = {\n weapon: Weapon | null;\n gloves: Gloves | null;\n agent: Agent | null;\n subject: ESubject | null;\n view: { view: EView; active: boolean };\n environment: string | null;\n background: Background;\n stickers: Array<Sticker & { uid?: string }>;\n charm: Charm | null;\n // Where the charm actually sits, in the form a cert names it: the composed ABSOLUTE\n // position in the weapon's model space, read off the manifest the render is using.\n charmAnchor: [number, number, number] | null;\n patches: Array<Patch>;\n // How many patch slots the mounted character authors — the render's own answer, read off\n // its landed manifest. null while no character manifest has answered (none asked, or still\n // composing): 0 is a real answer, \"this body authors none\".\n patchSlots: number | null;\n playing: boolean;\n animation: string | null;\n animations: Array<AnimationEntry>;\n // The character's celebrations: what the mounted body can play beyond its resting posture,\n // and the one running right now (null at rest). Driven through the same playAnimation /\n // stopAnimation door as the weapon clips.\n agentAnimation: string | null;\n agentAnimations: Array<string>;\n sound: { muted: boolean };\n firstPerson: FirstPersonSettings;\n facing: EFacing;\n placement: PlacementTarget;\n};\n","import type { Background, Weapon } from '@/contract/interfaces';\nimport { EBackgroundType } from '@/contract/interfaces';\n\n// The embed page's URL grammar, written once: the boot seed rides the URL, everything after\n// boot rides the protocol.\nexport const buildEmbedUrl = ({\n baseUrl,\n key,\n weapon,\n environment,\n background,\n interactive,\n autoplay,\n locale,\n}: {\n baseUrl: string;\n key?: string;\n weapon?: Weapon;\n environment?: string;\n background?: Background;\n interactive?: boolean;\n autoplay?: boolean;\n locale?: string;\n}): string => {\n const query = new URLSearchParams();\n if (key) query.set('key', key);\n if (weapon?.cert) {\n query.set('cert', weapon.cert);\n } else if (\n weapon &&\n typeof weapon.defIndex === 'number' &&\n typeof weapon.paintIndex === 'number'\n ) {\n query.set('def', String(weapon.defIndex));\n query.set('paint', String(weapon.paintIndex));\n if (weapon.seed !== undefined) query.set('seed', String(weapon.seed));\n if (weapon.float !== undefined)\n query.set('float', String(weapon.float));\n if (weapon.stattrak) query.set('stattrak', '1');\n if (weapon.kills !== undefined)\n query.set('kills', String(weapon.kills));\n if (weapon.name !== undefined) query.set('name', weapon.name);\n }\n if (environment) query.set('env', environment);\n if (background?.type === EBackgroundType.NONE)\n query.set('backdrop', 'false');\n if (interactive === false) query.set('interactive', 'false');\n if (autoplay) query.set('autoplay', '1');\n if (locale) query.set('lang', locale);\n const suffix = query.toString();\n return `${baseUrl}/v1/sdk${suffix ? `?${suffix}` : ''}`;\n};\n","// The wire format of the embed protocol, client side. Every name here is contract: a change is\n// an addition, never a redefinition.\n\nexport enum EProtocolMessageKind {\n COMMAND = 'command',\n RESPONSE = 'response',\n EVENT = 'event',\n // The viewer page saying \"I just started, greet me\". It carries no data, and the SDK answers\n // it with the handshake — which is what makes a reloaded viewer pick itself back up.\n ANNOUNCE = 'announce',\n}\n\n// The CLOSED error vocabulary. A code's meaning never changes; branch behavior on the code,\n// never on the message text.\nexport enum EErrorCode {\n INVALID_KEY = 'invalid_key',\n ORIGIN_NOT_ALLOWED = 'origin_not_allowed',\n NOT_ENTITLED = 'not_entitled',\n UNSUPPORTED_VIEW = 'unsupported_view',\n UNAVAILABLE_ITEM = 'unavailable_item',\n INVALID_ARGUMENT = 'invalid_argument',\n NOT_READY = 'not_ready',\n RATE_LIMITED = 'rate_limited',\n INTERNAL = 'internal',\n}\n\nexport enum EProtocolCommand {\n HELLO = 'hello',\n SET_WEAPON = 'setWeapon',\n SET_GLOVES = 'setGloves',\n SET_AGENT = 'setAgent',\n SET_SUBJECT = 'setSubject',\n SET_STICKERS = 'setStickers',\n SET_CHARM = 'setCharm',\n SET_PATCHES = 'setPatches',\n SET_VIEW = 'setView',\n SET_FIRST_PERSON_SETTINGS = 'setFirstPersonSettings',\n SET_FACING = 'setFacing',\n SET_ENVIRONMENT = 'setEnvironment',\n SET_BACKGROUND = 'setBackground',\n FOCUS = 'focus',\n RESET_CAMERA = 'resetCamera',\n PLAY = 'play',\n PAUSE = 'pause',\n PLAY_ANIMATION = 'playAnimation',\n STOP_ANIMATION = 'stopAnimation',\n START_FIRE = 'startFire',\n STOP_FIRE = 'stopFire',\n SET_SOUND = 'setSound',\n SET_LOCALE = 'setLocale',\n ARM_PLACEMENT = 'armPlacement',\n FORWARD_POINTER = 'forwardPointer',\n CAPTURE = 'capture',\n CATALOG_WEAPONS = 'catalogWeapons',\n CATALOG_STICKERS = 'catalogStickers',\n CATALOG_CHARMS = 'catalogCharms',\n CATALOG_PATCHES = 'catalogPatches',\n CATALOG_AGENTS = 'catalogAgents',\n CATALOG_WEAPON_MODELS = 'catalogWeaponModels',\n CATALOG_ENVIRONMENTS = 'catalogEnvironments',\n DESTROY = 'destroy',\n}\n\n// Every event the viewer emits, in glued lowercase: `<thing>change` for a state change (always\n// carrying what changed), a `start`/`move`/`end` triplet for a continuous gesture, a bare noun\n// for an isolated fact.\nexport enum EViewerEvent {\n READY = 'ready',\n ERROR = 'error',\n // The viewer reloaded and was greeted again: everything you had set is gone with the page\n // it lived in, and the scene is blank. Re-apply what you want on screen when you get this.\n RECONNECT = 'reconnect',\n PROGRESS = 'progress',\n UNAVAILABLE = 'unavailable',\n CHANGE = 'change',\n VIEW_CHANGE = 'viewchange',\n SUBJECT_CHANGE = 'subjectchange',\n COSMETICS_CHANGE = 'cosmeticschange',\n ANIMATION_CHANGE = 'animationchange',\n PLAYBACK_CHANGE = 'playbackchange',\n CAPABILITIES_CHANGE = 'capabilitieschange',\n PLACEMENT_START = 'placementstart',\n PLACEMENT_MOVE = 'placementmove',\n PLACEMENT_END = 'placementend',\n}\n\nexport type ViewerError = {\n code: EErrorCode;\n message?: string;\n};\n\nexport type ProtocolResponseMessage = {\n source: string;\n version: number;\n kind: EProtocolMessageKind.RESPONSE;\n id: string;\n} & ({ ok: true; value?: unknown } | { ok: false; error: ViewerError });\n\nexport type ProtocolEventMessage = {\n source: string;\n version: number;\n kind: EProtocolMessageKind.EVENT;\n name: EViewerEvent;\n payload?: unknown;\n};\n","import type { ViewerCapabilities, ViewerState } from '@/contract/interfaces';\nimport type { Viewer, ViewerMirror } from '@/lib/interfaces';\nimport type { ViewerEventHub } from '@/lib/helpers/createViewerEventHub';\nimport type { ViewerTransport } from '@/lib/helpers/createViewerTransport';\nimport { EProtocolCommand } from '@/protocol/interfaces';\n\n// The typed handle the integrator holds: every method one options object, one command, one\n// promise. The state and capability getters read the mirror synchronously — never an await.\nexport const buildViewerHandle = ({\n transport,\n hub,\n mirror,\n iframe,\n destroy,\n}: {\n transport: ViewerTransport;\n hub: ViewerEventHub;\n mirror: ViewerMirror;\n iframe: HTMLIFrameElement;\n destroy: () => void;\n}): Viewer => {\n const command = (\n name: EProtocolCommand,\n payload?: unknown,\n ): Promise<void> => transport.send({ name, payload }).then(() => undefined);\n\n return {\n get state() {\n return mirror.state as ViewerState;\n },\n get capabilities() {\n return mirror.capabilities as ViewerCapabilities;\n },\n on: (event, handler) => hub.on(event, handler),\n setWeapon: (args) => command(EProtocolCommand.SET_WEAPON, args),\n setGloves: (args) => command(EProtocolCommand.SET_GLOVES, args),\n setAgent: (args) => command(EProtocolCommand.SET_AGENT, args),\n setSubject: (args) => command(EProtocolCommand.SET_SUBJECT, args),\n setStickers: (args) => command(EProtocolCommand.SET_STICKERS, args),\n setCharm: (args) => command(EProtocolCommand.SET_CHARM, args),\n setPatches: (args) => command(EProtocolCommand.SET_PATCHES, args),\n setView: (args) => command(EProtocolCommand.SET_VIEW, args),\n setFirstPersonSettings: (args) =>\n command(EProtocolCommand.SET_FIRST_PERSON_SETTINGS, args),\n setFacing: (args) => command(EProtocolCommand.SET_FACING, args),\n setEnvironment: (args) =>\n command(EProtocolCommand.SET_ENVIRONMENT, args),\n setBackground: (args) => command(EProtocolCommand.SET_BACKGROUND, args),\n setSound: (args) => command(EProtocolCommand.SET_SOUND, args),\n setLocale: (args) => command(EProtocolCommand.SET_LOCALE, args),\n focus: (args) => command(EProtocolCommand.FOCUS, args),\n resetCamera: () => command(EProtocolCommand.RESET_CAMERA),\n play: () => command(EProtocolCommand.PLAY),\n pause: () => command(EProtocolCommand.PAUSE),\n playAnimation: (args) => command(EProtocolCommand.PLAY_ANIMATION, args),\n stopAnimation: () => command(EProtocolCommand.STOP_ANIMATION),\n startFire: () => command(EProtocolCommand.START_FIRE),\n stopFire: () => command(EProtocolCommand.STOP_FIRE),\n armPlacement: (args) => command(EProtocolCommand.ARM_PLACEMENT, args),\n forwardPointer: ({ x, y, phase }) => {\n const rect = iframe.getBoundingClientRect();\n return command(EProtocolCommand.FORWARD_POINTER, {\n x: x - rect.left,\n y: y - rect.top,\n phase,\n });\n },\n capture: () =>\n transport\n .send({ name: EProtocolCommand.CAPTURE })\n .then((value) => (value as { image: string }).image),\n catalog: {\n weapons: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_WEAPONS,\n payload: query,\n }),\n stickers: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_STICKERS,\n payload: query,\n }),\n charms: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_CHARMS,\n payload: query,\n }),\n patches: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_PATCHES,\n payload: query,\n }),\n agents: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_AGENTS,\n payload: query,\n }),\n weaponModels: () =>\n transport.send({\n name: EProtocolCommand.CATALOG_WEAPON_MODELS,\n }),\n environments: () =>\n transport.send({\n name: EProtocolCommand.CATALOG_ENVIRONMENTS,\n }),\n },\n destroy,\n };\n};\n","// The viewer's frame: an implementation detail the integrator never touches, filling the\n// container it is handed.\nexport const createEmbedIframe = ({\n src,\n}: {\n src: string;\n}): HTMLIFrameElement => {\n const iframe = document.createElement('iframe');\n iframe.src = src;\n iframe.style.width = '100%';\n iframe.style.height = '100%';\n iframe.style.display = 'block';\n iframe.style.border = '0';\n // Browsers composite a dark-scheme iframe on a light host as OPAQUE: pinning the scheme is\n // what keeps the transparent background actually transparent. You never have to know this.\n iframe.style.colorScheme = 'normal';\n iframe.allow = 'fullscreen';\n return iframe;\n};\n","import type { ViewerCapabilities, ViewerState } from '@/contract/interfaces';\nimport type { ViewerEventHandler, ViewerMirror } from '@/lib/interfaces';\nimport { EViewerEvent } from '@/protocol/interfaces';\n\nexport type ViewerEventHub = {\n on: (event: string, handler: ViewerEventHandler) => () => void;\n dispatch: ({ name, payload }: { name: string; payload: unknown }) => void;\n clear: () => void;\n};\n\n// The subscription side of the viewer, and the mirror's one writer: a `change` carries the\n// whole state, `capabilitieschange` the whole capability map — absorbed before the handlers\n// run, so a handler reading `viewer.state` already sees the truth it was told about.\nexport const createViewerEventHub = ({\n mirror,\n}: {\n mirror: ViewerMirror;\n}): ViewerEventHub => {\n const handlers = new Map<string, Set<ViewerEventHandler>>();\n\n return {\n on: (event, handler) => {\n const set = handlers.get(event) ?? new Set();\n set.add(handler);\n handlers.set(event, set);\n return () => {\n set.delete(handler);\n };\n },\n dispatch: ({ name, payload }) => {\n if (name === EViewerEvent.CHANGE) {\n const change = payload as { state?: ViewerState } | undefined;\n if (change?.state) mirror.state = change.state;\n }\n if (name === EViewerEvent.CAPABILITIES_CHANGE) {\n const change = payload as\n { capabilities?: ViewerCapabilities } | undefined;\n if (change?.capabilities)\n mirror.capabilities = change.capabilities;\n }\n for (const handler of handlers.get(name) ?? []) handler(payload);\n },\n clear: () => handlers.clear(),\n };\n};\n","let sequence = 0;\n\n// Correlation ids only need to be unique within one page's lifetime; the random prefix keeps\n// two viewers on the same page from ever colliding.\nconst prefix = Math.random().toString(36).slice(2, 8);\n\nexport const createCommandId = (): string => `${prefix}-${++sequence}`;\n","// The wire identity of every message crossing the iframe boundary. This file is the PUBLIC\n// twin of the render service's own declaration: the package cannot depend on private code, so\n// the wire format is declared on both sides and a conformity bench proves they never drift.\nexport const PROTOCOL_SOURCE = 'vskin-render';\n\n// One dial only: the protocol version this package ships is the version it speaks — never\n// overridden at run time. The service supports the current version and the previous one.\nexport const PROTOCOL_VERSION = 1;\n","import { COMMAND_TIMEOUT_MS } from '@/lib/constants';\nimport { createCommandId } from '@/lib/helpers/createCommandId';\nimport { PROTOCOL_SOURCE, PROTOCOL_VERSION } from '@/protocol/constants';\nimport { EErrorCode, EProtocolMessageKind } from '@/protocol/interfaces';\nimport type { ViewerError } from '@/protocol/interfaces';\n\nexport type ViewerTransport = {\n send: (args: {\n name: string;\n payload?: unknown;\n timeoutMs?: number;\n }) => Promise<unknown>;\n start: () => void;\n stop: () => void;\n // Settles every pending command with the given refusal — the teardown's last word.\n rejectAll: (args: { message: string }) => void;\n};\n\n// The wire side of the viewer: posts commands to the iframe at its precise origin, correlates\n// the one response each command gets, forwards events up. Everything else on the shared\n// `window` is ignored — responses are accepted only from OUR iframe's window AND origin.\nexport const createViewerTransport = ({\n iframe,\n embedOrigin,\n isDestroyed,\n onEvent,\n onAnnounce,\n}: {\n iframe: HTMLIFrameElement;\n embedOrigin: string;\n isDestroyed: () => boolean;\n onEvent: ({ name, payload }: { name: string; payload: unknown }) => void;\n // The page saying it just started. Fires on its first boot and again on every reload.\n onAnnounce: () => void;\n}): ViewerTransport => {\n const pending = new Map<\n string,\n {\n resolve: (value: unknown) => void;\n reject: (error: ViewerError) => void;\n timer: ReturnType<typeof setTimeout>;\n }\n >();\n\n const handleMessage = (event: MessageEvent) => {\n if (event.source !== iframe.contentWindow) return;\n if (event.origin !== embedOrigin) return;\n const data = event.data as\n { source?: unknown; kind?: unknown } | null | undefined;\n if (!data || data.source !== PROTOCOL_SOURCE) return;\n if (data.kind === EProtocolMessageKind.RESPONSE) {\n const response = event.data as {\n id: string;\n ok: boolean;\n value?: unknown;\n error?: ViewerError;\n };\n const waiter = pending.get(response.id);\n if (!waiter) return;\n pending.delete(response.id);\n clearTimeout(waiter.timer);\n if (response.ok) waiter.resolve(response.value);\n else waiter.reject(response.error ?? { code: EErrorCode.INTERNAL });\n return;\n }\n if (data.kind === EProtocolMessageKind.EVENT) {\n const message = event.data as { name: string; payload?: unknown };\n onEvent({ name: message.name, payload: message.payload });\n return;\n }\n if (data.kind === EProtocolMessageKind.ANNOUNCE) onAnnounce();\n };\n\n const send = ({\n name,\n payload,\n timeoutMs = COMMAND_TIMEOUT_MS,\n }: {\n name: string;\n payload?: unknown;\n timeoutMs?: number;\n }): Promise<unknown> => {\n if (isDestroyed()) {\n return Promise.reject({\n code: EErrorCode.NOT_READY,\n message: 'this viewer was destroyed',\n } satisfies ViewerError);\n }\n const id = createCommandId();\n return new Promise((resolve, reject) => {\n const timer = setTimeout(() => {\n pending.delete(id);\n reject({\n code: EErrorCode.INTERNAL,\n message: 'the viewer did not answer',\n } satisfies ViewerError);\n }, timeoutMs);\n pending.set(id, { resolve, reject, timer });\n iframe.contentWindow?.postMessage(\n {\n source: PROTOCOL_SOURCE,\n version: PROTOCOL_VERSION,\n kind: EProtocolMessageKind.COMMAND,\n id,\n name,\n payload,\n },\n embedOrigin,\n );\n });\n };\n\n return {\n send,\n start: () => window.addEventListener('message', handleMessage),\n stop: () => window.removeEventListener('message', handleMessage),\n rejectAll: ({ message }) => {\n for (const [, waiter] of pending) {\n clearTimeout(waiter.timer);\n waiter.reject({ code: EErrorCode.NOT_READY, message });\n }\n pending.clear();\n },\n };\n};\n","import { HELLO_RETRY_MS, HELLO_TIMEOUT_MS } from '@/lib/constants';\nimport type { ViewerMirror } from '@/lib/interfaces';\nimport type { ViewerTransport } from '@/lib/helpers/createViewerTransport';\nimport { PROTOCOL_VERSION } from '@/protocol/constants';\nimport { EErrorCode, EProtocolCommand } from '@/protocol/interfaces';\nimport type { ViewerError } from '@/protocol/interfaces';\nimport type { ViewerCapabilities, ViewerState } from '@/contract/interfaces';\n\n// The handshake: retried until the page's bridge is up, refused whole after the timeout. Its\n// answer seeds the mirror — whatever happened before the client was listening is in it.\nexport const performHandshake = ({\n transport,\n iframe,\n mirror,\n onGiveUp,\n}: {\n transport: ViewerTransport;\n iframe: HTMLIFrameElement;\n mirror: ViewerMirror;\n // Called once when the handshake is abandoned, before the rejection reaches the caller.\n onGiveUp: () => void;\n}): Promise<void> =>\n new Promise<void>((resolve, reject) => {\n let settled = false;\n const beginAt = Date.now();\n // The listener outlives nothing: a handshake is run again on every reload, and one\n // left behind per run would pile up on the frame.\n const settle = () => {\n settled = true;\n iframe.removeEventListener('load', attempt);\n };\n const attempt = () => {\n if (settled) return;\n if (Date.now() - beginAt > HELLO_TIMEOUT_MS) {\n settle();\n onGiveUp();\n return reject({\n code: EErrorCode.INVALID_KEY,\n message:\n 'the viewer never answered: the key was refused, this domain is not declared for it, or the render service is unreachable',\n } satisfies ViewerError);\n }\n transport\n .send({\n name: EProtocolCommand.HELLO,\n payload: { version: PROTOCOL_VERSION },\n timeoutMs: HELLO_RETRY_MS,\n })\n .then((value) => {\n if (settled) return;\n settle();\n const hello = value as {\n state?: ViewerState;\n capabilities?: ViewerCapabilities;\n };\n mirror.state = hello.state ?? mirror.state;\n mirror.capabilities =\n hello.capabilities ?? mirror.capabilities;\n resolve();\n })\n .catch(() => setTimeout(attempt, HELLO_RETRY_MS));\n };\n iframe.addEventListener('load', attempt);\n // A cached iframe can be complete before the listener lands.\n setTimeout(attempt, HELLO_RETRY_MS);\n });\n","// The viewer factory: creates the render iframe on the VSkin origin, drives it by messages,\n// and hands back a typed handle plus a catalog client. This file only assembles — the frame,\n// the transport, the event hub, the handle and the handshake are each their own helper.\n\nimport { DEFAULT_BASE_URL } from '@/lib/constants';\nimport { buildEmbedUrl } from '@/lib/helpers/buildEmbedUrl';\nimport { buildViewerHandle } from '@/lib/helpers/buildViewerHandle';\nimport { createEmbedIframe } from '@/lib/helpers/createEmbedIframe';\nimport { createViewerEventHub } from '@/lib/helpers/createViewerEventHub';\nimport { createViewerTransport } from '@/lib/helpers/createViewerTransport';\nimport { performHandshake } from '@/lib/helpers/performHandshake';\nimport type {\n CreateViewerOptions,\n Viewer,\n ViewerMirror,\n} from '@/lib/interfaces';\nimport { EProtocolCommand, EViewerEvent } from '@/protocol/interfaces';\nimport type { ViewerError } from '@/protocol/interfaces';\n\nexport type {\n CatalogQuery,\n CreateViewerOptions,\n Viewer,\n ViewerEventHandler,\n} from '@/lib/interfaces';\n\nexport const createViewer = ({\n container,\n key,\n baseUrl = DEFAULT_BASE_URL,\n weapon,\n environment,\n background,\n interactive,\n autoplay,\n locale,\n}: CreateViewerOptions): Promise<Viewer> => {\n const embedOrigin = new URL(baseUrl).origin;\n const iframe = createEmbedIframe({\n src: buildEmbedUrl({\n baseUrl,\n key,\n weapon,\n environment,\n background,\n interactive,\n autoplay,\n locale,\n }),\n });\n const mirror: ViewerMirror = { state: null, capabilities: null };\n const hub = createViewerEventHub({ mirror });\n let destroyed = false;\n // Whether a bridge has been greeted. What it guards: the FIRST announce is the page's\n // ordinary boot, which the handshake below is already answering; every later one means the\n // frame reloaded under us and the greeting has to be done again.\n let greeted = false;\n let greetingAgain = false;\n\n const greetAgain = () => {\n if (!greeted || greetingAgain || destroyed) return;\n greetingAgain = true;\n // Whatever was in flight died with the page that owed it an answer.\n transport.rejectAll({ message: 'the viewer reloaded' });\n void performHandshake({\n transport,\n iframe,\n mirror,\n // A reload that never answers leaves the viewer as it is: the frame is the\n // integrator's to keep or drop, and an error says so.\n onGiveUp: () => undefined,\n })\n .then(() =>\n hub.dispatch({\n name: EViewerEvent.RECONNECT,\n payload: undefined,\n }),\n )\n .catch((error: ViewerError) =>\n hub.dispatch({ name: EViewerEvent.ERROR, payload: error }),\n )\n .finally(() => {\n greetingAgain = false;\n });\n };\n\n const transport = createViewerTransport({\n iframe,\n embedOrigin,\n isDestroyed: () => destroyed,\n onEvent: hub.dispatch,\n onAnnounce: greetAgain,\n });\n\n const destroy = () => {\n if (destroyed) return;\n // The goodbye posts BEFORE the flag flips — a destroyed transport refuses to send.\n void transport\n .send({ name: EProtocolCommand.DESTROY })\n .catch(() => undefined);\n destroyed = true;\n transport.stop();\n iframe.remove();\n transport.rejectAll({ message: 'this viewer was destroyed' });\n hub.clear();\n };\n\n const viewer = buildViewerHandle({\n transport,\n hub,\n mirror,\n iframe,\n destroy,\n });\n\n transport.start();\n container.appendChild(iframe);\n\n return performHandshake({\n transport,\n iframe,\n mirror,\n onGiveUp: destroy,\n }).then(() => {\n greeted = true;\n return viewer;\n });\n};\n","import { CS2_INSPECT_LINK_PREFIX } from '@/lib/constants';\n\n// The steam:// inspect link for an item certificate. Pure and instant — the certificate IS the\n// link's payload, so this never talks to the viewer and works with no viewer mounted at all.\nexport const buildInspectLink = ({ cert }: { cert: string }): string =>\n `${CS2_INSPECT_LINK_PREFIX}${cert}`;\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/lib/constants.ts","../src/contract/interfaces.ts","../src/lib/helpers/buildEmbedUrl.ts","../src/protocol/interfaces.ts","../src/lib/helpers/buildViewerHandle.ts","../src/lib/helpers/createEmbedIframe.ts","../src/lib/helpers/createViewerEventHub.ts","../src/lib/helpers/createCommandId.ts","../src/protocol/constants.ts","../src/lib/helpers/createViewerTransport.ts","../src/lib/helpers/performHandshake.ts","../src/lib/createViewer.ts","../src/lib/buildInspectLink.ts"],"names":["EView","EBackgroundType","EFacing","EHandedness","ESubject","EFeature","EErrorCode","ERefusalFamily","EViewerEvent"],"mappings":"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","file":"index.cjs","sourcesContent":["// Where the viewer lives when the integration does not say otherwise.\nexport const DEFAULT_BASE_URL = 'https://render.vskin.gg';\n\n// The embed page answers the handshake as soon as its bridge is up — retried because the page\n// boots asynchronously behind the iframe's load event.\nexport const HELLO_RETRY_MS = 300;\nexport const HELLO_TIMEOUT_MS = 15000;\n\n// A command that never comes back (the page died, the network broke) must not hang a client's\n// await forever.\nexport const COMMAND_TIMEOUT_MS = 30000;\n\n// The command Steam itself serves in its inventory and market payloads. The space is\n// percent-encoded on purpose: a literal space truncates the steam:// command.\nexport const CS2_INSPECT_LINK_PREFIX =\n 'steam://run/730//+csgo_econ_action_preview%20';\n","// The viewer's public vocabulary: domain words only, no abbreviation, one options object per\n// method, enums whose values ARE the strings a plain-JavaScript consumer writes.\n\nexport enum EView {\n FREE = 'free',\n FIRST_PERSON = 'firstPerson',\n THIRD_PERSON = 'thirdPerson',\n}\n\n// The background is a VALUE, not a boolean: `none` composites the canvas straight onto your\n// page (put your own background behind the viewer), `environment` shows the map's own decor.\nexport enum EBackgroundType {\n NONE = 'none',\n ENVIRONMENT = 'environment',\n}\n\nexport type Background = {\n type: EBackgroundType;\n};\n\nexport enum EFacing {\n FRONT = 'front',\n BACK = 'back',\n}\n\nexport enum EHandedness {\n RIGHT = 'right',\n LEFT = 'left',\n}\n\n// Which of the two picked items the free view presents when a weapon and a pair of gloves are\n// both on stage.\nexport enum ESubject {\n WEAPON = 'weapon',\n GLOVES = 'gloves',\n}\n\n// The weapon as you describe it — identity, roll, marks — in the market's own words (`seed`\n// and `float`). The viewer owns the road to it: a seed or float alone re-rolls in place, a\n// name alone re-engraves the plate, a new identity re-mounts.\nexport type Weapon = {\n // The inspect certificate (hex), the market door: it carries identity, roll and cosmetics.\n cert?: string;\n // The manual door: the item's definition and finish indices.\n defIndex?: number;\n paintIndex?: number;\n seed?: number;\n float?: number;\n stattrak?: boolean;\n kills?: number;\n name?: string;\n};\n\nexport type Gloves = {\n cert?: string;\n defIndex?: number;\n paintIndex?: number;\n seed?: number;\n float?: number;\n};\n\nexport type Agent = {\n // The inspect certificate (hex): a character travels by cert too, patches included.\n cert?: string;\n defIndex?: number;\n};\n\nexport type Sticker = {\n id: number;\n slot: number;\n wear?: number;\n rotation?: number;\n offsetX?: number;\n offsetY?: number;\n};\n\nexport type Charm = {\n id: number;\n pattern?: number;\n // The display-case family: the sticker sealed inside the slab, by its id.\n wrappedSticker?: number;\n // The charm's placement, as a DELTA from the weapon's default hook in the weapon's model\n // space (Source inches) — the same numbers a free-placement drag settles on. Absent = the\n // authored hook. The state mirror's `charmAnchor` publishes the composed ABSOLUTE.\n offsetX?: number;\n offsetY?: number;\n offsetZ?: number;\n};\n\nexport type Patch = {\n id: number;\n slot: number;\n};\n\n// First-person dials in the GAME's units: `fov` is viewmodel_fov degrees, offsets are\n// viewmodel_offset inches. A new dial is a new FIELD here, never a new method.\nexport type FirstPersonSettings = {\n fov?: number;\n offsetX?: number;\n offsetY?: number;\n offsetZ?: number;\n handedness?: EHandedness;\n};\n\n// The camera's flight target. A sticker is named by its STABLE uid (a certificate may repeat a\n// slot, so a slot is not an identity); the state mirror publishes each sticker's uid.\nexport type FocusTarget =\n | { kind: 'sticker'; uid: string }\n | { kind: 'charm' }\n | { kind: 'patch'; slot: number }\n | null;\n\n// What the free-placement mode is armed on: while armed, pressing that cosmetic in the canvas\n// MOVES it instead of orbiting the item. Null disarms.\nexport type PlacementTarget =\n { kind: 'sticker'; slot: number } | { kind: 'charm' } | null;\n\n// One capability, two layers already intersected for you: `entitled` is what the plan bought\n// (stable for the session), `available` folds in what the current scene can serve (moving;\n// `capabilitieschange` fires when it does).\nexport type Capability = {\n entitled: boolean;\n available: boolean;\n};\n\nexport enum EFeature {\n SELECT_WEAPON = 'selectWeapon',\n SELECT_GLOVES = 'selectGloves',\n SELECT_AGENT = 'selectAgent',\n SELECT_ENVIRONMENT = 'selectEnvironment',\n EDIT_SEED = 'editSeed',\n EDIT_FLOAT = 'editFloat',\n EDIT_STATTRAK = 'editStattrak',\n EDIT_NAMETAG = 'editNametag',\n SELECT_STICKER = 'selectSticker',\n SELECT_CHARM = 'selectCharm',\n SELECT_PATCH = 'selectPatch',\n EDIT_STICKERS = 'editStickers',\n EDIT_CHARMS = 'editCharms',\n PLACE_STICKERS = 'placeStickers',\n PLACE_CHARM = 'placeCharm',\n SCREENSHOT = 'screenshot',\n INSPECT_LINK = 'inspectLink',\n SUBJECT_CONTROLS = 'subjectControls',\n WEAPON_ANIMATIONS = 'weaponAnimations',\n AGENT_ANIMATIONS = 'agentAnimations',\n}\n\nexport type ViewerCapabilities = {\n views: Record<EView, Capability>;\n features: Record<EFeature, Capability>;\n};\n\n// One animation the scene can play, with the one fact you need to offer it honestly: a\n// looping clip is a toggle, a one-shot replays.\nexport type AnimationEntry = {\n name: string;\n loop: boolean;\n};\n\n// The synchronous mirror: the last known truth, re-published whole on every `change` event.\n// Read it without ever awaiting.\nexport type ViewerState = {\n weapon: Weapon | null;\n gloves: Gloves | null;\n agent: Agent | null;\n subject: ESubject | null;\n view: { view: EView; active: boolean };\n environment: string | null;\n background: Background;\n stickers: Array<Sticker & { uid?: string }>;\n charm: Charm | null;\n // Where the charm actually sits, in the form a cert names it: the composed ABSOLUTE\n // position in the weapon's model space, read off the manifest the render is using.\n charmAnchor: [number, number, number] | null;\n patches: Array<Patch>;\n // How many patch slots the mounted character authors — the render's own answer, read off\n // its landed manifest. null while no character manifest has answered (none asked, or still\n // composing): 0 is a real answer, \"this body authors none\".\n patchSlots: number | null;\n playing: boolean;\n animation: string | null;\n animations: Array<AnimationEntry>;\n // The character's celebrations: what the mounted body can play beyond its resting posture,\n // and the one running right now (null at rest). Driven through the same playAnimation /\n // stopAnimation door as the weapon clips.\n agentAnimation: string | null;\n agentAnimations: Array<string>;\n sound: { muted: boolean };\n firstPerson: FirstPersonSettings;\n facing: EFacing;\n placement: PlacementTarget;\n};\n","import type { Background, Weapon } from '@/contract/interfaces';\nimport { EBackgroundType } from '@/contract/interfaces';\n\n// The embed page's URL grammar, written once: the boot seed rides the URL, everything after\n// boot rides the protocol.\nexport const buildEmbedUrl = ({\n baseUrl,\n key,\n weapon,\n environment,\n background,\n interactive,\n autoplay,\n locale,\n}: {\n baseUrl: string;\n key?: string;\n weapon?: Weapon;\n environment?: string;\n background?: Background;\n interactive?: boolean;\n autoplay?: boolean;\n locale?: string;\n}): string => {\n const query = new URLSearchParams();\n if (key) query.set('key', key);\n if (weapon?.cert) {\n query.set('cert', weapon.cert);\n } else if (\n weapon &&\n typeof weapon.defIndex === 'number' &&\n typeof weapon.paintIndex === 'number'\n ) {\n query.set('def', String(weapon.defIndex));\n query.set('paint', String(weapon.paintIndex));\n if (weapon.seed !== undefined) query.set('seed', String(weapon.seed));\n if (weapon.float !== undefined)\n query.set('float', String(weapon.float));\n if (weapon.stattrak) query.set('stattrak', '1');\n if (weapon.kills !== undefined)\n query.set('kills', String(weapon.kills));\n if (weapon.name !== undefined) query.set('name', weapon.name);\n }\n if (environment) query.set('env', environment);\n if (background?.type === EBackgroundType.NONE)\n query.set('backdrop', 'false');\n if (interactive === false) query.set('interactive', 'false');\n if (autoplay) query.set('autoplay', '1');\n if (locale) query.set('lang', locale);\n const suffix = query.toString();\n return `${baseUrl}/v1/sdk${suffix ? `?${suffix}` : ''}`;\n};\n","// The wire format of the embed protocol, client side. Every name here is contract: a change is\n// an addition, never a redefinition.\n\nexport enum EProtocolMessageKind {\n COMMAND = 'command',\n RESPONSE = 'response',\n EVENT = 'event',\n // The viewer page saying \"I just started, greet me\". It carries no data, and the SDK answers\n // it with the handshake — which is what makes a reloaded viewer pick itself back up.\n ANNOUNCE = 'announce',\n}\n\n// The CLOSED error vocabulary. A code's meaning never changes; branch behavior on the code,\n// never on the message text.\nexport enum EErrorCode {\n INVALID_KEY = 'invalid_key',\n ORIGIN_NOT_ALLOWED = 'origin_not_allowed',\n NOT_ENTITLED = 'not_entitled',\n UNSUPPORTED_VIEW = 'unsupported_view',\n UNAVAILABLE_ITEM = 'unavailable_item',\n INVALID_ARGUMENT = 'invalid_argument',\n NOT_READY = 'not_ready',\n RATE_LIMITED = 'rate_limited',\n INTERNAL = 'internal',\n // The embed server refused to serve the viewer at all. `family` on the error says whose\n // problem it is; the frame is left in place, showing the explanation.\n REFUSED = 'refused',\n}\n\n// Whose problem a refusal is, and all you learn of it: your integration mid-setup (a missing\n// key, a page opened outside an iframe), your account no longer opening the door (a revoked or\n// expired key, an undeclared domain, a plan without this surface), or an outage on our side.\nexport enum ERefusalFamily {\n SETUP = 'setup',\n CUT_OFF = 'cut_off',\n OUTAGE = 'outage',\n}\n\nexport enum EProtocolCommand {\n HELLO = 'hello',\n SET_WEAPON = 'setWeapon',\n SET_GLOVES = 'setGloves',\n SET_AGENT = 'setAgent',\n SET_SUBJECT = 'setSubject',\n SET_STICKERS = 'setStickers',\n SET_CHARM = 'setCharm',\n SET_PATCHES = 'setPatches',\n SET_VIEW = 'setView',\n SET_FIRST_PERSON_SETTINGS = 'setFirstPersonSettings',\n SET_FACING = 'setFacing',\n SET_ENVIRONMENT = 'setEnvironment',\n SET_BACKGROUND = 'setBackground',\n FOCUS = 'focus',\n RESET_CAMERA = 'resetCamera',\n PLAY = 'play',\n PAUSE = 'pause',\n PLAY_ANIMATION = 'playAnimation',\n STOP_ANIMATION = 'stopAnimation',\n START_FIRE = 'startFire',\n STOP_FIRE = 'stopFire',\n SET_SOUND = 'setSound',\n SET_LOCALE = 'setLocale',\n ARM_PLACEMENT = 'armPlacement',\n FORWARD_POINTER = 'forwardPointer',\n CAPTURE = 'capture',\n CATALOG_WEAPONS = 'catalogWeapons',\n CATALOG_STICKERS = 'catalogStickers',\n CATALOG_CHARMS = 'catalogCharms',\n CATALOG_PATCHES = 'catalogPatches',\n CATALOG_AGENTS = 'catalogAgents',\n CATALOG_WEAPON_MODELS = 'catalogWeaponModels',\n CATALOG_ENVIRONMENTS = 'catalogEnvironments',\n DESTROY = 'destroy',\n}\n\n// Every event the viewer emits, in glued lowercase: `<thing>change` for a state change (always\n// carrying what changed), a `start`/`move`/`end` triplet for a continuous gesture, a bare noun\n// for an isolated fact.\nexport enum EViewerEvent {\n READY = 'ready',\n ERROR = 'error',\n // The viewer reloaded and was greeted again: everything you had set is gone with the page\n // it lived in, and the scene is blank. Re-apply what you want on screen when you get this.\n RECONNECT = 'reconnect',\n PROGRESS = 'progress',\n UNAVAILABLE = 'unavailable',\n CHANGE = 'change',\n VIEW_CHANGE = 'viewchange',\n SUBJECT_CHANGE = 'subjectchange',\n COSMETICS_CHANGE = 'cosmeticschange',\n ANIMATION_CHANGE = 'animationchange',\n PLAYBACK_CHANGE = 'playbackchange',\n CAPABILITIES_CHANGE = 'capabilitieschange',\n PLACEMENT_START = 'placementstart',\n PLACEMENT_MOVE = 'placementmove',\n PLACEMENT_END = 'placementend',\n // Posted by the embed server's refusal page, never by a booted viewer: the frame is showing\n // a refusal screen. Never reaches `on`: it settles `createViewer` with a `refused` error.\n REFUSED = 'refused',\n}\n\nexport type ViewerError = {\n code: EErrorCode;\n message?: string;\n // With `refused` only: whose problem it is.\n family?: ERefusalFamily;\n};\n\nexport type ProtocolResponseMessage = {\n source: string;\n version: number;\n kind: EProtocolMessageKind.RESPONSE;\n id: string;\n} & ({ ok: true; value?: unknown } | { ok: false; error: ViewerError });\n\nexport type ProtocolEventMessage = {\n source: string;\n version: number;\n kind: EProtocolMessageKind.EVENT;\n name: EViewerEvent;\n payload?: unknown;\n};\n","import type { ViewerCapabilities, ViewerState } from '@/contract/interfaces';\nimport type { Viewer, ViewerMirror } from '@/lib/interfaces';\nimport type { ViewerEventHub } from '@/lib/helpers/createViewerEventHub';\nimport type { ViewerTransport } from '@/lib/helpers/createViewerTransport';\nimport { EProtocolCommand } from '@/protocol/interfaces';\n\n// The typed handle the integrator holds: every method one options object, one command, one\n// promise. The state and capability getters read the mirror synchronously — never an await.\nexport const buildViewerHandle = ({\n transport,\n hub,\n mirror,\n iframe,\n destroy,\n}: {\n transport: ViewerTransport;\n hub: ViewerEventHub;\n mirror: ViewerMirror;\n iframe: HTMLIFrameElement;\n destroy: () => void;\n}): Viewer => {\n const command = (\n name: EProtocolCommand,\n payload?: unknown,\n ): Promise<void> => transport.send({ name, payload }).then(() => undefined);\n\n return {\n get state() {\n return mirror.state as ViewerState;\n },\n get capabilities() {\n return mirror.capabilities as ViewerCapabilities;\n },\n on: (event, handler) => hub.on(event, handler),\n setWeapon: (args) => command(EProtocolCommand.SET_WEAPON, args),\n setGloves: (args) => command(EProtocolCommand.SET_GLOVES, args),\n setAgent: (args) => command(EProtocolCommand.SET_AGENT, args),\n setSubject: (args) => command(EProtocolCommand.SET_SUBJECT, args),\n setStickers: (args) => command(EProtocolCommand.SET_STICKERS, args),\n setCharm: (args) => command(EProtocolCommand.SET_CHARM, args),\n setPatches: (args) => command(EProtocolCommand.SET_PATCHES, args),\n setView: (args) => command(EProtocolCommand.SET_VIEW, args),\n setFirstPersonSettings: (args) =>\n command(EProtocolCommand.SET_FIRST_PERSON_SETTINGS, args),\n setFacing: (args) => command(EProtocolCommand.SET_FACING, args),\n setEnvironment: (args) =>\n command(EProtocolCommand.SET_ENVIRONMENT, args),\n setBackground: (args) => command(EProtocolCommand.SET_BACKGROUND, args),\n setSound: (args) => command(EProtocolCommand.SET_SOUND, args),\n setLocale: (args) => command(EProtocolCommand.SET_LOCALE, args),\n focus: (args) => command(EProtocolCommand.FOCUS, args),\n resetCamera: () => command(EProtocolCommand.RESET_CAMERA),\n play: () => command(EProtocolCommand.PLAY),\n pause: () => command(EProtocolCommand.PAUSE),\n playAnimation: (args) => command(EProtocolCommand.PLAY_ANIMATION, args),\n stopAnimation: () => command(EProtocolCommand.STOP_ANIMATION),\n startFire: () => command(EProtocolCommand.START_FIRE),\n stopFire: () => command(EProtocolCommand.STOP_FIRE),\n armPlacement: (args) => command(EProtocolCommand.ARM_PLACEMENT, args),\n forwardPointer: ({ x, y, phase }) => {\n const rect = iframe.getBoundingClientRect();\n return command(EProtocolCommand.FORWARD_POINTER, {\n x: x - rect.left,\n y: y - rect.top,\n phase,\n });\n },\n capture: () =>\n transport\n .send({ name: EProtocolCommand.CAPTURE })\n .then((value) => (value as { image: string }).image),\n catalog: {\n weapons: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_WEAPONS,\n payload: query,\n }),\n stickers: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_STICKERS,\n payload: query,\n }),\n charms: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_CHARMS,\n payload: query,\n }),\n patches: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_PATCHES,\n payload: query,\n }),\n agents: (query) =>\n transport.send({\n name: EProtocolCommand.CATALOG_AGENTS,\n payload: query,\n }),\n weaponModels: () =>\n transport.send({\n name: EProtocolCommand.CATALOG_WEAPON_MODELS,\n }),\n environments: () =>\n transport.send({\n name: EProtocolCommand.CATALOG_ENVIRONMENTS,\n }),\n },\n destroy,\n };\n};\n","// The viewer's frame: an implementation detail the integrator never touches, filling the\n// container it is handed.\nexport const createEmbedIframe = ({\n src,\n}: {\n src: string;\n}): HTMLIFrameElement => {\n const iframe = document.createElement('iframe');\n iframe.src = src;\n iframe.style.width = '100%';\n iframe.style.height = '100%';\n iframe.style.display = 'block';\n iframe.style.border = '0';\n // Browsers composite a dark-scheme iframe on a light host as OPAQUE: pinning the scheme is\n // what keeps the transparent background actually transparent. You never have to know this.\n iframe.style.colorScheme = 'normal';\n iframe.allow = 'fullscreen';\n return iframe;\n};\n","import type { ViewerCapabilities, ViewerState } from '@/contract/interfaces';\nimport type { ViewerEventHandler, ViewerMirror } from '@/lib/interfaces';\nimport { EViewerEvent } from '@/protocol/interfaces';\n\nexport type ViewerEventHub = {\n on: (event: string, handler: ViewerEventHandler) => () => void;\n dispatch: ({ name, payload }: { name: string; payload: unknown }) => void;\n clear: () => void;\n};\n\n// The subscription side of the viewer, and the mirror's one writer: a `change` carries the\n// whole state, `capabilitieschange` the whole capability map — absorbed before the handlers\n// run, so a handler reading `viewer.state` already sees the truth it was told about.\nexport const createViewerEventHub = ({\n mirror,\n}: {\n mirror: ViewerMirror;\n}): ViewerEventHub => {\n const handlers = new Map<string, Set<ViewerEventHandler>>();\n\n return {\n on: (event, handler) => {\n const set = handlers.get(event) ?? new Set();\n set.add(handler);\n handlers.set(event, set);\n return () => {\n set.delete(handler);\n };\n },\n dispatch: ({ name, payload }) => {\n if (name === EViewerEvent.CHANGE) {\n const change = payload as { state?: ViewerState } | undefined;\n if (change?.state) mirror.state = change.state;\n }\n if (name === EViewerEvent.CAPABILITIES_CHANGE) {\n const change = payload as\n { capabilities?: ViewerCapabilities } | undefined;\n if (change?.capabilities)\n mirror.capabilities = change.capabilities;\n }\n for (const handler of handlers.get(name) ?? []) handler(payload);\n },\n clear: () => handlers.clear(),\n };\n};\n","let sequence = 0;\n\n// Correlation ids only need to be unique within one page's lifetime; the random prefix keeps\n// two viewers on the same page from ever colliding.\nconst prefix = Math.random().toString(36).slice(2, 8);\n\nexport const createCommandId = (): string => `${prefix}-${++sequence}`;\n","// The wire identity of every message crossing the iframe boundary. This file is the PUBLIC\n// twin of the render service's own declaration: the package cannot depend on private code, so\n// the wire format is declared on both sides and a conformity bench proves they never drift.\nexport const PROTOCOL_SOURCE = 'vskin-render';\n\n// One dial only: the protocol version this package ships is the version it speaks — never\n// overridden at run time. The service supports the current version and the previous one.\nexport const PROTOCOL_VERSION = 1;\n","import { COMMAND_TIMEOUT_MS } from '@/lib/constants';\nimport { createCommandId } from '@/lib/helpers/createCommandId';\nimport { PROTOCOL_SOURCE, PROTOCOL_VERSION } from '@/protocol/constants';\nimport { EErrorCode, EProtocolMessageKind } from '@/protocol/interfaces';\nimport type { ViewerError } from '@/protocol/interfaces';\n\nexport type ViewerTransport = {\n send: (args: {\n name: string;\n payload?: unknown;\n timeoutMs?: number;\n }) => Promise<unknown>;\n start: () => void;\n stop: () => void;\n // Settles every pending command with the given refusal — the teardown's last word.\n rejectAll: (args: { message: string }) => void;\n};\n\n// The wire side of the viewer: posts commands to the iframe at its precise origin, correlates\n// the one response each command gets, forwards events up. Everything else on the shared\n// `window` is ignored — responses are accepted only from OUR iframe's window AND origin.\nexport const createViewerTransport = ({\n iframe,\n embedOrigin,\n isDestroyed,\n onEvent,\n onAnnounce,\n}: {\n iframe: HTMLIFrameElement;\n embedOrigin: string;\n isDestroyed: () => boolean;\n onEvent: ({ name, payload }: { name: string; payload: unknown }) => void;\n // The page saying it just started. Fires on its first boot and again on every reload.\n onAnnounce: () => void;\n}): ViewerTransport => {\n const pending = new Map<\n string,\n {\n resolve: (value: unknown) => void;\n reject: (error: ViewerError) => void;\n timer: ReturnType<typeof setTimeout>;\n }\n >();\n\n const handleMessage = (event: MessageEvent) => {\n if (event.source !== iframe.contentWindow) return;\n if (event.origin !== embedOrigin) return;\n const data = event.data as\n { source?: unknown; kind?: unknown } | null | undefined;\n if (!data || data.source !== PROTOCOL_SOURCE) return;\n if (data.kind === EProtocolMessageKind.RESPONSE) {\n const response = event.data as {\n id: string;\n ok: boolean;\n value?: unknown;\n error?: ViewerError;\n };\n const waiter = pending.get(response.id);\n if (!waiter) return;\n pending.delete(response.id);\n clearTimeout(waiter.timer);\n if (response.ok) waiter.resolve(response.value);\n else waiter.reject(response.error ?? { code: EErrorCode.INTERNAL });\n return;\n }\n if (data.kind === EProtocolMessageKind.EVENT) {\n const message = event.data as { name: string; payload?: unknown };\n onEvent({ name: message.name, payload: message.payload });\n return;\n }\n if (data.kind === EProtocolMessageKind.ANNOUNCE) onAnnounce();\n };\n\n const send = ({\n name,\n payload,\n timeoutMs = COMMAND_TIMEOUT_MS,\n }: {\n name: string;\n payload?: unknown;\n timeoutMs?: number;\n }): Promise<unknown> => {\n if (isDestroyed()) {\n return Promise.reject({\n code: EErrorCode.NOT_READY,\n message: 'this viewer was destroyed',\n } satisfies ViewerError);\n }\n const id = createCommandId();\n return new Promise((resolve, reject) => {\n const timer = setTimeout(() => {\n pending.delete(id);\n reject({\n code: EErrorCode.INTERNAL,\n message: 'the viewer did not answer',\n } satisfies ViewerError);\n }, timeoutMs);\n pending.set(id, { resolve, reject, timer });\n iframe.contentWindow?.postMessage(\n {\n source: PROTOCOL_SOURCE,\n version: PROTOCOL_VERSION,\n kind: EProtocolMessageKind.COMMAND,\n id,\n name,\n payload,\n },\n embedOrigin,\n );\n });\n };\n\n return {\n send,\n start: () => window.addEventListener('message', handleMessage),\n stop: () => window.removeEventListener('message', handleMessage),\n rejectAll: ({ message }) => {\n for (const [, waiter] of pending) {\n clearTimeout(waiter.timer);\n waiter.reject({ code: EErrorCode.NOT_READY, message });\n }\n pending.clear();\n },\n };\n};\n","import { HELLO_RETRY_MS, HELLO_TIMEOUT_MS } from '@/lib/constants';\nimport type { ViewerMirror } from '@/lib/interfaces';\nimport type { ViewerTransport } from '@/lib/helpers/createViewerTransport';\nimport { PROTOCOL_VERSION } from '@/protocol/constants';\nimport { EErrorCode, EProtocolCommand } from '@/protocol/interfaces';\nimport type { ERefusalFamily, ViewerError } from '@/protocol/interfaces';\nimport type { ViewerCapabilities, ViewerState } from '@/contract/interfaces';\n\n// The handshake: retried until the page's bridge is up, refused whole after the timeout. Its\n// answer seeds the mirror — whatever happened before the client was listening is in it. A page\n// the embed server refused says so itself, and the handshake settles on that word at once.\nexport const performHandshake = ({\n transport,\n iframe,\n mirror,\n onGiveUp,\n subscribeRefusal,\n}: {\n transport: ViewerTransport;\n iframe: HTMLIFrameElement;\n mirror: ViewerMirror;\n // Called once when the handshake is abandoned for want of an answer, before the rejection\n // reaches the caller. NOT called on a refusal: the frame then shows the explanation.\n onGiveUp: () => void;\n // Hands the refusal page's word to the handshake; the returned function unsubscribes.\n subscribeRefusal: (\n handler: (args: { family: ERefusalFamily }) => void,\n ) => () => void;\n}): Promise<void> =>\n new Promise<void>((resolve, reject) => {\n let settled = false;\n const beginAt = Date.now();\n // The listeners outlive nothing: a handshake is run again on every reload, and one\n // left behind per run would pile up on the frame.\n const settle = () => {\n settled = true;\n iframe.removeEventListener('load', attempt);\n unsubscribeRefusal();\n };\n const attempt = () => {\n if (settled) return;\n if (Date.now() - beginAt > HELLO_TIMEOUT_MS) {\n settle();\n onGiveUp();\n return reject({\n code: EErrorCode.INVALID_KEY,\n message:\n 'the viewer never answered: the render service is unreachable, or the frame was blocked before the page could boot',\n } satisfies ViewerError);\n }\n transport\n .send({\n name: EProtocolCommand.HELLO,\n payload: { version: PROTOCOL_VERSION },\n timeoutMs: HELLO_RETRY_MS,\n })\n .then((value) => {\n if (settled) return;\n settle();\n const hello = value as {\n state?: ViewerState;\n capabilities?: ViewerCapabilities;\n };\n mirror.state = hello.state ?? mirror.state;\n mirror.capabilities =\n hello.capabilities ?? mirror.capabilities;\n resolve();\n })\n .catch(() => setTimeout(attempt, HELLO_RETRY_MS));\n };\n const unsubscribeRefusal = subscribeRefusal(({ family }) => {\n if (settled) return;\n settle();\n reject({\n code: EErrorCode.REFUSED,\n family,\n message:\n 'the embed server refused this viewer; its family says whose problem it is',\n } satisfies ViewerError);\n });\n iframe.addEventListener('load', attempt);\n // A cached iframe can be complete before the listener lands.\n setTimeout(attempt, HELLO_RETRY_MS);\n });\n","// The viewer factory: creates the render iframe on the VSkin origin, drives it by messages,\n// and hands back a typed handle plus a catalog client. This file only assembles — the frame,\n// the transport, the event hub, the handle and the handshake are each their own helper.\n\nimport { DEFAULT_BASE_URL } from '@/lib/constants';\nimport { buildEmbedUrl } from '@/lib/helpers/buildEmbedUrl';\nimport { buildViewerHandle } from '@/lib/helpers/buildViewerHandle';\nimport { createEmbedIframe } from '@/lib/helpers/createEmbedIframe';\nimport { createViewerEventHub } from '@/lib/helpers/createViewerEventHub';\nimport { createViewerTransport } from '@/lib/helpers/createViewerTransport';\nimport { performHandshake } from '@/lib/helpers/performHandshake';\nimport type {\n CreateViewerOptions,\n Viewer,\n ViewerMirror,\n} from '@/lib/interfaces';\nimport { EProtocolCommand, EViewerEvent } from '@/protocol/interfaces';\nimport type { ERefusalFamily, ViewerError } from '@/protocol/interfaces';\n\nexport type {\n CatalogQuery,\n CreateViewerOptions,\n Viewer,\n ViewerEventHandler,\n} from '@/lib/interfaces';\n\nexport const createViewer = ({\n container,\n key,\n baseUrl = DEFAULT_BASE_URL,\n weapon,\n environment,\n background,\n interactive,\n autoplay,\n locale,\n}: CreateViewerOptions): Promise<Viewer> => {\n const embedOrigin = new URL(baseUrl).origin;\n const iframe = createEmbedIframe({\n src: buildEmbedUrl({\n baseUrl,\n key,\n weapon,\n environment,\n background,\n interactive,\n autoplay,\n locale,\n }),\n });\n const mirror: ViewerMirror = { state: null, capabilities: null };\n const hub = createViewerEventHub({ mirror });\n let destroyed = false;\n // Whether a bridge has been greeted. What it guards: the FIRST announce is the page's\n // ordinary boot, which the handshake below is already answering; every later one means the\n // frame reloaded under us and the greeting has to be done again.\n let greeted = false;\n let greetingAgain = false;\n\n // The refusal page's word, routed to whichever handshake is waiting for it.\n const subscribeRefusal = (\n handler: (args: { family: ERefusalFamily }) => void,\n ) =>\n hub.on(EViewerEvent.REFUSED, (payload) =>\n handler(payload as { family: ERefusalFamily }),\n );\n\n const greetAgain = () => {\n if (!greeted || greetingAgain || destroyed) return;\n greetingAgain = true;\n // Whatever was in flight died with the page that owed it an answer.\n transport.rejectAll({ message: 'the viewer reloaded' });\n void performHandshake({\n transport,\n iframe,\n mirror,\n // A reload that never answers leaves the viewer as it is: the frame is the\n // integrator's to keep or drop, and an error says so.\n onGiveUp: () => undefined,\n subscribeRefusal,\n })\n .then(() =>\n hub.dispatch({\n name: EViewerEvent.RECONNECT,\n payload: undefined,\n }),\n )\n .catch((error: ViewerError) =>\n hub.dispatch({ name: EViewerEvent.ERROR, payload: error }),\n )\n .finally(() => {\n greetingAgain = false;\n });\n };\n\n const transport = createViewerTransport({\n iframe,\n embedOrigin,\n isDestroyed: () => destroyed,\n onEvent: hub.dispatch,\n onAnnounce: greetAgain,\n });\n\n const destroy = () => {\n if (destroyed) return;\n // The goodbye posts BEFORE the flag flips — a destroyed transport refuses to send.\n void transport\n .send({ name: EProtocolCommand.DESTROY })\n .catch(() => undefined);\n destroyed = true;\n transport.stop();\n iframe.remove();\n transport.rejectAll({ message: 'this viewer was destroyed' });\n hub.clear();\n };\n\n const viewer = buildViewerHandle({\n transport,\n hub,\n mirror,\n iframe,\n destroy,\n });\n\n transport.start();\n container.appendChild(iframe);\n\n // Given up on = destroyed; refused = kept, the frame is showing the visitor why.\n return performHandshake({\n transport,\n iframe,\n mirror,\n onGiveUp: destroy,\n subscribeRefusal,\n }).then(() => {\n greeted = true;\n return viewer;\n });\n};\n","import { CS2_INSPECT_LINK_PREFIX } from '@/lib/constants';\n\n// The steam:// inspect link for an item certificate. Pure and instant — the certificate IS the\n// link's payload, so this never talks to the viewer and works with no viewer mounted at all.\nexport const buildInspectLink = ({ cert }: { cert: string }): string =>\n `${CS2_INSPECT_LINK_PREFIX}${cert}`;\n"]}
|
package/dist/index.d.cts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { C as CreateViewerOptions, V as Viewer } from './interfaces-
|
|
2
|
-
export { A as Agent, a as AnimationEntry, B as Background, b as Capability, c as CatalogQuery, d as Charm, E as EBackgroundType, e as EErrorCode, f as EFacing, g as EFeature, h as EHandedness, i as
|
|
1
|
+
import { C as CreateViewerOptions, V as Viewer } from './interfaces-iOmXANSI.cjs';
|
|
2
|
+
export { A as Agent, a as AnimationEntry, B as Background, b as Capability, c as CatalogQuery, d as Charm, E as EBackgroundType, e as EErrorCode, f as EFacing, g as EFeature, h as EHandedness, i as ERefusalFamily, j as ESubject, k as EView, l as EViewerEvent, F as FirstPersonSettings, m as FocusTarget, G as Gloves, P as Patch, n as PlacementTarget, S as Sticker, o as ViewerCapabilities, p as ViewerError, q as ViewerEventHandler, r as ViewerState, W as Weapon } from './interfaces-iOmXANSI.cjs';
|
|
3
3
|
|
|
4
4
|
declare const createViewer: ({ container, key, baseUrl, weapon, environment, background, interactive, autoplay, locale, }: CreateViewerOptions) => Promise<Viewer>;
|
|
5
5
|
|
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { C as CreateViewerOptions, V as Viewer } from './interfaces-
|
|
2
|
-
export { A as Agent, a as AnimationEntry, B as Background, b as Capability, c as CatalogQuery, d as Charm, E as EBackgroundType, e as EErrorCode, f as EFacing, g as EFeature, h as EHandedness, i as
|
|
1
|
+
import { C as CreateViewerOptions, V as Viewer } from './interfaces-iOmXANSI.js';
|
|
2
|
+
export { A as Agent, a as AnimationEntry, B as Background, b as Capability, c as CatalogQuery, d as Charm, E as EBackgroundType, e as EErrorCode, f as EFacing, g as EFeature, h as EHandedness, i as ERefusalFamily, j as ESubject, k as EView, l as EViewerEvent, F as FirstPersonSettings, m as FocusTarget, G as Gloves, P as Patch, n as PlacementTarget, S as Sticker, o as ViewerCapabilities, p as ViewerError, q as ViewerEventHandler, r as ViewerState, W as Weapon } from './interfaces-iOmXANSI.js';
|
|
3
3
|
|
|
4
4
|
declare const createViewer: ({ container, key, baseUrl, weapon, environment, background, interactive, autoplay, locale, }: CreateViewerOptions) => Promise<Viewer>;
|
|
5
5
|
|
package/dist/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { CS2_INSPECT_LINK_PREFIX } from './chunk-
|
|
2
|
-
export { EBackgroundType, EErrorCode, EFacing, EFeature, EHandedness, ESubject, EView, EViewerEvent, PROTOCOL_VERSION, createViewer } from './chunk-
|
|
1
|
+
import { CS2_INSPECT_LINK_PREFIX } from './chunk-Y4CYVADH.js';
|
|
2
|
+
export { EBackgroundType, EErrorCode, EFacing, EFeature, EHandedness, ERefusalFamily, ESubject, EView, EViewerEvent, PROTOCOL_VERSION, createViewer } from './chunk-Y4CYVADH.js';
|
|
3
3
|
|
|
4
4
|
// src/lib/buildInspectLink.ts
|
|
5
5
|
var buildInspectLink = ({ cert }) => `${CS2_INSPECT_LINK_PREFIX}${cert}`;
|
|
@@ -159,7 +159,13 @@ declare enum EErrorCode {
|
|
|
159
159
|
INVALID_ARGUMENT = "invalid_argument",
|
|
160
160
|
NOT_READY = "not_ready",
|
|
161
161
|
RATE_LIMITED = "rate_limited",
|
|
162
|
-
INTERNAL = "internal"
|
|
162
|
+
INTERNAL = "internal",
|
|
163
|
+
REFUSED = "refused"
|
|
164
|
+
}
|
|
165
|
+
declare enum ERefusalFamily {
|
|
166
|
+
SETUP = "setup",
|
|
167
|
+
CUT_OFF = "cut_off",
|
|
168
|
+
OUTAGE = "outage"
|
|
163
169
|
}
|
|
164
170
|
declare enum EViewerEvent {
|
|
165
171
|
READY = "ready",
|
|
@@ -176,11 +182,13 @@ declare enum EViewerEvent {
|
|
|
176
182
|
CAPABILITIES_CHANGE = "capabilitieschange",
|
|
177
183
|
PLACEMENT_START = "placementstart",
|
|
178
184
|
PLACEMENT_MOVE = "placementmove",
|
|
179
|
-
PLACEMENT_END = "placementend"
|
|
185
|
+
PLACEMENT_END = "placementend",
|
|
186
|
+
REFUSED = "refused"
|
|
180
187
|
}
|
|
181
188
|
type ViewerError = {
|
|
182
189
|
code: EErrorCode;
|
|
183
190
|
message?: string;
|
|
191
|
+
family?: ERefusalFamily;
|
|
184
192
|
};
|
|
185
193
|
|
|
186
194
|
type CatalogQuery = {
|
|
@@ -278,4 +286,4 @@ type CreateViewerOptions = {
|
|
|
278
286
|
locale?: string;
|
|
279
287
|
};
|
|
280
288
|
|
|
281
|
-
export { type Agent as A, type Background as B, type CreateViewerOptions as C, EBackgroundType as E, type FirstPersonSettings as F, type Gloves as G, type Patch as P, type Sticker as S, type Viewer as V, type Weapon as W, type AnimationEntry as a, type Capability as b, type CatalogQuery as c, type Charm as d, EErrorCode as e, EFacing as f, EFeature as g, EHandedness as h,
|
|
289
|
+
export { type Agent as A, type Background as B, type CreateViewerOptions as C, EBackgroundType as E, type FirstPersonSettings as F, type Gloves as G, type Patch as P, type Sticker as S, type Viewer as V, type Weapon as W, type AnimationEntry as a, type Capability as b, type CatalogQuery as c, type Charm as d, EErrorCode as e, EFacing as f, EFeature as g, EHandedness as h, ERefusalFamily as i, ESubject as j, EView as k, EViewerEvent as l, type FocusTarget as m, type PlacementTarget as n, type ViewerCapabilities as o, type ViewerError as p, type ViewerEventHandler as q, type ViewerState as r };
|
|
@@ -159,7 +159,13 @@ declare enum EErrorCode {
|
|
|
159
159
|
INVALID_ARGUMENT = "invalid_argument",
|
|
160
160
|
NOT_READY = "not_ready",
|
|
161
161
|
RATE_LIMITED = "rate_limited",
|
|
162
|
-
INTERNAL = "internal"
|
|
162
|
+
INTERNAL = "internal",
|
|
163
|
+
REFUSED = "refused"
|
|
164
|
+
}
|
|
165
|
+
declare enum ERefusalFamily {
|
|
166
|
+
SETUP = "setup",
|
|
167
|
+
CUT_OFF = "cut_off",
|
|
168
|
+
OUTAGE = "outage"
|
|
163
169
|
}
|
|
164
170
|
declare enum EViewerEvent {
|
|
165
171
|
READY = "ready",
|
|
@@ -176,11 +182,13 @@ declare enum EViewerEvent {
|
|
|
176
182
|
CAPABILITIES_CHANGE = "capabilitieschange",
|
|
177
183
|
PLACEMENT_START = "placementstart",
|
|
178
184
|
PLACEMENT_MOVE = "placementmove",
|
|
179
|
-
PLACEMENT_END = "placementend"
|
|
185
|
+
PLACEMENT_END = "placementend",
|
|
186
|
+
REFUSED = "refused"
|
|
180
187
|
}
|
|
181
188
|
type ViewerError = {
|
|
182
189
|
code: EErrorCode;
|
|
183
190
|
message?: string;
|
|
191
|
+
family?: ERefusalFamily;
|
|
184
192
|
};
|
|
185
193
|
|
|
186
194
|
type CatalogQuery = {
|
|
@@ -278,4 +286,4 @@ type CreateViewerOptions = {
|
|
|
278
286
|
locale?: string;
|
|
279
287
|
};
|
|
280
288
|
|
|
281
|
-
export { type Agent as A, type Background as B, type CreateViewerOptions as C, EBackgroundType as E, type FirstPersonSettings as F, type Gloves as G, type Patch as P, type Sticker as S, type Viewer as V, type Weapon as W, type AnimationEntry as a, type Capability as b, type CatalogQuery as c, type Charm as d, EErrorCode as e, EFacing as f, EFeature as g, EHandedness as h,
|
|
289
|
+
export { type Agent as A, type Background as B, type CreateViewerOptions as C, EBackgroundType as E, type FirstPersonSettings as F, type Gloves as G, type Patch as P, type Sticker as S, type Viewer as V, type Weapon as W, type AnimationEntry as a, type Capability as b, type CatalogQuery as c, type Charm as d, EErrorCode as e, EFacing as f, EFeature as g, EHandedness as h, ERefusalFamily as i, ESubject as j, EView as k, EViewerEvent as l, type FocusTarget as m, type PlacementTarget as n, type ViewerCapabilities as o, type ViewerError as p, type ViewerEventHandler as q, type ViewerState as r };
|
package/dist/react.cjs
CHANGED
|
@@ -266,13 +266,15 @@ var performHandshake = ({
|
|
|
266
266
|
transport,
|
|
267
267
|
iframe,
|
|
268
268
|
mirror,
|
|
269
|
-
onGiveUp
|
|
269
|
+
onGiveUp,
|
|
270
|
+
subscribeRefusal
|
|
270
271
|
}) => new Promise((resolve, reject) => {
|
|
271
272
|
let settled = false;
|
|
272
273
|
const beginAt = Date.now();
|
|
273
274
|
const settle = () => {
|
|
274
275
|
settled = true;
|
|
275
276
|
iframe.removeEventListener("load", attempt);
|
|
277
|
+
unsubscribeRefusal();
|
|
276
278
|
};
|
|
277
279
|
const attempt = () => {
|
|
278
280
|
if (settled) return;
|
|
@@ -281,7 +283,7 @@ var performHandshake = ({
|
|
|
281
283
|
onGiveUp();
|
|
282
284
|
return reject({
|
|
283
285
|
code: "invalid_key" /* INVALID_KEY */,
|
|
284
|
-
message: "the viewer never answered: the
|
|
286
|
+
message: "the viewer never answered: the render service is unreachable, or the frame was blocked before the page could boot"
|
|
285
287
|
});
|
|
286
288
|
}
|
|
287
289
|
transport.send({
|
|
@@ -297,6 +299,15 @@ var performHandshake = ({
|
|
|
297
299
|
resolve();
|
|
298
300
|
}).catch(() => setTimeout(attempt, HELLO_RETRY_MS));
|
|
299
301
|
};
|
|
302
|
+
const unsubscribeRefusal = subscribeRefusal(({ family }) => {
|
|
303
|
+
if (settled) return;
|
|
304
|
+
settle();
|
|
305
|
+
reject({
|
|
306
|
+
code: "refused" /* REFUSED */,
|
|
307
|
+
family,
|
|
308
|
+
message: "the embed server refused this viewer; its family says whose problem it is"
|
|
309
|
+
});
|
|
310
|
+
});
|
|
300
311
|
iframe.addEventListener("load", attempt);
|
|
301
312
|
setTimeout(attempt, HELLO_RETRY_MS);
|
|
302
313
|
});
|
|
@@ -331,6 +342,10 @@ var createViewer = ({
|
|
|
331
342
|
let destroyed = false;
|
|
332
343
|
let greeted = false;
|
|
333
344
|
let greetingAgain = false;
|
|
345
|
+
const subscribeRefusal = (handler) => hub.on(
|
|
346
|
+
"refused" /* REFUSED */,
|
|
347
|
+
(payload) => handler(payload)
|
|
348
|
+
);
|
|
334
349
|
const greetAgain = () => {
|
|
335
350
|
if (!greeted || greetingAgain || destroyed) return;
|
|
336
351
|
greetingAgain = true;
|
|
@@ -341,7 +356,8 @@ var createViewer = ({
|
|
|
341
356
|
mirror,
|
|
342
357
|
// A reload that never answers leaves the viewer as it is: the frame is the
|
|
343
358
|
// integrator's to keep or drop, and an error says so.
|
|
344
|
-
onGiveUp: () => void 0
|
|
359
|
+
onGiveUp: () => void 0,
|
|
360
|
+
subscribeRefusal
|
|
345
361
|
}).then(
|
|
346
362
|
() => hub.dispatch({
|
|
347
363
|
name: "reconnect" /* RECONNECT */,
|
|
@@ -382,7 +398,8 @@ var createViewer = ({
|
|
|
382
398
|
transport,
|
|
383
399
|
iframe,
|
|
384
400
|
mirror,
|
|
385
|
-
onGiveUp: destroy
|
|
401
|
+
onGiveUp: destroy,
|
|
402
|
+
subscribeRefusal
|
|
386
403
|
}).then(() => {
|
|
387
404
|
greeted = true;
|
|
388
405
|
return viewer;
|