/* * Copyright (C) 1997-2002 Kikutani Makoto (g@kondara.org) * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ /* * ext/slang/slmodule.c * */ #include #include #include #include #include #ifndef SLMEMSET # ifdef HAVE_MEMSET # define SLMEMSET memset # else # define SLMEMSET SLmemset # endif #endif #include "ruby.h" #include "slmodule.h" static char *Color_str [] = { "black", "red", "green", "brown", "blue", "magenta", "cyan", "lightgray", "gray", "brightred", "brightgreen", "yellow", "brightblue", "brightmagenta", "brightcyan", "white" }; static VALUE mSlang; static VALUE cScrW; static int Want_Window_Size_Change = 0; #ifdef SIGWINCH static void sig_winch_handler (int sig) { sig = errno; Want_Window_Size_Change = 1; SLsignal_intr (SIGWINCH, sig_winch_handler); errno = sig; } static VALUE sl_get_winch_flag(void) { return INT2FIX(Want_Window_Size_Change); } static VALUE sl_clr_winch_flag(void) { Want_Window_Size_Change = 0; return Qnil; } #endif static VALUE sltt_get_screen_size(void) { SLtt_get_screen_size (); return Qnil; } static VALUE slsig_block_signals(void) { SLsig_block_signals (); return Qnil; } static VALUE slsmg_suspend_smg(void) { SLsmg_suspend_smg (); return Qnil; } static VALUE slsmg_resume_smg(void) { SLsmg_resume_smg (); return Qnil; } static VALUE slsmg_erase_eos(void) { SLsmg_erase_eos (); return Qnil; } static VALUE slsmg_normal_video(void) { SLsmg_normal_video (); return Qnil; } static VALUE slsmg_reverse_video(void) { SLsmg_reverse_video (); return Qnil; } static VALUE slsmg_set_char_set(VALUE obj, VALUE set) { SLsmg_set_char_set (NUM2INT(set)); return Qnil; } static VALUE slsmg_forward(VALUE obj, VALUE set) { SLsmg_forward (NUM2INT(set)); return Qnil; } static VALUE slsmg_set_color(obj, color) VALUE obj; VALUE color; { FIXNUM_P(color); SLsmg_set_color(FIX2INT(color)); return Qnil; } static VALUE slsmg_gotorc(VALUE obj, VALUE row, VALUE col) { SLsmg_gotorc (NUM2INT(row), NUM2INT(col)); return Qnil; } static VALUE slsmg_printf(argc, argv, self) int argc; VALUE *argv; VALUE self; { VALUE str = rb_f_sprintf(argc, argv); /* SLsmg_printf("%s", RSTRING(str)->ptr); */ SLsmg_write_string(RSTRING(str)->ptr); return Qnil; } static VALUE slsmg_write_string(obj, str) VALUE obj; VALUE str; { Check_Type(str, T_STRING); SLsmg_write_string(RSTRING(str)->ptr); return Qnil; } static VALUE slsmg_write_nchars(obj, str, n) VALUE obj; VALUE str; VALUE n; { Check_Type(str, T_STRING); FIXNUM_P(n); SLsmg_write_nchars(RSTRING(str)->ptr, FIX2INT(n)); return Qnil; } static VALUE slsmg_write_char(obj, c) VALUE obj; VALUE c; { FIXNUM_P(c); SLsmg_write_char(FIX2INT(c)); return Qnil; } static VALUE slsmg_erase_eol(void) { SLsmg_erase_eol(); return Qnil; } static VALUE slsmg_cls(void) { SLsmg_cls(); return Qnil; } static VALUE slsmg_refresh(void) { SLsmg_refresh(); return Qnil; } static VALUE sltt_get_terminfo(void) { SLtt_get_terminfo(); return Qnil; } static VALUE slkp_init(void) { return INT2NUM(SLkp_init ()); } static VALUE sltt_set_mouse_mode(obj, mode, force) VALUE obj; VALUE mode; VALUE force; { SLtt_set_mouse_mode(NUM2INT(mode), NUM2INT(force)); return Qnil; } static VALUE sltty_set_suspend_state(obj, mode) VALUE obj; VALUE mode; { SLtty_set_suspend_state(NUM2INT(mode)); return Qnil; } static VALUE slsig_unblock_signals(void) { SLsig_unblock_signals(); return Qnil; } static VALUE slsmg_char_at(void) { return INT2NUM(SLsmg_char_at()); } static VALUE slsmg_draw_object(obj, r_r, r_c, r_object) VALUE obj; VALUE r_r; VALUE r_c; VALUE r_object; { int r = NUM2INT(r_r); int c = NUM2INT(r_c); unsigned char object = NUM2INT(r_object); SLsmg_draw_object (r, c, object); return Qnil; } static VALUE slkp_getkey(void) { return INT2NUM(SLkp_getkey()); #if 0 int c; while ((c = SLkp_getkey()) == 26) kill (0, SIGTSTP); return INT2NUM(c); #endif } static VALUE slang_getkey(void) { return INT2NUM(SLang_getkey()); } static VALUE sltt_beep(void) { SLtt_beep(); return Qnil; } static VALUE slang_reset_tty(void) { SLang_reset_tty (); return Qnil; } static VALUE slsmg_reset_smg(void) { SLsmg_reset_smg (); return Qnil; } static VALUE slsmg_init_smg(void) { SLsmg_init_smg (); return Qnil; } static VALUE slsmg_set_screen_start(VALUE obj, VALUE r_r, VALUE r_c) { int r = NUM2INT(r_r); int c = NUM2INT(r_c); VALUE ary; SLsmg_set_screen_start(&r, &c); ary = rb_ary_new2(2); rb_ary_push(ary, INT2FIX(r)); rb_ary_push(ary, INT2FIX(c)); return ary; } static VALUE slsmg_fill_region(obj, r_r, r_c, r_dr, r_dc, r_ch) VALUE obj; VALUE r_r; VALUE r_c; VALUE r_dr; VALUE r_dc; VALUE r_ch; { int r = NUM2INT(r_r); int c = NUM2INT(r_c); unsigned int dr = NUM2INT(r_dr); unsigned int dc = NUM2INT(r_dc); unsigned char ch = NUM2INT(r_ch); SLsmg_fill_region (r, c, dr, dc, ch); return Qnil; } static VALUE slsmg_write_color_chars(VALUE obj, VALUE str, VALUE len) { unsigned short *s; Check_Type(str, T_ARRAY); s = (unsigned short *) RARRAY(str)->ptr; SLsmg_write_color_chars (s, NUM2INT(len)); return Qnil; } static VALUE slsmg_read_raw(VALUE obj, VALUE l) { unsigned short *buf; int res, len, i; VALUE bary, ary; len = NUM2INT(l); if (NULL == (buf = (unsigned short *) SLMALLOC (len))) { fprintf(stderr, "malloc error.\n"); exit(-1); } res = SLsmg_read_raw (buf, len); bary = rb_ary_new2(len); for (i = 0; i < len; ++i) rb_ary_push(bary, INT2FIX(buf[i])); free(buf); ary = rb_ary_new2(2); rb_ary_push(ary, INT2FIX(res)); rb_ary_push(ary, bary); return ary; } static VALUE slsmg_write_raw(VALUE obj, VALUE b, VALUE l) { unsigned short *buf; int res, len; Check_Type(b, T_ARRAY); len = NUM2INT(l); buf = (unsigned short *) RARRAY(b)->ptr; res = SLsmg_write_raw (buf, len); return INT2FIX(res); } static VALUE slsmg_set_color_in_region(obj, r_color, r_r, r_c, r_dr, r_dc) VALUE obj; VALUE r_color; VALUE r_r; VALUE r_c; VALUE r_dr; VALUE r_dc; { int color = NUM2INT(r_color); int r = NUM2INT(r_r); int c = NUM2INT(r_c); int dr = NUM2INT(r_dr); int dc = NUM2INT(r_dc); SLsmg_set_color_in_region(color, r, c, dr, dc); return Qnil; } static VALUE slsmg_write_wrapped_string (obj, str, r_r, r_c, r_dr, r_dc, r_fill) VALUE obj; VALUE str; VALUE r_r; VALUE r_c; VALUE r_dr; VALUE r_dc; VALUE r_fill; { char *s; unsigned int dc = NUM2INT(r_dc); int r = NUM2INT(r_r); int c = NUM2INT(r_c); unsigned int dr = NUM2INT(r_dr); int fill = NUM2INT(r_fill); Check_Type(str, T_STRING); s = RSTRING(str)->ptr; SLsmg_write_wrapped_string (s, r, c, dr, dc, fill); return Qnil; } static VALUE slang_init_tty(obj, abort_char, no_flow_control, opost) VALUE obj; VALUE abort_char; VALUE no_flow_control; VALUE opost; { SLang_init_tty (NUM2INT(abort_char), NUM2INT(no_flow_control), NUM2INT(opost)); return Qnil; } int Mouse_on = 0; static void reset_exit (int sig) { SLsmg_gotorc (SLtt_Screen_Rows - 1, 0); SLsmg_refresh (); if (Mouse_on) SLtt_set_mouse_mode(0, 1); SLang_reset_tty (); SLsmg_reset_smg (); if (sig) { fprintf (stderr, "Exiting on signal %d\n", sig); exit (1); } exit (sig); } #ifdef SIGTSTP static void sigtstp_handler (int sig) { if (rb_respond_to(mSlang, rb_intern("slang_sigstp_handler_hook"))) { rb_funcall(mSlang, rb_intern("slang_sigstp_handler_hook"), 0); } if (Mouse_on) SLtt_set_mouse_mode(0, 1); SLsmg_suspend_smg (); kill (0, SIGSTOP); } #endif #ifdef SIGCONT static void sigcont_handler (int sig) { if (Mouse_on) SLtt_set_mouse_mode(1, 1); SLsmg_resume_smg (); SLang_reset_tty (); SLang_init_tty (-1, 0, 1); SLtty_set_suspend_state (1); if (rb_respond_to(mSlang, rb_intern("slang_sigcont_handler_hook"))) { rb_funcall(mSlang, rb_intern("slang_sigcont_handler_hook"), 0); } } #endif #ifdef SIGINT static void sigint_handler (int sig) { reset_exit (sig); } #endif #define ruby_signal(sig,handle) posix_signal((sig),(handle)) static void init_signals (void) { #ifdef SIGTSTP SLsignal (SIGTSTP, sigtstp_handler); #endif #ifdef SIGCONT SLsignal (SIGCONT, sigcont_handler); #endif #ifdef SIGINT SLsignal (SIGINT, sigint_handler); #endif #ifdef SIGWINCH SLsignal_intr (SIGWINCH, sig_winch_handler); #endif } static VALUE sl_init_signals(void) { init_signals(); return Qnil; } static void init_colors (void) { int i; char *fg, *bg; /* fg = color, bg = white */ bg = "white"; for (i = SL_BLACK; i <= SL_WHITE; ++i) { fg = Color_str[i]; SLtt_set_color (SL_BG_WHITE+i, NULL, fg, bg); } /* fg = color, bg = lightgray */ bg = "lightgray"; for (i = SL_BLACK; i <= SL_WHITE; ++i) { fg = Color_str[i]; SLtt_set_color (SL_BG_LGRAY+i, NULL, fg, bg); } /* fg = color, bg = blue */ bg = "blue"; for (i = SL_BLACK; i <= SL_WHITE; ++i) { fg = Color_str[i]; SLtt_set_color (SL_BG_BLUE+i, NULL, fg, bg); } /* fg = black, bg = color */ fg = "black"; for (i = SL_BLACK; i <= SL_WHITE; ++i) { bg = Color_str[i]; SLtt_set_color (SL_BG_COLORS+i, NULL, fg, bg); } /* normal color */ SLtt_set_color (0, NULL, "black", "white"); /* reverse color */ SLtt_set_color (1, NULL, "white", "black"); } static VALUE sl_init_colors(void) { init_colors(); return Qnil; } static VALUE sl_color_terminal(void) { if (SLtt_Use_Ansi_Colors) return TRUE; return FALSE; } static VALUE init_terminal(obj, t, s) VALUE obj; VALUE t; VALUE s; { int tty = NUM2INT(t); int smg = NUM2INT(s); SLsig_block_signals (); SLtt_get_terminfo (); /* SLkp_init assumes that SLtt_get_terminfo has been called. */ if (tty && (-1 == SLkp_init ())) { SLsig_unblock_signals (); return FALSE; } init_signals (); if (tty) SLang_init_tty (-1, 0, 1); if (tty) SLtty_set_suspend_state (1); if (smg) SLsmg_init_smg (); SLsig_unblock_signals (); if (SLtt_Use_Ansi_Colors) init_colors(); if (Mouse_on) SLtt_set_mouse_mode(1, 1); return TRUE; } static VALUE sl_reset(VALUE obj) { SLsmg_gotorc (SLtt_Screen_Rows - 1, 0); SLsmg_refresh (); if (Mouse_on) SLtt_set_mouse_mode(0, 1); SLang_reset_tty (); SLsmg_reset_smg (); return Qnil; } static VALUE sl_input_pending(VALUE obj, VALUE n) { int i; i = SLang_input_pending(NUM2INT(n)); return INT2FIX(i); } static VALUE slsmg_draw_hline(VALUE obj, VALUE n) { SLsmg_draw_hline(NUM2INT(n)); return Qnil; } static VALUE slsmg_draw_vline(VALUE obj, VALUE n) { SLsmg_draw_vline(NUM2INT(n)); return Qnil; } static VALUE slsmg_draw_box(VALUE obj, VALUE x1, VALUE y1, VALUE x2, VALUE y2) { SLsmg_draw_box(NUM2INT(x1), NUM2INT(y1), NUM2INT(x2), NUM2INT(y2)); return Qnil; } static VALUE slsmg_touch_lines(VALUE obj, VALUE r, VALUE c) { SLsmg_touch_lines(NUM2INT(r), NUM2INT(c)); return Qnil; } static VALUE slkp_define_keysym(VALUE obj, VALUE kseq, VALUE code) { Check_Type(kseq, T_STRING); (void) SLkp_define_keysym (RSTRING(kseq)->ptr, NUM2INT(code)); return Qnil; } int Mouse_Row, Mouse_Col; static VALUE sl_get_mouse_rc (void) { VALUE ary; Mouse_Col = (unsigned char) SLang_getkey () - 32 - 1; Mouse_Row = (unsigned char) SLang_getkey () - 32 - 1; ary = rb_ary_new2(2); rb_ary_push(ary, INT2FIX(Mouse_Col)); rb_ary_push(ary, INT2FIX(Mouse_Row)); return ary; } static VALUE sl_mouse_on(void) { Mouse_on = 1; return Qnil; } static VALUE sl_mouse_off(void) { Mouse_on = 0; return Qnil; } static VALUE slsmg_get_column(void) { return INT2FIX(SLsmg_get_column()); } static VALUE slsmg_get_row(void) { return INT2FIX(SLsmg_get_row()); } static VALUE sltt_set_color(VALUE obj, VALUE n, VALUE fg, VALUE bg) { FIXNUM_P(n); Check_Type(fg, T_STRING); Check_Type(bg, T_STRING); SLtt_set_color (FIX2INT(n), NULL, RSTRING(fg)->ptr, RSTRING(bg)->ptr); return Qnil; } static VALUE sltt_screen_rows(void) { return INT2FIX(SLtt_Screen_Rows); } static VALUE sltt_screen_cols(void) { return INT2FIX(SLtt_Screen_Cols); } static VALUE slang_cursor_on(void) { (void) SLtt_set_cursor_visibility (1); SLtt_flush_output (); return Qnil; } static VALUE slang_cursor_off(void) { (void) SLtt_set_cursor_visibility (0); SLtt_flush_output (); return Qnil; } /* the following minibuffer functions are retrieved from 'most' sources */ SLang_RLine_Info_Type *RLI; static void rline_update (unsigned char *buf, int len, int col) { SLsmg_gotorc (SLtt_Screen_Rows - 1, 0); SLsmg_write_nchars ((char *) buf, len); SLsmg_erase_eol (); SLsmg_gotorc (SLtt_Screen_Rows - 1, col); SLsmg_refresh (); } /* I want to use mouse left button click as RETURN key */ static void mouse_cmd (void) { /* Discard mouse info */ (void) SLang_getkey (); (void) SLang_getkey (); (void) SLang_getkey (); (void) SLang_ungetkey ('\r'); } static void g_abort (void) { /* (void) SLang_getkey (); */ (void) SLang_ungetkey ('\r'); SLKeyBoard_Quit = 1; /* SLang_Error == SL_USER_BREAK; */ } static void completion (void) { VALUE comp_str; char *s; if (rb_respond_to(mSlang, rb_intern("completion"))) { comp_str = rb_funcall(mSlang, rb_intern("completion"), 1, rb_str_new2(RLI->buf)); } else comp_str = Qnil; if (comp_str != Qnil) { Check_Type(comp_str, T_STRING); s = RSTRING(comp_str)->ptr; strncpy ((char *) RLI->buf, s, LONG_STRING - 1); RLI->point = strlen (s); RLI->len = strlen (s); } } static SLang_RLine_Info_Type *init_readline (void) { unsigned char *buf = NULL; SLang_RLine_Info_Type *rli; if ((NULL == (rli = (SLang_RLine_Info_Type *) SLMALLOC (sizeof(SLang_RLine_Info_Type)))) || (NULL == (buf = (unsigned char *) SLMALLOC (LONG_STRING)))) { fprintf(stderr, "malloc error.\n"); exit(-1); } SLMEMSET ((char *) rli, 0, sizeof (SLang_RLine_Info_Type)); rli->buf = buf; rli->buf_len = LONG_STRING - 1; rli->tab = 8; rli->dhscroll = 20; rli->getkey = SLang_getkey; rli->tt_goto_column = NULL; rli->update_hook = rline_update; if (SLang_init_readline (rli) < 0) { SLang_exit_error ("Unable to initialize readline library."); } SLkm_define_key ("\033[M", (FVOID_STAR)mouse_cmd, rli->keymap); SLkm_define_key ("\011", (FVOID_STAR)completion, rli->keymap); /* tab */ SLkm_define_key ("\007", (FVOID_STAR)g_abort, rli->keymap); return rli; } static int read_from_line(char *prompt, char *what, int noecho) { int i; if (RLI == NULL) { RLI = init_readline (); } RLI->edit_width = SLtt_Screen_Cols - 1; RLI->prompt = prompt; *RLI->buf = 0; if (noecho) RLI->flags |= SL_RLINE_NO_ECHO; /* SLsmg_refresh (); */ /* Last_Message = NULL; */ /* Minibuffer_Selected = 1; */ /* do not use default. The up arrow can always get it back. */ if (*what) { strncpy ((char *) RLI->buf, what, LONG_STRING - 1); RLI->point = strlen (what); } /* next routine returns -1 upon quit */ i = SLang_read_line (RLI); if ((i > 0) && !SLang_Error && !SLKeyBoard_Quit) { SLang_rline_save_line (RLI); strncpy(what, (char *) RLI->buf, LONG_STRING - 1); } if (SLKeyBoard_Quit) /* && SLang_Error == SL_USER_BREAK) */ i = -1; SLang_Error = SLKeyBoard_Quit = 0; /* Minibuffer_Selected = 0; */ /* if (i == -1) mini_message ("Aborted!", 1); */ return(i); } static VALUE sl_read_line(VALUE obj, VALUE prompt, VALUE init_val, VALUE noecho) { char what[LONG_STRING]; VALUE ary; int n; Check_Type(prompt, T_STRING); if (init_val != Qnil) { Check_Type(init_val, T_STRING); strncpy(what, RSTRING(init_val)->ptr, LONG_STRING - 1); } else what[0] = 0; n = read_from_line(RSTRING(prompt)->ptr, what, (noecho != Qnil)?1:0); ary = rb_ary_new2(2); rb_ary_push(ary, INT2FIX(n)); rb_ary_push(ary, rb_str_new2(what)); return ary; } static VALUE sl_set_slang_error(VALUE obj, VALUE n) { SLang_Error = NUM2INT(n); return Qnil; } static VALUE sl_set_slkeyboard_quit(VALUE obj, VALUE n) { SLKeyBoard_Quit = NUM2INT(n); return Qnil; } static VALUE slsmg_tab_width(void) { return INT2FIX(SLsmg_Tab_Width); } /* -------------------- SLscroll_window class -------------------- */ #if 0 /* from slang.h */ typedef struct { unsigned int flags; SLscroll_Type *top_window_line; /* list element at top of window */ SLscroll_Type *bot_window_line; /* list element at bottom of window */ SLscroll_Type *current_line; /* current list element */ SLscroll_Type *lines; /* first list element */ unsigned int nrows; /* number of rows in window */ unsigned int hidden_mask; /* applied to flags in SLscroll_Type */ unsigned int line_num; /* current line number (visible) */ unsigned int num_lines; /* total number of lines (visible) */ unsigned int window_row; /* row of current_line in window */ unsigned int border; /* number of rows that form scroll borde */ int cannot_scroll; /* should window scroll or recenter */ } SLscroll_Window_Type; #endif typedef struct _File_Line_Type { struct _File_Line_Type *next; struct _File_Line_Type *prev; VALUE data; /* pointer to line data */ } File_Line_Type; typedef struct _scrWdata { SLscroll_Window_Type *Line_Window; File_Line_Type *Lines; File_Line_Type *Last_Line; /* File_Line_Type *line; */ int cursor_line_color; int normal_color; int bar; int tilde; } scrWdata; static void free_lines(scrWdata *scrWp) { File_Line_Type *line, *next; line = scrWp->Lines; while (line != NULL) { next = line->next; free (line); line = next; } } static void free_scrW (scrWdata *scrWp) { if (scrWp->Line_Window) free(scrWp->Line_Window); free_lines(scrWp); } /* def new */ static VALUE scrW_new(class) VALUE class; { VALUE obj; scrWdata *scrWp; obj = Data_Make_Struct(class, scrWdata, 0, free_scrW, scrWp); scrWp->Line_Window = (SLscroll_Window_Type *) malloc(sizeof(SLscroll_Window_Type)); if (NULL == scrWp->Line_Window) return Qnil; memset ((char *)scrWp->Line_Window, 0, sizeof (SLscroll_Window_Type)); scrWp->Lines = NULL; scrWp->Last_Line = NULL; /* scrWp->line = NULL; */ scrWp->cursor_line_color = SL_BG_COLORS + SL_CYAN; /* FG=BLACK BG=CYAN */ scrWp->normal_color = SL_BG_LGRAY + SL_BLACK; /* FG=BLACK BG=LIGHTGRAY */ scrWp->bar = 0; scrWp->tilde = 1; return obj; } /* def add_line(data) */ static VALUE scrW_add_line(obj, data) VALUE obj; VALUE data; { scrWdata *scrWp; File_Line_Type *line; line = (File_Line_Type *) malloc (sizeof (File_Line_Type)); if (line == NULL) return INT2NUM((long)0); memset ((char *) line, sizeof (File_Line_Type), 0); line->data = data; Data_Get_Struct(obj, scrWdata, scrWp); if (scrWp->Lines == NULL) { scrWp->Lines = line; line->prev = NULL; } else { /* find last */ scrWp->Last_Line->next = line; line->prev = scrWp->Last_Line; } line->next = NULL; scrWp->Last_Line = line; return (VALUE)(((long)line) | FIXNUM_FLAG); } /* def insert_line(id, data) */ static VALUE scrW_insert_line(obj, id, data) VALUE obj; VALUE id; VALUE data; { scrWdata *scrWp; File_Line_Type *line; line = (File_Line_Type *) malloc (sizeof (File_Line_Type)); if (line == NULL) return INT2NUM((long)0); memset ((char *) line, sizeof (File_Line_Type), 0); line->data = data; Data_Get_Struct(obj, scrWdata, scrWp); if (scrWp->Lines == NULL) { scrWp->Lines = line; line->prev = NULL; line->next = NULL; scrWp->Line_Window->top_window_line = (SLscroll_Type *) line; scrWp->Line_Window->lines = (SLscroll_Type *) line; } else { /* find id */ File_Line_Type *p, *q; q = (File_Line_Type *)(id & ~FIXNUM_FLAG); for (p = scrWp->Lines; NULL != p->next; p = p->next) if (p == q) break; if (p != q) return INT2NUM((long)0); if (NULL == p->next) { /* add to last */ p->next = line; line->prev = p; line->next = NULL; scrWp->Last_Line = line; } else { line->next = p->next; line->prev = p; p->next->prev = line; p->next = line; } } return (VALUE)(((long)line) | FIXNUM_FLAG); } /* def replace_line(id, data) */ static VALUE scrW_replace_line(obj, id, data, cr) VALUE obj; VALUE id; VALUE data; VALUE cr; { scrWdata *scrWp; File_Line_Type *line; File_Line_Type *p, *q; line = (File_Line_Type *) malloc (sizeof (File_Line_Type)); if (line == NULL) return INT2NUM((long)0); memset ((char *) line, sizeof (File_Line_Type), 0); line->data = data; Data_Get_Struct(obj, scrWdata, scrWp); if (scrWp->Lines == NULL) { return INT2NUM((long)0); } /* find id */ q = (File_Line_Type *)(id & ~FIXNUM_FLAG); for (p = scrWp->Lines; NULL != p->next; p = p->next) if (p == q) break; if (p != q) return INT2NUM((long)0); if (p == scrWp->Lines) { /* first */ line->prev = NULL; line->next = p->next; if (NULL == p->next) scrWp->Last_Line = line; else p->next->prev = line; free(p); scrWp->Lines = line; /* because I modified the 1st entry ... */ scrWp->Line_Window->lines = (SLscroll_Type *) line; scrWp->Line_Window->top_window_line = (SLscroll_Type *) line; /* scrWp->Line_Window->current_line = (SLscroll_Type *) line; */ } else if (NULL == p->next) { /* last */ line->prev = p->prev; line->next = NULL; p->prev->next = line; scrWp->Last_Line = line; free(p); } else { line->prev = p->prev; line->next = p->next; p->prev->next = line; p->next->prev = line; free(p); } /* the following seems redundant, but necessary, why ? */ if (scrWp->Line_Window->top_window_line == (SLscroll_Type *)p) scrWp->Line_Window->top_window_line = (SLscroll_Type *) line; /* if (NUM2INT(cr) == 0) scrWp->Line_Window->top_window_line = (SLscroll_Type *) line; */ if (scrWp->Line_Window->current_line == (SLscroll_Type *)p) scrWp->Line_Window->current_line = (SLscroll_Type *) line; if (scrWp->Line_Window->bot_window_line == (SLscroll_Type *)p) scrWp->Line_Window->bot_window_line = (SLscroll_Type *) line; return (VALUE)(((long)line) | FIXNUM_FLAG); } /* def remove_line(id) */ static VALUE scrW_remove_line(obj, id) VALUE obj; VALUE id; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); if (scrWp->Lines == NULL) { return Qnil; } else { /* find id */ File_Line_Type *p, *q; /* q = (File_Line_Type *) NUM2INT(id); */ q = (File_Line_Type *)(id & ~FIXNUM_FLAG); for (p = scrWp->Lines; NULL != p->next; p = p->next) if (p == q) break; if (p != q) return Qnil; if (p == scrWp->Lines) { /* first */ p->next->prev = NULL; scrWp->Lines = p->next; if (scrWp->Line_Window->top_window_line == (SLscroll_Type *)p) scrWp->Line_Window->top_window_line = (SLscroll_Type *) p->next; free(p); } else if (NULL == p->next) { if (p == q) { /* remove last entry */ p->prev->next = NULL; scrWp->Last_Line = p->prev; if (scrWp->Line_Window->top_window_line == (SLscroll_Type *)p) scrWp->Line_Window->top_window_line = NULL; free (p); } else return Qnil; } else { p->next->prev = p->prev; p->prev->next = p->next; if (scrWp->Line_Window->top_window_line == (SLscroll_Type *)p) scrWp->Line_Window->top_window_line = (SLscroll_Type *) p->next; free (p); } } return TRUE; } /* def init_lines(n) */ static VALUE scrW_init_lines(obj, n) VALUE obj; VALUE n; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); scrWp->Line_Window->current_line = (SLscroll_Type *) scrWp->Lines; scrWp->Line_Window->lines = (SLscroll_Type *) scrWp->Lines; scrWp->Line_Window->line_num = 1; scrWp->Line_Window->num_lines = NUM2INT(n); return Qnil; } static VALUE scrW_current_line(obj) VALUE obj; { scrWdata *scrWp; File_Line_Type *line; Data_Get_Struct(obj, scrWdata, scrWp); line = (File_Line_Type *) scrWp->Line_Window->current_line; return line->data; } void erase_eol (int last_col, int put_bar) { int len; len = last_col - SLsmg_get_column () + 1; if (len < 0) return; while (len-- > 0) SLsmg_write_char(' '); if (put_bar) SLsmg_write_char(BAR_CHAR); } static VALUE slsmg_erase_eol2(obj, last_col, put_bar) VALUE obj; VALUE last_col; VALUE put_bar; { int lc = NUM2INT(last_col); int bar = NUM2INT(put_bar); erase_eol(lc, bar); return Qnil; } static int expand_tab(char *s, int cur_col, char *buf, int buf_size) { char *pp, *d, *d_end; int len; int tab_pos; tab_pos = SLsmg_Tab_Width; d_end = buf + buf_size; for (d = buf, pp = s; d < d_end-1 && *pp != '\n' && *pp != '\0';) if ('\t' == *pp) { while (d - buf + cur_col >= tab_pos) tab_pos += SLsmg_Tab_Width; while (pp < d_end-1 && ((d - buf + cur_col) < tab_pos)) *d++ = ' '; ++pp; } else *d++ = *pp++; *d = '\0'; len = strlen(buf); return len; } static VALUE sl_tabbed_len(VALUE obj, VALUE str) { int len; char buf[LONG_STRING]; Check_Type(str, T_STRING); len = expand_tab(RSTRING(str)->ptr, 0, buf, LONG_STRING); return INT2FIX(len); } static VALUE sl_expand_tab(VALUE obj, VALUE str) { int len; char buf[LONG_STRING]; Check_Type(str, T_STRING); len = expand_tab(RSTRING(str)->ptr, 0, buf, LONG_STRING); return rb_str_new2(buf); } #ifdef HAVE_KANJI_POS #define KANJI_POS(c, code) kanji_pos((c), (code)) #else /* this code is in Japanese version S-Lang library slkanji.c The original version was written by Kikutani, But this is written by Katsuta-san or Yoshino-san ?? I'm not sure */ #define ASCII 0 #define EUC 1 #define JIS 2 #define SJIS 3 static int iskanji(int c, int code) /*{{{*/ { /* if(!code) return FALSE; */ c = (c & 0xff); if(code == SJIS) { if((0x80 < c && c < 0xa0) || (0xe0 <= c && c <= 0xfc)) return TRUE; } else if(code == EUC) { if(0xa0 < c && c < 0xff) return TRUE; if(c == 0x8e) return TRUE; /* fake */ } else if(code == JIS) { if(0x20 < c && c < 0x7f) return TRUE; } return FALSE; } static int Mykanji_pos(unsigned char *beg, unsigned char *pos) /*{{{*/ { unsigned char *p = beg; if((beg == pos) || !iskanji(*(pos-1), EUC)) { if (iskanji(*pos, EUC)) return 1; /* KNAJI 1st byte */ else return ASCII; /* ASCII: 0 */ } while(p < pos) { if (iskanji(*p, EUC)) p++; p++; } if(p != pos) return (p - pos +1); if(iskanji(*p, EUC)) return 1; return ASCII; } #define KANJI_POS(c, code) Mykanji_pos((c), (code)) #endif static void write_string(VALUE self, char *s, int off, int last_col, VALUE hlrex, int normal_color) { char blank = ' '; char *p = s+off; int len, cur_col, col_width; char buf[LONG_STRING]; VALUE array, *ary; int ary_len = 0; if (strlen(s) < off) return; if (KANJI_POS(s, p) == 2) { /* Kanji second byte */ SLsmg_write_nchars (&blank, 1); ++p; } cur_col = SLsmg_get_column (); /* convert tabs */ len = expand_tab(p, cur_col, buf, LONG_STRING); /* it is necesary that calculating regexp array for expanded string */ if (rb_respond_to(self, rb_intern("get_hlarray"))) { array = rb_funcall(self, rb_intern("get_hlarray"), 2, rb_str_new2(buf), hlrex); // (VALUE)(long)buf, Qnil); // hlrex); } else array = Qnil; if (array != Qnil) { ary = (VALUE *)RARRAY(array)->ptr; ary_len = RARRAY(array)->len; } col_width = last_col - cur_col + 1; if (col_width <= len) SLsmg_write_nchars (buf, col_width); /* maybe consider regexp here, too */ else { if (ary_len > 0) { int i, b, ln, bufp; bufp = 0; for (i = 0; i < ary_len; i++) { VALUE *a; int color; /* in slang.rb/ def get_hlarray pa << [line.index(s), s.length, color] */ a = (VALUE *) RARRAY(ary[i])->ptr; b = NUM2INT(a[0]); ln = NUM2INT(a[1]); color = NUM2INT(a[2]); if (b - bufp > 0) { SLsmg_set_color(normal_color); SLsmg_write_nchars (buf+bufp, b-bufp); } SLsmg_set_color(color); SLsmg_write_nchars (buf+b, ln); bufp = b + ln; } SLsmg_set_color(normal_color); if (bufp < len) SLsmg_write_nchars (buf+bufp, len-bufp); } else { SLsmg_write_nchars (buf, len); #if 0 /* this is done by erase_eol ?? */ for (i = 0; i < col_width - len; ++i) SLsmg_write_nchars (&blank, 1); #endif } } #ifndef HAVE_KANJI_POS /* means not slang-ja */ if (KANJI_POS(s, p) == 1) { /* Kanji first byte */ SLsmg_write_char (' '); } #endif } static VALUE sl_write_string_with_offset(VALUE obj, VALUE self, VALUE s, VALUE off, VALUE ce, VALUE hlrex, VALUE ncolor) { int normal_color; scrWdata *scrWp; Check_Type(s, T_STRING); normal_color = NUM2INT(ncolor); if (strlen(RSTRING(s)->ptr) >= LONG_STRING){ static char buf[LONG_STRING]; strncpy(buf, RSTRING(s)->ptr, LONG_STRING); write_string (self, buf, NUM2INT(off), NUM2INT(ce), hlrex, normal_color); } else write_string (self, RSTRING(s)->ptr, NUM2INT(off), NUM2INT(ce), hlrex, normal_color); return Qnil; } /* def update_region(n) */ static VALUE scrW_update_region(obj, self, rbegin, rend, cbegin, cend, offset, cursor_line) VALUE obj; VALUE self; VALUE rbegin; VALUE rend; VALUE cbegin; VALUE cend; VALUE offset; VALUE cursor_line; { int row; File_Line_Type *line; scrWdata *scrWp; int b = NUM2INT(rbegin); int e = NUM2INT(rend); int cb = NUM2INT(cbegin); int ce = NUM2INT(cend); /* int off = NUM2INT(offset); */ int curline = NUM2INT(cursor_line); Data_Get_Struct(obj, scrWdata, scrWp); if (e <= b || ce <= cb) return FALSE; scrWp->Line_Window->nrows = e - b + 1; if (scrWp->Line_Window->top_window_line != NULL) { scrWp->Line_Window->current_line = scrWp->Line_Window->top_window_line; if (SLscroll_find_line_num (scrWp->Line_Window) < 0) return FALSE; } SLscroll_find_top (scrWp->Line_Window); row = b; line = (File_Line_Type *) scrWp->Line_Window->top_window_line; while (row < e) { SLsmg_gotorc (row, cb); if (SLtt_Use_Ansi_Colors) { if (row == curline) SLsmg_set_color(scrWp->cursor_line_color); else SLsmg_set_color(scrWp->normal_color); } else { if (row == curline) SLsmg_normal_video (); else SLsmg_reverse_video (); } if (line == NULL) { if (scrWp->tilde != 0) SLsmg_write_char ('~'); } else { if (rb_respond_to(self, rb_intern("write_line"))) { rb_funcall(self, rb_intern("write_line"), 2, (VALUE)(long)line->data, INT2NUM(row)); /* rb_funcall(self, rb_intern("write_line"), 2, line->data, INT2NUM(row)); */ } else { /* assume string */ Check_Type((VALUE)line->data, T_STRING); SLsmg_write_string (RSTRING(line->data)->ptr); } /* if (strlen(line->data) <= off+1) SLsmg_write_string (""); */ line = line->next; } erase_eol(ce, scrWp->bar); #if 0 if (row == curline) { if (SLtt_Use_Ansi_Colors) SLsmg_set_color(scrWp->normal_color); else SLsmg_normal_video (); } #endif row++; } return TRUE; } static VALUE scrW_main_loop(VALUE obj, VALUE self) { VALUE res; int key; for (;;) { rb_funcall(self, rb_intern("check_winch"), 0); rb_funcall(self, rb_intern("update_display"), 0); res = Qfalse; key = SLkp_getkey(); if (key == 'j') rb_funcall(self, rb_intern("forw_scr"), 0); else if (key == 'k') rb_funcall(self, rb_intern("back_scr"), 0); else res = rb_funcall(self, rb_intern("key_actions_call"), 1, INT2NUM(key)); if (rb_ivar_get(self, rb_intern("@do_break")) == Qtrue) break; } return Qnil; } /* SLsmg_normal_video (); */ static VALUE scrW_pageup(obj) VALUE obj; { scrWdata *scrWp; int res; Data_Get_Struct(obj, scrWdata, scrWp); res = SLscroll_pageup (scrWp->Line_Window); return INT2NUM(res); } static VALUE scrW_pagedown(obj) VALUE obj; { scrWdata *scrWp; int res; Data_Get_Struct(obj, scrWdata, scrWp); res = SLscroll_pagedown (scrWp->Line_Window); return INT2NUM(res); } static VALUE scrW_prev_n(obj, n) VALUE obj; VALUE n; { scrWdata *scrWp; int res; Data_Get_Struct(obj, scrWdata, scrWp); res = SLscroll_prev_n(scrWp->Line_Window, NUM2INT(n)); scrWp->Line_Window->top_window_line = scrWp->Line_Window->current_line; return INT2NUM( res ); } static VALUE scrW_next_n(obj, n) VALUE obj; VALUE n; { scrWdata *scrWp; int res; Data_Get_Struct(obj, scrWdata, scrWp); res = SLscroll_next_n(scrWp->Line_Window, NUM2INT(n)); scrWp->Line_Window->top_window_line = scrWp->Line_Window->current_line; return INT2NUM( res ); } static VALUE scrW_top_window_line_is_current_line(obj) VALUE obj; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); scrWp->Line_Window->top_window_line = scrWp->Line_Window->current_line; return Qnil; } static VALUE scrW_nrows(obj) VALUE obj; { int n; scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); n = scrWp->Line_Window->nrows; return INT2FIX(n); } static VALUE scrW_line_num(obj) VALUE obj; { int n; scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); n = scrWp->Line_Window->line_num; return INT2FIX(n); } static VALUE scrW_get_cursor_line_color(obj) VALUE obj; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); return INT2FIX(scrWp->cursor_line_color); } static VALUE scrW_get_normal_color(obj) VALUE obj; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); return INT2FIX(scrWp->normal_color); } static VALUE scrW_num_lines(obj) VALUE obj; { int n; scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); n = scrWp->Line_Window->num_lines; return INT2FIX(n); } static VALUE scrW_window_row(obj) VALUE obj; { int n; scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); n = scrWp->Line_Window->window_row; return INT2FIX(n); } static VALUE scrW_set_nrows(obj, n) VALUE obj; VALUE n; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); scrWp->Line_Window->nrows = NUM2INT(n); return Qnil; } static VALUE scrW_set_cursor_line_color(obj, n) VALUE obj; VALUE n; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); scrWp->cursor_line_color = NUM2INT(n); return Qnil; } static VALUE scrW_set_normal_color(obj, n) VALUE obj; VALUE n; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); scrWp->normal_color = NUM2INT(n); return Qnil; } static VALUE scrW_set_bar(obj, n) VALUE obj; VALUE n; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); scrWp->bar = NUM2INT(n); return Qnil; } static VALUE scrW_set_tilde(obj, n) VALUE obj; VALUE n; { scrWdata *scrWp; Data_Get_Struct(obj, scrWdata, scrWp); scrWp->tilde = NUM2INT(n); return Qnil; } /* -- used fo search -- */ static File_Line_Type *find_line = NULL; /* def position_nth_line(n) */ static VALUE scrW_find_set_nth_line(obj, n) VALUE obj; VALUE n; { File_Line_Type *line; scrWdata *scrWp; int i; Data_Get_Struct(obj, scrWdata, scrWp); for (i = 0, line = (File_Line_Type *) scrWp->Line_Window->lines; line && i < NUM2INT(n); ++i, line = line->next) ; find_line = line; return Qnil; } static VALUE scrW_find_next_line(void) { File_Line_Type *next; if (find_line) { next = find_line->next; if (NULL == next) return FALSE; find_line = next; return TRUE; } return FALSE; } static VALUE scrW_find_prev_line(void) { File_Line_Type *prev; if (find_line) { prev = find_line->prev; if (NULL == prev) return FALSE; find_line = prev; return TRUE; } return FALSE; } #if 0 static VALUE scrW_find_line(obj, cur_line) VALUE obj; VALUE cur_line; { scrWdata *scrWp; File_Line_Type *line; VALUE argv[2]; Data_Get_Struct(obj, scrWdata, scrWp); if (!rb_respond_to(self, rb_intern("find_line"))) { return Qnil; } if (scrWp->Lines == NULL) { return Qnil; } else { /* find id */ File_Line_Type *p, *q; q = (File_Line_Type *)(cur_id & ~FIXNUM_FLAG); for (p = scrWp->Lines; NULL != p; p = p->next) ; if (NULL == p) return Qnil; argv[0] = line->data; for (; NULL != p; p = p->next) ; rb_funcall2(self, rb_intern("write_line"), 2, argv); return FALSE; } #endif static VALUE scrW_find_current_line(void) { if (find_line) return find_line->data; return Qnil; } #ifdef HAVE_ISKCODE /* slang for jed */ #include #endif /*------------------------- Initialization -------------------------*/ void Init_slanglib() { mSlang = rb_define_module("Slanglib"); rb_define_module_function(mSlang, "sl_get_winch_flag", sl_get_winch_flag, 0); rb_define_module_function(mSlang, "sl_clr_winch_flag", sl_clr_winch_flag, 0); rb_define_module_function(mSlang, "sltt_get_screen_size", sltt_get_screen_size, 0); rb_define_module_function(mSlang, "slsig_block_signals", slsig_block_signals, 0); rb_define_module_function(mSlang, "slsmg_set_char_set", slsmg_set_char_set, 1); rb_define_module_function(mSlang, "slsmg_suspend_smg", slsmg_suspend_smg, 0); rb_define_module_function(mSlang, "slsmg_resume_smg", slsmg_resume_smg, 0); rb_define_module_function(mSlang, "slsmg_erase_eos", slsmg_erase_eos, 0); rb_define_module_function(mSlang, "slsmg_char_at", slsmg_char_at, 0); rb_define_module_function(mSlang, "slsmg_draw_object", slsmg_draw_object, 3); rb_define_module_function(mSlang, "slsmg_set_screen_start", slsmg_set_screen_start, 2); rb_define_module_function(mSlang, "slsmg_write_color_chars", slsmg_write_color_chars, 2); rb_define_module_function(mSlang, "slsmg_read_raw", slsmg_write_raw, 1); rb_define_module_function(mSlang, "slsmg_write_raw", slsmg_write_raw, 2); rb_define_module_function(mSlang, "slsmg_set_color_in_region", slsmg_set_color_in_region, 5); rb_define_module_function(mSlang, "slsmg_normal_video", slsmg_normal_video, 0); rb_define_module_function(mSlang, "slsmg_reverse_video", slsmg_reverse_video, 0); rb_define_module_function(mSlang, "slsmg_gotorc", slsmg_gotorc, 2); rb_define_module_function(mSlang, "slsmg_printf", slsmg_printf, -1); rb_define_module_function(mSlang, "slsmg_erase_eol", slsmg_erase_eol, 0); rb_define_module_function(mSlang, "slsmg_erase_eol2", slsmg_erase_eol2, 2); rb_define_module_function(mSlang, "slsmg_refresh", slsmg_refresh, 0); rb_define_module_function(mSlang, "slsig_unblock_signals", slsig_unblock_signals, 0); rb_define_module_function(mSlang, "slkp_getkey", slkp_getkey, 0); rb_define_module_function(mSlang, "slang_getkey", slang_getkey, 0); rb_define_module_function(mSlang, "sl_reset", sl_reset, 0); rb_define_module_function(mSlang, "sltt_set_color", sltt_set_color, 3); rb_define_module_function(mSlang, "sltt_beep", sltt_beep, 0); rb_define_module_function(mSlang, "slkp_define_keysym", slkp_define_keysym, 2); rb_define_module_function(mSlang, "sltt_screen_rows", sltt_screen_rows, 0); rb_define_module_function(mSlang, "sltt_screen_cols", sltt_screen_cols, 0); rb_define_module_function(mSlang, "slsmg_write_string", slsmg_write_string, 1); rb_define_module_function(mSlang, "slsmg_write_wrapped_string", slsmg_write_wrapped_string, 6); rb_define_module_function(mSlang, "slsmg_set_color", slsmg_set_color, 1); rb_define_module_function(mSlang, "slsmg_forward", slsmg_forward, 1); rb_define_module_function(mSlang, "sl_color_terminal?", sl_color_terminal, 0); rb_define_module_function(mSlang, "slsmg_write_nchars", slsmg_write_nchars, 2); rb_define_module_function(mSlang, "slsmg_write_char", slsmg_write_char, 1); rb_define_module_function(mSlang, "sl_mouse_on", sl_mouse_on, 0); rb_define_module_function(mSlang, "sl_mouse_off", sl_mouse_off, 0); rb_define_module_function(mSlang, "sl_get_mouse_rc", sl_get_mouse_rc, 0); rb_define_module_function(mSlang, "slsmg_cls", slsmg_cls, 0); rb_define_module_function(mSlang, "slsmg_draw_hline", slsmg_draw_hline, 1); rb_define_module_function(mSlang, "slsmg_draw_vline", slsmg_draw_vline, 1); rb_define_module_function(mSlang, "slsmg_draw_box", slsmg_draw_box, 4); rb_define_module_function(mSlang, "slsmg_touch_lines", slsmg_touch_lines, 2); rb_define_module_function(mSlang, "slsmg_get_column", slsmg_get_column, 0); rb_define_module_function(mSlang, "slsmg_tab_width", slsmg_tab_width, 0); rb_define_module_function(mSlang, "sl_tabbed_len", sl_tabbed_len, 1); rb_define_module_function(mSlang, "sl_expand_tab", sl_expand_tab, 1); rb_define_module_function(mSlang, "slsmg_get_row", slsmg_get_row, 0); rb_define_module_function(mSlang, "slang_reset_tty", slang_reset_tty, 0); rb_define_module_function(mSlang, "slsmg_reset_smg", slsmg_reset_smg, 0); rb_define_module_function(mSlang, "slsmg_init_smg", slsmg_init_smg, 0); rb_define_module_function(mSlang, "slang_init_tty", slang_init_tty, 3); rb_define_module_function(mSlang, "sltt_get_terminfo", sltt_get_terminfo, 0); rb_define_module_function(mSlang, "slkp_init", slkp_init, 0); rb_define_module_function(mSlang, "sltt_set_mouse_mode", sltt_set_mouse_mode, 2); rb_define_module_function(mSlang, "sltty_set_suspend_state", sltty_set_suspend_state, 1); rb_define_module_function(mSlang, "sl_init_signals", sl_init_signals, 0); rb_define_module_function(mSlang, "sl_init_colors", sl_init_colors, 0); rb_define_module_function(mSlang, "slang_cursor_on", slang_cursor_on, 0); rb_define_module_function(mSlang, "slang_cursor_off", slang_cursor_off, 0); rb_define_module_function(mSlang, "sl_read_line", sl_read_line, 3); rb_define_module_function(mSlang, "sl_input_pending", sl_input_pending, 1); rb_define_module_function(mSlang, "sl_set_slang_error", sl_set_slang_error, 1); rb_define_module_function(mSlang, "sl_set_slkeyboard_quit", sl_set_slkeyboard_quit, 1); rb_define_module_function(mSlang, "sl_write_string_with_offset", sl_write_string_with_offset, 6); rb_define_module_function(mSlang, "slsmg_fill_region", slsmg_fill_region, 5); /* rb_define_module_function(mSlang, "", , 0); */ #if 0 /* not yet implemented */ extern void SLsmg_vprintf (char *, va_list); extern int SLsmg_Scroll_Hash_Border; extern int SLsmg_Display_Eight_Bit; #endif rb_define_const(mSlang, "SL_KEY_ERR", INT2FIX(SL_KEY_ERR)); rb_define_const(mSlang, "SL_KEY_UP", INT2FIX(SL_KEY_UP)); rb_define_const(mSlang, "SL_KEY_DOWN", INT2FIX(SL_KEY_DOWN)); rb_define_const(mSlang, "SL_KEY_LEFT", INT2FIX(SL_KEY_LEFT)); rb_define_const(mSlang, "SL_KEY_RIGHT", INT2FIX(SL_KEY_RIGHT)); rb_define_const(mSlang, "SL_KEY_PPAGE", INT2FIX(SL_KEY_PPAGE)); rb_define_const(mSlang, "SL_KEY_NPAGE", INT2FIX(SL_KEY_NPAGE)); rb_define_const(mSlang, "SL_KEY_HOME", INT2FIX(SL_KEY_HOME)); rb_define_const(mSlang, "SL_KEY_END", INT2FIX(SL_KEY_END)); rb_define_const(mSlang, "SL_KEY_A1", INT2FIX(SL_KEY_A1)); rb_define_const(mSlang, "SL_KEY_A3", INT2FIX(SL_KEY_A3)); rb_define_const(mSlang, "SL_KEY_B2", INT2FIX(SL_KEY_B2)); rb_define_const(mSlang, "SL_KEY_C1", INT2FIX(SL_KEY_C1)); rb_define_const(mSlang, "SL_KEY_C3", INT2FIX(SL_KEY_C3)); rb_define_const(mSlang, "SL_KEY_REDO", INT2FIX(SL_KEY_REDO)); rb_define_const(mSlang, "SL_KEY_UNDO", INT2FIX(SL_KEY_UNDO)); rb_define_const(mSlang, "SL_KEY_BACKSPACE", INT2FIX(SL_KEY_BACKSPACE)); rb_define_const(mSlang, "SL_KEY_ENTER", INT2FIX(SL_KEY_ENTER)); rb_define_const(mSlang, "SL_KEY_IC", INT2FIX(SL_KEY_IC)); rb_define_const(mSlang, "SL_KEY_DELETE", INT2FIX(SL_KEY_DELETE)); rb_define_const(mSlang, "SL_KEY_F0", INT2FIX(SL_KEY_F0)); rb_define_const(mSlang, "SL_KEY_F1", INT2FIX(SL_KEY_F(1))); rb_define_const(mSlang, "SL_KEY_F2", INT2FIX(SL_KEY_F(2))); rb_define_const(mSlang, "SL_KEY_F3", INT2FIX(SL_KEY_F(3))); rb_define_const(mSlang, "SL_KEY_F4", INT2FIX(SL_KEY_F(4))); rb_define_const(mSlang, "SL_KEY_F5", INT2FIX(SL_KEY_F(5))); rb_define_const(mSlang, "SL_KEY_F6", INT2FIX(SL_KEY_F(6))); rb_define_const(mSlang, "SL_KEY_F7", INT2FIX(SL_KEY_F(7))); rb_define_const(mSlang, "SL_KEY_F8", INT2FIX(SL_KEY_F(8))); rb_define_const(mSlang, "SL_KEY_F9", INT2FIX(SL_KEY_F(9))); rb_define_const(mSlang, "SL_KEY_F10", INT2FIX(SL_KEY_F(10))); rb_define_const(mSlang, "SL_KEY_F11", INT2FIX(SL_KEY_F(11))); rb_define_const(mSlang, "SL_KEY_F12", INT2FIX(SL_KEY_F(12))); rb_define_const(mSlang, "SL_BG_WHITE", INT2FIX(SL_BG_WHITE)); rb_define_const(mSlang, "SL_BG_LGRAY", INT2FIX(SL_BG_LGRAY)); rb_define_const(mSlang, "SL_BG_BLUE", INT2FIX(SL_BG_BLUE)); rb_define_const(mSlang, "SL_BG_COLORS", INT2FIX(SL_BG_COLORS)); rb_define_const(mSlang, "SL_USER_COLOR", INT2FIX(SL_USER_COLOR)); rb_define_const(mSlang, "SL_BLACK", INT2FIX(SL_BLACK)); rb_define_const(mSlang, "SL_RED", INT2FIX(SL_RED)); rb_define_const(mSlang, "SL_GREEN", INT2FIX(SL_GREEN)); rb_define_const(mSlang, "SL_BROWN", INT2FIX(SL_BROWN)); rb_define_const(mSlang, "SL_BLUE", INT2FIX(SL_BLUE)); rb_define_const(mSlang, "SL_MAGENTA", INT2FIX(SL_MAGENTA)); rb_define_const(mSlang, "SL_CYAN", INT2FIX(SL_CYAN)); rb_define_const(mSlang, "SL_LIGHTGRAY", INT2FIX(SL_LIGHTGRAY)); rb_define_const(mSlang, "SL_GRAY", INT2FIX(SL_GRAY)); rb_define_const(mSlang, "SL_BRIGHTRED", INT2FIX(SL_BRIGHTRED)); rb_define_const(mSlang, "SL_BRIGHTGREEN", INT2FIX(SL_BRIGHTGREEN)); rb_define_const(mSlang, "SL_YELLOW", INT2FIX(SL_YELLOW)); rb_define_const(mSlang, "SL_BRIGHTBLUE", INT2FIX(SL_BRIGHTBLUE)); rb_define_const(mSlang, "SL_BRIGHTMAGENTA", INT2FIX(SL_BRIGHTMAGENTA)); rb_define_const(mSlang, "SL_BRIGHTCYAN", INT2FIX(SL_BRIGHTCYAN)); rb_define_const(mSlang, "SL_WHITE", INT2FIX(SL_WHITE)); cScrW = rb_define_class_under(mSlang, "Scroll_window", rb_cObject); rb_define_singleton_method(cScrW, "new", scrW_new, 0); rb_define_method(cScrW, "add_line", scrW_add_line, 1); rb_define_method(cScrW, "insert_line", scrW_insert_line, 2); rb_define_method(cScrW, "replace_line", scrW_replace_line, 3); rb_define_method(cScrW, "remove_line", scrW_remove_line, 1); rb_define_method(cScrW, "init_lines", scrW_init_lines, 1); rb_define_method(cScrW, "update_region", scrW_update_region, 7); rb_define_method(cScrW, "main_loop", scrW_main_loop, 1); rb_define_method(cScrW, "scroll_prev_n", scrW_prev_n, 1); rb_define_method(cScrW, "scroll_next_n", scrW_next_n, 1); rb_define_method(cScrW, "scroll_pageup", scrW_pageup, 0); rb_define_method(cScrW, "scroll_pagedown", scrW_pagedown, 0); rb_define_method(cScrW, "nrows", scrW_nrows, 0); rb_define_method(cScrW, "line_num", scrW_line_num, 0); rb_define_method(cScrW, "num_lines", scrW_num_lines, 0); rb_define_method(cScrW, "window_row", scrW_window_row, 0); rb_define_method(cScrW, "top_window_line_is_current_line", scrW_top_window_line_is_current_line, 0); rb_define_method(cScrW, "set_nrows", scrW_set_nrows, 1); rb_define_method(cScrW, "set_cursor_line_color", scrW_set_cursor_line_color, 1); rb_define_method(cScrW, "set_normal_color", scrW_set_cursor_line_color, 1); rb_define_method(cScrW, "set_bar", scrW_set_bar, 1); rb_define_method(cScrW, "set_tilde", scrW_set_tilde, 1); rb_define_method(cScrW, "current_line", scrW_current_line, 0); rb_define_method(cScrW, "find_set_nth_line", scrW_find_set_nth_line, 1); rb_define_method(cScrW, "find_current_line", scrW_find_current_line, 0); rb_define_method(cScrW, "find_prev_line", scrW_find_prev_line, 0); rb_define_method(cScrW, "find_next_line", scrW_find_next_line, 0); rb_define_method(cScrW, "get_cursor_line_color", scrW_get_cursor_line_color, 0); rb_define_method(cScrW, "get_normal_color", scrW_get_normal_color, 0); /* Init_slcurses(mSlang); */ #ifdef HAVE_ISKCODE /* slang for jed */ kSLcode = EUC; #endif }