初始化与结束

为了使用 NCURSES 库,你应该 #include <curses.h>,在编译时,应该加上 -lncurses。

stdscr

一般地,第一个函数调用必须是 initscr()。这个函数初始化终端,然后清屏。它的参数为空,返回值一般也不用管。它会初始化一个叫 stdscr 的变量,stdscr 有点像 stdin 或 stdout 的地位,它是 NCURSES 默认的窗口。紧接着 initscr() 的应该是其它初始化,下面一一介绍。

raw() 和 cbreak()

即时按键。raw() 和 cbreak() 两个函数都是用来关闭行缓冲以使按键可以马上被程序处理的。只是 cbreak() 可以在按 Ctrl-C 的时候退出程序,我一般用这个。两个函数都无参数。

keypad()

使用功能键。keypad() 可以用来打开一个窗口的功能键,从来使程序可以识别 F1、F2、Up、Down 等这样的按键。一般用 keypad (stdscr, TRUE) 来打开 stdscr 的这项功能。

echo() 和 noecho()

按键回显。echo() 和 noecho(),后者可以关闭按键回显,这在使用getch() 时特别有用。在程序中间,二者可以交替使用。两个函数都无参数。

nl() 和 nonl()

换行符。nl() 和 nonl(),用来设置换行是对应一个 '/n' 还是 '/r''/n'。一般使用默认的就要可以了,所以不需调用。两个函数都无参数。

has_colors()

启动颜色。has_colors() 返回一个 bool 值,用来表示终端是否支持颜色;支持则返回真。如果支持颜色,那么就可以用 start_color() 来打开颜色功能。

endwin()

结束很简单,只需调用 endwin(); 即可,但一定要记得调用。如下:   endwin();

初始化代码

initscr ();
cbreak ();
noecho ();
start_color ();
keypad (stdscr, TRUE);
getch();
endwin();

基本输入、输出函数

NCURSES 中基本的输入输出设计得跟标准 I/O 十分相似,比
如输出有 printw(),输入有 scanw(),呵呵,只是把“f”换成了“w”,其它
定义完全一样。
  

输入

1. getch() class: Get a character
2. scanw() class: Get formatted input
3. getstr() class: Get strings

mvsanw(y,x,"...")

输出

1. addch() class: Print single character with attributes
2. printw() class: Print formatted output similar to printf()
3. addstr() class: Print strings

mvaddch(), waddch() and mvwaddch(), mvwaddstr()

mvprintw(y,x, "...")

坐标和窗口

  坐标是相对于窗口的左上角的,从 (0, 0) 开始,但注意 NCURSES 里的下标是 (y, x) 表示的,这个务必记住。move(y, x); 可以直接移动 stdscr 的光标到某一位置。窗口 Window 是 NCURSES 的基本操作对象,事实上所有的的输入输出都关联到窗口上,如果缺省的话,就是 stdscr。

  例如 addch() 这一系列的函数有:addch()、mvaddch()、wadch() 和 mvwaddch() 四个。其中“mv”表示 move,也就是移动到某一坐标处再输出。而“w”表示 Window,即向某一窗口输出。而 move() 也可以变化成 wmove()。

要注意的是,这些输出不是直接输出到屏幕上的,而是输出到某一窗口。所以应该使用 refresh() 刷新 stdscr 的输出;对应的,用 wrefresh() 可以刷新某一窗口的输出; wrefresh(stdscr) == refresh()。

功能键

功能键可以在 man 3 getch 里查到,都是以 KEY_ 开头的。下面列出常用的一些:

回退键: KEY_BACKSPACE
Insert: KEY_IC
Delete: KEY_DC
上方向键: KEY_UP
左方向键: KEY_LEFT
F1: KEY_F()
F2: KEY_F()
PageUp: KEY_PPAGE
PageDown: KEY_NPAGE
TAB、ESC、ENTER 都是 ASCII 值对应。

窗口 WINDOW

newwin()和delwin()

WINDOW 是 NCURSES 管理的基本单元,也是应用的基础,后面要说到的Menus Library 和 Forms Library 都要用到 WINDOW 来管理其输出。  

每个窗口都对应一个数据结构,在创建窗口时 NCURSES 会分配这些空间,所以窗口使用完了应该删除。一个窗口的数据结构里记录有窗口的大小,窗口左上角的位置,一个显示缓冲区,当前颜色等等众多数据。  

你应该知道了,stdscr 是 NCURSES 缺省的窗口,也是启动后的第一个窗口。newwin() 可以建立一个新窗口,其声明是:

WINDOW* newwin(int height, int width, int y, int x);

