Pārlūkot izejas kodu

Add undo for autoScale and autoCenter, some type fixes

master
Palash Bansal pirms 1 gada
vecāks
revīzija
719838354e
Revīzijas autora e-pasta adrese nav piesaistīta nevienam kontam

+ 13
- 4
examples/dropzone-plugin/script.ts Parādīt failu

import {_testFinish, DropzonePlugin, LoadingScreenPlugin, ThreeViewer} from 'threepipe'
import {
_testFinish,
DropzonePlugin,
LoadingScreenPlugin,
PickingPlugin,
Rhino3dmLoadPlugin,
ThreeViewer,
} from 'threepipe'
import {TweakpaneUiPlugin} from '@threepipe/plugin-tweakpane' import {TweakpaneUiPlugin} from '@threepipe/plugin-tweakpane'


async function init() { async function init() {
const viewer = new ThreeViewer({ const viewer = new ThreeViewer({
canvas: document.getElementById('mcanvas') as HTMLCanvasElement, canvas: document.getElementById('mcanvas') as HTMLCanvasElement,
dropzone: { // this can also be set to true and configured by getting a reference to the DropzonePlugin dropzone: { // this can also be set to true and configured by getting a reference to the DropzonePlugin
allowedExtensions: ['gltf', 'glb', 'hdr', 'bin', 'png', 'jpeg', 'webp', 'jpg', 'exr', 'fbx', 'obj'], // only allow these file types. If undefined, all files are allowed.
allowedExtensions: ['gltf', 'glb', 'hdr', 'bin', 'png', 'jpeg', 'webp', 'jpg', 'exr', 'fbx', 'obj', '3dm'], // only allow these file types. If undefined, all files are allowed.
addOptions: { addOptions: {
disposeSceneObjects: true, // auto dispose of old scene objects disposeSceneObjects: true, // auto dispose of old scene objects
autoSetEnvironment: true, // when hdr is dropped autoSetEnvironment: true, // when hdr is dropped
importConfig: true, // import config from file importConfig: true, // import config from file
}, },
}, },
plugins: [LoadingScreenPlugin],
plugins: [LoadingScreenPlugin, PickingPlugin, Rhino3dmLoadPlugin],
}) })


await viewer.setEnvironmentMap('https://threejs.org/examples/textures/equirectangular/venice_sunset_1k.hdr') await viewer.setEnvironmentMap('https://threejs.org/examples/textures/equirectangular/venice_sunset_1k.hdr')
}) })


const ui = viewer.addPluginSync(TweakpaneUiPlugin, true) const ui = viewer.addPluginSync(TweakpaneUiPlugin, true)
ui.appendChild(dropzone.uiConfig)
// ui.appendChild(dropzone.uiConfig)
ui.setupPluginUi(DropzonePlugin)
ui.setupPluginUi(PickingPlugin)


} }



+ 15
- 15
plugins/plugin-template-rollup/rollup.config.mjs Parādīt failu

import resolve from '@rollup/plugin-node-resolve'; import resolve from '@rollup/plugin-node-resolve';
import typescript from '@rollup/plugin-typescript'; import typescript from '@rollup/plugin-typescript';
import license from 'rollup-plugin-license' import license from 'rollup-plugin-license'
import packageJson from './package.json' assert {type: 'json'};
import packageJson from './package.json' with {type: 'json'};
import path from 'path' import path from 'path'
import {fileURLToPath} from 'url'; import {fileURLToPath} from 'url';
import postcss from 'rollup-plugin-postcss' import postcss from 'rollup-plugin-postcss'
import replace from '@rollup/plugin-replace' import replace from '@rollup/plugin-replace'
import terser from "@rollup/plugin-terser";
import terser from '@rollup/plugin-terser';


const __filename = fileURLToPath(import.meta.url); const __filename = fileURLToPath(import.meta.url);
const __dirname = path.dirname(__filename); const __dirname = path.dirname(__filename);


const settings = { const settings = {
globals: { globals: {
"three": "threepipe", // just incase someone uses three
"threepipe": "threepipe",
"@threepipe/plugin-tweakpane": "@threepipe/plugin-tweakpane"
'three': 'threepipe', // just incase someone uses three
'threepipe': 'threepipe',
'@threepipe/plugin-tweakpane': '@threepipe/plugin-tweakpane',
}, },
sourcemap: true
sourcemap: true,
} }


