1*1182a44cSrillig /* $NetBSD: hack.terminfo.c,v 1.3 2021/05/02 12:50:44 rillig Exp $ */
298eb8895Sroy
398eb8895Sroy /*
498eb8895Sroy * Copyright (c) 1985, Stichting Centrum voor Wiskunde en Informatica,
598eb8895Sroy * Amsterdam
698eb8895Sroy * All rights reserved.
798eb8895Sroy *
898eb8895Sroy * Redistribution and use in source and binary forms, with or without
998eb8895Sroy * modification, are permitted provided that the following conditions are
1098eb8895Sroy * met:
1198eb8895Sroy *
1298eb8895Sroy * - Redistributions of source code must retain the above copyright notice,
1398eb8895Sroy * this list of conditions and the following disclaimer.
1498eb8895Sroy *
1598eb8895Sroy * - Redistributions in binary form must reproduce the above copyright
1698eb8895Sroy * notice, this list of conditions and the following disclaimer in the
1798eb8895Sroy * documentation and/or other materials provided with the distribution.
1898eb8895Sroy *
1998eb8895Sroy * - Neither the name of the Stichting Centrum voor Wiskunde en
2098eb8895Sroy * Informatica, nor the names of its contributors may be used to endorse or
2198eb8895Sroy * promote products derived from this software without specific prior
2298eb8895Sroy * written permission.
2398eb8895Sroy *
2498eb8895Sroy * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
2598eb8895Sroy * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
2698eb8895Sroy * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
2798eb8895Sroy * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
2898eb8895Sroy * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
2998eb8895Sroy * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
3098eb8895Sroy * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
3198eb8895Sroy * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
3298eb8895Sroy * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
3398eb8895Sroy * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
3498eb8895Sroy * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
3598eb8895Sroy */
3698eb8895Sroy
3798eb8895Sroy /*
3898eb8895Sroy * Copyright (c) 1982 Jay Fenlason <hack@gnu.org>
3998eb8895Sroy * All rights reserved.
4098eb8895Sroy *
4198eb8895Sroy * Redistribution and use in source and binary forms, with or without
4298eb8895Sroy * modification, are permitted provided that the following conditions
4398eb8895Sroy * are met:
4498eb8895Sroy * 1. Redistributions of source code must retain the above copyright
4598eb8895Sroy * notice, this list of conditions and the following disclaimer.
4698eb8895Sroy * 2. Redistributions in binary form must reproduce the above copyright
4798eb8895Sroy * notice, this list of conditions and the following disclaimer in the
4898eb8895Sroy * documentation and/or other materials provided with the distribution.
4998eb8895Sroy * 3. The name of the author may not be used to endorse or promote products
5098eb8895Sroy * derived from this software without specific prior written permission.
5198eb8895Sroy *
5298eb8895Sroy * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
5398eb8895Sroy * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
5498eb8895Sroy * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
5598eb8895Sroy * THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
5698eb8895Sroy * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
5798eb8895Sroy * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
5898eb8895Sroy * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
5998eb8895Sroy * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
6098eb8895Sroy * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
6198eb8895Sroy * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
6298eb8895Sroy */
6398eb8895Sroy
6498eb8895Sroy #include <sys/cdefs.h>
6598eb8895Sroy #ifndef lint
66*1182a44cSrillig __RCSID("$NetBSD: hack.terminfo.c,v 1.3 2021/05/02 12:50:44 rillig Exp $");
6798eb8895Sroy #endif /* not lint */
6898eb8895Sroy
6998eb8895Sroy #include <string.h>
7098eb8895Sroy #include <termios.h>
7198eb8895Sroy #include <term.h>
7298eb8895Sroy #include <stdlib.h>
7398eb8895Sroy #include <unistd.h>
7498eb8895Sroy #include "hack.h"
7598eb8895Sroy #include "extern.h"
7698eb8895Sroy #include "def.flag.h" /* for flags.nonull */
7798eb8895Sroy
7898eb8895Sroy char *CD; /* tested in pri.c: docorner() */
7998eb8895Sroy int CO, LI; /* used in pri.c and whatis.c */
8098eb8895Sroy
8198eb8895Sroy void
startup(void)8298eb8895Sroy startup(void)
8398eb8895Sroy {
8498eb8895Sroy
8598eb8895Sroy /* Will exit if no suitable term found */
8698eb8895Sroy setupterm(NULL, 0, NULL);
8798eb8895Sroy CO = columns;
8898eb8895Sroy LI = lines;
8998eb8895Sroy if (CO < COLNO || LI < ROWNO + 2)
9098eb8895Sroy setclipped();
9198eb8895Sroy if (clear_screen == NULL)
9298eb8895Sroy error("Hack needs clear_screen.");
9398eb8895Sroy if (over_strike)
9498eb8895Sroy error("Hack can't have over_strike.");
9598eb8895Sroy if (cursor_address == NULL) {
9698eb8895Sroy printf("Playing hack without cursor_address is suspect...");
9798eb8895Sroy getret();
9898eb8895Sroy }
9998eb8895Sroy set_whole_screen();
10098eb8895Sroy }
10198eb8895Sroy
10298eb8895Sroy void
startscreen(void)10398eb8895Sroy startscreen(void)
10498eb8895Sroy {
10598eb8895Sroy }
10698eb8895Sroy
10798eb8895Sroy void
endscreen(void)10898eb8895Sroy endscreen(void)
10998eb8895Sroy {
11098eb8895Sroy }
11198eb8895Sroy
11298eb8895Sroy static int
xputc(int c)11398eb8895Sroy xputc(int c)
11498eb8895Sroy {
11598eb8895Sroy return (fputc(c, stdout));
11698eb8895Sroy }
11798eb8895Sroy
11898eb8895Sroy static void
xputs(const char * s)11998eb8895Sroy xputs(const char *s)
12098eb8895Sroy {
12198eb8895Sroy tputs(s, 1, xputc);
12298eb8895Sroy }
12398eb8895Sroy
12498eb8895Sroy static void
cmov(int x,int y)12598eb8895Sroy cmov(int x, int y)
12698eb8895Sroy {
12798eb8895Sroy char *p;
12898eb8895Sroy
1294060cbcdSroy p = tiparm(cursor_address, y - 1, x - 1);
13098eb8895Sroy if (p) {
13198eb8895Sroy xputs(p);
13298eb8895Sroy cury = y;
13398eb8895Sroy curx = x;
13498eb8895Sroy }
13598eb8895Sroy }
13698eb8895Sroy
13798eb8895Sroy static void
nocmov(int x,int y)13898eb8895Sroy nocmov(int x, int y)
13998eb8895Sroy {
14098eb8895Sroy if (cury > y) {
14198eb8895Sroy if (cursor_up) {
14298eb8895Sroy while (cury > y) { /* Go up. */
14398eb8895Sroy xputs(cursor_up);
14498eb8895Sroy cury--;
14598eb8895Sroy }
14698eb8895Sroy } else if (cursor_address) {
14798eb8895Sroy cmov(x, y);
14898eb8895Sroy } else if (cursor_home) {
14998eb8895Sroy home();
15098eb8895Sroy curs(x, y);
15198eb8895Sroy } /* else impossible("..."); */
15298eb8895Sroy } else if (cury < y) {
15398eb8895Sroy if (cursor_address) {
15498eb8895Sroy cmov(x, y);
15598eb8895Sroy #if 0
15698eb8895Sroy } else if (XD) {
15798eb8895Sroy while (cury < y) {
15898eb8895Sroy xputs(XD);
15998eb8895Sroy cury++;
16098eb8895Sroy }
16198eb8895Sroy #endif
16298eb8895Sroy } else {
16398eb8895Sroy while (cury < y) {
16498eb8895Sroy xputc('\n');
16598eb8895Sroy curx = 1;
16698eb8895Sroy cury++;
16798eb8895Sroy }
16898eb8895Sroy }
16998eb8895Sroy }
17098eb8895Sroy if (curx < x) { /* Go to the right. */
17198eb8895Sroy if (!cursor_right)
17298eb8895Sroy cmov(x, y);
17398eb8895Sroy else /* bah */
17498eb8895Sroy /* should instead print what is there already */
17598eb8895Sroy while (curx < x) {
17698eb8895Sroy xputs(cursor_right);
17798eb8895Sroy curx++;
17898eb8895Sroy }
17998eb8895Sroy } else if (curx > x) {
18098eb8895Sroy while (curx > x)
18198eb8895Sroy backsp();
18298eb8895Sroy }
18398eb8895Sroy }
18498eb8895Sroy
18598eb8895Sroy /*
18698eb8895Sroy * Cursor movements
18798eb8895Sroy *
18898eb8895Sroy * x,y not xchar: perhaps xchar is unsigned and
18998eb8895Sroy * curx-x would be unsigned as well
19098eb8895Sroy */
19198eb8895Sroy void
curs(int x,int y)19298eb8895Sroy curs(int x, int y)
19398eb8895Sroy {
19498eb8895Sroy
19598eb8895Sroy if (y == cury && x == curx)
19698eb8895Sroy return;
19798eb8895Sroy if (!cursor_right && (curx != x || x <= 3)) { /* Extremely primitive */
19898eb8895Sroy cmov(x, y); /* bunker!wtm */
19998eb8895Sroy return;
20098eb8895Sroy }
20198eb8895Sroy if (abs(cury - y) <= 3 && abs(curx - x) <= 3)
20298eb8895Sroy nocmov(x, y);
20398eb8895Sroy else if ((x <= 3 && abs(cury - y) <= 3) ||
20498eb8895Sroy (!cursor_address && x < abs(curx - x)))
20598eb8895Sroy {
20698eb8895Sroy (void) putchar('\r');
20798eb8895Sroy curx = 1;
20898eb8895Sroy nocmov(x, y);
20998eb8895Sroy } else if (!cursor_address) {
21098eb8895Sroy nocmov(x, y);
21198eb8895Sroy } else
21298eb8895Sroy cmov(x, y);
21398eb8895Sroy }
21498eb8895Sroy
21598eb8895Sroy void
cl_end(void)21698eb8895Sroy cl_end(void)
21798eb8895Sroy {
21898eb8895Sroy if (clr_eol)
21998eb8895Sroy xputs(clr_eol);
22098eb8895Sroy else { /* no-CE fix - free after Harold Rynes */
22198eb8895Sroy /*
22298eb8895Sroy * this looks terrible, especially on a slow terminal but is
22398eb8895Sroy * better than nothing
22498eb8895Sroy */
22598eb8895Sroy int cx = curx, cy = cury;
22698eb8895Sroy
22798eb8895Sroy while (curx < COLNO) {
22898eb8895Sroy xputc(' ');
22998eb8895Sroy curx++;
23098eb8895Sroy }
23198eb8895Sroy curs(cx, cy);
23298eb8895Sroy }
23398eb8895Sroy }
23498eb8895Sroy
23598eb8895Sroy void
clearscreen(void)23698eb8895Sroy clearscreen(void)
23798eb8895Sroy {
23898eb8895Sroy xputs(clear_screen);
23998eb8895Sroy curx = cury = 1;
24098eb8895Sroy }
24198eb8895Sroy
24298eb8895Sroy void
home(void)24398eb8895Sroy home(void)
24498eb8895Sroy {
24598eb8895Sroy char *out;
24698eb8895Sroy
24798eb8895Sroy if (cursor_home)
24898eb8895Sroy xputs(cursor_home);
2494060cbcdSroy else if ((cursor_address) && (out = tiparm(cursor_address, 0, 0)))
25098eb8895Sroy xputs(out);
25198eb8895Sroy else
25298eb8895Sroy curs(1, 1); /* using UP ... */
25398eb8895Sroy curx = cury = 1;
25498eb8895Sroy }
25598eb8895Sroy
25698eb8895Sroy void
standoutbeg(void)25798eb8895Sroy standoutbeg(void)
25898eb8895Sroy {
25998eb8895Sroy if (enter_standout_mode && exit_standout_mode && !magic_cookie_glitch)
26098eb8895Sroy xputs(enter_standout_mode);
26198eb8895Sroy }
26298eb8895Sroy
26398eb8895Sroy void
standoutend(void)26498eb8895Sroy standoutend(void)
26598eb8895Sroy {
26698eb8895Sroy if (exit_standout_mode && enter_standout_mode && !magic_cookie_glitch)
26798eb8895Sroy xputs(exit_standout_mode);
26898eb8895Sroy }
26998eb8895Sroy
27098eb8895Sroy void
backsp(void)27198eb8895Sroy backsp(void)
27298eb8895Sroy {
27398eb8895Sroy if (cursor_left)
27498eb8895Sroy xputs(cursor_left);
27598eb8895Sroy else
27698eb8895Sroy (void) putchar('\b');
27798eb8895Sroy curx--;
27898eb8895Sroy }
27998eb8895Sroy
28098eb8895Sroy void
sound_bell(void)28198eb8895Sroy sound_bell(void)
28298eb8895Sroy {
28398eb8895Sroy (void) putchar('\007'); /* curx does not change */
28498eb8895Sroy (void) fflush(stdout);
28598eb8895Sroy }
28698eb8895Sroy
28798eb8895Sroy void
delay_output(void)28898eb8895Sroy delay_output(void)
28998eb8895Sroy {
29098eb8895Sroy
29198eb8895Sroy /* delay 50 ms - could also use a 'nap'-system call */
29298eb8895Sroy /* or the usleep call like this :-) */
29398eb8895Sroy usleep(50000);
29498eb8895Sroy }
29598eb8895Sroy
29698eb8895Sroy void
cl_eos(void)29798eb8895Sroy cl_eos(void)
29898eb8895Sroy { /* free after Robert Viduya *//* must only be
29998eb8895Sroy * called with curx = 1 */
30098eb8895Sroy
30198eb8895Sroy if (clr_eos)
30298eb8895Sroy xputs(clr_eos);
30398eb8895Sroy else {
30498eb8895Sroy int cx = curx, cy = cury;
30598eb8895Sroy while (cury <= LI - 2) {
30698eb8895Sroy cl_end();
30798eb8895Sroy xputc('\n');
30898eb8895Sroy curx = 1;
30998eb8895Sroy cury++;
31098eb8895Sroy }
31198eb8895Sroy cl_end();
31298eb8895Sroy curs(cx, cy);
31398eb8895Sroy }
31498eb8895Sroy }
315