mirror of
https://github.com/legop3/MultiRoombaRover.git
synced 2026-09-16 01:21:20 -04:00
guhwuh
This commit is contained in:
File diff suppressed because one or more lines are too long
@@ -5,7 +5,7 @@
|
||||
<link rel="icon" type="image/svg+xml" href="/vite.svg" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>webui</title>
|
||||
<script type="module" crossorigin src="/assets/index-BgmPrDPA.js"></script>
|
||||
<script type="module" crossorigin src="/assets/index-DwtMH0qf.js"></script>
|
||||
<link rel="stylesheet" crossorigin href="/assets/index-Dk59njim.css">
|
||||
</head>
|
||||
<body>
|
||||
|
||||
@@ -1,5 +1,8 @@
|
||||
import { useEffect, useRef, useState } from 'react';
|
||||
import { useDriveControl } from '../context/DriveControlContext.jsx';
|
||||
|
||||
const SLIDER_THROTTLE_MS = 150;
|
||||
|
||||
function formatDegrees(value) {
|
||||
if (typeof value !== 'number' || Number.isNaN(value)) return '—';
|
||||
return `${value > 0 ? '+' : ''}${value.toFixed(1)}°`;
|
||||
@@ -20,15 +23,53 @@ export default function CameraServoPanel() {
|
||||
|
||||
if (!enabled) return null;
|
||||
|
||||
const [pendingAngle, setPendingAngle] = useState(value);
|
||||
const throttleRef = useRef(null);
|
||||
const draggingRef = useRef(false);
|
||||
|
||||
useEffect(() => {
|
||||
if (!draggingRef.current) {
|
||||
setPendingAngle(value);
|
||||
}
|
||||
}, [value]);
|
||||
|
||||
useEffect(
|
||||
() => () => {
|
||||
if (throttleRef.current) {
|
||||
clearTimeout(throttleRef.current);
|
||||
}
|
||||
},
|
||||
[],
|
||||
);
|
||||
|
||||
const step =
|
||||
typeof config?.nudgeDegrees === 'number' && config.nudgeDegrees > 0
|
||||
? config.nudgeDegrees
|
||||
: 1;
|
||||
|
||||
const scheduleSend = (next) => {
|
||||
if (throttleRef.current) {
|
||||
clearTimeout(throttleRef.current);
|
||||
}
|
||||
throttleRef.current = setTimeout(() => {
|
||||
servo.setAngle(next);
|
||||
}, SLIDER_THROTTLE_MS);
|
||||
};
|
||||
|
||||
const handleSlider = (event) => {
|
||||
const next = Number.parseFloat(event.target.value);
|
||||
if (Number.isNaN(next)) return;
|
||||
servo.setAngle(next);
|
||||
draggingRef.current = true;
|
||||
setPendingAngle(next);
|
||||
scheduleSend(next);
|
||||
};
|
||||
|
||||
const commitSlider = () => {
|
||||
draggingRef.current = false;
|
||||
if (throttleRef.current) {
|
||||
clearTimeout(throttleRef.current);
|
||||
}
|
||||
servo.setAngle(pendingAngle);
|
||||
};
|
||||
|
||||
const handleNudge = (direction) => {
|
||||
@@ -49,8 +90,11 @@ export default function CameraServoPanel() {
|
||||
min={min}
|
||||
max={max}
|
||||
step={0.5}
|
||||
value={value}
|
||||
value={pendingAngle}
|
||||
onChange={handleSlider}
|
||||
onMouseUp={commitSlider}
|
||||
onTouchEnd={commitSlider}
|
||||
onPointerUp={commitSlider}
|
||||
/>
|
||||
<div className="mt-1 flex justify-between text-xs text-slate-400">
|
||||
<span>{formatDegrees(min)}</span>
|
||||
|
||||
Reference in New Issue
Block a user