export default { export default {
name: name, name: name,
format: 'es', format: 'es',
plugins: [ plugins: [
isProduction && terser()
]
isProduction && terser(),
],
}, },
{ {
file: './dist/index.js', file: './dist/index.js',
name: name, name: name,
format: 'umd', format: 'umd',
plugins: [ plugins: [
isProduction && terser()
]
}
isProduction && terser(),
],
},
], ],
external: Object.keys(settings.globals), external: Object.keys(settings.globals),
plugins: [ plugins: [
}), }),
postcss({ postcss({
modules: false, modules: false,
autoModules: true, // todo; issues with typescript import css, because inject is false
autoModules: true, // todo; issues with typescript import css, because inject is false
inject: false, inject: false,
minimize: isProduction, minimize: isProduction,
// Or with custom options for `postcss-modules` // Or with custom options for `postcss-modules`
include: 'node_modules/**', include: 'node_modules/**',
extensions: ['.js'], extensions: ['.js'],
ignoreGlobal: false, ignoreGlobal: false,
sourceMap: false
sourceMap: false,
}), }),
license({ license({
banner: ` banner: `
output: path.join(__dirname, 'dist', 'dependencies.txt'), output: path.join(__dirname, 'dist', 'dependencies.txt'),
includePrivate: true, // Default is false. includePrivate: true, // Default is false.
}, },
})
]
}),
],
} }

+ 17
- 1
plugins/svg-renderer/src/three-svg-renderer/core/SVGMesh.ts Parādīt failu



import {Color, Material, Mesh, Vector3} from 'three'; import {Color, Material, Mesh, Vector3} from 'three';
import {HalfedgeDS} from '../../three-mesh-halfedge'; import {HalfedgeDS} from '../../three-mesh-halfedge';
import {acceleratedRaycast, CENTER, MeshBVH, MeshBVHOptions} from 'three-mesh-bvh';
import {
acceleratedRaycast,
CENTER,
computeBoundsTree,
disposeBoundsTree,
MeshBVH,
MeshBVHOptions
} from 'three-mesh-bvh';
import {computeMorphedGeometry, disposeMesh} from '../utils/buffergeometry'; import {computeMorphedGeometry, disposeMesh} from '../utils/buffergeometry';


type ColorMaterial = Material & {color: Color}; type ColorMaterial = Material & {color: Color};
url: string; url: string;
} }


declare module 'three/src/core/BufferGeometry' {
export interface BufferGeometry {
boundsTree?: MeshBVH;
computeBoundsTree: typeof computeBoundsTree;
disposeBoundsTree: typeof disposeBoundsTree;
}
}


/** /**
* Mesh object that can be rendered as SVG. * Mesh object that can be rendered as SVG.
* Wrapper class around three mesh object that duplicates geometry if needed (i.e. * Wrapper class around three mesh object that duplicates geometry if needed (i.e.

+ 4
- 2
src/core/IObject.ts Parādīt failu

* @param autoScaleRadius - optional (taken from userData.autoScaleRadius by default) * @param autoScaleRadius - optional (taken from userData.autoScaleRadius by default)
* @param isCentered - optional (taken from userData.isCentered by default) * @param isCentered - optional (taken from userData.isCentered by default)
* @param setDirty - true by default * @param setDirty - true by default
* @param undo - undo any previous autoScale operation
*/ */
autoScale?(autoScaleRadius?: number, isCentered?: boolean, setDirty?: boolean): this
autoScale?(autoScaleRadius?: number, isCentered?: boolean, setDirty?: boolean, undo?: boolean): this


/** /**
* *
* @param setDirty - calls {@link setDirty} @default true * @param setDirty - calls {@link setDirty} @default true
* @param undo - undo any previous autoCenter operation
*/ */
autoCenter?(setDirty?: boolean): this
autoCenter?(setDirty?: boolean, undo?: boolean): this


