summaryrefslogtreecommitdiff
path: root/src/graph.js
diff options
context:
space:
mode:
Diffstat (limited to 'src/graph.js')
-rw-r--r--src/graph.js43
1 files changed, 37 insertions, 6 deletions
diff --git a/src/graph.js b/src/graph.js
index 880caab..84d9d79 100644
--- a/src/graph.js
+++ b/src/graph.js
@@ -6,9 +6,13 @@ import { randint, choice, pad } from "./utils/index.js";
const IMG_SCALE = 16;
const MAIN_IMG_SCALE = 80;
+const PAINTING_SCALE = 30;
+const VIDEO_SCALE = 40;
const OBJECT_SCALE = 10;
-export default function buildGraph({ db, objects, handlers }) {
+const PAINTINGS = new Set([2, 10, 21, 22, 23, 24, 27, 40, 42]);
+
+export default function buildGraph({ db, handlers }) {
const linkable = {};
const groups = {};
const data = { nodes: [], links: [] };
@@ -21,7 +25,7 @@ export default function buildGraph({ db, objects, handlers }) {
db.page.forEach((item, index) => {
const node = {
- title: pad(index + 1) + " " + item.title,
+ title: item.short_title,
id: index,
data: item,
groups: [],
@@ -77,6 +81,7 @@ export default function buildGraph({ db, objects, handlers }) {
const highlightNodes = new Set();
const highlightLinks = new Set();
let selectedNode = null;
+ const objects = [];
/** build group */
@@ -88,6 +93,7 @@ export default function buildGraph({ db, objects, handlers }) {
.nodeThreeObject((node) => {
let sprite, material, texture, video;
if (node.data.object) {
+ objects.push({ id: node.id, object: node.data.object });
const object = node.data.object;
var box = new THREE.Box3().setFromObject(object);
var center = new THREE.Vector3();
@@ -96,7 +102,8 @@ export default function buildGraph({ db, objects, handlers }) {
object.scale.set(OBJECT_SCALE, OBJECT_SCALE, OBJECT_SCALE);
return object;
} else if (node.data.thumbnail?.uri) {
- if (node.data.thumbnail.type === "video") {
+ const isVideo = node.data.thumbnail.type === "video";
+ if (isVideo) {
video = document.createElement("video");
video.src = node.data.thumbnail.uri;
video.muted = true;
@@ -113,6 +120,10 @@ export default function buildGraph({ db, objects, handlers }) {
sprite = new THREE.Sprite(material);
if (node.id === 0) {
sprite.scale.set(MAIN_IMG_SCALE, MAIN_IMG_SCALE / aspect);
+ } else if (PAINTINGS.has(node.id + 1)) {
+ sprite.scale.set(PAINTING_SCALE, PAINTING_SCALE / aspect);
+ } else if (isVideo) {
+ sprite.scale.set(VIDEO_SCALE, VIDEO_SCALE / aspect);
} else {
sprite.scale.set(IMG_SCALE, IMG_SCALE / aspect);
}
@@ -145,10 +156,16 @@ export default function buildGraph({ db, objects, handlers }) {
})
.linkWidth((link) => (highlightLinks.has(link) ? 4 : 1));
- // TrackballControls
graph.controls().addEventListener("change", () => {
- const position = graph.cameraPosition();
- // console.log(position);
+ const quaternion = graph.camera().quaternion;
+ const { axis, angle } = getAxisAndAngelFromQuaternion(quaternion);
+ objects.forEach(({ id, object }) => {
+ object.setRotationFromQuaternion(quaternion);
+ // the clock object is turned 90 degrees
+ if (id === 32) {
+ object.rotateY(Math.PI / 2);
+ }
+ });
});
const updateHighlight = () => {
@@ -237,4 +254,18 @@ export default function buildGraph({ db, objects, handlers }) {
// stars();
}
+function getAxisAndAngelFromQuaternion(q) {
+ const angle = 2 * Math.acos(q.w);
+ var s;
+ if (1 - q.w * q.w < 0.000001) {
+ // test to avoid divide by zero, s is always positive due to sqrt
+ // if s close to zero then direction of axis not important
+ // http://www.euclideanspace.com/maths/geometry/rotations/conversions/quaternionToAngle/
+ s = 1;
+ } else {
+ s = Math.sqrt(1 - q.w * q.w);
+ }
+ return { axis: new THREE.Vector3(q.x / s, q.y / s, q.z / s), angle };
+}
+
const commonGroups = (a, b) => union(a.groups, b.groups);