@inweb/viewer-visualize 26.10.3 → 26.10.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1266,6 +1266,161 @@
1266
1266
  }
1267
1267
  }
1268
1268
 
1269
+ class OdJoyStickDragger {
1270
+ constructor(global, container, callback, canvasElement) {
1271
+ this.hasEventListeners = false;
1272
+ const internalLineWidth = 2;
1273
+ const internalStrokeColor = "#003300";
1274
+ const externalLineWidth = 2;
1275
+ const externalStrokeColor = "#35436E";
1276
+ this.container = container;
1277
+ this.container.style.touchAction = "none";
1278
+ this.canvas = document.createElement("canvas");
1279
+ this.canvas.id = "odJoyStickCanvas";
1280
+ this.canvas.width = 200;
1281
+ this.canvas.height = 200;
1282
+ this.container.appendChild(this.canvas);
1283
+ const context = this.canvas.getContext("2d");
1284
+ let pressed = 0;
1285
+ const circumference = 2 * Math.PI;
1286
+ const internalRadius = (this.canvas.width - (this.canvas.width / 2 + 10)) / 2;
1287
+ const maxMoveStick = internalRadius + 5;
1288
+ const externalRadius = internalRadius + 30;
1289
+ const centerX = this.canvas.width / 2;
1290
+ const centerY = this.canvas.height / 2;
1291
+ let movedX = centerX;
1292
+ let movedY = centerY;
1293
+ this.onMouseDown = () => {
1294
+ event.preventDefault();
1295
+ pressed = 1;
1296
+ };
1297
+ this.onMouseMove = (event) => {
1298
+ event.preventDefault();
1299
+ if (pressed === 1) {
1300
+ movedX = event.pageX;
1301
+ movedY = event.pageY;
1302
+ if (this.canvas.offsetParent && this.canvas.offsetParent.tagName.toUpperCase() === "BODY") {
1303
+ movedX -= this.canvas.offsetLeft;
1304
+ movedY -= this.canvas.offsetTop;
1305
+ }
1306
+ else if (this.canvas.offsetParent) {
1307
+ movedX -= this.canvas.offsetParent.offsetLeft;
1308
+ movedY -= this.canvas.offsetParent.offsetTop;
1309
+ }
1310
+ context.clearRect(0, 0, this.canvas.width, this.canvas.height);
1311
+ this.drawExternal();
1312
+ this.drawInternal();
1313
+ callback({
1314
+ x: 100 * ((movedX - centerX) / maxMoveStick),
1315
+ y: 100 * ((movedY - centerY) / maxMoveStick) * -1,
1316
+ global: global,
1317
+ });
1318
+ }
1319
+ };
1320
+ this.onMouseUp = () => {
1321
+ event.preventDefault();
1322
+ pressed = 0;
1323
+ movedX = centerX;
1324
+ movedY = centerY;
1325
+ context.clearRect(0, 0, this.canvas.width, this.canvas.height);
1326
+ this.drawExternal();
1327
+ this.drawInternal();
1328
+ callback({
1329
+ x: 100 * ((movedX - centerX) / maxMoveStick),
1330
+ y: 100 * ((movedY - centerY) / maxMoveStick) * -1,
1331
+ global: global,
1332
+ });
1333
+ };
1334
+ this.drawExternal = () => {
1335
+ context.beginPath();
1336
+ context.arc(centerX, centerY, externalRadius, 0, circumference, false);
1337
+ context.lineWidth = externalLineWidth;
1338
+ context.strokeStyle = externalStrokeColor;
1339
+ context.globalAlpha = 0.5;
1340
+ context.stroke();
1341
+ };
1342
+ this.drawInternal = () => {
1343
+ context.beginPath();
1344
+ if (movedX < internalRadius) {
1345
+ movedX = maxMoveStick;
1346
+ }
1347
+ if (movedX + internalRadius > this.canvas.width) {
1348
+ movedX = this.canvas.width - maxMoveStick;
1349
+ }
1350
+ if (movedY < internalRadius) {
1351
+ movedY = maxMoveStick;
1352
+ }
1353
+ if (movedY + internalRadius > this.canvas.height) {
1354
+ movedY = this.canvas.height - maxMoveStick;
1355
+ }
1356
+ context.arc(movedX, movedY, internalRadius, 0, circumference, false);
1357
+ context.fillStyle = externalStrokeColor;
1358
+ context.lineWidth = internalLineWidth;
1359
+ context.strokeStyle = internalStrokeColor;
1360
+ context.globalAlpha = 0.5;
1361
+ context.fill();
1362
+ context.stroke();
1363
+ };
1364
+ const addEventListeners = () => {
1365
+ if (!this.hasEventListeners) {
1366
+ this.canvas.addEventListener("pointerdown", this.onMouseDown, false);
1367
+ document.addEventListener("pointermove", this.onMouseMove, false);
1368
+ document.addEventListener("pointerup", this.onMouseUp, false);
1369
+ this.hasEventListeners = true;
1370
+ }
1371
+ };
1372
+ const removeEventListeners = () => {
1373
+ if (this.hasEventListeners) {
1374
+ this.canvas.removeEventListener("pointerdown", this.onMouseDown, false);
1375
+ document.removeEventListener("pointermove", this.onMouseMove, false);
1376
+ document.removeEventListener("pointerup", this.onMouseUp, false);
1377
+ this.hasEventListeners = false;
1378
+ }
1379
+ };
1380
+ const updateContainerPosition = () => {
1381
+ if (canvasElement) {
1382
+ const rect = canvasElement.getBoundingClientRect();
1383
+ this.container.style.top = `${rect.height - 200}px`;
1384
+ this.container.style.left = `${rect.left}px`;
1385
+ this.container.style.width = `200px`;
1386
+ this.container.style.height = `200px`;
1387
+ }
1388
+ };
1389
+ const updateVisibility = () => {
1390
+ const isMobile = /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent);
1391
+ const isNarrowScreen = window.innerWidth < 1024;
1392
+ const shouldShow = isMobile || isNarrowScreen;
1393
+ if (shouldShow) {
1394
+ this.container.style.display = "block";
1395
+ addEventListeners();
1396
+ }
1397
+ else {
1398
+ this.container.style.display = "none";
1399
+ removeEventListeners();
1400
+ }
1401
+ };
1402
+ this.onResize = () => {
1403
+ updateVisibility();
1404
+ setTimeout(updateContainerPosition, 500);
1405
+ };
1406
+ updateVisibility();
1407
+ updateContainerPosition();
1408
+ window.addEventListener("resize", this.onResize, false);
1409
+ this.drawExternal();
1410
+ this.drawInternal();
1411
+ }
1412
+ cleanup() {
1413
+ window.removeEventListener("resize", this.onResize, false);
1414
+ if (this.hasEventListeners) {
1415
+ this.canvas.removeEventListener("pointerdown", this.onMouseDown, false);
1416
+ document.removeEventListener("pointermove", this.onMouseMove, false);
1417
+ document.removeEventListener("pointerup", this.onMouseUp, false);
1418
+ this.hasEventListeners = false;
1419
+ }
1420
+ this.canvas.remove();
1421
+ }
1422
+ }
1423
+
1269
1424
  const FocalLengthConst$1 = 42.0;
