/* bd-tsi.c, TSI specific key bindings and display commands * * dotscreen * A braille interface to unix tty terminals * Authors: Hadi Bargi Rangin bargi@dots.physics.orst.edu * Bill Barry barryb@dots.physics.orst.edu * * Copyright (c) 1995 by Science Access Project, Oregon State University. * * * 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 3, 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 (see the file COPYING); if not, see * https://www.gnu.org/licenses/, or contact Free Software Foundation, Inc., * 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA * **************************************************************** */ #include "config.h" #include "screen.h" #include "extern.h" #include "braille.h" #ifdef HAVE_BRAILLE extern struct display *display; struct key2rc { int key; int nr; char *arg1; char *arg2; }; static int tsi_ctype = 1; /* cursor type, 0,1,2 */ static int tsi_line_type; /* indicates number of cells on powerbraille display 01=20 cells 02=40 cells 03=80 cells */ static int display_status_tsi __P((void)); static int write_line_tsi __P((char*, int, int)); static void buttonpress_tsi __P((structkey2rc*)); static void buttonpress_navigator_40 __P((void)); static void buttonpress_powerbraille_40 __P((void)); static void buttonpress_powerbraille_80 __P((void)); int bd_init_powerbraille_40() { bd.write_line_braille = write_line_tsi; bd.buttonpress = buttonpress_powerbraille_40; bd.bd_response_test = display_status_tsi; bd.bd_ncells = 40; tsi_line_type = 2; return 0; } int bd_init_powerbraille_80() { bd.write_line_braille = write_line_tsi; bd.buttonpress = buttonpress_powerbraille_80; bd.bd_response_test = display_status_tsi; bd.bd_ncells = 80; tsi_line_type = 3; return 0; } int bd_init_navigator_40() { bd.write_line_braille = write_line_tsi; bd.buttonpress = buttonpress_navigator_40; bd.bd_response_test = display_status_tsi; bd.bd_ncells = 40; tsi_line_type = 2; return 0; } static int display_status_tsi() { char obuf[3], ibuf[20]; int r; obuf[0] = 0xff; obuf[1] = 0xff; obuf[2] = 0x0a; r = read(bd.bd_fd, ibuf, 20); /* flush the input port */ r = write(bd.bd_fd, obuf, 3); if (r != 3) return -1; /* we have written to the display asking for a response we wait 1 second for the response, read it and if no response we wait 2 seconds, if still no response, return -1 to indicate no braille display available */ sleep(1); r = read(bd.bd_fd, ibuf, 2); if (r == -1) { sleep(2); r = read(bd.bd_fd, ibuf, 2); } debug2("first chars from braille display %d %d\n", ibuf[0], ibuf[1]); if (r != 2 || ibuf[0] != 0 || ibuf[1] != 5) return -1; r = read(bd.bd_fd, ibuf, 2); if (r != 2) return -1; debug2("braille display size:%d dots:%d\n", ibuf[0], ibuf[1]); bd.bd_ncells = (unsigned char)ibuf[0]; if (bd.bd_ncells <= 1) return -1; r = read(bd.bd_fd, ibuf, 1); if (r != 1) return -1; if (ibuf[0] == 'V') r = read(bd.bd_fd, ibuf, 3); else r = read(bd.bd_fd, ibuf + 1, 2) + 1; if (r != 3) return -1; ibuf[3] = 0; debug1("braille display version %s\n", ibuf); bd.bd_version = atof(ibuf); return 0; } static int write_line_tsi(char *bstr, int line_length, int cursor_pos) { int obp, i; bd.bd_obuf[0] = 0xff; bd.bd_obuf[1] = 0xff; bd.bd_obuf[2] = tsi_line_type; bd.bd_obuf[3] = 0x07; bd.bd_obuf[4] = cursor_pos; bd.bd_obuf[5] = tsi_ctype; obp = 6; for (i = 0; i < line_length; i++) { bd.bd_obuf[2*i + obp] = 0; bd.bd_obuf[2*i + 1 + obp] = bd.bd_btable[(int)(unsigned char)bstr[i]]; } for (i = line_length; i < bd.bd_ncells; i++) { bd.bd_obuf[2*i + obp] = 0; bd.bd_obuf[2*i + 1 + obp] = bd.bd_btable[(int)' ']; } bd.bd_obuflen = 2*bd.bd_ncells + obp; return 0; } static struct key2rc keys_navigator_40[] = { {0x4000000, RC_STUFF, "-k", "kl"}, /* 1 */ {0x10000000, RC_STUFF, "-k", "kr"}, /* 3 */ {0x8000000, RC_STUFF, "-k", "ku"}, /* 2 */ {0x20000000, RC_STUFF, "-k", "kd"}, /* 4 */ {0x2000, RC_BD_BC_LEFT, 0, 0}, /* 6 */ {0x8000, RC_BD_BC_RIGHT, 0, 0}, /* 8 */ {0x4000, RC_BD_BC_UP, 0, 0}, /* 7 */ {0x10000, RC_BD_BC_DOWN, 0, 0}, /* 9 */ {0x6000, RC_BD_UPPER_LEFT, 0, 0}, /* 6, 7 */ {0xc000, RC_BD_UPPER_RIGHT, 0, 0}, /* 7, 8 */ {0x12000, RC_BD_LOWER_LEFT, 0, 0}, /* 6, 9 */ {0x18000, RC_BD_LOWER_RIGHT, 0, 0}, /* 8, 9 */ {0xa000, RC_BD_INFO, "1032", 0}, /* bc 6, 8 */ {0x14000000, RC_BD_INFO, "2301", 0}, /* sc 1, 3 */ {0x4008000, RC_BD_INFO, "3330", 0}, /* bc+sc 1, 8 */ {0x8010000, RC_BD_BELL, 0, 0}, /* 2, 9 */ {0x8004000, RC_BD_EIGHTDOT, 0, 0}, /* 2, 7 */ {0x40000000, RC_STUFF, "\015", 0}, /* 5 */ {0x20000, RC_BD_LINK, 0, 0}, /* 10 */ {0x10002000, RC_BD_SCROLL, 0, 0}, /* 3, 6 */ {0x20010000, RC_BD_NCRC, "+", 0}, /* 4, 9 */ {0x14000, RC_BD_SKIP, 0, 0}, /* 7, 9*/ {-1, RC_ILLEGAL, 0, 0} }; static struct key2rc keys_powerbraille_40[] = { {0x4000000, RC_STUFF, "-k", "kl"}, /* 1 */ {0x10000000, RC_STUFF, "-k", "kr"}, /* 3 */ {0x8000000, RC_STUFF, "-k", "ku"}, /* 2 */ {0x20000000, RC_STUFF, "-k", "kd"}, /* 4 */ {0x2000, RC_BD_BC_LEFT, 0, 0}, /* 6 */ {0x8000, RC_BD_BC_RIGHT, 0, 0}, /* 8 */ {0x4000, RC_BD_BC_UP, 0, 0}, /* 7 */ {0x10000, RC_BD_BC_DOWN, 0, 0}, /* 9 */ {0x8002000, RC_BD_UPPER_LEFT, 0, 0}, /* 2, 6 */ {0xc000, RC_BD_UPPER_RIGHT, 0, 0}, /* 7, 8 */ {0x20002000, RC_BD_LOWER_LEFT, 0, 0}, /* 3, 6 */ {0x18000, RC_BD_LOWER_RIGHT, 0, 0}, /* 8, 9 */ {0x8008000, RC_BD_INFO, "1032", 0}, /* bc 2, 8 */ {0x6000, RC_BD_INFO, "2301", 0}, /* 6, 7 */ {0x8004000, RC_BD_INFO, "3330", 0}, /* bc+sc 2, 7 */ {0x8010000, RC_BD_BELL, 0, 0}, /* 2, 9 */ {0x20008000, RC_BD_EIGHTDOT, 0, 0}, /* 4, 6 */ {0x40000000, RC_STUFF, "\015", 0}, /* 5 */ {0x20000, RC_BD_LINK, 0, 0}, /* 10 */ {0xa000, RC_BD_SCROLL, 0, 0}, /* 6, 8 */ {0x20010000, RC_BD_NCRC, "+", 0}, /* 4, 9 */ {0x20004000, RC_BD_SKIP, 0, 0}, /* 4, 7 */ {-1, RC_ILLEGAL, 0, 0} }; static struct key2rc keys_powerbraille_80[] = { {0x4000000, RC_STUFF, "-k", "kl"}, /* 1 */ {0x10000000, RC_STUFF, "-k", "kr"}, /* 3 */ {0x8000000, RC_STUFF, "-k", "ku"}, /* 2 */ {0x20000000, RC_STUFF, "-k", "kd"}, /* 4 */ {0x40000, RC_BD_BC_LEFT, 0, 0}, /* 6 */ {0x100000, RC_BD_BC_RIGHT, 0, 0}, /* 8 */ {0x4000, RC_BD_BC_UP, 0, 0}, /* 7 */ {0x10000, RC_BD_BC_DOWN, 0, 0}, /* 9 */ {0x44000, RC_BD_UPPER_LEFT, 0, 0}, /* 6, 7 */ {0x104000, RC_BD_UPPER_RIGHT, 0, 0}, /* 7, 8 */ {0x50000, RC_BD_LOWER_LEFT, 0, 0}, /* 6, 9 */ {0x110000, RC_BD_LOWER_RIGHT, 0, 0}, /* 8, 9 */ {0x8100000, RC_BD_INFO, "1032", 0}, /* 2, 8 */ {0x8040000, RC_BD_INFO, "2301", 0}, /* 2, 6 */ {0x140000, RC_BD_INFO, "3330", 0}, /* 6, 8 */ {0x8010000, RC_BD_BELL, 0, 0}, /* 2, 9 */ {0x8004000, RC_BD_EIGHTDOT, 0, 0}, /* 2, 7 */ {0x40000000, RC_STUFF, "\015", 0}, /* 5 */ {0x20000, RC_BD_LINK, 0, 0}, /* 10 */ {0x20004000, RC_BD_SCROLL, 0, 0}, /* 4, 7 */ {0x20010000, RC_BD_NCRC, "+", 0}, /* 4, 9 */ {0x40010000, RC_BD_SKIP, 0, 0}, /* 5, 9 */ {-1, RC_ILLEGAL, 0, 0} }; static void buttonpress_tsi(struct key2rc *tab) { int i, nb; int bkeys; unsigned char buf[10]; nb = read(bd.bd_fd, buf, 10); debug1("buttonpress_tsi: read %d bytes\n", nb); for (i = 0, bkeys = 0; i < nb; i++) { switch (buf[i] & 0xE0) { case 0x00: bkeys += ((int)(buf[i] & 0x1f)); break; case 0x20: bkeys += ((int)(buf[i] & 0x1f) << 5); break; case 0x40: bkeys += ((int)(buf[i] & 0x1f) << 9); break; case 0x60: bkeys += ((int)(buf[i] & 0x1f) << 13); break; case 0xA0: bkeys += ((int)(buf[i] & 0x1f) << 18); break; case 0xC0: bkeys += ((int)(buf[i] & 0x1f) << 22); break; case 0xE0: bkeys += ((int)(buf[i] & 0x1f) << 26); break; default: break; } } debug1("bkeys %x\n", bkeys); for (i = 0; tab[i].key != -1; i++) if (bkeys == tab[i].key) break; debug1("bkey index %d\n", i); if (tab[i].key != -1 && tab[i].nr != RC_ILLEGAL) { char *args[3]; int argl[2]; struct action act; args[0] = tab[i].arg1; args[1] = tab[i].arg2; args[2] = 0; argl[0] = args[0] ? strlen(args[0]) : 0; argl[1] = args[1] ? strlen(args[1]) : 0; act.nr = tab[i].nr; act.args = args; act.argl = argl; display = bd.bd_dpy; DoAction(&act, -2); } } static void buttonpress_navigator_40() { buttonpress_tsi(keys_navigator_40); } static void buttonpress_powerbraille_40() { buttonpress_tsi(keys_powerbraille_40); } static void buttonpress_powerbraille_80() { buttonpress_tsi(keys_powerbraille_80); } #endif /* HAVE_BRAILLE */