This repository has been archived on 2019-08-01. You can view files and clone it, but cannot push or open issues or pull requests.
ncurses-poll/README.md

73 lines
2.8 KiB
Markdown
Raw Permalink Normal View History

2019-08-01 17:50:35 +00:00
# ncurses-poll
## 1. Introduction
This repository contains a simple header, [ncurses-poll.hpp](src/ncurses-poll.hpp). With it, you can perform non-blocking I/O in your ncurses application.
## 2. Features
### 2.1 Multiple instances
Each instance of `ncurses_poll` wraps an ncurses `SCREEN*`. Multiple instances can be handled simultaneously in one thread.
Note that there's no need to call `set_term()` because this is done by the header before callbacks are invoked.
### 2.2 Boost.Asio and coroutines
Asynchronous I/O is achieved using Boost.Asio. Thus, other libraries(e.g. [Beast](https://github.com/boostorg/beast)) which uses Boost.Asio can be easily integrated into your ncurses applications.
Boost.Asio's stackless coroutine is also supported for cleaner and human-friendlier code.
## 3. Documentation
### 3.1 Event loop
An `ncurses_poll` instance must run within a Boost.Asio event loop (aka `io_context`). A const reference to an `io_context` instance should be passed to the constructor.
### 3.2 Session
The `ncurses_poll` class template requires a parameter `Session`, which is the type of session. The session may contain username, permission, or other data concerning a specific connection.
`Session` must be a class with a constructor which accepts a pointer to this `ncurses_poll<session>` class.
To get pointer to current session instance of an `ncurses_poll` instance, call `session()` method.
### 3.2 Async read/write
A read/write operation may block, so we need to determine whether the stream is readable/writable before performing I/O.
The `on_readable` and `on_writable` methods accept a single parameter, the const reference to a callback function. Once the stream is readable/writable, the given callback will be invoked.
The callback function should be of the following type:
```C++
using callback =
std::function<void(const boost::system::error_code&, ncurses_poll*)>;
```
* The first argument of callback is the error code, upon success it yields zero, otherwise it is set to the corresponding errno. You should always handle `error_code` before performing I/O.
* The second argument is the pointer to the `ncurses_poll` instance.
### 3.3 Using coroutines
Boost.Asio's stackless coroutine requires a `boost::asio::coroutine` instance. You can simply use the `coro` property of `ncurses_poll`. For example, in a callback function:
```C++
if (!ec) reenter(poll->coro) for (;;) {
yield poll->on_writable(cb);
// ...
}
```
### 3.4 Other operations
To get corresponding `io_context` instance, call `get_io_context()` method.
To get `SCREEN` pointer to current ncurses instance, call `screen()` method.
### 3.5 See also
* [Examples](/examples) for using `ncurses_poll`.
* [Ncurses Programming Guide](http://www.cs.ukzn.ac.za/~hughm/os/notes/ncurses.html).
* Boost.Asio [documentation](https://www.boost.org/doc/libs/1_67_0/doc/html/boost_asio.html).