Skip to content

Commit

Permalink
Added virtual-camera model as camera on export
Browse files Browse the repository at this point in the history
  • Loading branch information
Vlad Stepura committed Nov 6, 2019
1 parent 04eeac6 commit d381348
Show file tree
Hide file tree
Showing 3 changed files with 76 additions and 9 deletions.
3 changes: 2 additions & 1 deletion src/js/services/model-loader.js
Original file line number Diff line number Diff line change
Expand Up @@ -235,7 +235,8 @@ const pathToShotGeneratorData =
// calculate filepath
const builtInFolder = type => ({
'object': path.join(pathToShotGeneratorData, 'objects'),
'character': path.join(pathToShotGeneratorData, 'dummies', 'gltf')
'character': path.join(pathToShotGeneratorData, 'dummies', 'gltf'),
'xr': path.join(pathToShotGeneratorData, 'xr')
}[type])

const projectFolder = type => ({
Expand Down
4 changes: 2 additions & 2 deletions src/js/shot-generator/Editor.js
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ const Icon = require('./Icon')
const Toolbar = require('./Toolbar')
const FatalErrorBoundary = require('./FatalErrorBoundary')

const useExportToGltf = require('./use-export-to-gltf')
const {useExportToGltf, loadCameraModel} = require('./use-export-to-gltf')

const ModelLoader = require('../services/model-loader')

Expand Down Expand Up @@ -391,7 +391,7 @@ const Editor = connect(
// TODO cancellation (e.g.: redux-saga)
const loadSceneObjects = async (dispatch, state) => {
let storyboarderFilePath = state.meta.storyboarderFilePath

loadCameraModel(storyboarderFilePath)
const loadables = Object.values(sceneObjects)
// has a value for model
.filter(o => o.model != null)
Expand Down
78 changes: 72 additions & 6 deletions src/js/shot-generator/use-export-to-gltf.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,17 +9,80 @@ const THREE = require('three')
window.THREE = window.THREE || THREE
require('../vendor/three/examples/js/exporters/GLTFExporter.js')
require('../vendor/three/examples/js/utils/SkeletonUtils')

const {gltfLoader} = require('./Components')
const {
getSceneObjects
} = require('../shared/reducers/shot-generator')

const notifications = require('../window/notifications')

const useExportToGltf = (sceneRef) => {

const ModelLoader = require('../services/model-loader')

const materialFactory = () => new THREE.MeshBasicMaterial({
color: 0x8c78f1,
flatShading: false
})

const meshFactory = originalMesh => {
let mesh = originalMesh.clone()
mesh.geometry.computeBoundingBox()

// create a skeleton if one is not provided
if (mesh instanceof THREE.SkinnedMesh && !mesh.skeleton) {
mesh.skeleton = new THREE.Skeleton()
}

let material = materialFactory()

if (mesh.material.map) {
material.map = mesh.material.map
material.map.needsUpdate = true
}
mesh.material = material

return mesh
}



let virtualCameraObject = null
const loadModels = (models) => {
return Promise.all(
models.map((modelPath) => {
return new Promise((resolve, reject) => {
gltfLoader.load(
modelPath,
modelData => resolve(modelData.scene),
null,
reject
)
})
})
)
}

const loadCameraModel = (storyboarderFilePath) => {
let expectedCameraFilepath = ModelLoader.getFilepathForModel({
model: 'virtual-camera',
type: 'xr'
}, { storyboarderFilePath })
loadModels([expectedCameraFilepath ]).then(([virtualCamera]) => {
virtualCameraObject = new THREE.Object3D()
virtualCamera.traverse( function ( child ) {
if ( child instanceof THREE.Mesh ) {
let mesh = meshFactory(child)
virtualCameraObject.add(mesh)
}
})
})
}

const useExportToGltf = (sceneRef, storyboarderFilePath) => {
const meta = useSelector(state => state.meta)
const board = useSelector(state => state.board)
const sceneObjects = useSelector(getSceneObjects)

useEffect(() => {
if (board && meta && meta.storyboarderFilePath) {
ipcRenderer.on('shot-generator:export-gltf', () => {
Expand All @@ -29,7 +92,6 @@ const useExportToGltf = (sceneRef) => {
})
let scene = new THREE.Scene()
for (let child of sceneRef.current.children) {
// console.log('\tScene contains:', child)
// HACK test to avoid IconSprites, which fail to .clone
if (!child.icon) {
if (child.userData.id && sceneObjects[child.userData.id]) {
Expand All @@ -46,6 +108,12 @@ const useExportToGltf = (sceneRef) => {
simpleMesh.position.copy(skinnedMesh.worldPosition())
scene.add( simpleMesh)

} else if (sceneObject.type === "camera") {
let camera = virtualCameraObject.clone()
camera.position.copy(child.worldPosition())
camera.quaternion.copy(child.worldQuaternion())
camera.scale.copy(child.worldScale())
scene.add(camera)
} else if (sceneObject) {
let clone = child.clone()

Expand All @@ -65,8 +133,6 @@ const useExportToGltf = (sceneRef) => {
}
}

console.log('\tExporting Scene:', scene)

let exporter = new THREE.GLTFExporter()
let options = {
binary: true,
Expand Down Expand Up @@ -104,4 +170,4 @@ const useExportToGltf = (sceneRef) => {
}, [board, meta, sceneObjects])
}

module.exports = useExportToGltf
module.exports = {useExportToGltf, loadCameraModel}

0 comments on commit d381348

Please sign in to comment.