Scrio 介紹 - 特色與支援 ======================= 作者: 遊手好閒的石頭成 (shirock@mail.educities.edu.tw) 日期: 2001/03/31 關於 scrio 的更多資訊。 我前文已說明了 scrio 的用途及架構,接下來,我將說明它的特色、支援 度。 1.支援 ANSI 控制碼的使用,而不像 cursor 不能使用。 2.可顯示各種字元。 可顯示中文,因為 scrio 沒有字元集的概念,你給它什麼資料,它就輸 出什麼,至於如何呈現這些資料,則是終端機或 telnet 程式的事。 3.同時支援虛擬終端機(TTY)及 NOTTY 兩種模式。 在初始化時,只要呼叫 init_term() 即可,scrio 會自動判斷使用者是 否透過 tty 設備。 當使用 NOTTY 模式時, scrio 會呼叫 init_telnet() 做 TELNET 初始 動作。 變數 termtype 儲存了 scrio 所採用的模式 (TERM_GENERIC 或 TERM_SOCKET)。 4.函數分工明確。 基本的終端機控制函數,皆放在 io.c 中;而可做較多變化,重視使用 者介面功能的部份,則位於 screen.c 中。 在 io.c 中,即包含了下列控制動作: * 字串輸出: do_output(), ochar(), ostr(), ochattr(), oflush() ochattr() 是用來控制字元屬性(顏色)的,一但使用 ochattr() 設定屬性後,接下來的輸出,都會用這個屬性,直到再次使用 ochattr() 改變屬性。 * 游標位置: do_move(), do_down(), do_up(), do_right(), do_left(), do_home(), do_savecursor(), do_restorecursor() * 畫面清除: do_clear(), do_cleol(), do_clbol(), do_clbot() * 資料捲動: do_scrollforward(), do_scrollreverse(), do_scrollregion(), do_scrollregionreset() 。 do_scrollregion() 是用來限制捲動範圍的,也就是局部捲動。 * 輸入: add_io(), igetch(), igetkey(), ireadline() igetkey() 是用來讀取鍵值的,如果按下字元鍵,則鍵值跟 igetch() 一樣,但若按下其他鍵,如 F1、F2、方向鍵等, 會傳回 KEY_F1, KEY_F2, KEY_UP, KEY_HOME 等值。 可接受的鍵值,定義在 scrio.h 中,有: KEY_ESC, KEY_BACKSPC, KEY_TAB, KEY_ENTER, KEY_NEWLINE, KEY_UP ~ KEY_LEFT, KEY_HOME ~ KEY_PGDN, KEY_F1 ~ KEY_F12 5.畫面緩衝區,採用 text video memory 的方式,將字元及屬性,以 一對一對應方式,分開存放。 從前,是將屬性以控制碼方式,混雜在一般字元中,但這樣有兩個缺點: * 浪費記憶體空間。 由於無法確定在一行資料中,會有多少控制碼,所以必須使用較大的 空間存放一行資料,一般是 256 bytes,但還是有可能不夠,此時有 buffer flow 的風險。 * 定位不準。 當要在指定位置,儲放要顯示的資料時,會因為忽略了控制碼,而發 生顯示後,資料內容偏掉位置的情形。 但現在,這兩個問題都解決了,每行所需的空間,永遠是每行字元數*2, 一個 80x24 的畫面,其畫面緩衝區只要 80*2*24 bytes ,保證沒有 buffer flow 的問題。而且也不會再出現資料顯示偏移的情形。 特點如下: (1) 定位準確。 (2) 可保存局部文字內容 (3) 可改變字元,而不變屬性;或只變屬性而不變字元 (4) 支援 定位,不會將 TAB 字元當一個空白來顯示 6.可調整的顯示行為。 可選擇是否停用 ANSI 控制碼 - set_ansicode() ,當停用時,字串中 的 ANSI 控制碼,將如用一般字元顯示出來( ESC 字元會用 * 表示)。 可選擇是否自動換行 - set_autowarp() 。 7.支援使用者多工輸入 (1) 支援多重輸入來源,使用 add_io() 加入其他的輸入來源後, igetch() 或 igetkey() 即可自動判斷有資料的輸入源,是鍵盤 或是遠端輸入 ( I_OTHERDATA )。 理論上,甚至可以指定輸入源的"事件處理"函數 ( add_io 的第 二個參數 handler ),當有資料來到時,自動呼叫之,不會打斷 igetch() 或 igetkey() 。 (2) 可設定指定按鍵的特定處理函數,即快鍵。 add_igetkey_filter(), remove_igetkey_filter() ,另外,這 個機制,是局部性的,亦即它不會在你不想要它發生時發生。 ps. Ctrl-L 是強制重繪鍵,無法做為其他用途。 (3) 強大的欄位輸入 - getdata() ,可輸入超長字串內容,當輸入的 字串內容,超出欄位寬度時,會自動捲動。 並可做表格(多欄位)輸入 - textfield() ,及對欄位內容設查核 函數。 8.畫面 (1) 缺點: 無視窗,以全螢幕為標的。 (2) 可保存畫面內容: getscrline(), getscrlines(), setscrline(), setscrlines(), save_screen(), restore_screen() (3) 可以劃出方塊 draw_box(), 以及一個簡單的訊息視窗函數 messagebox() (4) 可指定額外的更新函數 add_flush() 。 ※須自行規劃 Window Manager ,以管理畫面上各元件的顯示, 由 WM 將其最終 repaint 動作,加入額外的更新函數中。 -- The TIP Project 根基於 Firebird BBS 原始碼的改進計劃 Short URL: http://fbtip.tsx.org/ Group: http://groups.yahoo.com/list/firebird-tip Mailing list: firebird-tip@yahoogroups.com