forked from 1b-agent/opencadstudio-upstream
feat(plugin): AutoCAD-compatible PAUSE, ENTER keyword, and command streaming
This commit is contained in:
1 parent
fd2062bdec
commit
fbedb3736e
8 files changed
+250
-3
No files matched your search
@@ -530,6 +530,7 @@ impl OpenCADStudio {
|
||||
} else {
|
||||
None
|
||||
};
|
||||
let is_escape = matches!(&input, StepInput::Escape);
|
||||
let result: Option<CmdResult> = {
|
||||
let Some(cmd) = self.tabs[i].active_cmd.as_mut() else {
|
||||
return Task::none();
|
||||
@@ -552,12 +553,58 @@ impl OpenCADStudio {
|
||||
self.record_dimension_entity_points(i, None, handle, Vec::new());
|
||||
}
|
||||
self.sync_dimension_snaps(i);
|
||||
match result {
|
||||
if is_escape {
|
||||
self.tabs[i].pending_pause_tokens = None;
|
||||
}
|
||||
let task = match result {
|
||||
Some(r) => self.apply_cmd_result(r),
|
||||
None => Task::none(),
|
||||
};
|
||||
if !is_escape && self.tabs[i].active_cmd.is_some() && self.tabs[i].pending_pause_tokens.is_some() {
|
||||
let drain_task = self.drain_pending_pause_tokens(i);
|
||||
Task::batch([task, drain_task])
|
||||
} else {
|
||||
task
|
||||
}
|
||||
}
|
||||
|
||||
/// Process queued tokens buffered after a PAUSE (or `\`) until the queue is
|
||||
/// empty or another PAUSE / cancellation is encountered.
|
||||
pub(super) fn drain_pending_pause_tokens(&mut self, tab_idx: usize) -> Task<Message> {
|
||||
let Some(mut tokens) = self.tabs[tab_idx].pending_pause_tokens.take() else {
|
||||
return Task::none();
|
||||
};
|
||||
let mut tasks = Vec::new();
|
||||
while !tokens.is_empty() {
|
||||
if self.tabs[tab_idx].active_cmd.is_none() {
|
||||
break;
|
||||
}
|
||||
let token = tokens.remove(0);
|
||||
let trimmed = token.trim();
|
||||
if trimmed.eq_ignore_ascii_case("PAUSE") || trimmed == "\\" {
|
||||
self.tabs[tab_idx].pending_pause_tokens = Some(tokens);
|
||||
break;
|
||||
}
|
||||
if trimmed.is_empty()
|
||||
|| trimmed.eq_ignore_ascii_case("ENTER")
|
||||
|| trimmed.eq_ignore_ascii_case("RETURN")
|
||||
|| trimmed == "\n"
|
||||
{
|
||||
tasks.push(self.feed_command(StepInput::Enter));
|
||||
} else if trimmed.eq_ignore_ascii_case("ESC")
|
||||
|| trimmed.eq_ignore_ascii_case("ESCAPE")
|
||||
|| trimmed.eq_ignore_ascii_case("CANCEL")
|
||||
{
|
||||
self.tabs[tab_idx].pending_pause_tokens = None;
|
||||
tasks.push(self.feed_command(StepInput::Escape));
|
||||
break;
|
||||
} else {
|
||||
tasks.push(self.feed_active_cmd(&token));
|
||||
}
|
||||
}
|
||||
Task::batch(tasks)
|
||||
}
|
||||
|
||||
/// Run one whole command-line string. A single word or an inline-argument
|
||||
/// command (`PDMODE 3`, `LAYER Walls`, `UCS Z 90` pasted as one line)
|
||||
/// dispatches as-is; for a multi-token line whose first word starts an
|
||||
@@ -624,10 +671,19 @@ impl OpenCADStudio {
|
||||
let mut tasks = Vec::new();
|
||||
// First token is the command verb itself; prompts start consuming after it.
|
||||
let mut consumed = 1;
|
||||
for tok in &tokens[1..] {
|
||||
let mut paused = false;
|
||||
for (idx, tok) in tokens[1..].iter().enumerate() {
|
||||
if self.tabs[i].active_cmd.is_none() {
|
||||
break;
|
||||
}
|
||||
let trimmed = tok.trim();
|
||||
if trimmed.eq_ignore_ascii_case("PAUSE") || trimmed == "\\" {
|
||||
let remainder: Vec<String> = tokens[1 + idx + 1..].to_vec();
|
||||
self.tabs[i].pending_pause_tokens = Some(remainder);
|
||||
consumed = tokens.len();
|
||||
paused = true;
|
||||
break;
|
||||
}
|
||||
tasks.push(self.feed_active_cmd(tok));
|
||||
consumed += 1;
|
||||
}
|
||||
@@ -658,7 +714,9 @@ impl OpenCADStudio {
|
||||
if consumed < tokens.len() {
|
||||
self.command_line.unconsumed = tokens[consumed..].to_vec();
|
||||
}
|
||||
tasks.push(self.feed_command(StepInput::Enter));
|
||||
if !paused {
|
||||
tasks.push(self.feed_command(StepInput::Enter));
|
||||
}
|
||||
Task::batch(tasks)
|
||||
}
|
||||
|
||||
|
||||
Reference in new issue
Block a user