Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adaptive Physics Time Step #989

Merged
merged 9 commits into from
Jun 29, 2024
Merged
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 12 additions & 4 deletions .github/workflows/FissionESLintFormat.yml
Original file line number Diff line number Diff line change
Expand Up @@ -28,17 +28,25 @@ jobs:
cd fission
npm run lint
continue-on-error: true
- name: Check EsLint
run: |
if [ ${{ steps.linter-validation.outcome }} == "success" ]; then
echo "EsLint Validation Passed"
else
echo "EsLint Validation Failed"
exit 1
fi
- name: Prettier
id: prettier-validation
run: |
cd fission
npm run prettier
continue-on-error: true
- name: Check Success
- name: Check Prettier
run: |
if [ ${{ steps.linter-validation.outcome }} == "success" ]; then
echo "Format Validation Passed"
if [ ${{ steps.prettier-validation.outcome }} == "success" ]; then
echo "Prettier Validation Passed"
else
echo "Format Validation Failed"
echo "Prettier Validation Failed"
exit 1
fi
6 changes: 3 additions & 3 deletions fission/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,12 @@
"scripts": {
"dev": "vite --open",
"build": "tsc && vite build",
"lint": "eslint . --ext ts,tsx --report-unused-disable-directives",
"preview": "vite preview --base=/fission/",
"test": "vitest",
"lint:fix": "bun run lint --fix || npm run lint --fix",
"lint": "eslint . --ext ts,tsx --report-unused-disable-directives",
"lint:fix": "eslint . --ext ts,tsx --report-unused-disable-directives --fix",
"prettier": "bun x prettier src --check || npx prettier src --check",
"prettier:fix": "bun run prettier --write || npm run prettier --write",
"prettier:fix": "bun x prettier src --write || npx prettier src --write",
"format": "(bun run prettier:fix && bun run lint:fix) || (npm run prettier:fix && npm run lint:fix)",
"build:prod": "tsc && vite build --base=/fission/",
"assetpack": "run-script-os",
Expand Down
10 changes: 5 additions & 5 deletions fission/src/Synthesis.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -49,11 +49,11 @@ import ScoringZonesPanel from "@/panels/configuring/scoring/ScoringZonesPanel"
import ZoneConfigPanel from "@/panels/configuring/scoring/ZoneConfigPanel"
import ScoreboardPanel from "@/panels/information/ScoreboardPanel"
import DriverStationPanel from "@/panels/simulation/DriverStationPanel"
import ManageAssembliesModal from '@/modals/spawning/ManageAssembliesModal.tsx';
import World from '@/systems/World.ts';
import { AddRobotsModal, AddFieldsModal, SpawningModal } from '@/modals/spawning/SpawningModals.tsx';
import ImportMirabufModal from '@/modals/mirabuf/ImportMirabufModal.tsx';
import ImportLocalMirabufModal from '@/modals/mirabuf/ImportLocalMirabufModal.tsx';
import ManageAssembliesModal from "@/modals/spawning/ManageAssembliesModal.tsx"
import World from "@/systems/World.ts"
import { AddRobotsModal, AddFieldsModal, SpawningModal } from "@/modals/spawning/SpawningModals.tsx"
import ImportMirabufModal from "@/modals/mirabuf/ImportMirabufModal.tsx"
import ImportLocalMirabufModal from "@/modals/mirabuf/ImportLocalMirabufModal.tsx"

const DEFAULT_MIRA_PATH = "/api/mira/Robots/Team 2471 (2018)_v7.mira"

Expand Down
3 changes: 2 additions & 1 deletion fission/src/mirabuf/MirabufParser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,8 @@ class MirabufParser {
}

// 1: Initial Rigidgroups from ancestorial breaks in joints
(Object.keys(assembly.data!.joints!.jointInstances!) as string[]).forEach(key => {
const jointInstanceKeys = Object.keys(assembly.data!.joints!.jointInstances!) as string[]
jointInstanceKeys.forEach(key => {
if (key != GROUNDED_JOINT_ID) {
const jInst = assembly.data!.joints!.jointInstances![key]
const [ancestorA, ancestorB] = this.FindAncestorialBreak(jInst.parentPart!, jInst.childPart!)
Expand Down
7 changes: 3 additions & 4 deletions fission/src/systems/input/InputSystem.ts
Original file line number Diff line number Diff line change
Expand Up @@ -121,10 +121,9 @@ class InputSystem extends WorldSystem {
}

// Returns true if two modifier states are identical
private static CompareModifiers(state1: ModifierState, state2: ModifierState) : boolean {
if (!state1 || !state2)
return false;

private static CompareModifiers(state1: ModifierState, state2: ModifierState): boolean {
if (!state1 || !state2) return false

return (
state1.alt == state2.alt &&
state1.ctrl == state2.ctrl &&
Expand Down
25 changes: 21 additions & 4 deletions fission/src/systems/physics/PhysicsSystem.ts
Original file line number Diff line number Diff line change
Expand Up @@ -31,8 +31,16 @@ const LAYER_GHOST = 10
// Please update this accordingly.
const COUNT_OBJECT_LAYERS = 11

export const SIMULATION_PERIOD = 1.0 / 120.0
const STANDARD_SUB_STEPS = 3
export const STANDARD_SIMULATION_PERIOD = 1.0 / 60.0
const MIN_SIMULATION_PERIOD = 1.0 / 120.0
const MAX_SIMULATION_PERIOD = 1.0 / 10.0
const STANDARD_SUB_STEPS = 2
const TIMESTEP_ADJUSTMENT = 0.0001

let lastDeltaT = STANDARD_SIMULATION_PERIOD
export function GetLastDeltaT(): number {
return lastDeltaT
}

// Friction constants
const FLOOR_FRICTION = 0.7
Expand Down Expand Up @@ -704,8 +712,17 @@ class PhysicsSystem extends WorldSystem {
return this._joltPhysSystem.GetBodyLockInterface().TryGetBody(bodyId)
}

public Update(_: number): void {
this._joltInterface.Step(SIMULATION_PERIOD, STANDARD_SUB_STEPS)
public Update(deltaT: number): void {
const diffDeltaT = deltaT - lastDeltaT
lastDeltaT = lastDeltaT + Math.min(TIMESTEP_ADJUSTMENT, Math.max(-TIMESTEP_ADJUSTMENT, diffDeltaT))

lastDeltaT = Math.min(MAX_SIMULATION_PERIOD, Math.max(MIN_SIMULATION_PERIOD, lastDeltaT))

const substeps = Math.max(1, Math.floor((STANDARD_SIMULATION_PERIOD / lastDeltaT) * STANDARD_SUB_STEPS))

console.log(`DeltaT: ${lastDeltaT.toFixed(5)}, Substeps: ${substeps}`)

this._joltInterface.Step(lastDeltaT, substeps)
}

public Destroy(): void {
Expand Down
8 changes: 4 additions & 4 deletions fission/src/systems/simulation/behavior/GenericArmBehavior.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,10 @@ import InputSystem, { emptyModifierState } from "@/systems/input/InputSystem"
class GenericArmBehavior extends Behavior {
private _hingeDriver: HingeDriver

private _positiveInput: string;
private _negativeInput: string;
private _rotationalSpeed = 6;
private _positiveInput: string
private _negativeInput: string

private _rotationalSpeed = 6

constructor(hingeDriver: HingeDriver, hingeStimulus: HingeStimulus, jointIndex: number) {
super([hingeDriver], [hingeStimulus])
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ class GenericElevatorBehavior extends Behavior {
private _positiveInput: string
private _negativeInput: string

private _linearSpeed = 2.5;
private _linearSpeed = 2.5

constructor(sliderDriver: SliderDriver, sliderStimulus: SliderStimulus, jointIndex: number) {
super([sliderDriver], [sliderStimulus])
Expand All @@ -35,11 +35,11 @@ class GenericElevatorBehavior extends Behavior {

// Changes the elevators target position
moveElevator(linearVelocity: number) {
this._sliderDriver.targetVelocity = linearVelocity;
this._sliderDriver.targetVelocity = linearVelocity
}

public Update(_: number): void {
this.moveElevator(InputSystem.GetAxis(this._positiveInput, this._negativeInput)*this._linearSpeed);
this.moveElevator(InputSystem.GetAxis(this._positiveInput, this._negativeInput) * this._linearSpeed)
}
}

Expand Down
4 changes: 2 additions & 2 deletions fission/src/systems/simulation/driver/Driver.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ abstract class Driver {

export enum DriverControlMode {
Velocity = 0,
Position = 1
Position = 1,
}

export default Driver;
export default Driver
8 changes: 4 additions & 4 deletions fission/src/systems/simulation/driver/HingeDriver.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import Jolt from "@barclah/jolt-physics"
import Driver, { DriverControlMode } from "./Driver"
import { SIMULATION_PERIOD } from "@/systems/physics/PhysicsSystem"
import { GetLastDeltaT } from "@/systems/physics/PhysicsSystem"
import JOLT from "@/util/loading/JoltSyncLoader"

class HingeDriver extends Driver {
Expand All @@ -21,7 +21,7 @@ class HingeDriver extends Driver {
return this._targetAngle
}
public set targetAngle(rads: number) {
this._targetAngle = Math.max(this._constraint.GetLimitsMin(), Math.min(this._constraint.GetLimitsMax(), rads));
this._targetAngle = Math.max(this._constraint.GetLimitsMin(), Math.min(this._constraint.GetLimitsMax(), rads))
}

public set minTorqueLimit(nm: number) {
Expand Down Expand Up @@ -61,7 +61,7 @@ class HingeDriver extends Driver {
const springSettings = motorSettings.mSpringSettings

// These values were selected based on the suggestions of the documentation for stiff control.
springSettings.mFrequency = 20 * (1.0 / SIMULATION_PERIOD)
springSettings.mFrequency = 20 * (1.0 / GetLastDeltaT())
springSettings.mDamping = 0.995

motorSettings.mSpringSettings = springSettings
Expand All @@ -82,4 +82,4 @@ class HingeDriver extends Driver {
}
}

export default HingeDriver
export default HingeDriver
48 changes: 24 additions & 24 deletions fission/src/systems/simulation/driver/SliderDriver.ts
Original file line number Diff line number Diff line change
@@ -1,21 +1,20 @@
import Jolt from "@barclah/jolt-physics";
import Driver, { DriverControlMode } from "./Driver";
import { SIMULATION_PERIOD } from "@/systems/physics/PhysicsSystem";
import JOLT from "@/util/loading/JoltSyncLoader";
import Jolt from "@barclah/jolt-physics"
import Driver, { DriverControlMode } from "./Driver"
import { GetLastDeltaT } from "@/systems/physics/PhysicsSystem"
import JOLT from "@/util/loading/JoltSyncLoader"

class SliderDriver extends Driver {
private _constraint: Jolt.SliderConstraint

private _constraint: Jolt.SliderConstraint;

private _controlMode: DriverControlMode = DriverControlMode.Velocity;
private _targetVelocity: number = 0.0;
private _targetPosition: number = 0.0;
private _controlMode: DriverControlMode = DriverControlMode.Velocity
private _targetVelocity: number = 0.0
private _targetPosition: number = 0.0

public get targetVelocity(): number {
return this._targetVelocity;
return this._targetVelocity
}
public set targetVelocity(radsPerSec: number) {
this._targetVelocity = radsPerSec;
this._targetVelocity = radsPerSec
}

public get targetPosition(): number {
Expand All @@ -38,21 +37,21 @@ class SliderDriver extends Driver {
}

public get controlMode(): DriverControlMode {
return this._controlMode;
return this._controlMode
}

public set controlMode(mode: DriverControlMode) {
this._controlMode = mode;
this._controlMode = mode
switch (mode) {
case DriverControlMode.Velocity:
this._constraint.SetMotorState(JOLT.EMotorState_Velocity);
break;
this._constraint.SetMotorState(JOLT.EMotorState_Velocity)
break
case DriverControlMode.Position:
this._constraint.SetMotorState(JOLT.EMotorState_Position);
break;
this._constraint.SetMotorState(JOLT.EMotorState_Position)
break
default:
// idk
break;
break
}
}

Expand All @@ -63,21 +62,22 @@ class SliderDriver extends Driver {

const motorSettings = this._constraint.GetMotorSettings()
const springSettings = motorSettings.mSpringSettings
springSettings.mFrequency = 20 * (1.0 / SIMULATION_PERIOD)
springSettings.mFrequency = 20 * (1.0 / GetLastDeltaT())
springSettings.mDamping = 0.999

motorSettings.mSpringSettings = springSettings
motorSettings.mMinForceLimit = -900.0
motorSettings.mMaxForceLimit = 900.0

this._constraint.SetMotorState(JOLT.EMotorState_Velocity)
this.controlMode = DriverControlMode.Velocity;
this.controlMode = DriverControlMode.Velocity
}

public Update(_: number): void {if (this._controlMode == DriverControlMode.Velocity) {
this._constraint.SetTargetVelocity(this._targetVelocity);
public Update(_: number): void {
if (this._controlMode == DriverControlMode.Velocity) {
this._constraint.SetTargetVelocity(this._targetVelocity)
} else if (this._controlMode == DriverControlMode.Position) {
this._constraint.SetTargetPosition(this._targetPosition);
this._constraint.SetTargetPosition(this._targetPosition)
}
}
}
Expand Down
6 changes: 1 addition & 5 deletions fission/src/ui/components/MainHUD.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -125,11 +125,7 @@ const MainHUD: React.FC = () => {
icon={<IoPeople />}
onClick={() => openModal("import-local-mirabuf")}
/>
<MainHUDButton
value={"Test God Mode"}
icon={<IoGameControllerOutline />}
onClick={TestGodMode}
/>
<MainHUDButton value={"Test God Mode"} icon={<IoGameControllerOutline />} onClick={TestGodMode} />
</div>
<div className="flex flex-col gap-0 bg-background w-full rounded-3xl">
<MainHUDButton
Expand Down
42 changes: 22 additions & 20 deletions fission/src/ui/modals/mirabuf/ImportLocalMirabufModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -35,34 +35,36 @@ const ImportLocalMirabufModal: React.FC<ModalPropsImpl> = ({ modalId }) => {
modalId={modalId}
acceptEnabled={selectedFile !== undefined}
onAccept={() => {
if (selectedFile) {
console.log(`Mira: '${selectedFile}'`)
showTooltip("controls", [
{ control: "WASD", description: "Drive" },
{ control: "E", description: "Intake" },
{ control: "Q", description: "Dispense" },
])
if (selectedFile) {
console.log(`Mira: '${selectedFile}'`)
showTooltip("controls", [
{ control: "WASD", description: "Drive" },
{ control: "E", description: "Intake" },
{ control: "Q", description: "Dispense" },
])

CreateMirabufFromUrl(URL.createObjectURL(selectedFile)).then(x => {
if (x) {
World.SceneRenderer.RegisterSceneObject(x)
}
})
}
CreateMirabufFromUrl(URL.createObjectURL(selectedFile)).then(x => {
if (x) {
World.SceneRenderer.RegisterSceneObject(x)
}
})
}
}
}}
>
<div className="flex flex-col items-center gap-5">
<input ref={fileUploadRef} onChange={onInputChanged} type="file" hidden={true} />
<Button value="Upload" size={ButtonSize.Large} onClick={uploadClicked} />
{
selectedFile
? (<Label className="text-center" size={LabelSize.Medium}>{`Selected File: ${selectedFile.name}`}</Label>)
: (<></>)
}
{selectedFile ? (
<Label
className="text-center"
size={LabelSize.Medium}
>{`Selected File: ${selectedFile.name}`}</Label>
) : (
<></>
)}
</div>
</Modal>
)
}

export default ImportLocalMirabufModal
export default ImportLocalMirabufModal
3 changes: 3 additions & 0 deletions fission/src/ui/modals/mirabuf/ImportMirabufModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -33,13 +33,15 @@ const ImportMirabufModal: React.FC<ModalPropsImpl> = ({ modalId }) => {
const [selectedFolder, setSelectedFolder] = useState<Folder | undefined>(undefined)

const [hubs, setHubs] = useState<Hub[] | undefined>(undefined)
// prettier-ignore
useEffect(() => {
(async () => {
setHubs(await getHubs())
})()
}, [])

const [projects, setProjects] = useState<Project[] | undefined>(undefined)
// prettier-ignore
useEffect(() => {
(async () => {
if (selectedHub) {
Expand All @@ -49,6 +51,7 @@ const ImportMirabufModal: React.FC<ModalPropsImpl> = ({ modalId }) => {
}, [selectedHub])

const [folderData, setFolderData] = useState<Data[] | undefined>(undefined)
// prettier-ignore
useEffect(() => {
(async () => {
if (selectedProject) {
Expand Down
Loading
Loading