其中 (y, x) 是窗口左上角的坐标。窗口建立后,如果想要打开功能键的话,应该调用 keypad()。我一般是两个一起使用。  

一个窗口使用完后,应该删除掉,函数是 delwin(),参数是要删除的窗口指针。在删除窗口之前,你也许要清除窗口里的内容,可以用 wclear()。但是 wclear() 似乎并不使用当前颜色,而只是使窗口黑掉。

box(win, 0, 0) 和 wborder()

画框时可能要用到一些 ASCII 之外的字符,NCURSES 定义了一些字符,以 ASC_ 开头,如果终端不支持这些字符,NCURSES 会自动以相似的字符代替。

wrefresh()和redrawwin(win)

在窗口里,你就可以输出东西了,addch()、addstr() 和 printw() 几类函数可以随意使用,但一定要记得 wrefresh()。要注意的是,窗口的 refresh 是优化了的,它只会刷新被改变的部分,所以效率是比较高的。   

当窗口比较多时,为了显示被埋在下面的窗口,可以使用 redrawwin(win) 来重绘窗口,这个时候 wrefresh() 并不是那么有效。

wnoutrefresh(win) 和 doupdate()

wnoutrefresh(win) 和 doupdate() 是很好的一对搭配。当你窗口很多时,对每个窗口直接用 wrefresh() 是比交耗时的。这时你可以用 wnoutrefresh() 来更新每个窗口的缓冲区,最后用 doupdate() 显示。

子窗口

你也可以创建一个窗口的子窗口,函数是 subwin() 和 derwin(),它们的定义是:

WINDOW *subwin(WINDOW *orig, int lines, int cols, int y, int x);
WINDOW *derwin(WINDOW *orig, int lines, int cols, int y, int x);

它们都是在窗口 orig 中创建一个 lines * cols 大小的子窗口,它们的区别是前者的 (y, x) 是相对于屏幕的,而后者的 (y, x) 是相对于窗口 orig 的。子窗口共享窗口 orig 的内存。在 wrefresh 子窗口前,应该调用 touchwin(orig) 或 touchline(orig),否则可能输出不正常。

清除窗体

delch和wdelch

首先我们谈到能清楚字符和行的函数,delch和wdelch能删除掉窗体逻辑指针指向的字符,下一个字符和一直到行末的字符都会左移 一个位置.

deleteln和wdeleteln

能删除掉逻辑指针指向的行,并且上移下一行.

clrteol和wclrtoeol

clrteol和wclrtoeol能清除掉从逻辑指针指向位置右边字符开始到行末的所有字符.

clrtbot和wclrtobot

clrtbot和wclrtobot 首先清除掉从逻辑指针所在位置右边字符开始到行末的所有字符,接着删除下面所有行.

erase和werase

除了这些,还有一些函数能清除整个屏幕和窗体.有两种方法可以清除掉整个屏幕.第一个是先用空白字符填充 屏幕所有区域,然后再调用refresh函数.另外一种方法是用固定的终端控制字符清除.第一种方法比较慢,因为它需要重写 当前屏幕.第二种能迅速清除整个屏幕内容.

erase和werase用空白字符替换窗体的文本字符,在下一次调用refresh后屏幕内容将会被清除掉.但是如果窗体 需要清掉整个屏幕, 这将一个比较苯的办法.您可以使用上面讲的第一种方法来完成.当窗体需要被清除的是一个屏幕那么宽, 您可以使用下面讲的函数来非常好的完成您的任务.

clear和wclear

在涉及到其他函数之前,我们先来讨论一下_clear标志位.如果设置了该标志,那么它会存在WINDOW结构中. 当调用它时,它会用refresh来发送控制代码到终端,refresh检查窗体的宽度是否是屏幕的宽度(使用_FULLWIN标志位). 如果是的话,它将用内置的终端方法刷新屏幕,它将写入除了空白字符外的文本字符到屏幕,这是一种非常快速清屏的方法. 为什么仅仅当窗体的宽度和屏幕宽度相等时才用内置的终端方法清屏呢?那是因为控制终端代码不仅仅只清除窗体自身 ,它还可以清除当前屏幕._clear标志位由clearok函数控制.

函数clear和wclear被用来清除和屏幕宽度一样的窗体内容.实际上,这些函数等同与使用werase和clearok. 首先,它用空白字符填充窗体的文本字符.接着,设置_clear标志位,如果窗体宽度和屏幕宽度一样,就使用内置的终端方法 清屏,如果不一样就用空白字符填充窗体所有区域再用refresh刷新.

