Reintegrated VR compnent.
This commit is contained in:
parent
4f39030ed4
commit
5d3cad0def
@ -33,12 +33,9 @@ export class DiagramManager {
|
||||
this._me = getMe();
|
||||
this._scene = DefaultScene.Scene;
|
||||
this._config = new AppConfig();
|
||||
|
||||
this._diagramMenuManager = new DiagramMenuManager(this.onDiagramEventObservable, controllerObservable, this._config, readyObservable);
|
||||
this._diagramEntityActionManager = buildEntityActionManager(controllerObservable);
|
||||
this.onDiagramEventObservable.add(this.onDiagramEvent, DiagramEventObserverMask.FROM_DB, true, this);
|
||||
|
||||
|
||||
this.onUserEventObservable.add((user) => {
|
||||
if (user.id != this._me) {
|
||||
this._logger.debug('user event', user);
|
||||
@ -140,6 +137,12 @@ export class DiagramManager {
|
||||
private onDiagramEvent(event: DiagramEvent) {
|
||||
let diagramObject = this._diagramObjects.get(event?.entity?.id);
|
||||
switch (event.type) {
|
||||
case DiagramEventType.CLEAR:
|
||||
this._diagramObjects.forEach((value, key) => {
|
||||
value.dispose();
|
||||
});
|
||||
this._diagramObjects.clear();
|
||||
break;
|
||||
case DiagramEventType.ADD:
|
||||
if (diagramObject) {
|
||||
diagramObject.fromDiagramEntity(event.entity);
|
||||
|
||||
3
src/integration/database/database.ts
Normal file
3
src/integration/database/database.ts
Normal file
@ -0,0 +1,3 @@
|
||||
import {DEFAULT_DB_NAME} from "../../util/constants";
|
||||
|
||||
export const db = new PouchDB(DEFAULT_DB_NAME);
|
||||
105
src/integration/database/pouchData.ts
Normal file
105
src/integration/database/pouchData.ts
Normal file
@ -0,0 +1,105 @@
|
||||
import {Observable} from "@babylonjs/core";
|
||||
import {DiagramEntity, DiagramEventType} from "../../diagram/types/diagramEntity";
|
||||
import {DiagramManager} from "../../diagram/diagramManager";
|
||||
import {DiagramEventObserverMask} from "../../diagram/types/diagramEventObserverMask";
|
||||
import log, {Logger} from "loglevel";
|
||||
import PouchDB from 'pouchdb';
|
||||
|
||||
export class PouchData {
|
||||
public readonly onDBEntityUpdateObservable: Observable<DiagramEntity> = new Observable<DiagramEntity>();
|
||||
public readonly onDBEntityRemoveObservable: Observable<DiagramEntity> = new Observable<DiagramEntity>();
|
||||
private _db: PouchDB;
|
||||
private _diagramManager: DiagramManager;
|
||||
private _logger: Logger = log.getLogger('PouchData');
|
||||
|
||||
constructor() {
|
||||
|
||||
}
|
||||
|
||||
public async setDb(dbname: string) {
|
||||
if (this._db) {
|
||||
await this._db.close();
|
||||
}
|
||||
this._db = new PouchDB(dbname);
|
||||
const all = await this._db.allDocs({include_docs: true});
|
||||
for (const dbEntity of all.rows) {
|
||||
this.onDBEntityUpdateObservable.notifyObservers(dbEntity.doc, DiagramEventObserverMask.FROM_DB);
|
||||
}
|
||||
}
|
||||
|
||||
public setDiagramManager(diagramManager: DiagramManager) {
|
||||
this._diagramManager = diagramManager;
|
||||
diagramManager.onDiagramEventObservable.add((evt) => {
|
||||
this._logger.debug(evt);
|
||||
if (!evt?.entity) {
|
||||
this._logger.warn('no entity');
|
||||
return;
|
||||
}
|
||||
if (!evt?.entity?.id) {
|
||||
this._logger.warn('no entity id');
|
||||
return;
|
||||
}
|
||||
switch (evt.type) {
|
||||
case DiagramEventType.REMOVE:
|
||||
this.remove(evt.entity.id);
|
||||
break;
|
||||
case DiagramEventType.ADD:
|
||||
case DiagramEventType.MODIFY:
|
||||
case DiagramEventType.DROP:
|
||||
this.upsert(evt.entity);
|
||||
break;
|
||||
default:
|
||||
this._logger.warn('unknown diagram event type', evt);
|
||||
}
|
||||
}, DiagramEventObserverMask.TO_DB);
|
||||
|
||||
this.onDBEntityUpdateObservable.add((evt) => {
|
||||
this._logger.debug(evt);
|
||||
if (evt.id != 'metadata' && evt.type != 'user') {
|
||||
diagramManager.onDiagramEventObservable.notifyObservers({
|
||||
type: DiagramEventType.ADD,
|
||||
entity: evt
|
||||
}, DiagramEventObserverMask.FROM_DB);
|
||||
} else {
|
||||
|
||||
}
|
||||
});
|
||||
this.onDBEntityRemoveObservable.add((entity) => {
|
||||
this._logger.debug(entity);
|
||||
diagramManager.onDiagramEventObservable.notifyObservers(
|
||||
{type: DiagramEventType.REMOVE, entity: entity}, DiagramEventObserverMask.FROM_DB);
|
||||
});
|
||||
}
|
||||
|
||||
public async remove(id: string) {
|
||||
if (!id) {
|
||||
return;
|
||||
}
|
||||
try {
|
||||
const doc = await this._db.get(id);
|
||||
await this._db.remove(doc);
|
||||
} catch (err) {
|
||||
this._logger.error(err);
|
||||
}
|
||||
}
|
||||
|
||||
public async upsert(entity: DiagramEntity) {
|
||||
if (!entity) {
|
||||
return;
|
||||
}
|
||||
if (entity.template == '#image-template' && !entity.image) {
|
||||
this._logger.error('no image data', entity);
|
||||
return;
|
||||
}
|
||||
let doc = null;
|
||||
try {
|
||||
doc = await this._db.get(entity.id, {conflicts: true, include_docs: true});
|
||||
await this._db.put({_id: doc._id, _rev: doc._rev, ...entity});
|
||||
} catch (err) {
|
||||
await this._db.put({_id: entity.id, ...entity});
|
||||
}
|
||||
if (doc && doc._conflicts) {
|
||||
this._logger.warn('CONFLICTS!', doc._conflicts);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -20,9 +20,9 @@ export default function CreateDiagramModal({createOpened, closeCreate}) {
|
||||
console.error(err);
|
||||
}
|
||||
const id = 'diagram-' + v4();
|
||||
const newDiagram = {...diagram, _id: id}
|
||||
const newDiagram = {...diagram, _id: id, type: 'diagram'};
|
||||
if (!doc) {
|
||||
await db.put({_id: 'directory', diagrams: [newDiagram]});
|
||||
await db.put({_id: 'directory', diagrams: [newDiagram], type: 'directory'});
|
||||
} else {
|
||||
if (doc.diagrams) {
|
||||
doc.diagrams.push(newDiagram);
|
||||
@ -96,6 +96,5 @@ export default function CreateDiagramModal({createOpened, closeCreate}) {
|
||||
</Stack>
|
||||
|
||||
</Modal>
|
||||
|
||||
)
|
||||
}
|
||||
19
src/react/pages/editDataModal.tsx
Normal file
19
src/react/pages/editDataModal.tsx
Normal file
@ -0,0 +1,19 @@
|
||||
export default function EditDataModal({currentDb}) {
|
||||
if (currentDb) {
|
||||
|
||||
return (
|
||||
<div>
|
||||
<h1>Edit Data</h1>
|
||||
<form>
|
||||
<label htmlFor="name">Name</label>
|
||||
<input type="text" id="name" name="name"/>
|
||||
<label htmlFor="value">Value</label>
|
||||
<input type="text" id="value" name="value"/>
|
||||
<button type="submit">Save</button>
|
||||
</form>
|
||||
</div>
|
||||
)
|
||||
} else {
|
||||
return <h1>Nothing Selected</h1>
|
||||
}
|
||||
}
|
||||
@ -3,7 +3,7 @@ import React from "react";
|
||||
import {useDoc, usePouch} from "use-pouchdb";
|
||||
import {IconPencilBolt, IconTrash} from "@tabler/icons-react";
|
||||
|
||||
export default function ManageDiagramsModal({openCreate, manageOpened, closeManage}) {
|
||||
export default function ManageDiagramsModal({setDbName, openCreate, manageOpened, closeManage}) {
|
||||
const {doc: diagram, error} = useDoc('directory', {}, {_id: 'directory', diagrams: []});
|
||||
const [selected, setSelected] = React.useState(null);
|
||||
const db = usePouch();
|
||||
@ -30,7 +30,11 @@ export default function ManageDiagramsModal({openCreate, manageOpened, closeMana
|
||||
</Card.Section>
|
||||
<Card.Section>
|
||||
<Group justify="space-evenly">
|
||||
<Button leftSection={<IconPencilBolt size={16}/>} size="xs">Select</Button>
|
||||
<Button
|
||||
onClick={() => {
|
||||
setDbName(diagram._id)
|
||||
}}
|
||||
leftSection={<IconPencilBolt size={16}/>} size="xs">Select</Button>
|
||||
<Button bg="red" size="xs"><IconTrash size={16}/></Button>
|
||||
</Group>
|
||||
</Card.Section>
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
//import VrApp from '../../vrApp';
|
||||
import VrApp from '../../vrApp';
|
||||
import React, {useEffect, useState} from "react";
|
||||
import {Affix, Burger, Group, Menu} from "@mantine/core";
|
||||
import VrTemplate from "../vrTemplate";
|
||||
@ -9,9 +9,28 @@ import ManageDiagramsModal from "./manageDiagramsModal";
|
||||
import {useNavigate} from "react-router-dom";
|
||||
import {useDisclosure} from "@mantine/hooks";
|
||||
|
||||
let vrApp: VrApp = null;
|
||||
|
||||
export default function VrExperience() {
|
||||
const [createOpened, {open: openCreate, close: closeCreate}] = useDisclosure(false);
|
||||
const [manageOpened, {open: openManage, close: closeManage}] = useDisclosure(false);
|
||||
const [currentDb, setCurrentDb] = useState(null);
|
||||
const [dbName, setDbName] = useState('vr');
|
||||
useEffect(() => {
|
||||
if (vrApp && dbName) {
|
||||
console.log('here');
|
||||
console.log(dbName);
|
||||
try {
|
||||
vrApp.setDb(dbName).then((db) => {
|
||||
setCurrentDb(db);
|
||||
console.log(db);
|
||||
});
|
||||
} catch (err) {
|
||||
console.log(err);
|
||||
}
|
||||
closeManage();
|
||||
}
|
||||
}, [dbName]);
|
||||
useEffect(() => {
|
||||
const data = window.localStorage.getItem('createOpened');
|
||||
if (data === 'true') {
|
||||
@ -20,6 +39,7 @@ export default function VrExperience() {
|
||||
navigator.xr.isSessionSupported('immersive-vr').then((supported) => {
|
||||
setImmersiveDisabled(!supported);
|
||||
});
|
||||
vrApp = new VrApp(document.getElementById('vrCanvas') as HTMLCanvasElement);
|
||||
}, []);
|
||||
useEffect(() => {
|
||||
console.log('Create Opened: ', createOpened);
|
||||
@ -30,7 +50,7 @@ export default function VrExperience() {
|
||||
const navigate = useNavigate();
|
||||
|
||||
const availableInFree = () => {
|
||||
return null
|
||||
return null;
|
||||
}
|
||||
const availableInBasic = () => {
|
||||
return <Group w={50}>Basic</Group>
|
||||
@ -55,12 +75,14 @@ export default function VrExperience() {
|
||||
const manageModal = () => {
|
||||
if (manageOpened) {
|
||||
return <ManageDiagramsModal openCreate={openCreate}
|
||||
manageOpened={manageOpened} closeManage={closeManage}/>
|
||||
manageOpened={manageOpened}
|
||||
closeManage={closeManage}
|
||||
setDbName={setDbName}/>
|
||||
} else {
|
||||
return <></>
|
||||
}
|
||||
}
|
||||
console.log('VrExperience');
|
||||
|
||||
return (
|
||||
<React.StrictMode>
|
||||
<VrTemplate>
|
||||
@ -122,9 +144,7 @@ export default function VrExperience() {
|
||||
</Menu.Dropdown>
|
||||
</Menu>
|
||||
</Affix>
|
||||
<canvas id="gameCanvas" style={{width: '100%', height: '100vh'}}/>
|
||||
|
||||
|
||||
<canvas id="vrCanvas" style={{width: '100%', height: '100vh'}}/>
|
||||
</VrTemplate>
|
||||
</React.StrictMode>
|
||||
)
|
||||
|
||||
@ -4,13 +4,13 @@ import React from "react";
|
||||
import {theme} from "./theme";
|
||||
import {Provider} from "use-pouchdb";
|
||||
import PouchDB from 'pouchdb';
|
||||
import {DEFAULT_DB_NAME} from "../util/constants";
|
||||
|
||||
const db = new PouchDB('mydb');
|
||||
const db = new PouchDB(DEFAULT_DB_NAME);
|
||||
export default function VrTemplate(props: { children: React.ReactNode }) {
|
||||
return (
|
||||
<Provider pouchdb={db}>
|
||||
<MantineProvider defaultColorScheme="dark" theme={theme}>
|
||||
|
||||
<Container fluid={true}>
|
||||
{props.children}
|
||||
</Container>
|
||||
|
||||
1
src/util/constants.ts
Normal file
1
src/util/constants.ts
Normal file
@ -0,0 +1 @@
|
||||
export const DEFAULT_DB_NAME = "mydb";
|
||||
@ -1,19 +0,0 @@
|
||||
export function buildQuestLink() {
|
||||
/*
|
||||
<div id="questLaunch"><a href="https://www.oculus.com/open_url/?url=https://www.deepdiagram.com/" target="_blank">Launch
|
||||
On Quest</a>
|
||||
</div>
|
||||
*/
|
||||
const div = document.createElement("div");
|
||||
div.id = "questLaunch";
|
||||
const a = document.createElement("a");
|
||||
a.href = "https://www.oculus.com/open_url/?url=" + window.location.href;
|
||||
a.target = "_blank";
|
||||
a.innerText = "Launch On Quest";
|
||||
div.appendChild(a);
|
||||
const main = document.querySelector('#main');
|
||||
if (main) {
|
||||
//main.appendChild(div);
|
||||
}
|
||||
|
||||
}
|
||||
22
src/vrApp.ts
22
src/vrApp.ts
@ -4,13 +4,12 @@ import {DiagramManager} from "./diagram/diagramManager";
|
||||
import log, {Logger} from "loglevel";
|
||||
import {CustomEnvironment} from "./util/customEnvironment";
|
||||
import {Spinner} from "./objects/spinner";
|
||||
import {PouchdbPersistenceManager} from "./integration/database/pouchdbPersistenceManager";
|
||||
import {addSceneInspector} from "./util/functions/sceneInspector";
|
||||
import {groundMeshObserver} from "./util/functions/groundMeshObserver";
|
||||
import {buildQuestLink} from "./util/functions/buildQuestLink";
|
||||
import {exportGltf} from "./util/functions/exportGltf";
|
||||
import {DefaultScene} from "./defaultScene";
|
||||
import {Introduction} from "./tutorial/introduction";
|
||||
import {PouchData} from "./integration/database/pouchData";
|
||||
|
||||
const webGpu = false;
|
||||
|
||||
@ -18,7 +17,9 @@ log.setLevel('error', false);
|
||||
export default class VrApp {
|
||||
//preTasks = [havokModule];
|
||||
private logger: Logger = log.getLogger('App');
|
||||
private _canvas: HTMLCanvasElement
|
||||
private _canvas: HTMLCanvasElement;
|
||||
private _db: PouchData;
|
||||
|
||||
|
||||
constructor(canvas: HTMLCanvasElement) {
|
||||
this._canvas = canvas;
|
||||
@ -27,6 +28,10 @@ export default class VrApp {
|
||||
});
|
||||
}
|
||||
|
||||
public async setDb(dbname: string) {
|
||||
this._db.setDb(dbname);
|
||||
return this._db;
|
||||
}
|
||||
public async initialize(scene: Scene) {
|
||||
setMainCamera(scene);
|
||||
const spinner = new Spinner();
|
||||
@ -35,7 +40,9 @@ export default class VrApp {
|
||||
const diagramManager = new DiagramManager(diagramReadyObservable);
|
||||
diagramReadyObservable.add((ready) => {
|
||||
if (ready) {
|
||||
initDb(diagramManager);
|
||||
const db = new PouchData();
|
||||
db.setDiagramManager(diagramManager);
|
||||
this._db = db;
|
||||
} else {
|
||||
this.logger.error('DiagramManager not ready');
|
||||
}
|
||||
@ -79,7 +86,7 @@ export default class VrApp {
|
||||
});
|
||||
}
|
||||
}
|
||||
buildQuestLink();
|
||||
|
||||
function setMainCamera(scene: Scene) {
|
||||
const CAMERA_NAME = 'Main Camera';
|
||||
const camera: FreeCamera = new FreeCamera(CAMERA_NAME,
|
||||
@ -87,11 +94,6 @@ function setMainCamera(scene: Scene) {
|
||||
scene.setActiveCameraByName(CAMERA_NAME);
|
||||
}
|
||||
|
||||
async function initDb(diagramManager: DiagramManager) {
|
||||
const db = new PouchdbPersistenceManager();
|
||||
db.setDiagramManager(diagramManager);
|
||||
await db.initialize();
|
||||
}
|
||||
|
||||
function initEnvironment(diagramManager: DiagramManager, spinner: Spinner) {
|
||||
const environment = new CustomEnvironment("default", diagramManager.config);
|
||||
|
||||
Loading…
Reference in New Issue
Block a user