1270
1425
  const calcFocalLength$1 = (lensLength, fieldWidth, fieldHeight) => {
1271
1426
  return (lensLength / FocalLengthConst$1) * Math.sqrt(fieldWidth * fieldWidth + fieldHeight * fieldHeight);
@@ -1275,15 +1430,19 @@
1275
1430
  super(subject);
1276
1431
  this.viewer = undefined;
1277
1432
  this.multiplier = 5;
1278
- this.speed = 1;
1433
+ this.baseSpeed = 1;
1279
1434
  this.keyPressMap = new Set();
1280
1435
  this.keydown = this.keydown.bind(this);
1281
1436
  this.keyup = this.keyup.bind(this);
1282
1437
  this.lastFrameTS = 0;
1438
+ this.lastFrameJoyStickTS = 0;
1283
1439
  this.animationId = undefined;
1284
1440
  this.processMovement = this.processMovement.bind(this);
1441
+ this.processJoyStickMovement = this.processJoyStickMovement.bind(this);
1285
1442
  this.deltaAngle = Math.PI / 3600;
1286
1443
  this.autoSelect = true;
1444
+ this.isJoyStickMoving = false;
1445
+ this.addJoyStickDragger();
1287
1446
  }
1288
1447
  initialize() {
1289
1448
  super.initialize();
@@ -1294,7 +1453,7 @@
1294
1453
  this.viewer.setEnableWCS(false);
1295
1454
  const view = this.viewer.activeView;
1296
1455
  const maxDimension = this.getMaxDimension(view);
1297
- this.speed = maxDimension / 30000;
1456
+ this.baseSpeed = maxDimension / 30000;
1298
1457
  this.subject.emitEvent({ type: "walkstart" });
1299
1458
  this.viewParams = this.getViewParams();
1300
1459
  this.setViewParams(this.viewParams);
@@ -1334,6 +1493,8 @@
1334
1493
  }
1335
1494
  this.subject.update(true);
1336
1495
  this.subject.options.enableZoomWheel = this.enableZoomWheelPreviousValue;
1496
+ this.joyStickOverlayElement.remove();
1497
+ this.joyStickDragger.cleanup();
1337
1498
  }
