unify timeout 😍
This commit is contained in:
parent
cac4d698c3
commit
6138d70a6f
@ -75,6 +75,37 @@ impl MouseInterpolator{
|
|||||||
self.output.append(&mut self.buffer);
|
self.output.append(&mut self.buffer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
fn get_timedout_at(&self,time_limit:SessionTime)->Option<SessionTime>{
|
||||||
|
match &self.buffer_state{
|
||||||
|
BufferState::Unbuffered=>None,
|
||||||
|
BufferState::Initializing(time,_mouse_state)
|
||||||
|
|BufferState::Buffered(time,_mouse_state)=>{
|
||||||
|
let timeout=*time+MOUSE_TIMEOUT;
|
||||||
|
(timeout<time_limit).then_some(timeout)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fn timeout(&mut self){
|
||||||
|
let buffer_state=core::mem::replace(&mut self.buffer_state,BufferState::Unbuffered);
|
||||||
|
match buffer_state{
|
||||||
|
BufferState::Unbuffered=>(),
|
||||||
|
BufferState::Initializing(_time,mouse_state)
|
||||||
|
|BufferState::Buffered(_time,mouse_state)=>{
|
||||||
|
// convert to BufferState::Unbuffered
|
||||||
|
// use the first instruction which should be a mouse instruction
|
||||||
|
// to push a ReplaceMouse instruction
|
||||||
|
// duplicate the current mouse
|
||||||
|
self.push_mouse(TimedInstruction{
|
||||||
|
// This should be simulation_timer.time(timeout)
|
||||||
|
// but the timer is not accessible from this scope
|
||||||
|
// and it's just here to say that the mouse isn't moving anyways.
|
||||||
|
// I think this is a divide by zero bug, two identical mouse_states will occupy the interpolation state
|
||||||
|
time:mouse_state.time,
|
||||||
|
instruction:MouseInstruction::SetNextMouse(mouse_state),
|
||||||
|
});
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
pub fn push_unbuffered_input(&mut self,ins:DoubleTimedUnbufferedInstruction){
|
pub fn push_unbuffered_input(&mut self,ins:DoubleTimedUnbufferedInstruction){
|
||||||
// new input
|
// new input
|
||||||
// if there is zero instruction buffered, it means the mouse is not moving
|
// if there is zero instruction buffered, it means the mouse is not moving
|
||||||
@ -86,6 +117,11 @@ impl MouseInterpolator{
|
|||||||
// a mouse event is buffered, and exists within the last 10ms
|
// a mouse event is buffered, and exists within the last 10ms
|
||||||
// case 3: stop
|
// case 3: stop
|
||||||
// a mouse event is buffered, but no mouse events have transpired within 10ms
|
// a mouse event is buffered, but no mouse events have transpired within 10ms
|
||||||
|
|
||||||
|
// push buffered mouse instruction and flush buffer to output
|
||||||
|
if self.get_timedout_at(ins.time).is_some(){
|
||||||
|
self.timeout();
|
||||||
|
}
|
||||||
// replace_with allows the enum variant to safely be replaced from behind a mutable reference
|
// replace_with allows the enum variant to safely be replaced from behind a mutable reference
|
||||||
let (ins_mouse,ins_other)=replace_with::replace_with_or_abort_and_return(&mut self.buffer_state,|buffer_state|{
|
let (ins_mouse,ins_other)=replace_with::replace_with_or_abort_and_return(&mut self.buffer_state,|buffer_state|{
|
||||||
let next_state=match buffer_state{
|
let next_state=match buffer_state{
|
||||||
@ -96,18 +132,6 @@ impl MouseInterpolator{
|
|||||||
BufferState::Unbuffered
|
BufferState::Unbuffered
|
||||||
},
|
},
|
||||||
BufferState::Initializing(time,mouse_state)=>{
|
BufferState::Initializing(time,mouse_state)=>{
|
||||||
let timeout=time+MOUSE_TIMEOUT;
|
|
||||||
if timeout<ins.time{
|
|
||||||
// duplicate the current mouse
|
|
||||||
let ins_mouse=TimedInstruction{
|
|
||||||
// This should be simulation_timer.time(time)
|
|
||||||
// but the timer is not accessible from this scope
|
|
||||||
// and it's just here to say that the mouse isn't moving anyways.
|
|
||||||
time:ins.instruction.time,
|
|
||||||
instruction:MouseInstruction::SetNextMouse(MouseState{pos:mouse_state.pos,time:ins.instruction.time}),
|
|
||||||
};
|
|
||||||
return ((Some(ins_mouse),None),BufferState::Unbuffered);
|
|
||||||
}
|
|
||||||
if let Instruction::MoveMouse(pos)=ins.instruction.instruction{
|
if let Instruction::MoveMouse(pos)=ins.instruction.instruction{
|
||||||
let next_mouse_state=MouseState{pos,time:ins.instruction.time};
|
let next_mouse_state=MouseState{pos,time:ins.instruction.time};
|
||||||
let ins_mouse=TimedInstruction{
|
let ins_mouse=TimedInstruction{
|
||||||
@ -122,19 +146,6 @@ impl MouseInterpolator{
|
|||||||
BufferState::Initializing(time,mouse_state)
|
BufferState::Initializing(time,mouse_state)
|
||||||
},
|
},
|
||||||
BufferState::Buffered(time,mouse_state)=>{
|
BufferState::Buffered(time,mouse_state)=>{
|
||||||
// TODO: deduplicate code with above case
|
|
||||||
let timeout=time+MOUSE_TIMEOUT;
|
|
||||||
if timeout<ins.time{
|
|
||||||
// duplicate the current mouse
|
|
||||||
let ins_mouse=TimedInstruction{
|
|
||||||
// This should be simulation_timer.time(timeout)
|
|
||||||
// but the timer is not accessible from this scope
|
|
||||||
// and it's just here to say that the mouse isn't moving anyways.
|
|
||||||
time:ins.instruction.time,
|
|
||||||
instruction:MouseInstruction::SetNextMouse(MouseState{pos:mouse_state.pos,time:ins.instruction.time}),
|
|
||||||
};
|
|
||||||
return ((Some(ins_mouse),None),BufferState::Unbuffered);
|
|
||||||
}
|
|
||||||
if let Instruction::MoveMouse(pos)=ins.instruction.instruction{
|
if let Instruction::MoveMouse(pos)=ins.instruction.instruction{
|
||||||
let next_mouse_state=MouseState{pos,time:ins.instruction.time};
|
let next_mouse_state=MouseState{pos,time:ins.instruction.time};
|
||||||
let ins_mouse=TimedInstruction{
|
let ins_mouse=TimedInstruction{
|
||||||
@ -174,60 +185,23 @@ impl MouseInterpolator{
|
|||||||
self.output.len()!=0
|
self.output.len()!=0
|
||||||
}
|
}
|
||||||
pub fn buffered_instruction_with_timeout(&self,time_limit:SessionTime)->Option<TimedInstruction<StepInstruction,SessionTimeInner>>{
|
pub fn buffered_instruction_with_timeout(&self,time_limit:SessionTime)->Option<TimedInstruction<StepInstruction,SessionTimeInner>>{
|
||||||
match &self.buffer_state{
|
match self.get_timedout_at(time_limit){
|
||||||
BufferState::Unbuffered=>self.has_output().then_some(TimedInstruction{
|
Some(timeout)=>Some(TimedInstruction{
|
||||||
|
time:timeout,
|
||||||
|
instruction:StepInstruction::Timeout,
|
||||||
|
}),
|
||||||
|
None=>self.has_output().then_some(TimedInstruction{
|
||||||
|
// this timestamp should not matter
|
||||||
time:time_limit,
|
time:time_limit,
|
||||||
instruction:StepInstruction::Pop,
|
instruction:StepInstruction::Pop,
|
||||||
}),
|
}),
|
||||||
BufferState::Initializing(time,_mouse_state)
|
|
||||||
|BufferState::Buffered(time,_mouse_state)=>{
|
|
||||||
let timeout=*time+MOUSE_TIMEOUT;
|
|
||||||
if timeout<time_limit{
|
|
||||||
// if the mouse has stopped moving for over 10ms, emit DoStepReplaceMouse at that exact timestamp
|
|
||||||
Some(TimedInstruction{
|
|
||||||
time:timeout,
|
|
||||||
instruction:StepInstruction::Timeout,
|
|
||||||
})
|
|
||||||
}else if self.has_output(){
|
|
||||||
// emit Step
|
|
||||||
Some(TimedInstruction{
|
|
||||||
// this timestamp should not matter
|
|
||||||
// verify this and potentially emit a different type using the enum only
|
|
||||||
time:time_limit,
|
|
||||||
instruction:StepInstruction::Pop,
|
|
||||||
})
|
|
||||||
}else{
|
|
||||||
None
|
|
||||||
}
|
|
||||||
},
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// include timestamp and implement InstructionConsumer?
|
// include timestamp and implement InstructionConsumer?
|
||||||
pub fn pop_buffered_instruction(&mut self,ins:StepInstruction)->Option<TimedInstruction<PhysicsInputInstruction,PhysicsTimeInner>>{
|
pub fn pop_buffered_instruction(&mut self,ins:StepInstruction)->Option<TimedInstruction<PhysicsInputInstruction,PhysicsTimeInner>>{
|
||||||
match ins{
|
match ins{
|
||||||
// could check if self.is_first_ready()
|
|
||||||
StepInstruction::Pop=>(),
|
StepInstruction::Pop=>(),
|
||||||
StepInstruction::Timeout=>{
|
StepInstruction::Timeout=>self.timeout(),
|
||||||
let buffer_state=core::mem::replace(&mut self.buffer_state,BufferState::Unbuffered);
|
|
||||||
match buffer_state{
|
|
||||||
BufferState::Unbuffered=>(),
|
|
||||||
BufferState::Initializing(_time,mouse_state)
|
|
||||||
|BufferState::Buffered(_time,mouse_state)=>{
|
|
||||||
// convert to BufferState::Unbuffered
|
|
||||||
// use the first instruction which should be a mouse instruction
|
|
||||||
// to push a ReplaceMouse instruction
|
|
||||||
// duplicate the current mouse
|
|
||||||
self.push_mouse(TimedInstruction{
|
|
||||||
// This should be simulation_timer.time(timeout)
|
|
||||||
// but the timer is not accessible from this scope
|
|
||||||
// and it's just here to say that the mouse isn't moving anyways.
|
|
||||||
// I think this is a divide by zero bug, two identical mouse_states will occupy the interpolation state
|
|
||||||
time:mouse_state.time,
|
|
||||||
instruction:MouseInstruction::SetNextMouse(mouse_state),
|
|
||||||
});
|
|
||||||
},
|
|
||||||
}
|
|
||||||
},
|
|
||||||
}
|
}
|
||||||
self.output.pop_front()
|
self.output.pop_front()
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user