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

Add Event::Terminate #554

Open
Riey opened this issue Mar 28, 2021 · 11 comments
Open

Add Event::Terminate #554

Riey opened this issue Mar 28, 2021 · 11 comments

Comments

@Riey
Copy link
Contributor

Riey commented Mar 28, 2021

Is your feature request related to a problem? Please describe.

Terminal program often face to SIGINT, SIGTERM and I think it's common to write handler for these signals

so I have to use another crate like ctrl_c however crossterm already can do it will fit well with existing event loop

Describe the solution you'd like

Add new event variant for those termination signals Event::Exit, Event::Terminate, ... whatever

Describe alternatives you've considered in any

Additional context

I have no idea how windows can make this event

@TimonPost
Copy link
Member

We could do that, but what do we do if someone wants to use CTRL + C with a other use case in mind?

@Riey
Copy link
Contributor Author

Riey commented Mar 28, 2021

CTRL + C doesn't affected if someone want to use CTRL + C as KeyEvent they already use raw mode and it doesn't trigger SIGINT by key stroke

@mainrs
Copy link
Contributor

mainrs commented Mar 29, 2021

This sounds really useful! I already do have to register a custom hook in almost all of the CLIs I have, this would (at least for me :) ) reduce boilerplate :)

@TimonPost
Copy link
Member

@Riey okay. It would be nice to have. Sounds very usefull.

@pickfire
Copy link
Contributor

pickfire commented Jun 3, 2021

And suspend as well.

@yunlingz
Copy link

yunlingz commented Jun 8, 2021

It would be very useful to have POSIX signal events like SIGCONT, SIGINT, SIGTSTP....

How about a new event type Event::Signal(libc::c_int) ?

Without signal events, it's very very difficult and tricky to implement job controlling for crossterm-based tui app, such as using ctrl-z to suspend the app to background and using fg to bring it back to front.

@pickfire
Copy link
Contributor

pickfire commented Jun 8, 2021

libc:c_int is a bit overkill and less safe, ideally it should be an enum of signals exposed from signal-hook maybe. Yeah, I am trying to do ctrl-z as well and it seemed like the only method now is to manually implement signal-hook ourselves.

@yunlingz
Copy link

yunlingz commented Jun 8, 2021

For now, I can only implement ctrl-z like this, and suspending does work. But restoring by fg is not possible, since it relies on SIGCONT signal.

Similar feature request has been proposed by #494 already.

Event::Key(KeyEvent {
    code: kcode,
    modifiers: KeyModifiers::CONTROL,
}) => match kcode {
    KeyCode::Char('c') => break,
    KeyCode::Char('z') => {
        execute!(
            terminal.backend_mut(),
            LeaveAlternateScreen,
            cursor::Show,
        )
        .unwrap();
        disable_raw_mode().unwrap();
        unsafe { libc::raise(libc::SIGTSTP) };
    }
    _ => {}
},

@mainrs
Copy link
Contributor

mainrs commented Jun 9, 2021

How would this feature be handled on Windows? Does Windows support a backgorund signal or an equivalent feature for sending a process into the background? 🤔

@pickfire
Copy link
Contributor

Helix did get suspend to work by using signal-hook-tokio https://github.com/helix-editor/helix/blob/9400d743075375e9c9ad90cc91c5530445d8c304/helix-term/src/application.rs#L255-L270, but not sure why disable_raw_mode does not seemed to disable stuff cleanly that in git commit when I suspend the raw mode still seemed to be there (I can't really check) but when I removed both enable_raw_mode and disable_raw_mode suspend works correctly.

@Ben-PH
Copy link

Ben-PH commented Jul 6, 2023

I'm making a tui using an actor model: each actor has a channel to send data to the main event loop, which iterates over data from actors as they come in.

One of those actors is the crossterm event reader.

One of the things I need to consider is graceful shutdown. If the system gets a sig-int (physical ctrl-c, triggered by the OS, or whatever) I would like to be able to get my actors to shutdown gracefully.

My xterm system is basically this, spawned in a dedicated thread:

loop {
    term_ev_tx
        .send(event::read())
        .expect("Todo: setup channel failure story");
}

The problem here, is that once the thread is blocked on read, it's only means of exit is an actual terminal event, or process cleanup.

Some sort of mechanism to be unblocked by the library user, such as a Condvar or similar, would be an awesome feature.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

6 participants