总而言之,如果您知道窗体的宽度和屏幕宽度一样,就使用clear或者wclear,这个速度将非常快.如果窗体宽度 不是和屏幕宽度一样,那么使用wclear和werase将没有任何分别.

颜色

实际上在 NCURSES 里颜色只是字符属性的一部分,另一种是 highlighting
(高亮)。我更喜欢将它们统称为颜色。通过设置字符的属性和高亮显示,就可
以获得一个漂亮界面。

  只有在 start_color() 后,才能使颜色;当然,高亮显示不需要这样。

  NCURSES 预定义了八种颜色,以 COLOR_ 开头,有 COLOR_BLACK、
COLOR_RED、COLOR_GREEN 等。比较奇怪一点的是,你必须成对使用这些颜色,
也就是同时指定前景色和背景色。init_pair(pair, g, b) 用来指定一个
COLOR_PAIR(“色对”)的,pair 是一个 1 到 COLOR_PAIRS-1 之间的值。
COLOR_PAIRS 指定了色对的最大数目,相应有 COLORS 指定了颜色的最大数目。

  高亮的属性是以 A_ 开头的,有 A_NORMAL、A_REVERSE、A_UNDERLINE、
A_BOLD 等。但是这些高亮属性与终端有很大关系,例如我基本上只能用到
A_REVERSE,也就是反色。

  attron() 和 attroff() 用来设置字符的属性,之后输出的字符都会具有改
变后的属性。例如 attron(A_REVERSE) 可以打开反色属性,可能的就是黑底白
字变成白底黑字。attron(COLOR_PAIR(n)) 则可以打开色对 n 所对应的前景和
背景。注意在 attron() 之后,对应地用 attroff() 来关闭。在 attron() 的
时候,高亮与颜色应该可以通过“或”运算同时使用。

  设定色对的一个技巧是使用颜色本身作序号,如 init_pair(COLOR_RED,
COLOR_RED, COLOR_BLACK);,这样 COLOR_PAIR(COLOR_RED) 就很明显了。

  chtype 类型可以同时携带字符及其属性。这是 addch() 的参数类型。

  wchgat() 是一个极有用的函数,它可以改变从当前光标位置开始若干字节
的属性,这个在显示菜单或按钮时特别有用。但我在用这个函数时被郁闷了,不
知什么原因,这个函数总是不灵。

  我现在使用 wchgat() 的方法是:通过 derwin() 申请一个子窗口,然后用
wchgat() 来改变子窗口中字符的属性,然后更新到父窗口。问题真不少,居然
mvwchgat() 不能正常工作,所以不得已我只有先 wmove() 然后再 wchgat()。

  chgat() 的参数有四个,第一个是要改变属性的字符的长度,-1 表示到窗
口结尾;第二个是属性;第三个是颜色号,注意不要用 COLOR_PAIR,直接用色
对的序号;第四个参数保留,真接填 NULL。它从当前光标改变若干字符的属性
后,会返回原光标处。哦,你应该知道 chgat() 与 wchgat() 的关系吧。

Panel、Menus 和 Forms

  NCURSES 还有这三个库:Panel Library、Menus Library 和 Forms
Library。其头文件分别为 <panel.h>、<menu.h> 和 <form.h>;编译选项分别
为 -lpanel、-lmenu 和 -lform,注意最好放在 -lncurses 前。

  Panel 不了解;Menus 和 Forms 也只是简单抄了例子。

  Menus 与 Forms 都要先手动创建基本元素,然后有一个“驱动”函数可以
用来驱动 Menus 或 Forms。你要做的就是从 wgetch() 接收按键,转化成命令
然后通过“驱动”函数来驱动 Menus 或 Forms。

  Menus 主要提供对菜单的支持;Forms 提供一些输入的部件等。

一些函数

1. getmaxyx

getmaxyx(stdscr,row,col); /* get the number of rows and columns */
mvprintw(row/,(col−strlen(mesg))/,"%s",mesg);
/* print the message at the center of the screen */
mvprintw(row−,,"This screen has %d rows and %d columns\n",row,col);

The above program introduces us to a new function getmaxyx(), a macro defined in ncurses.h. It gives
the number of columns and the number of rows in a given window. getmaxyx() does this by updating the
variables given to it. Since getmaxyx() is not a function we don't pass pointers to it, we just give two
integer variables.

参考:

http://blog.csdn.net/cxjddd/article/details/139990

