mirror of
https://github.com/yeicor-3d/yet-another-cad-viewer.git
synced 2025-12-20 06:27:04 +01:00
Compare commits
25 Commits
v0.10.0-rc
...
v0.10.2-al
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
f86b714c08 | ||
|
|
2ae7c86f8d | ||
|
|
0908216bfc | ||
|
|
7871a5070d | ||
|
|
5173f00d29 | ||
|
|
c2ef910783 | ||
|
|
5a5f948224 | ||
|
|
dbeae5632e | ||
|
|
59116e4a1a | ||
|
|
0be0103c3c | ||
|
|
d6deef9e7f | ||
|
|
ad956762f4 | ||
|
|
a4acd2f3d3 | ||
|
|
c877fef490 | ||
|
|
0855a9c6c7 | ||
|
|
657b34d098 | ||
|
|
ad83f1c937 | ||
|
|
38be4c638b | ||
|
|
63f2b716d6 | ||
|
|
9e70a3998d | ||
|
|
c7c4adc250 | ||
|
|
393decd876 | ||
|
|
111f417905 | ||
|
|
7296b15a67 | ||
|
|
f2a607bb00 |
1
.github/workflows/deploy1.yml
vendored
1
.github/workflows/deploy1.yml
vendored
@@ -16,6 +16,7 @@ jobs:
|
|||||||
- uses: "actions/checkout@v4"
|
- uses: "actions/checkout@v4"
|
||||||
with: # Ensure we are not in a detached HEAD state
|
with: # Ensure we are not in a detached HEAD state
|
||||||
ref: "master"
|
ref: "master"
|
||||||
|
token: "${{ secrets.GH_PAT }}"
|
||||||
# Check that the tag commit is the latest master commit
|
# Check that the tag commit is the latest master commit
|
||||||
- run: |
|
- run: |
|
||||||
git fetch --tags
|
git fetch --tags
|
||||||
|
|||||||
@@ -15,15 +15,17 @@ in a web browser.
|
|||||||
- Select any entity and measure bounding box size and distances.
|
- Select any entity and measure bounding box size and distances.
|
||||||
- Hot reloading while editing the CAD model (using the `yacv-server` package).
|
- Hot reloading while editing the CAD model (using the `yacv-server` package).
|
||||||
- Fully-featured static deployment: just upload the viewer and models to your server.
|
- Fully-featured static deployment: just upload the viewer and models to your server.
|
||||||
|
- Build123d playground! Code and build your model fully inside the
|
||||||
|
browser: [demo](https://yeicor-3d.github.io/yet-another-cad-viewer/#pg_code_url=https://raw.githubusercontent.com/gumyr/build123d/refs/heads/dev/examples/toy_truck.py).
|
||||||
|
|
||||||
## Usage
|
## Usage
|
||||||
|
|
||||||
The [example](example) is a fully working project that shows how to use the viewer.
|
The [example](example) is a fully working project that shows how to use the viewer.
|
||||||
|
|
||||||
You can play with the latest
|
You can play with the latest
|
||||||
demo [here](https://yeicor-3d.github.io/yet-another-cad-viewer/?preload=logo.glb&preload=logo_hl.glb&preload=fox.glb&preload=img.jpg.glb&preload=location.glb)
|
demo [here](https://yeicor-3d.github.io/yet-another-cad-viewer/?preload=logo.glb&preload=logo_hl.glb&preload=logo_hl_tex.glb&preload=fox.glb&preload=img.jpg.glb&preload=location.glb)
|
||||||
(or
|
(or
|
||||||
[without animation](https://yeicor-3d.github.io/yet-another-cad-viewer/?autoplay=false&preload=logo.glb&preload=logo_hl.glb&preload=fox.glb&preload=img.jpg.glb&preload=location.glb)).
|
[without animation](https://yeicor-3d.github.io/yet-another-cad-viewer/?autoplay=false&preload=logo.glb&preload=logo_hl.glb&preload=logo_hl_tex.glb&preload=fox.glb&preload=img.jpg.glb&preload=location.glb)).
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
@@ -32,4 +34,5 @@ demo [here](https://yeicor-3d.github.io/yet-another-cad-viewer/?preload=logo.glb
|
|||||||
- [cq-studio](https://github.com/ccazabon/cq-studio) provides an alternative workflow that detects file changes instead
|
- [cq-studio](https://github.com/ccazabon/cq-studio) provides an alternative workflow that detects file changes instead
|
||||||
of relying on an interactive environment like Jupyter for hot-reloading.
|
of relying on an interactive environment like Jupyter for hot-reloading.
|
||||||
Uses the same backend and frontend behind the scenes.
|
Uses the same backend and frontend behind the scenes.
|
||||||
- [build123d-docker](https://github.com/derhuerst/build123d-docker/pkgs/container/build123d) provides docker images for Yet Another CAD Viewer and other projects, with automatic updates.
|
- [build123d-docker](https://github.com/derhuerst/build123d-docker/pkgs/container/build123d) provides docker images for
|
||||||
|
Yet Another CAD Viewer and other projects, with automatic updates.
|
||||||
|
|||||||
@@ -53,7 +53,7 @@ async function onModelUpdateRequest(event: NetworkUpdateEvent) {
|
|||||||
let model = event.models[modelIndex];
|
let model = event.models[modelIndex];
|
||||||
tools.value?.removeObjectSelections(model.name);
|
tools.value?.removeObjectSelections(model.name);
|
||||||
try {
|
try {
|
||||||
let loadHelpers = (await settings()).loadHelpers;
|
let loadHelpers = (await settings).loadHelpers;
|
||||||
if (!model.isRemove) {
|
if (!model.isRemove) {
|
||||||
doc = await SceneMgr.loadModel(sceneUrl, doc, model.name, model.url, isLast && loadHelpers, isLast);
|
doc = await SceneMgr.loadModel(sceneUrl, doc, model.name, model.url, isLast && loadHelpers, isLast);
|
||||||
} else {
|
} else {
|
||||||
@@ -83,7 +83,7 @@ networkMgr.addEventListener('update-early',
|
|||||||
networkMgr.addEventListener('update', (e) => onModelUpdateRequest(e as NetworkUpdateEvent));
|
networkMgr.addEventListener('update', (e) => onModelUpdateRequest(e as NetworkUpdateEvent));
|
||||||
let preloadingModels = ref<Array<string>>([]);
|
let preloadingModels = ref<Array<string>>([]);
|
||||||
(async () => { // Start loading all configured models ASAP
|
(async () => { // Start loading all configured models ASAP
|
||||||
let sett = await settings();
|
let sett = await settings;
|
||||||
if (sett.preload.length > 0) {
|
if (sett.preload.length > 0) {
|
||||||
watch(viewer, (newViewer) => {
|
watch(viewer, (newViewer) => {
|
||||||
if (newViewer) {
|
if (newViewer) {
|
||||||
@@ -108,6 +108,23 @@ async function loadModelManual() {
|
|||||||
const modelUrl = prompt("For an improved experience in viewing CAD/GLTF models with automatic updates, it's recommended to use the official yacv_server Python package. This ensures seamless serving of models and automatic updates.\n\nOtherwise, enter the URL of the model to load:");
|
const modelUrl = prompt("For an improved experience in viewing CAD/GLTF models with automatic updates, it's recommended to use the official yacv_server Python package. This ensures seamless serving of models and automatic updates.\n\nOtherwise, enter the URL of the model to load:");
|
||||||
if (modelUrl) await networkMgr.load(modelUrl);
|
if (modelUrl) await networkMgr.load(modelUrl);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Detect dropped .glb files and load them manually
|
||||||
|
document.body.addEventListener("dragover", e => {
|
||||||
|
e.preventDefault(); // Allow drop
|
||||||
|
});
|
||||||
|
|
||||||
|
document.body.addEventListener("drop", async e => {
|
||||||
|
e.preventDefault();
|
||||||
|
const file = e.dataTransfer?.files?.[0];
|
||||||
|
if (!file) return;
|
||||||
|
|
||||||
|
const ext = file.name.split('.').pop()?.toLowerCase();
|
||||||
|
if (ext === 'glb' || ext === 'gltf') {
|
||||||
|
await networkMgr.load(file);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
|
|||||||
@@ -15,11 +15,11 @@ let isSmallBuild = typeof __YACV_SMALL_BUILD__ !== 'undefined' && __YACV_SMALL_B
|
|||||||
*
|
*
|
||||||
* Remember to call mergeFinalize after all models have been merged (slower required operations).
|
* Remember to call mergeFinalize after all models have been merged (slower required operations).
|
||||||
*/
|
*/
|
||||||
export async function mergePartial(url: string, name: string, document: Document, networkFinished: () => void = () => {
|
export async function mergePartial(url: string | Blob, name: string, document: Document, networkFinished: () => void = () => {
|
||||||
}): Promise<Document> {
|
}): Promise<Document> {
|
||||||
// Fetch the complete document from the network
|
// Fetch the complete document from the network
|
||||||
// This could be done at the same time as the document is being processed, but I wanted better metrics
|
// This could be done at the same time as the document is being processed, but I wanted better metrics
|
||||||
let response = await fetch(url);
|
let response = await fetchOrRead(url);
|
||||||
let buffer = await response.arrayBuffer();
|
let buffer = await response.arrayBuffer();
|
||||||
networkFinished();
|
networkFinished();
|
||||||
|
|
||||||
@@ -118,3 +118,30 @@ function mergeScenes(): Transform {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Fetches a URL or reads it if it is a Blob URL */
|
||||||
|
async function fetchOrRead(url: string | Blob) {
|
||||||
|
if (url instanceof Blob) {
|
||||||
|
// Use the FileReader API as fetch does not support Blob URLs
|
||||||
|
return new Promise<Response>((resolve, reject) => {
|
||||||
|
const reader = new FileReader();
|
||||||
|
reader.onloadend = (event: ProgressEvent<FileReader>) => {
|
||||||
|
if (event.target && event.target.result) {
|
||||||
|
resolve(new Response(event.target.result));
|
||||||
|
} else {
|
||||||
|
reject(new Error("Failed to read Blob URL: " + url));
|
||||||
|
}
|
||||||
|
};
|
||||||
|
reader.onerror = (error) => {
|
||||||
|
reject(new Error("Error reading Blob URL: " + url + " - " + error));
|
||||||
|
};
|
||||||
|
// Read the Blob URL as an ArrayBuffer
|
||||||
|
reader.readAsArrayBuffer(new Blob([url]));
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
// Fetch the URL
|
||||||
|
return fetch(url);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -4,12 +4,12 @@ const batchTimeout = 250; // ms
|
|||||||
|
|
||||||
export class NetworkUpdateEventModel {
|
export class NetworkUpdateEventModel {
|
||||||
name: string;
|
name: string;
|
||||||
url: string;
|
url: string | Blob;
|
||||||
// TODO: Detect and manage instances of the same object (same hash, different name)
|
// TODO: Detect and manage instances of the same object (same hash, different name)
|
||||||
hash: string | null;
|
hash: string | null;
|
||||||
isRemove: boolean | null; // This is null for a shutdown event
|
isRemove: boolean | null; // This is null for a shutdown event
|
||||||
|
|
||||||
constructor(name: string, url: string, hash: string | null, isRemove: boolean | null) {
|
constructor(name: string, url: string | Blob, hash: string | null, isRemove: boolean | null) {
|
||||||
this.name = name;
|
this.name = name;
|
||||||
this.url = url;
|
this.url = url;
|
||||||
this.hash = hash;
|
this.hash = hash;
|
||||||
@@ -42,18 +42,26 @@ export class NetworkManager extends EventTarget {
|
|||||||
*
|
*
|
||||||
* Updates will be emitted as "update" events, including the download URL and the model name.
|
* Updates will be emitted as "update" events, including the download URL and the model name.
|
||||||
*/
|
*/
|
||||||
async load(url: string) {
|
async load(url: string | Blob) {
|
||||||
if (url.startsWith("dev+") || url.startsWith("dev ")) {
|
if (!(url instanceof Blob) && (url.startsWith("dev+") || url.startsWith("dev "))) {
|
||||||
let baseUrl = new URL(url.slice(4));
|
let baseUrl = new URL(url.slice(4));
|
||||||
baseUrl.searchParams.set("api_updates", "true");
|
baseUrl.searchParams.set("api_updates", "true");
|
||||||
await this.monitorDevServer(baseUrl);
|
await this.monitorDevServer(baseUrl);
|
||||||
} else {
|
} else {
|
||||||
// Get the last part of the URL as the "name" of the model
|
let name;
|
||||||
let name = url.split("/").pop();
|
let hash = null;
|
||||||
name = name?.split(".")[0] || `unknown-${Math.random()}`;
|
if (url instanceof Blob) {
|
||||||
// Use a head request to get the hash of the file
|
if (url instanceof File) name = (url as File).name
|
||||||
let response = await fetch(url, {method: "HEAD"});
|
else name = `blob-${Math.random()}`;
|
||||||
let hash = response.headers.get("etag");
|
name = name.replace('.glb', '').replace('.gltf', '');
|
||||||
|
} else {
|
||||||
|
// Get the last part of the URL as the "name" of the model
|
||||||
|
name = url.split("/").pop();
|
||||||
|
name = name?.split(".")[0] || `unknown-${Math.random()}`;
|
||||||
|
// Use a head request to get the hash of the file
|
||||||
|
let response = await fetch(url, {method: "HEAD"});
|
||||||
|
hash = response.headers.get("etag");
|
||||||
|
}
|
||||||
// Only trigger an update if the hash has changed
|
// Only trigger an update if the hash has changed
|
||||||
this.foundModel(name, hash, url, false);
|
this.foundModel(name, hash, url, false);
|
||||||
}
|
}
|
||||||
@@ -61,7 +69,7 @@ export class NetworkManager extends EventTarget {
|
|||||||
|
|
||||||
private async monitorDevServer(url: URL, stop: () => boolean = () => false) {
|
private async monitorDevServer(url: URL, stop: () => boolean = () => false) {
|
||||||
while (!stop()) {
|
while (!stop()) {
|
||||||
let monitorEveryMs = (await settings()).monitorEveryMs;
|
let monitorEveryMs = (await settings).monitorEveryMs;
|
||||||
try {
|
try {
|
||||||
// WARNING: This will spam the console logs with failed requests when the server is down
|
// WARNING: This will spam the console logs with failed requests when the server is down
|
||||||
const controller = new AbortController();
|
const controller = new AbortController();
|
||||||
@@ -92,7 +100,7 @@ export class NetworkManager extends EventTarget {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private foundModel(name: string, hash: string | null, url: string, isRemove: boolean | null, disconnect: () => void = () => {
|
private foundModel(name: string, hash: string | null, url: string | Blob, isRemove: boolean | null, disconnect: () => void = () => {
|
||||||
}) {
|
}) {
|
||||||
// console.debug("Found model", name, "with hash", hash, "at", url, "isRemove", isRemove);
|
// console.debug("Found model", name, "with hash", hash, "at", url, "isRemove", isRemove);
|
||||||
|
|
||||||
|
|||||||
@@ -9,7 +9,7 @@ import {Matrix4} from "three/src/math/Matrix4.js"
|
|||||||
/** This class helps manage SceneManagerData. All methods are static to support reactivity... */
|
/** This class helps manage SceneManagerData. All methods are static to support reactivity... */
|
||||||
export class SceneMgr {
|
export class SceneMgr {
|
||||||
/** Loads a GLB model from a URL and adds it to the viewer or replaces it if the names match */
|
/** Loads a GLB model from a URL and adds it to the viewer or replaces it if the names match */
|
||||||
static async loadModel(sceneUrl: Ref<string>, document: Document, name: string, url: string, updateHelpers: boolean = true, reloadScene: boolean = true): Promise<Document> {
|
static async loadModel(sceneUrl: Ref<string>, document: Document, name: string, url: string | Blob, updateHelpers: boolean = true, reloadScene: boolean = true): Promise<Document> {
|
||||||
let loadStart = performance.now();
|
let loadStart = performance.now();
|
||||||
let loadNetworkEnd: number;
|
let loadNetworkEnd: number;
|
||||||
|
|
||||||
@@ -100,7 +100,9 @@ export class SceneMgr {
|
|||||||
newAxes(helpersDoc, bb.getSize(new Vector3()).multiplyScalar(0.5), transform);
|
newAxes(helpersDoc, bb.getSize(new Vector3()).multiplyScalar(0.5), transform);
|
||||||
newGridBox(helpersDoc, bb.getSize(new Vector3()), transform);
|
newGridBox(helpersDoc, bb.getSize(new Vector3()), transform);
|
||||||
let helpersUrl = URL.createObjectURL(new Blob([await toBuffer(helpersDoc)]));
|
let helpersUrl = URL.createObjectURL(new Blob([await toBuffer(helpersDoc)]));
|
||||||
return await SceneMgr.loadModel(sceneUrl, document, extrasNameValueHelpers, helpersUrl, false, reloadScene);
|
let newDocument = await SceneMgr.loadModel(sceneUrl, document, extrasNameValueHelpers, helpersUrl, false, reloadScene);
|
||||||
|
URL.revokeObjectURL(helpersUrl);
|
||||||
|
return newDocument;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Serializes the current document into a GLB and updates the viewerSrc */
|
/** Serializes the current document into a GLB and updates the viewerSrc */
|
||||||
@@ -112,6 +114,7 @@ export class SceneMgr {
|
|||||||
let buffer = await toBuffer(document);
|
let buffer = await toBuffer(document);
|
||||||
let blob = new Blob([buffer], {type: 'model/gltf-binary'});
|
let blob = new Blob([buffer], {type: 'model/gltf-binary'});
|
||||||
console.debug("Showing current doc", document, "with", buffer.length, "total bytes");
|
console.debug("Showing current doc", document, "with", buffer.length, "total bytes");
|
||||||
|
if (sceneUrl.value.startsWith("blob:")) URL.revokeObjectURL(sceneUrl.value);
|
||||||
sceneUrl.value = URL.createObjectURL(blob);
|
sceneUrl.value = URL.createObjectURL(blob);
|
||||||
|
|
||||||
return document;
|
return document;
|
||||||
|
|||||||
@@ -1,11 +1,9 @@
|
|||||||
// These are the default values for the settings, which are overridden below
|
// These are the default values for the settings, which are overridden below
|
||||||
import {ungzip} from "pako";
|
import {ungzip} from "pako";
|
||||||
import {b66Decode} from "../tools/b66.ts";
|
import {b64UrlDecode} from "../tools/b64.ts";
|
||||||
|
|
||||||
let settingsCache: any = null;
|
const firstTimeNames: Array<string> = []; // Needed for array values, which clear the array when overridden
|
||||||
|
export const settings = (async () => {
|
||||||
export async function settings() {
|
|
||||||
if (settingsCache !== null) return settingsCache;
|
|
||||||
let settings = {
|
let settings = {
|
||||||
preload: [
|
preload: [
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
@@ -80,6 +78,12 @@ export async function settings() {
|
|||||||
// Get the default preload URL if not overridden (requires a fetch that is avoided if possible)
|
// Get the default preload URL if not overridden (requires a fetch that is avoided if possible)
|
||||||
for (let i = 0; i < settings.preload.length; i++) {
|
for (let i = 0; i < settings.preload.length; i++) {
|
||||||
let url = settings.preload[i];
|
let url = settings.preload[i];
|
||||||
|
// Ignore empty preload URLs to allow overriding default auto behavior
|
||||||
|
if (url === '') {
|
||||||
|
settings.preload = settings.preload.slice(0, i).concat(settings.preload.slice(i + 1));
|
||||||
|
continue; // Skip this preload URL
|
||||||
|
}
|
||||||
|
// Handle special <auto> preload URL
|
||||||
if (url === '<auto>') {
|
if (url === '<auto>') {
|
||||||
if (settings.pg_code != "") { // <auto> means no preload URL if code is set
|
if (settings.pg_code != "") { // <auto> means no preload URL if code is set
|
||||||
settings.preload = settings.preload.slice(0, i).concat(settings.preload.slice(i + 1));
|
settings.preload = settings.preload.slice(0, i).concat(settings.preload.slice(i + 1));
|
||||||
@@ -102,9 +106,9 @@ export async function settings() {
|
|||||||
// Auto-decompress the code and other playground settings
|
// Auto-decompress the code and other playground settings
|
||||||
if (settings.pg_code.length > 0) {
|
if (settings.pg_code.length > 0) {
|
||||||
try {
|
try {
|
||||||
settings.pg_code = ungzip(b66Decode(settings.pg_code), {to: 'string'});
|
settings.pg_code = ungzip(b64UrlDecode(settings.pg_code), {to: 'string'});
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.warn("Failed to decompress code (assuming raw code):", error);
|
console.log("pg_code is not base64url+gzipped, assuming raw code. Decoding error:", error);
|
||||||
}
|
}
|
||||||
if (settings.pg_opacity_loading < 0) {
|
if (settings.pg_opacity_loading < 0) {
|
||||||
// If the opacity is not set, use 0.0 if preload is set, otherwise 0.9
|
// If the opacity is not set, use 0.0 if preload is set, otherwise 0.9
|
||||||
@@ -112,11 +116,9 @@ export async function settings() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
settingsCache = settings;
|
|
||||||
return settings;
|
return settings;
|
||||||
}
|
})()
|
||||||
|
|
||||||
const firstTimeNames: Array<string> = []; // Needed for array values, which clear the array when overridden
|
|
||||||
function parseSetting(name: string, value: string, settings: any): any {
|
function parseSetting(name: string, value: string, settings: any): any {
|
||||||
let arrayElem = name.endsWith(".0")
|
let arrayElem = name.endsWith(".0")
|
||||||
if (arrayElem) name = name.slice(0, -2);
|
if (arrayElem) name = name.slice(0, -2);
|
||||||
|
|||||||
@@ -60,7 +60,7 @@ const clipPlaneZ = ref(1);
|
|||||||
const clipPlaneSwappedZ = ref(false);
|
const clipPlaneSwappedZ = ref(false);
|
||||||
const edgeWidth = ref(0);
|
const edgeWidth = ref(0);
|
||||||
(async () => {
|
(async () => {
|
||||||
let s = await settings();
|
let s = await settings;
|
||||||
edgeWidth.value = s.edgeWidth;
|
edgeWidth.value = s.edgeWidth;
|
||||||
})();
|
})();
|
||||||
|
|
||||||
|
|||||||
@@ -4,26 +4,34 @@ import {VueMonacoEditor} from '@guolao/vue-monaco-editor'
|
|||||||
import {nextTick, onMounted, ref, shallowRef} from "vue";
|
import {nextTick, onMounted, ref, shallowRef} from "vue";
|
||||||
import Loading from "../misc/Loading.vue";
|
import Loading from "../misc/Loading.vue";
|
||||||
import {newPyodideWorker} from "./pyodide-worker-api.ts";
|
import {newPyodideWorker} from "./pyodide-worker-api.ts";
|
||||||
import {mdiCircleOpacity, mdiClose, mdiContentSave, mdiFolderOpen, mdiPlay, mdiReload, mdiShare} from "@mdi/js";
|
import {
|
||||||
|
mdiBroom,
|
||||||
|
mdiCircleOpacity,
|
||||||
|
mdiClose,
|
||||||
|
mdiContentSave,
|
||||||
|
mdiFolderOpen,
|
||||||
|
mdiPlay,
|
||||||
|
mdiReload,
|
||||||
|
mdiShare
|
||||||
|
} from "@mdi/js";
|
||||||
import {VBtn, VCard, VCardText, VSlider, VSpacer, VToolbar, VToolbarTitle, VTooltip} from "vuetify/components";
|
import {VBtn, VCard, VCardText, VSlider, VSpacer, VToolbar, VToolbarTitle, VTooltip} from "vuetify/components";
|
||||||
// @ts-expect-error
|
// @ts-expect-error
|
||||||
import SvgIcon from '@jamescoyle/vue-icon';
|
import SvgIcon from '@jamescoyle/vue-icon';
|
||||||
import {version as pyodideVersion} from "pyodide";
|
import {version as pyodideVersion} from "pyodide";
|
||||||
import {gzip} from 'pako';
|
import {gzip} from 'pako';
|
||||||
import {b66Encode} from "./b66.ts";
|
import {b64UrlEncode} from "./b64.ts";
|
||||||
import {Base64} from 'js-base64'; // More compatible with binary data from python...
|
import {Base64} from 'js-base64'; // More compatible with binary data from python...
|
||||||
import {NetworkUpdateEvent, NetworkUpdateEventModel} from "../misc/network.ts";
|
import {NetworkUpdateEvent, NetworkUpdateEventModel} from "../misc/network.ts";
|
||||||
import {settings} from "../misc/settings.ts";
|
import {settings} from "../misc/settings.ts";
|
||||||
// @ts-expect-error
|
// @ts-expect-error
|
||||||
import playgroundStartupCode from './PlaygroundStartup.py?raw';
|
import playgroundStartupCode from './PlaygroundStartup.py?raw';
|
||||||
|
|
||||||
const props = defineProps<{ initialCode: string }>();
|
const model = defineModel<{ code: string, firstTime: boolean }>({required: true}); // Initial code should only be set on first load!
|
||||||
const emit = defineEmits<{ close: [], updateModel: [NetworkUpdateEvent] }>()
|
const emit = defineEmits<{ close: [], updateModel: [NetworkUpdateEvent] }>()
|
||||||
|
|
||||||
// ============ LOAD MONACO EDITOR ============
|
// ============ LOAD MONACO EDITOR ============
|
||||||
setupMonaco() // Must be called before using the editor
|
setupMonaco() // Must be called before using the editor
|
||||||
|
|
||||||
const code = ref((import.meta as any)?.hot?.data?.code || props.initialCode);
|
|
||||||
const outputText = ref(``);
|
const outputText = ref(``);
|
||||||
|
|
||||||
function output(text: string) {
|
function output(text: string) {
|
||||||
@@ -51,21 +59,24 @@ const MONACO_EDITOR_OPTIONS = {
|
|||||||
const editorTheme = window.matchMedia("(prefers-color-scheme: dark)").matches ? `vs-dark` : `vs`
|
const editorTheme = window.matchMedia("(prefers-color-scheme: dark)").matches ? `vs-dark` : `vs`
|
||||||
const editor = shallowRef()
|
const editor = shallowRef()
|
||||||
const handleMount = (editorInstance: typeof VueMonacoEditor) => (editor.value = editorInstance)
|
const handleMount = (editorInstance: typeof VueMonacoEditor) => (editor.value = editorInstance)
|
||||||
const opacity = ref(0.9); // Opacity for the editor
|
const opacity = ref(0.9); // Opacity for the editor (overriden when settings are loaded)
|
||||||
|
|
||||||
// ============ LOAD PYODIDE (ASYNC) ============
|
// ============ LOAD PYODIDE (ASYNC) ============
|
||||||
let pyodideWorker: ReturnType<typeof newPyodideWorker> | null = (import.meta as any).hot?.data?.pyodideWorker || null;
|
let pyodideWorker: ReturnType<typeof newPyodideWorker> | null = (import.meta as any).hot?.data?.pyodideWorker || null;
|
||||||
const running = ref(true);
|
const running = ref(true);
|
||||||
|
|
||||||
async function setupPyodide() {
|
async function setupPyodide(first: boolean, loadSnapshot: Uint8Array | undefined = undefined) {
|
||||||
running.value = true;
|
running.value = true;
|
||||||
if (opacity.value == 0.0) opacity.value = 0.9; // User doesn't know how to show code again, reset after reopening
|
if (opacity.value == 0.0 && !first) opacity.value = 0.9; // User doesn't know how to show code again, reset after reopening
|
||||||
if (pyodideWorker === null) {
|
if (pyodideWorker === null) {
|
||||||
output("Creating new Pyodide worker...\n");
|
output("Creating new Pyodide worker...\n");
|
||||||
pyodideWorker = newPyodideWorker({
|
pyodideWorker = newPyodideWorker(Object.assign({
|
||||||
indexURL: `https://cdn.jsdelivr.net/pyodide/v${pyodideVersion}/full/`, // FIXME: Local deployment?
|
// Note: python wheels are downloaded from the CDN, as we can't know which ones are needed in advance to bundle them
|
||||||
|
// Furthermore, this lets us use the latest version of all wheels including ocp-specific ones without app updates
|
||||||
|
indexURL: `https://cdn.jsdelivr.net/pyodide/v${pyodideVersion}/full/`,
|
||||||
packages: ["micropip", "sqlite3"], // Faster load if done here
|
packages: ["micropip", "sqlite3"], // Faster load if done here
|
||||||
});
|
// _makeSnapshot: true, // Enable snapshotting for faster startup (still experimental: breaks loading any packages)
|
||||||
|
}, (loadSnapshot ? {_loadSnapshot: loadSnapshot} : {}))); // Load snapshot if provided
|
||||||
if ((import.meta as any).hot) (import.meta as any).hot.data.pyodideWorker = pyodideWorker
|
if ((import.meta as any).hot) (import.meta as any).hot.data.pyodideWorker = pyodideWorker
|
||||||
} else {
|
} else {
|
||||||
output("Reusing existing Pyodide instance...\n");
|
output("Reusing existing Pyodide instance...\n");
|
||||||
@@ -73,7 +84,7 @@ async function setupPyodide() {
|
|||||||
output("Preloading packages...\n");
|
output("Preloading packages...\n");
|
||||||
await pyodideWorker.asyncRun(playgroundStartupCode, output, output); // Also import yacv_server and mock ocp_vscode here for faster custom code execution
|
await pyodideWorker.asyncRun(playgroundStartupCode, output, output); // Also import yacv_server and mock ocp_vscode here for faster custom code execution
|
||||||
running.value = false; // Indicate that Pyodide is ready
|
running.value = false; // Indicate that Pyodide is ready
|
||||||
output("Pyodide worker initialized.\n");
|
output("Pyodide worker ready.\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
async function runCode() {
|
async function runCode() {
|
||||||
@@ -88,8 +99,7 @@ async function runCode() {
|
|||||||
output("Running code...\n");
|
output("Running code...\n");
|
||||||
try {
|
try {
|
||||||
running.value = true;
|
running.value = true;
|
||||||
if ((import.meta as any).hot) (import.meta as any).hot.data.code = code.value; // Save code for hot reload
|
await pyodideWorker.asyncRun(model.value.code, output, (msg: string) => {
|
||||||
await pyodideWorker.asyncRun(code.value, output, (msg: string) => {
|
|
||||||
// Detect models printed to console (since http server is not available in pyodide)
|
// Detect models printed to console (since http server is not available in pyodide)
|
||||||
if (msg.startsWith(yacvServerModelPrefix)) {
|
if (msg.startsWith(yacvServerModelPrefix)) {
|
||||||
const modelData = msg.slice(yacvServerModelPrefix.length);
|
const modelData = msg.slice(yacvServerModelPrefix.length);
|
||||||
@@ -99,7 +109,7 @@ async function runCode() {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
output(`Error running initial code: ${e}\n`);
|
output(`Error running code: ${e}\n`);
|
||||||
} finally {
|
} finally {
|
||||||
running.value = false; // Indicate that Pyodide is ready
|
running.value = false; // Indicate that Pyodide is ready
|
||||||
}
|
}
|
||||||
@@ -131,7 +141,7 @@ function onModelData(modelData: string) {
|
|||||||
"Invalid GLTF binary data received: " + binaryData.slice(0, 4).toString());
|
"Invalid GLTF binary data received: " + binaryData.slice(0, 4).toString());
|
||||||
// - Create a Blob from the binary data to be used as a URL
|
// - Create a Blob from the binary data to be used as a URL
|
||||||
const blob = new Blob([binaryData], {type: 'model/gltf-binary'});
|
const blob = new Blob([binaryData], {type: 'model/gltf-binary'});
|
||||||
modelMetadata.url = URL.createObjectURL(blob); // Set the hacked URL in the model metadata
|
modelMetadata.url = URL.createObjectURL(blob); // Set the hacked URL in the model metadata XXX: revoked on App.vue
|
||||||
}
|
}
|
||||||
// - Emit the event with the model metadata and URL
|
// - Emit the event with the model metadata and URL
|
||||||
let networkUpdateEvent = new NetworkUpdateEvent([modelMetadata], () => {
|
let networkUpdateEvent = new NetworkUpdateEvent([modelMetadata], () => {
|
||||||
@@ -139,22 +149,26 @@ function onModelData(modelData: string) {
|
|||||||
emit('updateModel', networkUpdateEvent);
|
emit('updateModel', networkUpdateEvent);
|
||||||
}
|
}
|
||||||
|
|
||||||
function resetWorker() {
|
function resetWorker(loadSnapshot: Uint8Array | undefined = undefined) {
|
||||||
if (pyodideWorker) {
|
if (pyodideWorker) {
|
||||||
pyodideWorker.terminate(); // Terminate existing worker
|
pyodideWorker.terminate(); // Terminate existing worker
|
||||||
pyodideWorker = null; // Reset worker reference
|
pyodideWorker = null; // Reset worker reference
|
||||||
}
|
}
|
||||||
outputText.value = ``; // Clear output text
|
outputText.value = ``; // Clear output text
|
||||||
setupPyodide(); // Reinitialize Pyodide
|
setupPyodide(false, loadSnapshot); // Reinitialize Pyodide
|
||||||
}
|
}
|
||||||
|
|
||||||
function shareLink() {
|
function shareLink() {
|
||||||
const baseUrl = window.location
|
const baseUrl = window.location
|
||||||
const urlParams = new URLSearchParams(baseUrl.hash.slice(1)); // Keep all previous URL parameters
|
const searchParams = new URLSearchParams(baseUrl.search);
|
||||||
urlParams.set('pg_code', b66Encode(gzip(code.value, {level: 9}))); // Compress and encode the code
|
searchParams.delete('pg_code_url'); // Remove any existing pg_code parameter
|
||||||
const shareUrl = `${baseUrl.origin}${baseUrl.pathname}${baseUrl.search}#${urlParams.toString()}`; // Prefer hash to GET (bigger limits)
|
searchParams.delete('pg_code'); // Remove any existing pg_code parameter
|
||||||
|
const hashParams = new URLSearchParams(baseUrl.hash.slice(1)); // Keep all previous URL parameters
|
||||||
|
hashParams.delete('pg_code_url') // Would overwrite the pg_code parameter
|
||||||
|
hashParams.set('pg_code', b64UrlEncode(gzip(model.value.code, {level: 9}))); // Compress and encode the code
|
||||||
|
const shareUrl = `${baseUrl.origin}${baseUrl.pathname}?${searchParams}#${hashParams}`; // Prefer hash to GET
|
||||||
output(`Share link ready: ${shareUrl}\n`)
|
output(`Share link ready: ${shareUrl}\n`)
|
||||||
if (!navigator.clipboard) {
|
if (navigator.clipboard?.writeText === undefined) {
|
||||||
output("Clipboard API not available. Please copy the link manually.\n");
|
output("Clipboard API not available. Please copy the link manually.\n");
|
||||||
return;
|
return;
|
||||||
} else {
|
} else {
|
||||||
@@ -172,27 +186,28 @@ function loadSnapshot() {
|
|||||||
throw new Error("Not implemented yet!"); // TODO: Implement snapshot loading
|
throw new Error("Not implemented yet!"); // TODO: Implement snapshot loading
|
||||||
}
|
}
|
||||||
|
|
||||||
const reused = (import.meta as any).hot?.data?.pyodideWorker !== undefined;
|
|
||||||
(async () => {
|
(async () => {
|
||||||
const sett = await settings()
|
const sett = await settings
|
||||||
if (!reused) opacity.value = sett.pg_opacity_loading
|
if (model.value.firstTime) opacity.value = sett.pg_opacity_loading
|
||||||
await setupPyodide()
|
await setupPyodide(true);
|
||||||
if (props.initialCode != "" && !reused) await runCode();
|
if (model.value.firstTime) {
|
||||||
if (!reused) opacity.value = sett.pg_opacity_loaded
|
await runCode();
|
||||||
|
opacity.value = sett.pg_opacity_loaded
|
||||||
|
model.value.firstTime = false
|
||||||
|
}
|
||||||
})()
|
})()
|
||||||
|
|
||||||
// Add keyboard shortcuts
|
// Add keyboard shortcuts
|
||||||
const editorRef = ref<HTMLElement | null>(null);
|
const editorRef = ref<HTMLElement | null>(null);
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
if (editorRef.value) {
|
if (editorRef.value) {
|
||||||
console.log(editorRef.value)
|
|
||||||
editorRef.value.addEventListener('keydown', (event: Event) => {
|
editorRef.value.addEventListener('keydown', (event: Event) => {
|
||||||
if (!(event instanceof KeyboardEvent)) return; // Ensure event is a KeyboardEvent
|
if (!(event instanceof KeyboardEvent)) return; // Ensure event is a KeyboardEvent
|
||||||
if (event.key === 'Enter' && event.ctrlKey) {
|
if (event.key === 'F10') { // Run code on F10
|
||||||
event.preventDefault(); // Prevent default behavior of Enter key
|
event.preventDefault(); // Prevent default behavior of the key
|
||||||
runCode(); // Run code on Ctrl+Enter
|
runCode();
|
||||||
} else if (event.key === 'Escape') {
|
} else if (event.key === 'Escape') { // Close on Escape key
|
||||||
emit('close'); // Close on Escape key
|
emit('close');
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -256,11 +271,17 @@ onMounted(() => {
|
|||||||
<!-- Only show content if opacity is greater than 0 -->
|
<!-- Only show content if opacity is greater than 0 -->
|
||||||
<div class="playground-container">
|
<div class="playground-container">
|
||||||
<div class="playground-editor" ref="editorRef">
|
<div class="playground-editor" ref="editorRef">
|
||||||
<VueMonacoEditor v-model:value="code" :theme="editorTheme" :options="MONACO_EDITOR_OPTIONS"
|
<VueMonacoEditor v-model:value="model.code" :theme="editorTheme" :options="MONACO_EDITOR_OPTIONS"
|
||||||
language="python" @mount="handleMount"/>
|
language="python" @mount="handleMount"/>
|
||||||
</div>
|
</div>
|
||||||
<div class="playground-console">
|
<div class="playground-console">
|
||||||
<h3>Console Output</h3>
|
<h3 style="display:flex; align-items: center; justify-content: space-between; margin: 0;">
|
||||||
|
Console Output
|
||||||
|
<v-spacer></v-spacer>
|
||||||
|
<v-btn @click="outputText = ''">
|
||||||
|
<svg-icon :path="mdiBroom" type="mdi" class="h-"/>
|
||||||
|
</v-btn>
|
||||||
|
</h3>
|
||||||
<pre>{{ outputText }}</pre> <!-- Placeholder for console output -->
|
<pre>{{ outputText }}</pre> <!-- Placeholder for console output -->
|
||||||
<Loading v-if="running"/>
|
<Loading v-if="running"/>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -8,43 +8,17 @@ await micropip.install("lib3mf")
|
|||||||
micropip.add_mock_package("py-lib3mf", "2.4.1", modules={"py_lib3mf": 'from lib3mf import *'})
|
micropip.add_mock_package("py-lib3mf", "2.4.1", modules={"py_lib3mf": 'from lib3mf import *'})
|
||||||
|
|
||||||
# Install the yacv_server package, which is the main server for the OCP.wasm playground; and also preinstalls build123d.
|
# Install the yacv_server package, which is the main server for the OCP.wasm playground; and also preinstalls build123d.
|
||||||
await micropip.install("yacv_server")
|
await micropip.install("yacv_server", pre=True)
|
||||||
|
|
||||||
# Preimport the yacv_server package to ensure it is available in the global scope, and mock the ocp_vscode package.
|
# Preimport the yacv_server package to ensure it is available in the global scope, and mock the ocp_vscode package.
|
||||||
from yacv_server import *
|
from yacv_server import *
|
||||||
|
|
||||||
micropip.add_mock_package("ocp-vscode", "2.8.9", modules={"ocp_vscode": 'from yacv_server import *'})
|
micropip.add_mock_package("ocp-vscode", "2.8.9", modules={"ocp_vscode": 'from yacv_server import *'})
|
||||||
show_object = show
|
show_object = show
|
||||||
|
|
||||||
# Preinstall a font to avoid issues with no font being available.
|
# Preinstall the font-fetcher package and install its hook to automatically download any requested font.
|
||||||
def install_font_to_ocp(font_url, font_name=None):
|
await micropip.install("font-fetcher", pre=True)
|
||||||
# noinspection PyUnresolvedReferences
|
|
||||||
from pyodide.http import pyfetch
|
|
||||||
from OCP.Font import Font_FontMgr, Font_SystemFont, Font_FA_Regular
|
|
||||||
from OCP.TCollection import TCollection_AsciiString
|
|
||||||
import os, asyncio
|
|
||||||
|
|
||||||
font_name = font_name if font_name is not None else font_url.split("/")[-1]
|
from font_fetcher.ocp import install_ocp_font_hook
|
||||||
|
|
||||||
# Choose a "system-like" font directory
|
install_ocp_font_hook()
|
||||||
font_path = os.path.join("/tmp", font_name)
|
|
||||||
os.makedirs(os.path.dirname(font_path), exist_ok=True)
|
|
||||||
|
|
||||||
# Download the font using pyfetch
|
|
||||||
loop = asyncio.get_event_loop()
|
|
||||||
response = loop.run_until_complete(pyfetch(font_url))
|
|
||||||
font_data = loop.run_until_complete(response.bytes())
|
|
||||||
|
|
||||||
# Save it to the system-like folder
|
|
||||||
with open(font_path, "wb") as f:
|
|
||||||
f.write(font_data)
|
|
||||||
|
|
||||||
mgr = Font_FontMgr.GetInstance_s()
|
|
||||||
font_t = Font_SystemFont(TCollection_AsciiString(font_path))
|
|
||||||
font_t.SetFontPath(Font_FA_Regular, TCollection_AsciiString(font_path))
|
|
||||||
assert mgr.RegisterFont(font_t, False)
|
|
||||||
#print(f"✅ Font installed at: {font_path}")
|
|
||||||
return font_path
|
|
||||||
|
|
||||||
|
|
||||||
# Make sure there is at least one font installed, so that the tests can run
|
|
||||||
install_font_to_ocp("https://raw.githubusercontent.com/xbmc/xbmc/d3a7f95f3f017b8e861d5d95cc4b33eef4286ce2/media/Fonts/arial.ttf")
|
|
||||||
|
|||||||
@@ -28,7 +28,7 @@ import SvgIcon from '@jamescoyle/vue-icon';
|
|||||||
import type {ModelViewerElement} from '@google/model-viewer';
|
import type {ModelViewerElement} from '@google/model-viewer';
|
||||||
import Loading from "../misc/Loading.vue";
|
import Loading from "../misc/Loading.vue";
|
||||||
import type ModelViewerWrapper from "../viewer/ModelViewerWrapper.vue";
|
import type ModelViewerWrapper from "../viewer/ModelViewerWrapper.vue";
|
||||||
import {defineAsyncComponent, ref, type Ref} from "vue";
|
import {defineAsyncComponent, ref} from "vue";
|
||||||
import type {SelectionInfo} from "./selection";
|
import type {SelectionInfo} from "./selection";
|
||||||
import {settings} from "../misc/settings.ts";
|
import {settings} from "../misc/settings.ts";
|
||||||
import type {NetworkUpdateEvent} from "../misc/network.ts";
|
import type {NetworkUpdateEvent} from "../misc/network.ts";
|
||||||
@@ -59,12 +59,14 @@ const emit = defineEmits<{ findModel: [string], updateModel: [NetworkUpdateEvent
|
|||||||
|
|
||||||
const sett = ref<any | null>(null);
|
const sett = ref<any | null>(null);
|
||||||
const showPlaygroundDialog = ref(false);
|
const showPlaygroundDialog = ref(false);
|
||||||
|
const pg_model = ref({code: '# Loading...', firstTime: false});
|
||||||
(async () => {
|
(async () => {
|
||||||
sett.value = await settings();
|
sett.value = await settings;
|
||||||
showPlaygroundDialog.value = sett.value.pg_code != "";
|
pg_model.value = {code: sett.value.pg_code, firstTime: true};
|
||||||
|
showPlaygroundDialog.value = pg_model.value.code != "";
|
||||||
})();
|
})();
|
||||||
|
|
||||||
let selection: Ref<Array<SelectionInfo>> = ref([]);
|
let selection = ref<Array<SelectionInfo>>([]);
|
||||||
let selectionFaceCount = () => selection.value.filter((s) => s.kind == 'face').length
|
let selectionFaceCount = () => selection.value.filter((s) => s.kind == 'face').length
|
||||||
let selectionEdgeCount = () => selection.value.filter((s) => s.kind == 'edge').length
|
let selectionEdgeCount = () => selection.value.filter((s) => s.kind == 'edge').length
|
||||||
let selectionVertexCount = () => selection.value.filter((s) => s.kind == "vertex").length
|
let selectionVertexCount = () => selection.value.filter((s) => s.kind == "vertex").length
|
||||||
@@ -126,6 +128,7 @@ async function downloadSceneGlb() {
|
|||||||
link.download = file.name;
|
link.download = file.name;
|
||||||
link.href = URL.createObjectURL(file);
|
link.href = URL.createObjectURL(file);
|
||||||
link.click();
|
link.click();
|
||||||
|
URL.revokeObjectURL(link.href);
|
||||||
}
|
}
|
||||||
|
|
||||||
async function openGithub() {
|
async function openGithub() {
|
||||||
@@ -193,7 +196,7 @@ document.addEventListener('keydown', (event) => {
|
|||||||
</template>
|
</template>
|
||||||
<template v-slot:default="{ isActive }">
|
<template v-slot:default="{ isActive }">
|
||||||
<if-not-small-build>
|
<if-not-small-build>
|
||||||
<playground-dialog-content v-if="sett != null" :initial-code="sett.pg_code" @close="isActive.value = false"
|
<playground-dialog-content v-if="sett != null" v-model="pg_model" @close="isActive.value = false"
|
||||||
@update-model="(event: NetworkUpdateEvent) => emit('updateModel', event)"/>
|
@update-model="(event: NetworkUpdateEvent) => emit('updateModel', event)"/>
|
||||||
</if-not-small-build>
|
</if-not-small-build>
|
||||||
</template>
|
</template>
|
||||||
|
|||||||
21
frontend/tools/b64.ts
Normal file
21
frontend/tools/b64.ts
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
export function b64UrlEncode(data: Uint8Array): string {
|
||||||
|
const base64 = btoa(String.fromCharCode(...data));
|
||||||
|
return base64.replace(/\+/g, '-').replace(/\//g, '_').replace(/=+$/, '');
|
||||||
|
}
|
||||||
|
|
||||||
|
export function b64UrlDecode(encoded: string): Uint8Array {
|
||||||
|
// Replace URL-safe characters with standard base64 characters
|
||||||
|
let base64 = encoded.replace(/-/g, '+').replace(/_/g, '/');
|
||||||
|
// Add padding if necessary
|
||||||
|
const padding = base64.length % 4;
|
||||||
|
if (padding) {
|
||||||
|
base64 += '='.repeat(4 - padding);
|
||||||
|
}
|
||||||
|
// Decode the base64 string to a byte array
|
||||||
|
const binaryString = atob(base64);
|
||||||
|
const byteArray = new Uint8Array(binaryString.length);
|
||||||
|
for (let i = 0; i < binaryString.length; i++) {
|
||||||
|
byteArray[i] = binaryString.charCodeAt(i);
|
||||||
|
}
|
||||||
|
return byteArray;
|
||||||
|
}
|
||||||
@@ -1,54 +0,0 @@
|
|||||||
// B66 encoding and decoding functions for compact url query parameter values. https://gist.github.com/danneu/6755394
|
|
||||||
const alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789.-_~";
|
|
||||||
|
|
||||||
export function b66Encode(data: Uint8Array): string {
|
|
||||||
let result = "";
|
|
||||||
let bits = 0;
|
|
||||||
let value = 0;
|
|
||||||
|
|
||||||
for (let byte of data) {
|
|
||||||
value = (value << 8) | byte;
|
|
||||||
bits += 8;
|
|
||||||
|
|
||||||
while (bits >= 6) {
|
|
||||||
bits -= 6;
|
|
||||||
result += alphabet[(value >> bits) & 0x3F];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (bits > 0) {
|
|
||||||
result += alphabet[(value << (6 - bits)) & 0x3F];
|
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
export function b66Decode(encoded: string): Uint8Array {
|
|
||||||
let result = [];
|
|
||||||
let bits = 0;
|
|
||||||
let value = 0;
|
|
||||||
|
|
||||||
for (let char of encoded) {
|
|
||||||
const index = alphabet.indexOf(char);
|
|
||||||
if (index === -1) {
|
|
||||||
throw new Error(`Invalid character '${char}' in B66 encoded string.`);
|
|
||||||
}
|
|
||||||
|
|
||||||
value = (value << 6) | index;
|
|
||||||
bits += 6;
|
|
||||||
|
|
||||||
while (bits >= 8) {
|
|
||||||
bits -= 8;
|
|
||||||
result.push((value >> bits) & 0xFF);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (bits > 0) {
|
|
||||||
// If there are leftover bits, they should not be present in a valid B66 encoding.
|
|
||||||
if (value << (8 - bits)) {
|
|
||||||
throw new Error("Invalid B66 encoding: leftover bits.");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return new Uint8Array(result);
|
|
||||||
}
|
|
||||||
@@ -38,6 +38,7 @@ export function newPyodideWorker(initOpts: Parameters<typeof loadPyodide>[0]) {
|
|||||||
mkdirTree: (path: string) => commonRequestResponse({type: "mkdirTree", id: requestId++, path}),
|
mkdirTree: (path: string) => commonRequestResponse({type: "mkdirTree", id: requestId++, path}),
|
||||||
writeFile: (path: string, content: string) =>
|
writeFile: (path: string, content: string) =>
|
||||||
commonRequestResponse({type: "writeFile", id: requestId++, path, content}),
|
commonRequestResponse({type: "writeFile", id: requestId++, path, content}),
|
||||||
|
makeSnapshot: () => commonRequestResponse({type: "makeSnapshot", id: requestId++}),
|
||||||
terminate: () => worker.terminate()
|
terminate: () => worker.terminate()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -25,6 +25,9 @@ export type MessageEventDataIn = {
|
|||||||
id: number;
|
id: number;
|
||||||
path: string;
|
path: string;
|
||||||
content: string;
|
content: string;
|
||||||
|
} | {
|
||||||
|
type: 'makeSnapshot';
|
||||||
|
id: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
self.onmessage = async (event: MessageEvent<MessageEventDataIn>) => {
|
self.onmessage = async (event: MessageEvent<MessageEventDataIn>) => {
|
||||||
@@ -64,6 +67,15 @@ self.onmessage = async (event: MessageEvent<MessageEventDataIn>) => {
|
|||||||
} catch (error: any) {
|
} catch (error: any) {
|
||||||
self.postMessage({id: event.data.id, error: error.message});
|
self.postMessage({id: event.data.id, error: error.message});
|
||||||
}
|
}
|
||||||
|
} else if (event.data.type === 'makeSnapshot') {
|
||||||
|
// Take a snapshot of the current Pyodide filesystem.
|
||||||
|
const pyodide = await pyodideReadyPromise;
|
||||||
|
try {
|
||||||
|
const snapshot = pyodide.makeMemorySnapshot();
|
||||||
|
self.postMessage({id: event.data.id, result: snapshot});
|
||||||
|
} catch (error: any) {
|
||||||
|
self.postMessage({id: event.data.id, error: error.message});
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
console.error("Unknown message type:", (event.data as any)?.type);
|
console.error("Unknown message type:", (event.data as any)?.type);
|
||||||
self.postMessage({id: (event.data as any)?.id, error: "Unknown message type: " + (event.data as any)?.type});
|
self.postMessage({id: (event.data as any)?.id, error: "Unknown message type: " + (event.data as any)?.type});
|
||||||
|
|||||||
@@ -29,7 +29,7 @@ const renderer = ref<Renderer | null>(null);
|
|||||||
const controls = ref<SmoothControls | null>(null);
|
const controls = ref<SmoothControls | null>(null);
|
||||||
|
|
||||||
const sett = ref<any | null>(null);
|
const sett = ref<any | null>(null);
|
||||||
(async () => sett.value = await settings())();
|
(async () => sett.value = await settings)();
|
||||||
|
|
||||||
let lastCameraTargetPosition: Vector3 | undefined = undefined;
|
let lastCameraTargetPosition: Vector3 | undefined = undefined;
|
||||||
let lastCameraZoom: number | undefined = undefined;
|
let lastCameraZoom: number | undefined = undefined;
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import {settings} from "../misc/settings.ts";
|
|||||||
export let currentSceneRotation = 0; // radians, 0 is the default rotation
|
export let currentSceneRotation = 0; // radians, 0 is the default rotation
|
||||||
|
|
||||||
export async function setupLighting(modelViewer: ModelViewerElement) {
|
export async function setupLighting(modelViewer: ModelViewerElement) {
|
||||||
modelViewer[$scene].environmentIntensity = (await settings()).environmentIntensity;
|
modelViewer[$scene].environmentIntensity = (await settings).environmentIntensity;
|
||||||
// Code is mostly copied from the example at: https://modelviewer.dev/examples/stagingandcameras/#turnSkybox
|
// Code is mostly copied from the example at: https://modelviewer.dev/examples/stagingandcameras/#turnSkybox
|
||||||
let lastX: number;
|
let lastX: number;
|
||||||
let panning = false;
|
let panning = false;
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "yet-another-cad-viewer",
|
"name": "yet-another-cad-viewer",
|
||||||
"version": "0.10.0-rc.2",
|
"version": "0.10.2-alpha.1",
|
||||||
"description": "",
|
"description": "",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"private": true,
|
"private": true,
|
||||||
|
|||||||
231
poetry.lock
generated
231
poetry.lock
generated
@@ -104,78 +104,93 @@ markers = {main = "sys_platform == \"win32\""}
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "contourpy"
|
name = "contourpy"
|
||||||
version = "1.3.2"
|
version = "1.3.3"
|
||||||
description = "Python library for calculating contours of 2D quadrilateral grids"
|
description = "Python library for calculating contours of 2D quadrilateral grids"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.10"
|
python-versions = ">=3.11"
|
||||||
groups = ["main"]
|
groups = ["main"]
|
||||||
files = [
|
files = [
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:ba38e3f9f330af820c4b27ceb4b9c7feee5fe0493ea53a8720f4792667465934"},
|
{file = "contourpy-1.3.3-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:709a48ef9a690e1343202916450bc48b9e51c049b089c7f79a267b46cffcdaa1"},
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:dc41ba0714aa2968d1f8674ec97504a8f7e334f48eeacebcaa6256213acb0989"},
|
{file = "contourpy-1.3.3-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:23416f38bfd74d5d28ab8429cc4d63fa67d5068bd711a85edb1c3fb0c3e2f381"},
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9be002b31c558d1ddf1b9b415b162c603405414bacd6932d031c5b5a8b757f0d"},
|
{file = "contourpy-1.3.3-cp311-cp311-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:929ddf8c4c7f348e4c0a5a3a714b5c8542ffaa8c22954862a46ca1813b667ee7"},
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8d2e74acbcba3bfdb6d9d8384cdc4f9260cae86ed9beee8bd5f54fee49a430b9"},
|
{file = "contourpy-1.3.3-cp311-cp311-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:9e999574eddae35f1312c2b4b717b7885d4edd6cb46700e04f7f02db454e67c1"},
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e259bced5549ac64410162adc973c5e2fb77f04df4a439d00b478e57a0e65512"},
|
{file = "contourpy-1.3.3-cp311-cp311-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:0bf67e0e3f482cb69779dd3061b534eb35ac9b17f163d851e2a547d56dba0a3a"},
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ad687a04bc802cbe8b9c399c07162a3c35e227e2daccf1668eb1f278cb698631"},
|
{file = "contourpy-1.3.3-cp311-cp311-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:51e79c1f7470158e838808d4a996fa9bac72c498e93d8ebe5119bc1e6becb0db"},
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-musllinux_1_2_aarch64.whl", hash = "sha256:cdd22595308f53ef2f891040ab2b93d79192513ffccbd7fe19be7aa773a5e09f"},
|
{file = "contourpy-1.3.3-cp311-cp311-musllinux_1_2_aarch64.whl", hash = "sha256:598c3aaece21c503615fd59c92a3598b428b2f01bfb4b8ca9c4edeecc2438620"},
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-musllinux_1_2_x86_64.whl", hash = "sha256:b4f54d6a2defe9f257327b0f243612dd051cc43825587520b1bf74a31e2f6ef2"},
|
{file = "contourpy-1.3.3-cp311-cp311-musllinux_1_2_x86_64.whl", hash = "sha256:322ab1c99b008dad206d406bb61d014cf0174df491ae9d9d0fac6a6fda4f977f"},
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-win32.whl", hash = "sha256:f939a054192ddc596e031e50bb13b657ce318cf13d264f095ce9db7dc6ae81c0"},
|
{file = "contourpy-1.3.3-cp311-cp311-win32.whl", hash = "sha256:fd907ae12cd483cd83e414b12941c632a969171bf90fc937d0c9f268a31cafff"},
|
||||||
{file = "contourpy-1.3.2-cp310-cp310-win_amd64.whl", hash = "sha256:c440093bbc8fc21c637c03bafcbef95ccd963bc6e0514ad887932c18ca2a759a"},
|
{file = "contourpy-1.3.3-cp311-cp311-win_amd64.whl", hash = "sha256:3519428f6be58431c56581f1694ba8e50626f2dd550af225f82fb5f5814d2a42"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:6a37a2fb93d4df3fc4c0e363ea4d16f83195fc09c891bc8ce072b9d084853445"},
|
{file = "contourpy-1.3.3-cp311-cp311-win_arm64.whl", hash = "sha256:15ff10bfada4bf92ec8b31c62bf7c1834c244019b4a33095a68000d7075df470"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:b7cd50c38f500bbcc9b6a46643a40e0913673f869315d8e70de0438817cb7773"},
|
{file = "contourpy-1.3.3-cp312-cp312-macosx_10_13_x86_64.whl", hash = "sha256:b08a32ea2f8e42cf1d4be3169a98dd4be32bafe4f22b6c4cb4ba810fa9e5d2cb"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d6658ccc7251a4433eebd89ed2672c2ed96fba367fd25ca9512aa92a4b46c4f1"},
|
{file = "contourpy-1.3.3-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:556dba8fb6f5d8742f2923fe9457dbdd51e1049c4a43fd3986a0b14a1d815fc6"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:70771a461aaeb335df14deb6c97439973d253ae70660ca085eec25241137ef43"},
|
{file = "contourpy-1.3.3-cp312-cp312-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:92d9abc807cf7d0e047b95ca5d957cf4792fcd04e920ca70d48add15c1a90ea7"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:65a887a6e8c4cd0897507d814b14c54a8c2e2aa4ac9f7686292f9769fcf9a6ab"},
|
{file = "contourpy-1.3.3-cp312-cp312-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:b2e8faa0ed68cb29af51edd8e24798bb661eac3bd9f65420c1887b6ca89987c8"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3859783aefa2b8355697f16642695a5b9792e7a46ab86da1118a4a23a51a33d7"},
|
{file = "contourpy-1.3.3-cp312-cp312-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:626d60935cf668e70a5ce6ff184fd713e9683fb458898e4249b63be9e28286ea"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-musllinux_1_2_aarch64.whl", hash = "sha256:eab0f6db315fa4d70f1d8ab514e527f0366ec021ff853d7ed6a2d33605cf4b83"},
|
{file = "contourpy-1.3.3-cp312-cp312-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:4d00e655fcef08aba35ec9610536bfe90267d7ab5ba944f7032549c55a146da1"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-musllinux_1_2_x86_64.whl", hash = "sha256:d91a3ccc7fea94ca0acab82ceb77f396d50a1f67412efe4c526f5d20264e6ecd"},
|
{file = "contourpy-1.3.3-cp312-cp312-musllinux_1_2_aarch64.whl", hash = "sha256:451e71b5a7d597379ef572de31eeb909a87246974d960049a9848c3bc6c41bf7"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-win32.whl", hash = "sha256:1c48188778d4d2f3d48e4643fb15d8608b1d01e4b4d6b0548d9b336c28fc9b6f"},
|
{file = "contourpy-1.3.3-cp312-cp312-musllinux_1_2_x86_64.whl", hash = "sha256:459c1f020cd59fcfe6650180678a9993932d80d44ccde1fa1868977438f0b411"},
|
||||||
{file = "contourpy-1.3.2-cp311-cp311-win_amd64.whl", hash = "sha256:5ebac872ba09cb8f2131c46b8739a7ff71de28a24c869bcad554477eb089a878"},
|
{file = "contourpy-1.3.3-cp312-cp312-win32.whl", hash = "sha256:023b44101dfe49d7d53932be418477dba359649246075c996866106da069af69"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-macosx_10_13_x86_64.whl", hash = "sha256:4caf2bcd2969402bf77edc4cb6034c7dd7c0803213b3523f111eb7460a51b8d2"},
|
{file = "contourpy-1.3.3-cp312-cp312-win_amd64.whl", hash = "sha256:8153b8bfc11e1e4d75bcb0bff1db232f9e10b274e0929de9d608027e0d34ff8b"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:82199cb78276249796419fe36b7386bd8d2cc3f28b3bc19fe2454fe2e26c4c15"},
|
{file = "contourpy-1.3.3-cp312-cp312-win_arm64.whl", hash = "sha256:07ce5ed73ecdc4a03ffe3e1b3e3c1166db35ae7584be76f65dbbe28a7791b0cc"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:106fab697af11456fcba3e352ad50effe493a90f893fca6c2ca5c033820cea92"},
|
{file = "contourpy-1.3.3-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:177fb367556747a686509d6fef71d221a4b198a3905fe824430e5ea0fda54eb5"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d14f12932a8d620e307f715857107b1d1845cc44fdb5da2bc8e850f5ceba9f87"},
|
{file = "contourpy-1.3.3-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:d002b6f00d73d69333dac9d0b8d5e84d9724ff9ef044fd63c5986e62b7c9e1b1"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:532fd26e715560721bb0d5fc7610fce279b3699b018600ab999d1be895b09415"},
|
{file = "contourpy-1.3.3-cp313-cp313-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:348ac1f5d4f1d66d3322420f01d42e43122f43616e0f194fc1c9f5d830c5b286"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f26b383144cf2d2c29f01a1e8170f50dacf0eac02d64139dcd709a8ac4eb3cfe"},
|
{file = "contourpy-1.3.3-cp313-cp313-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:655456777ff65c2c548b7c454af9c6f33f16c8884f11083244b5819cc214f1b5"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-musllinux_1_2_aarch64.whl", hash = "sha256:c49f73e61f1f774650a55d221803b101d966ca0c5a2d6d5e4320ec3997489441"},
|
{file = "contourpy-1.3.3-cp313-cp313-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:644a6853d15b2512d67881586bd03f462c7ab755db95f16f14d7e238f2852c67"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-musllinux_1_2_x86_64.whl", hash = "sha256:3d80b2c0300583228ac98d0a927a1ba6a2ba6b8a742463c564f1d419ee5b211e"},
|
{file = "contourpy-1.3.3-cp313-cp313-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:4debd64f124ca62069f313a9cb86656ff087786016d76927ae2cf37846b006c9"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-win32.whl", hash = "sha256:90df94c89a91b7362e1142cbee7568f86514412ab8a2c0d0fca72d7e91b62912"},
|
{file = "contourpy-1.3.3-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:a15459b0f4615b00bbd1e91f1b9e19b7e63aea7483d03d804186f278c0af2659"},
|
||||||
{file = "contourpy-1.3.2-cp312-cp312-win_amd64.whl", hash = "sha256:8c942a01d9163e2e5cfb05cb66110121b8d07ad438a17f9e766317bcb62abf73"},
|
{file = "contourpy-1.3.3-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:ca0fdcd73925568ca027e0b17ab07aad764be4706d0a925b89227e447d9737b7"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:de39db2604ae755316cb5967728f4bea92685884b1e767b7c24e983ef5f771cb"},
|
{file = "contourpy-1.3.3-cp313-cp313-win32.whl", hash = "sha256:b20c7c9a3bf701366556e1b1984ed2d0cedf999903c51311417cf5f591d8c78d"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:3f9e896f447c5c8618f1edb2bafa9a4030f22a575ec418ad70611450720b5b08"},
|
{file = "contourpy-1.3.3-cp313-cp313-win_amd64.whl", hash = "sha256:1cadd8b8969f060ba45ed7c1b714fe69185812ab43bd6b86a9123fe8f99c3263"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:71e2bd4a1c4188f5c2b8d274da78faab884b59df20df63c34f74aa1813c4427c"},
|
{file = "contourpy-1.3.3-cp313-cp313-win_arm64.whl", hash = "sha256:fd914713266421b7536de2bfa8181aa8c699432b6763a0ea64195ebe28bff6a9"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:de425af81b6cea33101ae95ece1f696af39446db9682a0b56daaa48cfc29f38f"},
|
{file = "contourpy-1.3.3-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:88df9880d507169449d434c293467418b9f6cbe82edd19284aa0409e7fdb933d"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:977e98a0e0480d3fe292246417239d2d45435904afd6d7332d8455981c408b85"},
|
{file = "contourpy-1.3.3-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:d06bb1f751ba5d417047db62bca3c8fde202b8c11fb50742ab3ab962c81e8216"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:434f0adf84911c924519d2b08fc10491dd282b20bdd3fa8f60fd816ea0b48841"},
|
{file = "contourpy-1.3.3-cp313-cp313t-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:e4e6b05a45525357e382909a4c1600444e2a45b4795163d3b22669285591c1ae"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:c66c4906cdbc50e9cba65978823e6e00b45682eb09adbb78c9775b74eb222422"},
|
{file = "contourpy-1.3.3-cp313-cp313t-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:ab3074b48c4e2cf1a960e6bbeb7f04566bf36b1861d5c9d4d8ac04b82e38ba20"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:8b7fc0cd78ba2f4695fd0a6ad81a19e7e3ab825c31b577f384aa9d7817dc3bef"},
|
{file = "contourpy-1.3.3-cp313-cp313t-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:6c3d53c796f8647d6deb1abe867daeb66dcc8a97e8455efa729516b997b8ed99"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-win32.whl", hash = "sha256:15ce6ab60957ca74cff444fe66d9045c1fd3e92c8936894ebd1f3eef2fff075f"},
|
{file = "contourpy-1.3.3-cp313-cp313t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:50ed930df7289ff2a8d7afeb9603f8289e5704755c7e5c3bbd929c90c817164b"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313-win_amd64.whl", hash = "sha256:e1578f7eafce927b168752ed7e22646dad6cd9bca673c60bff55889fa236ebf9"},
|
{file = "contourpy-1.3.3-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:4feffb6537d64b84877da813a5c30f1422ea5739566abf0bd18065ac040e120a"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-macosx_10_13_x86_64.whl", hash = "sha256:0475b1f6604896bc7c53bb070e355e9321e1bc0d381735421a2d2068ec56531f"},
|
{file = "contourpy-1.3.3-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:2b7e9480ffe2b0cd2e787e4df64270e3a0440d9db8dc823312e2c940c167df7e"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-macosx_11_0_arm64.whl", hash = "sha256:c85bb486e9be652314bb5b9e2e3b0d1b2e643d5eec4992c0fbe8ac71775da739"},
|
{file = "contourpy-1.3.3-cp313-cp313t-win32.whl", hash = "sha256:283edd842a01e3dcd435b1c5116798d661378d83d36d337b8dde1d16a5fc9ba3"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:745b57db7758f3ffc05a10254edd3182a2a83402a89c00957a8e8a22f5582823"},
|
{file = "contourpy-1.3.3-cp313-cp313t-win_amd64.whl", hash = "sha256:87acf5963fc2b34825e5b6b048f40e3635dd547f590b04d2ab317c2619ef7ae8"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:970e9173dbd7eba9b4e01aab19215a48ee5dd3f43cef736eebde064a171f89a5"},
|
{file = "contourpy-1.3.3-cp313-cp313t-win_arm64.whl", hash = "sha256:3c30273eb2a55024ff31ba7d052dde990d7d8e5450f4bbb6e913558b3d6c2301"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:c6c4639a9c22230276b7bffb6a850dfc8258a2521305e1faefe804d006b2e532"},
|
{file = "contourpy-1.3.3-cp314-cp314-macosx_10_13_x86_64.whl", hash = "sha256:fde6c716d51c04b1c25d0b90364d0be954624a0ee9d60e23e850e8d48353d07a"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:cc829960f34ba36aad4302e78eabf3ef16a3a100863f0d4eeddf30e8a485a03b"},
|
{file = "contourpy-1.3.3-cp314-cp314-macosx_11_0_arm64.whl", hash = "sha256:cbedb772ed74ff5be440fa8eee9bd49f64f6e3fc09436d9c7d8f1c287b121d77"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:d32530b534e986374fc19eaa77fcb87e8a99e5431499949b828312bdcd20ac52"},
|
{file = "contourpy-1.3.3-cp314-cp314-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:22e9b1bd7a9b1d652cd77388465dc358dafcd2e217d35552424aa4f996f524f5"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:e298e7e70cf4eb179cc1077be1c725b5fd131ebc81181bf0c03525c8abc297fd"},
|
{file = "contourpy-1.3.3-cp314-cp314-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:a22738912262aa3e254e4f3cb079a95a67132fc5a063890e224393596902f5a4"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-win32.whl", hash = "sha256:d0e589ae0d55204991450bb5c23f571c64fe43adaa53f93fc902a84c96f52fe1"},
|
{file = "contourpy-1.3.3-cp314-cp314-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:afe5a512f31ee6bd7d0dda52ec9864c984ca3d66664444f2d72e0dc4eb832e36"},
|
||||||
{file = "contourpy-1.3.2-cp313-cp313t-win_amd64.whl", hash = "sha256:78e9253c3de756b3f6a5174d024c4835acd59eb3f8e2ca13e775dbffe1558f69"},
|
{file = "contourpy-1.3.3-cp314-cp314-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:f64836de09927cba6f79dcd00fdd7d5329f3fccc633468507079c829ca4db4e3"},
|
||||||
{file = "contourpy-1.3.2-pp310-pypy310_pp73-macosx_10_15_x86_64.whl", hash = "sha256:fd93cc7f3139b6dd7aab2f26a90dde0aa9fc264dbf70f6740d498a70b860b82c"},
|
{file = "contourpy-1.3.3-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:1fd43c3be4c8e5fd6e4f2baeae35ae18176cf2e5cced681cca908addf1cdd53b"},
|
||||||
{file = "contourpy-1.3.2-pp310-pypy310_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:107ba8a6a7eec58bb475329e6d3b95deba9440667c4d62b9b6063942b61d7f16"},
|
{file = "contourpy-1.3.3-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:6afc576f7b33cf00996e5c1102dc2a8f7cc89e39c0b55df93a0b78c1bd992b36"},
|
||||||
{file = "contourpy-1.3.2-pp310-pypy310_pp73-win_amd64.whl", hash = "sha256:ded1706ed0c1049224531b81128efbd5084598f18d8a2d9efae833edbd2b40ad"},
|
{file = "contourpy-1.3.3-cp314-cp314-win32.whl", hash = "sha256:66c8a43a4f7b8df8b71ee1840e4211a3c8d93b214b213f590e18a1beca458f7d"},
|
||||||
{file = "contourpy-1.3.2-pp311-pypy311_pp73-macosx_10_15_x86_64.whl", hash = "sha256:5f5964cdad279256c084b69c3f412b7801e15356b16efa9d78aa974041903da0"},
|
{file = "contourpy-1.3.3-cp314-cp314-win_amd64.whl", hash = "sha256:cf9022ef053f2694e31d630feaacb21ea24224be1c3ad0520b13d844274614fd"},
|
||||||
{file = "contourpy-1.3.2-pp311-pypy311_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:49b65a95d642d4efa8f64ba12558fcb83407e58a2dfba9d796d77b63ccfcaff5"},
|
{file = "contourpy-1.3.3-cp314-cp314-win_arm64.whl", hash = "sha256:95b181891b4c71de4bb404c6621e7e2390745f887f2a026b2d99e92c17892339"},
|
||||||
{file = "contourpy-1.3.2-pp311-pypy311_pp73-win_amd64.whl", hash = "sha256:8c5acb8dddb0752bf252e01a3035b21443158910ac16a3b0d20e7fed7d534ce5"},
|
{file = "contourpy-1.3.3-cp314-cp314t-macosx_10_13_x86_64.whl", hash = "sha256:33c82d0138c0a062380332c861387650c82e4cf1747aaa6938b9b6516762e772"},
|
||||||
{file = "contourpy-1.3.2.tar.gz", hash = "sha256:b6945942715a034c671b7fc54f9588126b0b8bf23db2696e3ca8328f3ff0ab54"},
|
{file = "contourpy-1.3.3-cp314-cp314t-macosx_11_0_arm64.whl", hash = "sha256:ea37e7b45949df430fe649e5de8351c423430046a2af20b1c1961cae3afcda77"},
|
||||||
|
{file = "contourpy-1.3.3-cp314-cp314t-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:d304906ecc71672e9c89e87c4675dc5c2645e1f4269a5063b99b0bb29f232d13"},
|
||||||
|
{file = "contourpy-1.3.3-cp314-cp314t-manylinux_2_26_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:ca658cd1a680a5c9ea96dc61cdbae1e85c8f25849843aa799dfd3cb370ad4fbe"},
|
||||||
|
{file = "contourpy-1.3.3-cp314-cp314t-manylinux_2_26_s390x.manylinux_2_28_s390x.whl", hash = "sha256:ab2fd90904c503739a75b7c8c5c01160130ba67944a7b77bbf36ef8054576e7f"},
|
||||||
|
{file = "contourpy-1.3.3-cp314-cp314t-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:b7301b89040075c30e5768810bc96a8e8d78085b47d8be6e4c3f5a0b4ed478a0"},
|
||||||
|
{file = "contourpy-1.3.3-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:2a2a8b627d5cc6b7c41a4beff6c5ad5eb848c88255fda4a8745f7e901b32d8e4"},
|
||||||
|
{file = "contourpy-1.3.3-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:fd6ec6be509c787f1caf6b247f0b1ca598bef13f4ddeaa126b7658215529ba0f"},
|
||||||
|
{file = "contourpy-1.3.3-cp314-cp314t-win32.whl", hash = "sha256:e74a9a0f5e3fff48fb5a7f2fd2b9b70a3fe014a67522f79b7cca4c0c7e43c9ae"},
|
||||||
|
{file = "contourpy-1.3.3-cp314-cp314t-win_amd64.whl", hash = "sha256:13b68d6a62db8eafaebb8039218921399baf6e47bf85006fd8529f2a08ef33fc"},
|
||||||
|
{file = "contourpy-1.3.3-cp314-cp314t-win_arm64.whl", hash = "sha256:b7448cb5a725bb1e35ce88771b86fba35ef418952474492cf7c764059933ff8b"},
|
||||||
|
{file = "contourpy-1.3.3-pp311-pypy311_pp73-macosx_10_15_x86_64.whl", hash = "sha256:cd5dfcaeb10f7b7f9dc8941717c6c2ade08f587be2226222c12b25f0483ed497"},
|
||||||
|
{file = "contourpy-1.3.3-pp311-pypy311_pp73-macosx_11_0_arm64.whl", hash = "sha256:0c1fc238306b35f246d61a1d416a627348b5cf0648648a031e14bb8705fcdfe8"},
|
||||||
|
{file = "contourpy-1.3.3-pp311-pypy311_pp73-manylinux_2_26_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:70f9aad7de812d6541d29d2bbf8feb22ff7e1c299523db288004e3157ff4674e"},
|
||||||
|
{file = "contourpy-1.3.3-pp311-pypy311_pp73-manylinux_2_27_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:5ed3657edf08512fc3fe81b510e35c2012fbd3081d2e26160f27ca28affec989"},
|
||||||
|
{file = "contourpy-1.3.3-pp311-pypy311_pp73-win_amd64.whl", hash = "sha256:3d1a3799d62d45c18bafd41c5fa05120b96a28079f2393af559b843d1a966a77"},
|
||||||
|
{file = "contourpy-1.3.3.tar.gz", hash = "sha256:083e12155b210502d0bca491432bb04d56dc3432f95a979b429f2848c3dbe880"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
numpy = ">=1.23"
|
numpy = ">=1.25"
|
||||||
|
|
||||||
[package.extras]
|
[package.extras]
|
||||||
bokeh = ["bokeh", "selenium"]
|
bokeh = ["bokeh", "selenium"]
|
||||||
docs = ["furo", "sphinx (>=7.2)", "sphinx-copybutton"]
|
docs = ["furo", "sphinx (>=7.2)", "sphinx-copybutton"]
|
||||||
mypy = ["bokeh", "contourpy[bokeh,docs]", "docutils-stubs", "mypy (==1.15.0)", "types-Pillow"]
|
mypy = ["bokeh", "contourpy[bokeh,docs]", "docutils-stubs", "mypy (==1.17.0)", "types-Pillow"]
|
||||||
test = ["Pillow", "contourpy[test-no-images]", "matplotlib"]
|
test = ["Pillow", "contourpy[test-no-images]", "matplotlib"]
|
||||||
test-no-images = ["pytest", "pytest-cov", "pytest-rerunfailures", "pytest-xdist", "wurlitzer"]
|
test-no-images = ["pytest", "pytest-cov", "pytest-rerunfailures", "pytest-xdist", "wurlitzer"]
|
||||||
|
|
||||||
@@ -1082,49 +1097,67 @@ six = ">=1.5"
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "scipy"
|
name = "scipy"
|
||||||
version = "1.16.0"
|
version = "1.16.1"
|
||||||
description = "Fundamental algorithms for scientific computing in Python"
|
description = "Fundamental algorithms for scientific computing in Python"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.11"
|
python-versions = ">=3.11"
|
||||||
groups = ["main"]
|
groups = ["main"]
|
||||||
files = [
|
files = [
|
||||||
{file = "scipy-1.16.0-cp311-cp311-macosx_10_14_x86_64.whl", hash = "sha256:deec06d831b8f6b5fb0b652433be6a09db29e996368ce5911faf673e78d20085"},
|
{file = "scipy-1.16.1-cp311-cp311-macosx_10_14_x86_64.whl", hash = "sha256:c033fa32bab91dc98ca59d0cf23bb876454e2bb02cbe592d5023138778f70030"},
|
||||||
{file = "scipy-1.16.0-cp311-cp311-macosx_12_0_arm64.whl", hash = "sha256:d30c0fe579bb901c61ab4bb7f3eeb7281f0d4c4a7b52dbf563c89da4fd2949be"},
|
{file = "scipy-1.16.1-cp311-cp311-macosx_12_0_arm64.whl", hash = "sha256:6e5c2f74e5df33479b5cd4e97a9104c511518fbd979aa9b8f6aec18b2e9ecae7"},
|
||||||
{file = "scipy-1.16.0-cp311-cp311-macosx_14_0_arm64.whl", hash = "sha256:b2243561b45257f7391d0f49972fca90d46b79b8dbcb9b2cb0f9df928d370ad4"},
|
{file = "scipy-1.16.1-cp311-cp311-macosx_14_0_arm64.whl", hash = "sha256:0a55ffe0ba0f59666e90951971a884d1ff6f4ec3275a48f472cfb64175570f77"},
|
||||||
{file = "scipy-1.16.0-cp311-cp311-macosx_14_0_x86_64.whl", hash = "sha256:e6d7dfc148135e9712d87c5f7e4f2ddc1304d1582cb3a7d698bbadedb61c7afd"},
|
{file = "scipy-1.16.1-cp311-cp311-macosx_14_0_x86_64.whl", hash = "sha256:f8a5d6cd147acecc2603fbd382fed6c46f474cccfcf69ea32582e033fb54dcfe"},
|
||||||
{file = "scipy-1.16.0-cp311-cp311-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:90452f6a9f3fe5a2cf3748e7be14f9cc7d9b124dce19667b54f5b429d680d539"},
|
{file = "scipy-1.16.1-cp311-cp311-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:cb18899127278058bcc09e7b9966d41a5a43740b5bb8dcba401bd983f82e885b"},
|
||||||
{file = "scipy-1.16.0-cp311-cp311-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:a2f0bf2f58031c8701a8b601df41701d2a7be17c7ffac0a4816aeba89c4cdac8"},
|
{file = "scipy-1.16.1-cp311-cp311-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:adccd93a2fa937a27aae826d33e3bfa5edf9aa672376a4852d23a7cd67a2e5b7"},
|
||||||
{file = "scipy-1.16.0-cp311-cp311-musllinux_1_2_aarch64.whl", hash = "sha256:6c4abb4c11fc0b857474241b812ce69ffa6464b4bd8f4ecb786cf240367a36a7"},
|
{file = "scipy-1.16.1-cp311-cp311-musllinux_1_2_aarch64.whl", hash = "sha256:18aca1646a29ee9a0625a1be5637fa798d4d81fdf426481f06d69af828f16958"},
|
||||||
{file = "scipy-1.16.0-cp311-cp311-musllinux_1_2_x86_64.whl", hash = "sha256:b370f8f6ac6ef99815b0d5c9f02e7ade77b33007d74802efc8316c8db98fd11e"},
|
{file = "scipy-1.16.1-cp311-cp311-musllinux_1_2_x86_64.whl", hash = "sha256:d85495cef541729a70cdddbbf3e6b903421bc1af3e8e3a9a72a06751f33b7c39"},
|
||||||
{file = "scipy-1.16.0-cp311-cp311-win_amd64.whl", hash = "sha256:a16ba90847249bedce8aa404a83fb8334b825ec4a8e742ce6012a7a5e639f95c"},
|
{file = "scipy-1.16.1-cp311-cp311-win_amd64.whl", hash = "sha256:226652fca853008119c03a8ce71ffe1b3f6d2844cc1686e8f9806edafae68596"},
|
||||||
{file = "scipy-1.16.0-cp312-cp312-macosx_10_14_x86_64.whl", hash = "sha256:7eb6bd33cef4afb9fa5f1fb25df8feeb1e52d94f21a44f1d17805b41b1da3180"},
|
{file = "scipy-1.16.1-cp312-cp312-macosx_10_14_x86_64.whl", hash = "sha256:81b433bbeaf35728dad619afc002db9b189e45eebe2cd676effe1fb93fef2b9c"},
|
||||||
{file = "scipy-1.16.0-cp312-cp312-macosx_12_0_arm64.whl", hash = "sha256:1dbc8fdba23e4d80394ddfab7a56808e3e6489176d559c6c71935b11a2d59db1"},
|
{file = "scipy-1.16.1-cp312-cp312-macosx_12_0_arm64.whl", hash = "sha256:886cc81fdb4c6903a3bb0464047c25a6d1016fef77bb97949817d0c0d79f9e04"},
|
||||||
{file = "scipy-1.16.0-cp312-cp312-macosx_14_0_arm64.whl", hash = "sha256:7dcf42c380e1e3737b343dec21095c9a9ad3f9cbe06f9c05830b44b1786c9e90"},
|
{file = "scipy-1.16.1-cp312-cp312-macosx_14_0_arm64.whl", hash = "sha256:15240c3aac087a522b4eaedb09f0ad061753c5eebf1ea430859e5bf8640d5919"},
|
||||||
{file = "scipy-1.16.0-cp312-cp312-macosx_14_0_x86_64.whl", hash = "sha256:26ec28675f4a9d41587266084c626b02899db373717d9312fa96ab17ca1ae94d"},
|
{file = "scipy-1.16.1-cp312-cp312-macosx_14_0_x86_64.whl", hash = "sha256:65f81a25805f3659b48126b5053d9e823d3215e4a63730b5e1671852a1705921"},
|
||||||
{file = "scipy-1.16.0-cp312-cp312-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:952358b7e58bd3197cfbd2f2f2ba829f258404bdf5db59514b515a8fe7a36c52"},
|
{file = "scipy-1.16.1-cp312-cp312-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:6c62eea7f607f122069b9bad3f99489ddca1a5173bef8a0c75555d7488b6f725"},
|
||||||
{file = "scipy-1.16.0-cp312-cp312-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:03931b4e870c6fef5b5c0970d52c9f6ddd8c8d3e934a98f09308377eba6f3824"},
|
{file = "scipy-1.16.1-cp312-cp312-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:f965bbf3235b01c776115ab18f092a95aa74c271a52577bcb0563e85738fd618"},
|
||||||
{file = "scipy-1.16.0-cp312-cp312-musllinux_1_2_aarch64.whl", hash = "sha256:512c4f4f85912767c351a0306824ccca6fd91307a9f4318efe8fdbd9d30562ef"},
|
{file = "scipy-1.16.1-cp312-cp312-musllinux_1_2_aarch64.whl", hash = "sha256:f006e323874ffd0b0b816d8c6a8e7f9a73d55ab3b8c3f72b752b226d0e3ac83d"},
|
||||||
{file = "scipy-1.16.0-cp312-cp312-musllinux_1_2_x86_64.whl", hash = "sha256:e69f798847e9add03d512eaf5081a9a5c9a98757d12e52e6186ed9681247a1ac"},
|
{file = "scipy-1.16.1-cp312-cp312-musllinux_1_2_x86_64.whl", hash = "sha256:e8fd15fc5085ab4cca74cb91fe0a4263b1f32e4420761ddae531ad60934c2119"},
|
||||||
{file = "scipy-1.16.0-cp312-cp312-win_amd64.whl", hash = "sha256:adf9b1999323ba335adc5d1dc7add4781cb5a4b0ef1e98b79768c05c796c4e49"},
|
{file = "scipy-1.16.1-cp312-cp312-win_amd64.whl", hash = "sha256:f7b8013c6c066609577d910d1a2a077021727af07b6fab0ee22c2f901f22352a"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313-macosx_10_14_x86_64.whl", hash = "sha256:e9f414cbe9ca289a73e0cc92e33a6a791469b6619c240aa32ee18abdce8ab451"},
|
{file = "scipy-1.16.1-cp313-cp313-macosx_10_14_x86_64.whl", hash = "sha256:5451606823a5e73dfa621a89948096c6528e2896e40b39248295d3a0138d594f"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313-macosx_12_0_arm64.whl", hash = "sha256:bbba55fb97ba3cdef9b1ee973f06b09d518c0c7c66a009c729c7d1592be1935e"},
|
{file = "scipy-1.16.1-cp313-cp313-macosx_12_0_arm64.whl", hash = "sha256:89728678c5ca5abd610aee148c199ac1afb16e19844401ca97d43dc548a354eb"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313-macosx_14_0_arm64.whl", hash = "sha256:58e0d4354eacb6004e7aa1cd350e5514bd0270acaa8d5b36c0627bb3bb486974"},
|
{file = "scipy-1.16.1-cp313-cp313-macosx_14_0_arm64.whl", hash = "sha256:e756d688cb03fd07de0fffad475649b03cb89bee696c98ce508b17c11a03f95c"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313-macosx_14_0_x86_64.whl", hash = "sha256:75b2094ec975c80efc273567436e16bb794660509c12c6a31eb5c195cbf4b6dc"},
|
{file = "scipy-1.16.1-cp313-cp313-macosx_14_0_x86_64.whl", hash = "sha256:5aa2687b9935da3ed89c5dbed5234576589dd28d0bf7cd237501ccfbdf1ad608"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:6b65d232157a380fdd11a560e7e21cde34fdb69d65c09cb87f6cc024ee376351"},
|
{file = "scipy-1.16.1-cp313-cp313-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:0851f6a1e537fe9399f35986897e395a1aa61c574b178c0d456be5b1a0f5ca1f"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:1d8747f7736accd39289943f7fe53a8333be7f15a82eea08e4afe47d79568c32"},
|
{file = "scipy-1.16.1-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:fedc2cbd1baed37474b1924c331b97bdff611d762c196fac1a9b71e67b813b1b"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:eb9f147a1b8529bb7fec2a85cf4cf42bdfadf9e83535c309a11fdae598c88e8b"},
|
{file = "scipy-1.16.1-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:2ef500e72f9623a6735769e4b93e9dcb158d40752cdbb077f305487e3e2d1f45"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:d2b83c37edbfa837a8923d19c749c1935ad3d41cf196006a24ed44dba2ec4358"},
|
{file = "scipy-1.16.1-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:978d8311674b05a8f7ff2ea6c6bce5d8b45a0cb09d4c5793e0318f448613ea65"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313-win_amd64.whl", hash = "sha256:79a3c13d43c95aa80b87328a46031cf52508cf5f4df2767602c984ed1d3c6bbe"},
|
{file = "scipy-1.16.1-cp313-cp313-win_amd64.whl", hash = "sha256:81929ed0fa7a5713fcdd8b2e6f73697d3b4c4816d090dd34ff937c20fa90e8ab"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313t-macosx_10_14_x86_64.whl", hash = "sha256:f91b87e1689f0370690e8470916fe1b2308e5b2061317ff76977c8f836452a47"},
|
{file = "scipy-1.16.1-cp313-cp313t-macosx_10_14_x86_64.whl", hash = "sha256:bcc12db731858abda693cecdb3bdc9e6d4bd200213f49d224fe22df82687bdd6"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313t-macosx_12_0_arm64.whl", hash = "sha256:88a6ca658fb94640079e7a50b2ad3b67e33ef0f40e70bdb7dc22017dae73ac08"},
|
{file = "scipy-1.16.1-cp313-cp313t-macosx_12_0_arm64.whl", hash = "sha256:744d977daa4becb9fc59135e75c069f8d301a87d64f88f1e602a9ecf51e77b27"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313t-macosx_14_0_arm64.whl", hash = "sha256:ae902626972f1bd7e4e86f58fd72322d7f4ec7b0cfc17b15d4b7006efc385176"},
|
{file = "scipy-1.16.1-cp313-cp313t-macosx_14_0_arm64.whl", hash = "sha256:dc54f76ac18073bcecffb98d93f03ed6b81a92ef91b5d3b135dcc81d55a724c7"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313t-macosx_14_0_x86_64.whl", hash = "sha256:8cb824c1fc75ef29893bc32b3ddd7b11cf9ab13c1127fe26413a05953b8c32ed"},
|
{file = "scipy-1.16.1-cp313-cp313t-macosx_14_0_x86_64.whl", hash = "sha256:367d567ee9fc1e9e2047d31f39d9d6a7a04e0710c86e701e053f237d14a9b4f6"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:de2db7250ff6514366a9709c2cba35cb6d08498e961cba20d7cff98a7ee88938"},
|
{file = "scipy-1.16.1-cp313-cp313t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:4cf5785e44e19dcd32a0e4807555e1e9a9b8d475c6afff3d21c3c543a6aa84f4"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:e85800274edf4db8dd2e4e93034f92d1b05c9421220e7ded9988b16976f849c1"},
|
{file = "scipy-1.16.1-cp313-cp313t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:3d0b80fb26d3e13a794c71d4b837e2a589d839fd574a6bbb4ee1288c213ad4a3"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:4f720300a3024c237ace1cb11f9a84c38beb19616ba7c4cdcd771047a10a1706"},
|
{file = "scipy-1.16.1-cp313-cp313t-musllinux_1_2_aarch64.whl", hash = "sha256:8503517c44c18d1030d666cb70aaac1cc8913608816e06742498833b128488b7"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:aad603e9339ddb676409b104c48a027e9916ce0d2838830691f39552b38a352e"},
|
{file = "scipy-1.16.1-cp313-cp313t-musllinux_1_2_x86_64.whl", hash = "sha256:30cc4bb81c41831ecfd6dc450baf48ffd80ef5aed0f5cf3ea775740e80f16ecc"},
|
||||||
{file = "scipy-1.16.0-cp313-cp313t-win_amd64.whl", hash = "sha256:f56296fefca67ba605fd74d12f7bd23636267731a72cb3947963e76b8c0a25db"},
|
{file = "scipy-1.16.1-cp313-cp313t-win_amd64.whl", hash = "sha256:c24fa02f7ed23ae514460a22c57eca8f530dbfa50b1cfdbf4f37c05b5309cc39"},
|
||||||
{file = "scipy-1.16.0.tar.gz", hash = "sha256:b5ef54021e832869c8cfb03bc3bf20366cbcd426e02a58e8a58d7584dfbb8f62"},
|
{file = "scipy-1.16.1-cp314-cp314-macosx_10_14_x86_64.whl", hash = "sha256:796a5a9ad36fa3a782375db8f4241ab02a091308eb079746bc0f874c9b998318"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314-macosx_12_0_arm64.whl", hash = "sha256:3ea0733a2ff73fd6fdc5fecca54ee9b459f4d74f00b99aced7d9a3adb43fb1cc"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314-macosx_14_0_arm64.whl", hash = "sha256:85764fb15a2ad994e708258bb4ed8290d1305c62a4e1ef07c414356a24fcfbf8"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314-macosx_14_0_x86_64.whl", hash = "sha256:ca66d980469cb623b1759bdd6e9fd97d4e33a9fad5b33771ced24d0cb24df67e"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:e7cc1ffcc230f568549fc56670bcf3df1884c30bd652c5da8138199c8c76dae0"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:3ddfb1e8d0b540cb4ee9c53fc3dea3186f97711248fb94b4142a1b27178d8b4b"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:4dc0e7be79e95d8ba3435d193e0d8ce372f47f774cffd882f88ea4e1e1ddc731"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:f23634f9e5adb51b2a77766dac217063e764337fbc816aa8ad9aaebcd4397fd3"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314-win_amd64.whl", hash = "sha256:57d75524cb1c5a374958a2eae3d84e1929bb971204cc9d52213fb8589183fc19"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314t-macosx_10_14_x86_64.whl", hash = "sha256:d8da7c3dd67bcd93f15618938f43ed0995982eb38973023d46d4646c4283ad65"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314t-macosx_12_0_arm64.whl", hash = "sha256:cc1d2f2fd48ba1e0620554fe5bc44d3e8f5d4185c8c109c7fbdf5af2792cfad2"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314t-macosx_14_0_arm64.whl", hash = "sha256:21a611ced9275cb861bacadbada0b8c0623bc00b05b09eb97f23b370fc2ae56d"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314t-macosx_14_0_x86_64.whl", hash = "sha256:8dfbb25dffc4c3dd9371d8ab456ca81beeaf6f9e1c2119f179392f0dc1ab7695"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314t-manylinux2014_aarch64.manylinux_2_17_aarch64.whl", hash = "sha256:f0ebb7204f063fad87fc0a0e4ff4a2ff40b2a226e4ba1b7e34bf4b79bf97cd86"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314t-manylinux2014_x86_64.manylinux_2_17_x86_64.whl", hash = "sha256:f1b9e5962656f2734c2b285a8745358ecb4e4efbadd00208c80a389227ec61ff"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314t-musllinux_1_2_aarch64.whl", hash = "sha256:5e1a106f8c023d57a2a903e771228bf5c5b27b5d692088f457acacd3b54511e4"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314t-musllinux_1_2_x86_64.whl", hash = "sha256:709559a1db68a9abc3b2c8672c4badf1614f3b440b3ab326d86a5c0491eafae3"},
|
||||||
|
{file = "scipy-1.16.1-cp314-cp314t-win_amd64.whl", hash = "sha256:c0c804d60492a0aad7f5b2bb1862f4548b990049e27e828391ff2bf6f7199998"},
|
||||||
|
{file = "scipy-1.16.1.tar.gz", hash = "sha256:44c76f9e8b6e8e488a586190ab38016e4ed2f8a038af7cd3defa903c0a2238b3"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.dependencies]
|
[package.dependencies]
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ build-backend = "poetry.core.masonry.api"
|
|||||||
|
|
||||||
[tool.poetry]
|
[tool.poetry]
|
||||||
name = "yacv-server"
|
name = "yacv-server"
|
||||||
version = "0.10.0-rc.2"
|
version = "0.10.2-alpha.1"
|
||||||
description = "Yet Another CAD Viewer (server)"
|
description = "Yet Another CAD Viewer (server)"
|
||||||
authors = ["Yeicor <4929005+Yeicor@users.noreply.github.com>"]
|
authors = ["Yeicor <4929005+Yeicor@users.noreply.github.com>"]
|
||||||
license = "MIT"
|
license = "MIT"
|
||||||
|
|||||||
@@ -141,7 +141,6 @@ class YACV:
|
|||||||
"""Initializes the YACV server"""
|
"""Initializes the YACV server"""
|
||||||
raw_protocol = os.getenv('YACV_PROTOCOL', 'http' if sys.platform != 'emscripten' else 'stderr').upper()
|
raw_protocol = os.getenv('YACV_PROTOCOL', 'http' if sys.platform != 'emscripten' else 'stderr').upper()
|
||||||
self.protocol = YACVProtocol[raw_protocol] if raw_protocol in YACVProtocol.__members__ else YACVProtocol.HTTP
|
self.protocol = YACVProtocol[raw_protocol] if raw_protocol in YACVProtocol.__members__ else YACVProtocol.HTTP
|
||||||
self.protocol = YACVProtocol.STDERR
|
|
||||||
self.server_thread = None
|
self.server_thread = None
|
||||||
self.server = None
|
self.server = None
|
||||||
self.startup_complete = threading.Event()
|
self.startup_complete = threading.Event()
|
||||||
|
|||||||
207
yarn.lock
207
yarn.lock
@@ -815,105 +815,105 @@
|
|||||||
resolved "https://registry.yarnpkg.com/@rolldown/pluginutils/-/pluginutils-1.0.0-beta.29.tgz#f8fc9a8788757dccba0d3b7fee93183621773d4c"
|
resolved "https://registry.yarnpkg.com/@rolldown/pluginutils/-/pluginutils-1.0.0-beta.29.tgz#f8fc9a8788757dccba0d3b7fee93183621773d4c"
|
||||||
integrity sha512-NIJgOsMjbxAXvoGq/X0gD7VPMQ8j9g0BiDaNjVNVjvl+iKXxL3Jre0v31RmBYeLEmkbj2s02v8vFTbUXi5XS2Q==
|
integrity sha512-NIJgOsMjbxAXvoGq/X0gD7VPMQ8j9g0BiDaNjVNVjvl+iKXxL3Jre0v31RmBYeLEmkbj2s02v8vFTbUXi5XS2Q==
|
||||||
|
|
||||||
"@rollup/rollup-android-arm-eabi@4.45.1":
|
"@rollup/rollup-android-arm-eabi@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.45.1.tgz#8560592f0dcf43b8cb0949af9f1d916205148d12"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.46.0.tgz#b7783a0b32aa633fa2735e9e1ac2de0c80207313"
|
||||||
integrity sha512-NEySIFvMY0ZQO+utJkgoMiCAjMrGvnbDLHvcmlA33UXJpYBCvlBEbMMtV837uCkS+plG2umfhn0T5mMAxGrlRA==
|
integrity sha512-9f3nSTFI2ivfxc7/tHBHcJ8pRnp8ROrELvsVprlQPVvcZ+j5zztYd+PTJGpyIOAdTvNwNrpCXswKSeoQcyGjMQ==
|
||||||
|
|
||||||
"@rollup/rollup-android-arm64@4.45.1":
|
"@rollup/rollup-android-arm64@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.45.1.tgz#6bfb777bbce998691b6fd3e916b05cd46392d020"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.46.0.tgz#d2fb87e8d352ed15a5513817978b4b89f3547556"
|
||||||
integrity sha512-ujQ+sMXJkg4LRJaYreaVx7Z/VMgBBd89wGS4qMrdtfUFZ+TSY5Rs9asgjitLwzeIbhwdEhyj29zhst3L1lKsRQ==
|
integrity sha512-tFZSEhqJ8Yrpe50TzOdeoYi72gi/jsnT7y8Qrozf3cNu28WX+s6I3XzEPUAqoaT9SAS8Xz9AzGTFlxxCH/w20w==
|
||||||
|
|
||||||
"@rollup/rollup-darwin-arm64@4.45.1":
|
"@rollup/rollup-darwin-arm64@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.45.1.tgz#7efce10220293a22e7b7b595d05d8b8400a7bcf3"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.46.0.tgz#a4433c387b8ebec610445b631a42c474e8bc944c"
|
||||||
integrity sha512-FSncqHvqTm3lC6Y13xncsdOYfxGSLnP+73k815EfNmpewPs+EyM49haPS105Rh4aF5mJKywk9X0ogzLXZzN9lA==
|
integrity sha512-+DikIIs+p6yU2hF51UaWG8BnHbq90X0QIOt5zqSKSZxY+G3qqdLih214e9InJal21af2PuuxkDectetGfbVPJw==
|
||||||
|
|
||||||
"@rollup/rollup-darwin-x64@4.45.1":
|
"@rollup/rollup-darwin-x64@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.45.1.tgz#c617a8ece21050bfbea299c126767d2e70cfa79a"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.46.0.tgz#d1f2285c9324e2a9dd284702a4e8029fae77d731"
|
||||||
integrity sha512-2/vVn/husP5XI7Fsf/RlhDaQJ7x9zjvC81anIVbr4b/f0xtSmXQTFcGIQ/B1cXIYM6h2nAhJkdMHTnD7OtQ9Og==
|
integrity sha512-5a+NofhdEB/WimSlFMskbFQn1vqz1FWryYpA99trmZGO6qEmiS0IsX6w4B3d91U878Q2ZQdiaFF1gxX4P147og==
|
||||||
|
|
||||||
"@rollup/rollup-freebsd-arm64@4.45.1":
|
"@rollup/rollup-freebsd-arm64@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.45.1.tgz#5a6af0a9acf82162d2910933649ae24fc0ea3ecb"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.46.0.tgz#5ce48e85792cb149117ebc7e77907762532d1849"
|
||||||
integrity sha512-4g1kaDxQItZsrkVTdYQ0bxu4ZIQ32cotoQbmsAnW1jAE4XCMbcBPDirX5fyUzdhVCKgPcrwWuucI8yrVRBw2+g==
|
integrity sha512-igr/RlKPS3OCy4jD3XBmAmo3UAcNZkJSubRsw1JeM8bAbwf15k/3eMZXD91bnjheijJiOJcga3kfCLKjV8IXNg==
|
||||||
|
|
||||||
"@rollup/rollup-freebsd-x64@4.45.1":
|
"@rollup/rollup-freebsd-x64@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.45.1.tgz#ae9709463560196fc275bd0da598668a2e341023"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.46.0.tgz#29c03ae6c7dcfa49ab6e1b3bb0f95711bed6cf79"
|
||||||
integrity sha512-L/6JsfiL74i3uK1Ti2ZFSNsp5NMiM4/kbbGEcOCps99aZx3g8SJMO1/9Y0n/qKlWZfn6sScf98lEOUe2mBvW9A==
|
integrity sha512-MdigWzPSHlQzB1xZ+MdFDWTAH+kcn7UxjEBoOKuaso7z1DRlnAnrknB1mTtNOQ+GdPI8xgExAGwHeqQjntR0Cg==
|
||||||
|
|
||||||
"@rollup/rollup-linux-arm-gnueabihf@4.45.1":
|
"@rollup/rollup-linux-arm-gnueabihf@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.45.1.tgz#6ec52661764dbd54c19d6520a403aa385a5c0fbf"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.46.0.tgz#2ffe0d9e8049386d8a625803ee30bc0ea6810281"
|
||||||
integrity sha512-RkdOTu2jK7brlu+ZwjMIZfdV2sSYHK2qR08FUWcIoqJC2eywHbXr0L8T/pONFwkGukQqERDheaGTeedG+rra6Q==
|
integrity sha512-dmZseE0ZwA/4yy1+BwFrDqFTjjNg24GO9xSrb1weVbt6AFkhp5pz1gVS7IMtfIvoWy8yp6q/zN0bKnefRUImvQ==
|
||||||
|
|
||||||
"@rollup/rollup-linux-arm-musleabihf@4.45.1":
|
"@rollup/rollup-linux-arm-musleabihf@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.45.1.tgz#fd33ba4a43ef8419e96811236493d19436271923"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.46.0.tgz#ab01d5b33bf67fd5b6ec48deb812800e235501a1"
|
||||||
integrity sha512-3kJ8pgfBt6CIIr1o+HQA7OZ9mp/zDk3ctekGl9qn/pRBgrRgfwiffaUmqioUGN9hv0OHv2gxmvdKOkARCtRb8Q==
|
integrity sha512-fzhfn6p9Cfm3W8UrWKIa4l7Wfjs/KGdgaswMBBE3KY3Ta43jg2XsPrAtfezHpsRk0Nx+TFuS3hZk/To2N5kFPQ==
|
||||||
|
|
||||||
"@rollup/rollup-linux-arm64-gnu@4.45.1":
|
"@rollup/rollup-linux-arm64-gnu@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.45.1.tgz#933b3d99b73c9d7bf4506cab0d5d313c7e74fd2d"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.46.0.tgz#7eef79d5c8cd7ba0eadd3d23e9fec0d532bcd307"
|
||||||
integrity sha512-k3dOKCfIVixWjG7OXTCOmDfJj3vbdhN0QYEqB+OuGArOChek22hn7Uy5A/gTDNAcCy5v2YcXRJ/Qcnm4/ma1xw==
|
integrity sha512-vVDD+iPDPmJQ5nAQ5Tifq3ywdv60FartglFI8VOCK+hcU9aoG0qlQTsDJP97O5yiTaTqlneZWoARMcVC5nyUoQ==
|
||||||
|
|
||||||
"@rollup/rollup-linux-arm64-musl@4.45.1":
|
"@rollup/rollup-linux-arm64-musl@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.45.1.tgz#dbe9ae24ee9e97b75662fddcb69eb7f23c89280a"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.46.0.tgz#87bbcd241fc8a79d23be1ffd333b8e5c4e4604ee"
|
||||||
integrity sha512-PmI1vxQetnM58ZmDFl9/Uk2lpBBby6B6rF4muJc65uZbxCs0EA7hhKCk2PKlmZKuyVSHAyIw3+/SiuMLxKxWog==
|
integrity sha512-0d0jx08fzDHCzXqrtCMEEyxKU0SvJrWmUjUDE2/KDQ2UDJql0tfiwYvEx1oHELClKO8CNdE+AGJj+RqXscZpdQ==
|
||||||
|
|
||||||
"@rollup/rollup-linux-loongarch64-gnu@4.45.1":
|
"@rollup/rollup-linux-loongarch64-gnu@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-loongarch64-gnu/-/rollup-linux-loongarch64-gnu-4.45.1.tgz#818c5a071eec744436dbcdd76fe9c3c869dc9a8d"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-loongarch64-gnu/-/rollup-linux-loongarch64-gnu-4.46.0.tgz#a5207714d3dca6cc4de95204901a95bcc17614e7"
|
||||||
integrity sha512-9UmI0VzGmNJ28ibHW2GpE2nF0PBQqsyiS4kcJ5vK+wuwGnV5RlqdczVocDSUfGX/Na7/XINRVoUgJyFIgipoRg==
|
integrity sha512-XBYu9oW9eKJadWn8M7hkTZsD4yG+RrsTrVEgyKwb4L72cpJjRbRboTG9Lg9fec8MxJp/cfTHAocg4mnismQR8A==
|
||||||
|
|
||||||
"@rollup/rollup-linux-powerpc64le-gnu@4.45.1":
|
"@rollup/rollup-linux-ppc64-gnu@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-powerpc64le-gnu/-/rollup-linux-powerpc64le-gnu-4.45.1.tgz#6b8591def27d886fa147fb0340126c7d6682a7e4"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.46.0.tgz#e231fd7c5a7b18dbef04a0f93f6b7618a8e73282"
|
||||||
integrity sha512-7nR2KY8oEOUTD3pBAxIBBbZr0U7U+R9HDTPNy+5nVVHDXI4ikYniH1oxQz9VoB5PbBU1CZuDGHkLJkd3zLMWsg==
|
integrity sha512-wJaRvcT17PoOK6Ggcfo3nouFlybHvARBS4jzT0PC/lg17fIJHcDS2fZz3sD+iA4nRlho2zE6OGbU0HvwATdokQ==
|
||||||
|
|
||||||
"@rollup/rollup-linux-riscv64-gnu@4.45.1":
|
"@rollup/rollup-linux-riscv64-gnu@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.45.1.tgz#f1861ac4ee8da64e0b0d23853ff26fe2baa876cf"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.46.0.tgz#e4ef1760ee218cad43f441a7bb59b6131664197d"
|
||||||
integrity sha512-nlcl3jgUultKROfZijKjRQLUu9Ma0PeNv/VFHkZiKbXTBQXhpytS8CIj5/NfBeECZtY2FJQubm6ltIxm/ftxpw==
|
integrity sha512-GZ5bkMFteAGkcmh8x0Ok4LSa+L62Ez0tMsHPX6JtR0wl4Xc3bQcrFHDiR5DGLEDFtGrXih4Nd/UDaFqs968/wA==
|
||||||
|
|
||||||
"@rollup/rollup-linux-riscv64-musl@4.45.1":
|
"@rollup/rollup-linux-riscv64-musl@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.45.1.tgz#320c961401a923b374e358664527b188e374e1ae"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.46.0.tgz#dc49cb69aee50a7135b486a5db8f47146f465f5d"
|
||||||
integrity sha512-HJV65KLS51rW0VY6rvZkiieiBnurSzpzore1bMKAhunQiECPuxsROvyeaot/tcK3A3aGnI+qTHqisrpSgQrpgA==
|
integrity sha512-7CjPw6FflFsVOUfWOrVrREiV3IYXG4RzZ1ZQUaT3BtSK8YXN6x286o+sruPZJESIaPebYuFowmg54ZdrkVBYog==
|
||||||
|
|
||||||
"@rollup/rollup-linux-s390x-gnu@4.45.1":
|
"@rollup/rollup-linux-s390x-gnu@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.45.1.tgz#1763eed3362b50b6164d3f0947486c03cc7e616d"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.46.0.tgz#467c43e7c39ee519c9c76d6f75fc22c0b095768e"
|
||||||
integrity sha512-NITBOCv3Qqc6hhwFt7jLV78VEO/il4YcBzoMGGNxznLgRQf43VQDae0aAzKiBeEPIxnDrACiMgbqjuihx08OOw==
|
integrity sha512-nmvnl0ZiuysltcB/cKjUh40Rx4FbSyueERDsl2FLvLYr6pCgSsvGr3SocUT84svSpmloS7f1DRWqtRha74Gi1w==
|
||||||
|
|
||||||
"@rollup/rollup-linux-x64-gnu@4.45.1":
|
"@rollup/rollup-linux-x64-gnu@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.45.1.tgz#0d4c8d0b8f801902f0844a40a9d981a0179f4971"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.46.0.tgz#f094a39afaa12c26e08338a2b5d6bd63cc63ec9a"
|
||||||
integrity sha512-+E/lYl6qu1zqgPEnTrs4WysQtvc/Sh4fC2nByfFExqgYrqkKWp1tWIbe+ELhixnenSpBbLXNi6vbEEJ8M7fiHw==
|
integrity sha512-Cv+moII5C8RM6gZbR3cb21o6rquVDZrN2o81maROg1LFzBz2dZUwIQSxFA8GtGZ/F2KtsqQ2z3eFPBb6akvQNg==
|
||||||
|
|
||||||
"@rollup/rollup-linux-x64-musl@4.45.1":
|
"@rollup/rollup-linux-x64-musl@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.45.1.tgz#ec30bb48b5fe22a3aaba98072f2d5b7139e1a8eb"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.46.0.tgz#173ddb452911847fc2ec8387f410378fcf88a951"
|
||||||
integrity sha512-a6WIAp89p3kpNoYStITT9RbTbTnqarU7D8N8F2CV+4Cl9fwCOZraLVuVFvlpsW0SbIiYtEnhCZBPLoNdRkjQFw==
|
integrity sha512-PHcMG8DZTM9RCIjp8QIfN0VYtX0TtBPnWOTRurFhoCDoi9zptUZL2k7pCs+5rgut7JAiUsYy+huyhVKPcmxoog==
|
||||||
|
|
||||||
"@rollup/rollup-win32-arm64-msvc@4.45.1":
|
"@rollup/rollup-win32-arm64-msvc@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.45.1.tgz#27a6e48d1502e8e4bed96bedfb533738655874f2"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.46.0.tgz#91a1b3199aedc5cd51004b21f6c465d3cf74d5d0"
|
||||||
integrity sha512-T5Bi/NS3fQiJeYdGvRpTAP5P02kqSOpqiopwhj0uaXB6nzs5JVi2XMJb18JUSKhCOX8+UE1UKQufyD6Or48dJg==
|
integrity sha512-1SI/Rd47e8aQJeFWMDg16ET+fjvCcD/CzeaRmIEPmb05hx+3cCcwIF4ebUag4yTt/D1peE+Mgp0+Po3M358cAA==
|
||||||
|
|
||||||
"@rollup/rollup-win32-ia32-msvc@4.45.1":
|
"@rollup/rollup-win32-ia32-msvc@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.45.1.tgz#a2fbad3bec20ff879f3fd51720adf33692ca8f3d"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.46.0.tgz#da901027ad9753faa93412ed3fd9e6cacb6c8659"
|
||||||
integrity sha512-lxV2Pako3ujjuUe9jiU3/s7KSrDfH6IgTSQOnDWr9aJ92YsFd7EurmClK0ly/t8dzMkDtd04g60WX6yl0sGfdw==
|
integrity sha512-JwOCYxmumFDfDhx4kNyz6kTVK3gWzBIvVdMNzQMRDubcoGRDniOOmo6DDNP42qwZx3Bp9/6vWJ+kNzNqXoHmeA==
|
||||||
|
|
||||||
"@rollup/rollup-win32-x64-msvc@4.45.1":
|
"@rollup/rollup-win32-x64-msvc@4.46.0":
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.45.1.tgz#e5085c6d13da15b4c5133cd2a6bb11f25b6bb77a"
|
resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.46.0.tgz#a45b0f6f45c86e355a85ba3c753bf0f59541c2c7"
|
||||||
integrity sha512-M/fKi4sasCdM8i0aWJjCSFm2qEnYRR8AMLG2kxp6wD13+tMGA4Z1tVAuHkNRjud5SW2EM3naLuK35w9twvf6aA==
|
integrity sha512-IPMIfrfkG1GaEXi+JSsQEx8x9b4b+hRZXO7KYc2pKio3zO2/VDXDs6B9Ts/nnO+25Fk1tdAVtUn60HKKPPzDig==
|
||||||
|
|
||||||
"@sigstore/bundle@^3.1.0":
|
"@sigstore/bundle@^3.1.0":
|
||||||
version "3.1.0"
|
version "3.1.0"
|
||||||
@@ -2631,32 +2631,32 @@ retry@^0.12.0:
|
|||||||
integrity sha512-9LkiTwjUh6rT555DtE9rTX+BKByPfrMzEAtnlEtdEwr3Nkffwiihqe2bWADg+OQRjt9gl6ICdmB/ZFDCGAtSow==
|
integrity sha512-9LkiTwjUh6rT555DtE9rTX+BKByPfrMzEAtnlEtdEwr3Nkffwiihqe2bWADg+OQRjt9gl6ICdmB/ZFDCGAtSow==
|
||||||
|
|
||||||
rollup@^4.40.0:
|
rollup@^4.40.0:
|
||||||
version "4.45.1"
|
version "4.46.0"
|
||||||
resolved "https://registry.yarnpkg.com/rollup/-/rollup-4.45.1.tgz#d0ef72a8d0a9210d832f9c3c5f3b6a2aa4b0ba64"
|
resolved "https://registry.yarnpkg.com/rollup/-/rollup-4.46.0.tgz#f8b74becb74d26a703ae0ef737ff465a1feb9447"
|
||||||
integrity sha512-4iya7Jb76fVpQyLoiVpzUrsjQ12r3dM7fIVz+4NwoYvZOShknRmiv+iu9CClZml5ZLGb0XMcYLutK6w9tgxHDw==
|
integrity sha512-ONmkT3Ud3IfW15nl7l4qAZko5/2iZ5ALVBDh02ZSZ5IGVLJSYkRcRa3iB58VyEIyoofs9m2xdVrm+lTi97+3pw==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@types/estree" "1.0.8"
|
"@types/estree" "1.0.8"
|
||||||
optionalDependencies:
|
optionalDependencies:
|
||||||
"@rollup/rollup-android-arm-eabi" "4.45.1"
|
"@rollup/rollup-android-arm-eabi" "4.46.0"
|
||||||
"@rollup/rollup-android-arm64" "4.45.1"
|
"@rollup/rollup-android-arm64" "4.46.0"
|
||||||
"@rollup/rollup-darwin-arm64" "4.45.1"
|
"@rollup/rollup-darwin-arm64" "4.46.0"
|
||||||
"@rollup/rollup-darwin-x64" "4.45.1"
|
"@rollup/rollup-darwin-x64" "4.46.0"
|
||||||
"@rollup/rollup-freebsd-arm64" "4.45.1"
|
"@rollup/rollup-freebsd-arm64" "4.46.0"
|
||||||
"@rollup/rollup-freebsd-x64" "4.45.1"
|
"@rollup/rollup-freebsd-x64" "4.46.0"
|
||||||
"@rollup/rollup-linux-arm-gnueabihf" "4.45.1"
|
"@rollup/rollup-linux-arm-gnueabihf" "4.46.0"
|
||||||
"@rollup/rollup-linux-arm-musleabihf" "4.45.1"
|
"@rollup/rollup-linux-arm-musleabihf" "4.46.0"
|
||||||
"@rollup/rollup-linux-arm64-gnu" "4.45.1"
|
"@rollup/rollup-linux-arm64-gnu" "4.46.0"
|
||||||
"@rollup/rollup-linux-arm64-musl" "4.45.1"
|
"@rollup/rollup-linux-arm64-musl" "4.46.0"
|
||||||
"@rollup/rollup-linux-loongarch64-gnu" "4.45.1"
|
"@rollup/rollup-linux-loongarch64-gnu" "4.46.0"
|
||||||
"@rollup/rollup-linux-powerpc64le-gnu" "4.45.1"
|
"@rollup/rollup-linux-ppc64-gnu" "4.46.0"
|
||||||
"@rollup/rollup-linux-riscv64-gnu" "4.45.1"
|
"@rollup/rollup-linux-riscv64-gnu" "4.46.0"
|
||||||
"@rollup/rollup-linux-riscv64-musl" "4.45.1"
|
"@rollup/rollup-linux-riscv64-musl" "4.46.0"
|
||||||
"@rollup/rollup-linux-s390x-gnu" "4.45.1"
|
"@rollup/rollup-linux-s390x-gnu" "4.46.0"
|
||||||
"@rollup/rollup-linux-x64-gnu" "4.45.1"
|
"@rollup/rollup-linux-x64-gnu" "4.46.0"
|
||||||
"@rollup/rollup-linux-x64-musl" "4.45.1"
|
"@rollup/rollup-linux-x64-musl" "4.46.0"
|
||||||
"@rollup/rollup-win32-arm64-msvc" "4.45.1"
|
"@rollup/rollup-win32-arm64-msvc" "4.46.0"
|
||||||
"@rollup/rollup-win32-ia32-msvc" "4.45.1"
|
"@rollup/rollup-win32-ia32-msvc" "4.46.0"
|
||||||
"@rollup/rollup-win32-x64-msvc" "4.45.1"
|
"@rollup/rollup-win32-x64-msvc" "4.46.0"
|
||||||
fsevents "~2.3.2"
|
fsevents "~2.3.2"
|
||||||
|
|
||||||
safe-buffer@~5.2.0:
|
safe-buffer@~5.2.0:
|
||||||
@@ -2940,6 +2940,7 @@ three-mesh-bvh@^0.9.0:
|
|||||||
|
|
||||||
"three-orientation-gizmo@git+https://github.com/jrj2211/three-orientation-gizmo.git":
|
"three-orientation-gizmo@git+https://github.com/jrj2211/three-orientation-gizmo.git":
|
||||||
version "1.1.0"
|
version "1.1.0"
|
||||||
|
uid "000281f0559c316f72cdd23a1885d63ae6901095"
|
||||||
resolved "git+https://github.com/jrj2211/three-orientation-gizmo.git#000281f0559c316f72cdd23a1885d63ae6901095"
|
resolved "git+https://github.com/jrj2211/three-orientation-gizmo.git#000281f0559c316f72cdd23a1885d63ae6901095"
|
||||||
dependencies:
|
dependencies:
|
||||||
three "^0.125.0"
|
three "^0.125.0"
|
||||||
|
|||||||
Reference in New Issue
Block a user