mirror of
https://github.com/legop3/MultiRoombaRover.git
synced 2026-09-15 17:12:59 -04:00
output rate limit and override gating
This commit is contained in:
File diff suppressed because one or more lines are too long
@@ -11,7 +11,7 @@
|
||||
<meta name="apple-mobile-web-app-status-bar-style" content="black-translucent" />
|
||||
<meta name="apple-mobile-web-app-title" content="Multi Roomba Rover" />
|
||||
<title>Multi Roomba Rover</title>
|
||||
<script type="module" crossorigin src="/assets/index-BU08RP3S.js"></script>
|
||||
<script type="module" crossorigin src="/assets/index-DlZ3NGp7.js"></script>
|
||||
<link rel="stylesheet" crossorigin href="/assets/index-BBEWYgmH.css">
|
||||
</head>
|
||||
<body>
|
||||
|
||||
@@ -73,6 +73,7 @@ export default function OvercurrentLimiterPanel() {
|
||||
<div className="surface text-[0.7rem] text-slate-400">
|
||||
<div>{`A charge ${overcurrentLimiter?.config?.meterAChargeSec}s · A decay ${overcurrentLimiter?.config?.meterADecaySec}s`}</div>
|
||||
<div>{`B charge ${overcurrentLimiter?.config?.meterBChargeSec}s · B decay ${overcurrentLimiter?.config?.meterBDecaySec}s`}</div>
|
||||
<div>{`Output rate ${overcurrentLimiter?.config?.outputRateMs}ms`}</div>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
@@ -142,6 +142,8 @@ export function ControlSystemProvider({ children }) {
|
||||
const driveSpeedsRef = useRef(state.drive.speeds);
|
||||
const auxValuesRef = useRef(state.aux);
|
||||
const limiterScaleToken = useMemo(() => JSON.stringify(overcurrentLimiter.scales), [overcurrentLimiter.scales]);
|
||||
const limiterDriveSentAtRef = useRef(0);
|
||||
const limiterAuxSentAtRef = useRef(0);
|
||||
|
||||
useEffect(() => {
|
||||
driveSpeedsRef.current = state.drive.speeds;
|
||||
@@ -152,19 +154,23 @@ export function ControlSystemProvider({ children }) {
|
||||
}, [state.aux]);
|
||||
|
||||
useEffect(() => {
|
||||
if (!pipeline.roverId || overcurrentLimiter.adminImmune) return;
|
||||
if (!pipeline.roverId || overcurrentLimiter.adminImmune || !overcurrentLimiter.isActive) return;
|
||||
const outputRateMs = Math.max(0, Number(overcurrentLimiter?.config?.outputRateMs) || 0);
|
||||
const now = typeof performance !== 'undefined' ? performance.now() : Date.now();
|
||||
const drive = driveSpeedsRef.current || { left: 0, right: 0 };
|
||||
const aux = auxValuesRef.current || { main: 0, side: 0, vacuum: 0 };
|
||||
const driveActive = Boolean(drive.left || drive.right);
|
||||
const auxActive = Boolean(aux.main || aux.side || aux.vacuum);
|
||||
if (!driveActive && !auxActive) return;
|
||||
if (driveActive) {
|
||||
if (driveActive && now - limiterDriveSentAtRef.current >= outputRateMs) {
|
||||
limiterDriveSentAtRef.current = now;
|
||||
pipeline.sendDriveDirect(drive);
|
||||
}
|
||||
if (auxActive) {
|
||||
if (auxActive && now - limiterAuxSentAtRef.current >= outputRateMs) {
|
||||
limiterAuxSentAtRef.current = now;
|
||||
pipeline.sendAuxMotors(aux);
|
||||
}
|
||||
}, [limiterScaleToken, overcurrentLimiter.adminImmune, pipeline]);
|
||||
}, [limiterScaleToken, overcurrentLimiter.adminImmune, overcurrentLimiter.config, overcurrentLimiter.isActive, pipeline]);
|
||||
|
||||
const setDriveVector = useCallback(
|
||||
(vector, meta = {}) => {
|
||||
|
||||
@@ -8,10 +8,11 @@ export const OVERCURRENT_GROUPS = [
|
||||
];
|
||||
|
||||
export const DEFAULT_OVERCURRENT_LIMITS = {
|
||||
meterAChargeSec: 3,
|
||||
meterAChargeSec: 9,
|
||||
meterADecaySec: 9,
|
||||
meterBChargeSec: 1,
|
||||
meterBDecaySec: 10,
|
||||
meterBChargeSec: 5,
|
||||
meterBDecaySec: 5,
|
||||
outputRateMs: 250,
|
||||
};
|
||||
|
||||
function createInitialMeters() {
|
||||
@@ -139,6 +140,7 @@ export function useOvercurrentLimiter(roverId, options = {}) {
|
||||
meters,
|
||||
overcurrent,
|
||||
scales,
|
||||
isActive: (scales?.drive?.left ?? 1) < 1 || (scales?.drive?.right ?? 1) < 1 || (scales?.aux?.main ?? 1) < 1 || (scales?.aux?.side ?? 1) < 1,
|
||||
config,
|
||||
adminImmune,
|
||||
}),
|
||||
@@ -150,6 +152,7 @@ export function applyDriveOvercurrentScale(speeds = {}, scales, adminImmune = fa
|
||||
if (adminImmune || !scales?.drive) return speeds;
|
||||
const leftScale = typeof scales.drive.left === 'number' ? scales.drive.left : 1;
|
||||
const rightScale = typeof scales.drive.right === 'number' ? scales.drive.right : 1;
|
||||
if (leftScale >= 0.999 && rightScale >= 0.999) return speeds;
|
||||
return {
|
||||
left: Math.round((speeds.left ?? 0) * leftScale),
|
||||
right: Math.round((speeds.right ?? 0) * rightScale),
|
||||
@@ -161,6 +164,7 @@ export function applyAuxOvercurrentScale(values = {}, scales, adminImmune = fals
|
||||
const mainScale = typeof scales.aux.main === 'number' ? scales.aux.main : 1;
|
||||
const sideScale = typeof scales.aux.side === 'number' ? scales.aux.side : 1;
|
||||
const vacuumScale = typeof scales.aux.vacuum === 'number' ? scales.aux.vacuum : 1;
|
||||
if (mainScale >= 0.999 && sideScale >= 0.999 && vacuumScale >= 0.999) return values;
|
||||
return {
|
||||
main: Math.round((values.main ?? 0) * mainScale),
|
||||
side: Math.round((values.side ?? 0) * sideScale),
|
||||
|
||||
Reference in New Issue
Block a user