1338
1499
  keydown(ev) {
1339
1500
  switch (ev.code) {
@@ -1375,31 +1536,32 @@
1375
1536
  this.animationId = requestAnimationFrame(this.processMovement);
1376
1537
  if (this.lastFrameTS !== 0) {
1377
1538
  const deltaTS = timestamp - this.lastFrameTS;
1378
- const currentDelta = this.multiplier * deltaTS * this.speed;
1379
- for (const keyCode of this.keyPressMap) {
1380
- switch (keyCode) {
1381
- case "KeyW":
1382
- this.moveForward(currentDelta);
1383
- break;
1384
- case "KeyS":
1385
- this.moveBackward(currentDelta);
1386
- break;
1387
- case "KeyA":
1388
- this.cameraWalker.moveLeft(currentDelta);
1389
- break;
1390
- case "KeyD":
1391
- this.cameraWalker.moveRight(currentDelta);
1392
- break;
1393
- case "KeyQ":
1394
- this.cameraWalker.moveUp(currentDelta);
1395
- break;
1396
- case "KeyE":
1397
- this.cameraWalker.moveDown(currentDelta);
1398
- break;
1399
- }
1539
+ if (deltaTS > 0) {
1540
+ const currentDelta = this.multiplier * deltaTS * this.baseSpeed;
1541
+ Array.from(this.keyPressMap).forEach((keyCode) => {
1542
+ switch (keyCode) {
1543
+ case "KeyW":
1544
+ this.moveForward(currentDelta);
1545
+ break;
1546
+ case "KeyS":
1547
+ this.moveBackward(currentDelta);
1548
+ break;
1549
+ case "KeyA":
1550
+ this.cameraWalker.moveLeft(currentDelta);
1551
+ break;
1552
+ case "KeyD":
1553
+ this.cameraWalker.moveRight(currentDelta);
1554
+ break;
1555
+ case "KeyQ":
1556
+ this.cameraWalker.moveUp(currentDelta);
1557
+ break;
1558
+ case "KeyE":
1559
+ this.cameraWalker.moveDown(currentDelta);
1560
+ break;
1561
+ }
1562
+ });
1563
+ this.proceedChangeCamera();
1400
1564
  }
1401
- this.subject.update();
1402
- this.subject.emitEvent({ type: "changecamera" });
1403
1565
  }
1404
1566
  this.lastFrameTS = timestamp;
1405
1567
  }
@@ -1485,6 +1647,58 @@
1485
1647
  const volume = [xmax - xmin, ymax - ymin, zmax - zmin];
1486
1648
  return Math.max(...volume);
1487
1649
  }
1650
+ addJoyStickDragger() {
1651
+ this.joyStickOverlayElement = document.createElement("div");
1652
+ this.joyStickOverlayElement.id = "joyStickDiv";
1653
+ this.joyStickOverlayElement.style.background = "rgba(0,0,0,0)";
1654
+ this.joyStickOverlayElement.style.position = "fixed";
1655
+ this.joyStickOverlayElement.style.zIndex = "0";
1656
+ document.body.appendChild(this.joyStickOverlayElement);
1657
+ this.joyStickDragger = new OdJoyStickDragger(this, this.joyStickOverlayElement, (stickData) => {
1658
+ if (Math.sqrt(stickData.x * stickData.x + stickData.y * stickData.y) > 20) {
1659
+ this.lastJoyStickCoord = { x: stickData.x, y: stickData.y };
1660
+ if (!this.animationId && !this.isJoyStickMoving) {
1661
+ this.isJoyStickMoving = true;
1662
+ this.processJoyStickMovement(0);
1663
+ }
1664
+ }
1665
+ else {
1666
+ this.isJoyStickMoving = false;
1667
+ window.cancelAnimationFrame(this.animationId);
1668
+ this.animationId = undefined;
1669
+ this.lastFrameJoyStickTS = 0;
1670
+ }
1671
+ }, this.m_module.canvas);
1672
+ }
1673
+ processJoyStickMovement(timestamp) {
1674
+ if (!this.isJoyStickMoving)
1675
+ return;
1676
+ this.animationId = requestAnimationFrame(this.processJoyStickMovement);
1677
+ if (this.lastFrameJoyStickTS !== 0) {
1678
+ const deltaTS = timestamp - this.lastFrameJoyStickTS;
1679
+ if (deltaTS > 0) {
1680
+ const maxJoystickDistance = 100;
1681
+ const forward = this.lastJoyStickCoord.y / maxJoystickDistance;
1682
+ const right = this.lastJoyStickCoord.x / maxJoystickDistance;
1683
+ const currentDelta = this.multiplier * deltaTS * this.baseSpeed;
1684
+ this.moveTotal(currentDelta, forward, right);
1685
+ }
1686
+ }
1687
+ this.lastFrameJoyStickTS = timestamp;
1688
+ }
1689
+ moveTotal(currentDelta, forward, right) {
1690
+ if (forward !== 0) {
1691
+ this.moveForward(currentDelta * forward);
1692
+ }
1693
+ if (right !== 0) {
1694
+ this.cameraWalker.moveRight(currentDelta * right);
1695
+ }
1696
+ this.proceedChangeCamera();
1697
+ }
1698
+ proceedChangeCamera() {
1699
+ this.subject.update();
1700
+ this.subject.emitEvent({ type: "changecamera" });
1701
+ }
1488
1702
  }