ncurse 笔记的更多相关文章

  1. 《Linux内核设计与实现》课本第一章&第二章学习笔记

    <Linux内核设计与实现>课本学习笔记 By20135203齐岳 一.Linux内核简介 Unix内核的特点 Unix很简洁,所提供的系统调用都有很明确的设计目的. Unix中一切皆文件 ...

  2. 《Linux内核设计与实现》 第一二章学习笔记

    <Linux内核设计与实现> 第一二章学习笔记 第一章 Linux内核简介 1.1 Unix的历史 Unix的特点 Unix很简洁,所提供的系统调用都有很明确的设计目的. Unix中一切皆 ...

  3. 《Linux内核设计与实现》第一、二章学习笔记

    <Linux内核设计与实现>第一.二章学习笔记 姓名:王玮怡  学号:20135116 第一章 Linux内核简介 一.关于Unix ——一个支持抢占式多任务.多线程.虚拟内存.换页.动态 ...

  4. 《Linux内核设计与实现》Chapter 2 读书笔记

    <Linux内核设计与实现>Chapter 2 读书笔记 一.获取内核源码 1.使用Git 我们曾经在以前的学习中使用过Git方法 $ git clone git://git.kernel ...

  5. git-简单流程(学习笔记)

    这是阅读廖雪峰的官方网站的笔记,用于自己以后回看 1.进入项目文件夹 初始化一个Git仓库,使用git init命令. 添加文件到Git仓库,分两步: 第一步,使用命令git add <file ...

  6. js学习笔记:webpack基础入门(一)

    之前听说过webpack,今天想正式的接触一下,先跟着webpack的官方用户指南走: 在这里有: 如何安装webpack 如何使用webpack 如何使用loader 如何使用webpack的开发者 ...

  7. SQL Server技术内幕笔记合集

    SQL Server技术内幕笔记合集 发这一篇文章主要是方便大家找到我的笔记入口,方便大家o(∩_∩)o Microsoft SQL Server 6.5 技术内幕 笔记http://www.cnbl ...

  8. PHP-自定义模板-学习笔记

    1.  开始 这几天,看了李炎恢老师的<PHP第二季度视频>中的“章节7:创建TPL自定义模板”,做一个学习笔记,通过绘制架构图.UML类图和思维导图,来对加深理解. 2.  整体架构图 ...

  9. PHP-会员登录与注册例子解析-学习笔记

    1.开始 最近开始学习李炎恢老师的<PHP第二季度视频>中的“章节5:使用OOP注册会员”,做一个学习笔记,通过绘制基本页面流程和UML类图,来对加深理解. 2.基本页面流程 3.通过UM ...

随机推荐

  1. Android中对TextView中的部分内容的字体样式的设置方法

    Android中的TextView中内容,有时候需要对其部分内容添加下划线和颜色操作: String str = "回复 " + uname + " 的评论: " ...

  2. delphi 文件夹操作

    文件的拖放和打开拖拽 user shellapi type TForm1 = class(TForm) ListView1: TListView; procedure FormCreate(Sende ...

  3. docker组件如何协作(7)

    还记得我们运行的第一个容器吗?现在通过它来体会一下 Docker 各个组件是如何协作的. 容器启动过程如下: Docker 客户端执行 docker run 命令. Docker daemon 发现本 ...

  4. CentOS7编译安装MPLAYER!!!

    Linux装软件就是折磨人!! Mplayer官网下好release版本 然后./configure --[options] 注意:--prefix=/usr/local/mplayer 是安装路径- ...

  5. P1435 回文字串

    P1435 回文字串 题目背景 IOI2000第一题 题目描述 回文词是一种对称的字符串.任意给定一个字符串,通过插入若干字符,都可以变成回文词.此题的任务是,求出将给定字符串变成回文词所需要插入的最 ...

  6. c# api身份验证和授权

    授权 1. 全局 config.Filters.Add(new AuthorizeAttribute()); 2.控制器级别 [Authorize] public class HelloControl ...

  7. SDL系列之 - 字体显示测试

    例9.7:设计一个程序,初始化视频子系统,设置显示模式为640*480,表面的色深为16位,使用SDL_ttf库在屏幕上显示“Linux下TrueType字体显示示例”,字体大小为38,颜色为红色.设 ...

  8. pyJWT

    现在用JWT 加密太火了,怎么能不跟上潮流?否则销售都不好意思出去吹牛逼! PyJWT是一个Python库,用来编码/解码JWT(JSON Web Token)的 1.定义:根据维基百科的定义,JSO ...

  9. Vue番外篇-路由进阶(一)

    Vue的router默认是 export default new Router({ mode: 'history', routes: [ { path: '/', name: 'HelloWorld' ...

  10. 2018-2-13-win10-edge扩展

    title author date CreateTime categories win10 edge扩展 lindexi 2018-2-13 17:23:3 +0800 2018-2-13 17:23 ...