/** /**
* @deprecated use object directly * @deprecated use object directly

+ 1
- 1
src/core/material/IMaterialUi.ts Parādīt failu

children: [ children: [
{ {
type: 'slider', type: 'slider',
bounds: [-0.2, 0.2],
bounds: [-1, 1],
stepSize: 0.001, stepSize: 0.001,
property: [material, 'bumpScale'], property: [material, 'bumpScale'],
hidden: ()=>!material.bumpMap, hidden: ()=>!material.bumpMap,

+ 7
- 4
src/core/object/IObjectUi.ts Parādīt failu

type: 'checkbox', type: 'checkbox',
label: 'Auto LookAt Target', label: 'Auto LookAt Target',
getValue: ()=>this.userData.autoLookAtTarget ?? false, getValue: ()=>this.userData.autoLookAtTarget ?? false,
setValue: (v)=>{
setValue: (v: boolean)=>{
this.userData.autoLookAtTarget = v this.userData.autoLookAtTarget = v
config.uiRefresh?.(true, 'postFrame') config.uiRefresh?.(true, 'postFrame')
}, },
] ]
} }



export function makeIObject3DUiConfig(this: IObject3D, isMesh?:boolean): UiObjectConfig { export function makeIObject3DUiConfig(this: IObject3D, isMesh?:boolean): UiObjectConfig {
if (!this) return {} if (!this) return {}
if (this.uiConfig) return this.uiConfig if (this.uiConfig) return this.uiConfig
label: 'Auto Scale', label: 'Auto Scale',
hidden: ()=>!this.autoScale, hidden: ()=>!this.autoScale,
prompt: ['Auto Scale Radius: Object will be scaled to the given radius', this.userData.autoScaleRadius || '2', true], prompt: ['Auto Scale Radius: Object will be scaled to the given radius', this.userData.autoScaleRadius || '2', true],
value: ()=>{
value: async()=>{
const def = (this.userData.autoScaleRadius || 2) + '' const def = (this.userData.autoScaleRadius || 2) + ''
const res = prompt('Auto Scale Radius: Object will be scaled to the given radius', def) const res = prompt('Auto Scale Radius: Object will be scaled to the given radius', def)
if (res === null) return if (res === null) return
const rad = parseFloat(res || def) const rad = parseFloat(res || def)
if (Math.abs(rad) > 0) this.autoScale?.(rad)
if (Math.abs(rad) > 0) {
this.autoScale?.(rad)
return ()=>this.autoScale?.(rad, undefined, undefined, true)
}
}, },
}, },
{ {
const res = confirm('Auto Center: Object will be centered, are you sure you want to proceed?') const res = confirm('Auto Center: Object will be centered, are you sure you want to proceed?')
if (!res) return if (!res) return
this.autoCenter?.(true) this.autoCenter?.(true)
return ()=>this.autoCenter?.(true, true)
}, },
}, },
{ {

+ 41
- 18
src/core/object/iObjectCommons.ts Parādīt failu

upgradeObject3D: upgradeObject3D, upgradeObject3D: upgradeObject3D,
makeUiConfig: makeIObject3DUiConfig, makeUiConfig: makeIObject3DUiConfig,


autoCenter: function<T extends IObject3D>(this: T, setDirty = true): T {
const bb = new Box3B().expandByObject(this, true, true)
const center = bb.getCenter(new Vector3())
this.position.sub(center)
autoCenter: function<T extends IObject3D>(this: T, setDirty = true, undo = false): T {
if (undo) {
if (!this.userData.autoCentered || !this.userData._lastCenter) return this
this.position.add(this.userData._lastCenter)
delete this.userData.autoCentered
delete this.userData.isCentered
delete this.userData._lastCenter
} else {
const bb = new Box3B().expandByObject(this, true, true)
const center = bb.getCenter(new Vector3())
this.userData._lastCenter = center/* .clone()*/
this.position.sub(center)
this.userData.autoCentered = true
this.userData.isCentered = true
}
this.updateMatrix() this.updateMatrix()
this.userData.autoCentered = true
this.userData.isCentered = true
if (setDirty) this.setDirty({change: 'autoCenter'})
if (setDirty) this.setDirty({change: 'autoCenter', undo})
return this return this
}, },
autoScale: function<T extends IObject3D>(this: T, autoScaleRadius?: number, isCentered?: boolean, setDirty = true): T {
const bbox = new Box3B().expandByObject(this, true, true)
const radius = bbox.getSize(new Vector3()).length() * 0.5
if (autoScaleRadius === undefined) {
autoScaleRadius = this.userData.autoScaleRadius || 1
autoScale: function<T extends IObject3D>(this: T, autoScaleRadius?: number, isCentered?: boolean, setDirty = true, undo = false): T {
let scale = 1
if (undo) { // Note - undo only works for quick undo, not for multiple times
if (!this.userData.autoScaled || !this.userData._lastScaleRadius) return this
const rad = this.userData.autoScaleRadius || autoScaleRadius || 1
scale = this.userData._lastScaleRadius / rad
if (!isFinite(scale)) return this // NaN when radius is 0
this.userData.autoScaled = true
this.userData.autoScaleRadius = autoScaleRadius
delete this.userData._lastScaleRadius
} else {
const bbox = new Box3B().expandByObject(this, true, true)
const radius = bbox.getSize(new Vector3()).length() * 0.5
if (autoScaleRadius === undefined) {
autoScaleRadius = this.userData.autoScaleRadius || 1
}
scale = autoScaleRadius / radius
if (!isFinite(scale)) return this // NaN when radius is 0
this.userData.autoScaled = true
this.userData.autoScaleRadius = autoScaleRadius
this.userData._lastScaleRadius = radius
} }
const scale = autoScaleRadius / radius
// this.scale.multiplyScalar(20 / radius)
if (!isFinite(scale)) return this // NaN when radius is 0


if (this.userData.pseudoCentered) { if (this.userData.pseudoCentered) {
this.children.forEach(child => { this.children.forEach(child => {
} else } else
this.scale.multiplyScalar(scale) this.scale.multiplyScalar(scale)
if (isCentered || this.userData.isCentered) this.position.multiplyScalar(scale) if (isCentered || this.userData.isCentered) this.position.multiplyScalar(scale)

this.traverse((obj) => { this.traverse((obj) => {
const l = obj as any const l = obj as any
if (l.isLight && l.shadow?.camera?.right) { if (l.isLight && l.shadow?.camera?.right) {
obj.setDirty() obj.setDirty()
} }
}) })
this.userData.autoScaled = true
this.userData.autoScaleRadius = autoScaleRadius
if (setDirty) this.setDirty({change: 'autoScale'})
if (setDirty) this.setDirty({change: 'autoScale', undo})
return this return this
}, },



Notiek ielāde…
Atcelt
Saglabāt