1489
1703
 
1490
1704
  const FocalLengthConst = 42.0;
@@ -1501,10 +1715,34 @@
1501
1715
  this.keydown = this.keydown.bind(this);
1502
1716
  this.keyup = this.keyup.bind(this);
1503
1717
  this.lastFrameTS = 0;
1718
+ this.lastFrameJoyStickTS = 0;
1504
1719
  this.animationId = undefined;
1505
1720
  this.processMovement = this.processMovement.bind(this);
1721
+ this.processJoyMovement = this.processJoyMovement.bind(this);
1506
1722
  this.deltaAngle = Math.PI / 3600;
1507
1723
  this.autoSelect = true;
1724
+ this.moving = false;
1725
+ this.joyStickOverlayElement = document.createElement("div");
1726
+ this.joyStickOverlayElement.id = "joyStickDiv";
1727
+ this.joyStickOverlayElement.style.background = "rgba(0,0,0,0)";
1728
+ this.joyStickOverlayElement.style.position = "fixed";
1729
+ this.joyStickOverlayElement.style.zIndex = "0";
1730
+ document.body.appendChild(this.joyStickOverlayElement);
1731
+ this.joyStickDragger = new OdJoyStickDragger(this, this.joyStickOverlayElement, (stickData) => {
1732
+ if (Math.sqrt(stickData.x * stickData.x + stickData.y * stickData.y) > 20) {
1733
+ this.lastJoyStickCoord = { x: stickData.x, y: stickData.y };
1734
+ if (!this.animationId && !this.moving) {
1735
+ this.moving = true;
1736
+ this.processJoyMovement(0);
1737
+ }
1738
+ }
1739
+ else {
1740
+ this.moving = false;
1741
+ window.cancelAnimationFrame(this.animationId);
1742
+ this.animationId = undefined;
1743
+ this.lastFrameJoyStickTS = 0;
1744
+ }
1745
+ }, this.m_module.canvas);
1508
1746
  }
1509
1747
  initialize() {
1510
1748
  super.initialize();
@@ -1555,6 +1793,8 @@
1555
1793
  }
1556
1794
  this.subject.update(true);
1557
1795
  this.subject.options.enableZoomWheel = this.enableZoomWheelPreviousValue;
1796
+ this.joyStickOverlayElement.remove();
1797
+ this.joyStickDragger.cleanup();
1558
1798
  }
1559
1799
  keydown(ev) {
1560
1800
  switch (ev.code) {
@@ -1685,6 +1925,37 @@
1685
1925
  const volume = [xmax - xmin, ymax - ymin, zmax - zmin];
1686
1926
  return Math.max(...volume);
1687
1927
  }
1928
+ processJoyMovement(timestamp) {
1929
+ if (!this.moving)
1930
+ return;
1931
+ this.animationId = requestAnimationFrame(this.processJoyMovement);
1932
+ if (this.lastFrameJoyStickTS !== 0) {
1933
+ const deltaTS = timestamp - this.lastFrameJoyStickTS;
1934
+ if (deltaTS > 0) {
1935
+ const maxJoystickDistance = 100;
1936
+ const forward = this.lastJoyStickCoord.y / maxJoystickDistance;
1937
+ const right = this.lastJoyStickCoord.x / maxJoystickDistance;
1938
+ const currentDelta = this.multiplier * deltaTS * this.speed;
1939
+ this.moveTotal(currentDelta, forward, right);
1940
+ }
1941
+ }
1942
+ this.lastFrameJoyStickTS = timestamp;
1943
+ }
1944
+ moveTotal(currentDelta, forward, right) {
1945
+ if (forward !== 0) {
1946
+ if (forward > 0) {
1947
+ this.cameraFlyer.moveForward(currentDelta * forward);
1948
+ }
1949
+ else {
1950
+ this.cameraFlyer.moveBackward(currentDelta * Math.abs(forward));
1951
+ }
1952
+ }
1953
+ if (right !== 0) {
1954
+ this.cameraFlyer.moveRight(currentDelta * right);
1955
+ }
1956
+ this.subject.update();
1957
+ this.subject.emitEvent({ type: "changecamera" });
1958
+ }
1688
1959
  }
1689
1960
 
1690
1961
  class OdBaseCuttingPlaneDragger extends OdBaseDragger {