1 /* $NetBSD: addbytes.c,v 1.21 2000/12/19 21:34:24 jdc Exp $ */ 2 3 /* 4 * Copyright (c) 1987, 1993, 1994 5 * The Regents of the University of California. All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 3. All advertising materials mentioning features or use of this software 16 * must display the following acknowledgement: 17 * This product includes software developed by the University of 18 * California, Berkeley and its contributors. 19 * 4. Neither the name of the University nor the names of its contributors 20 * may be used to endorse or promote products derived from this software 21 * without specific prior written permission. 22 * 23 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 24 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 26 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 27 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 33 * SUCH DAMAGE. 34 */ 35 36 #include <sys/cdefs.h> 37 #ifndef lint 38 #if 0 39 static char sccsid[] = "@(#)addbytes.c 8.4 (Berkeley) 5/4/94"; 40 #else 41 __RCSID("$NetBSD: addbytes.c,v 1.21 2000/12/19 21:34:24 jdc Exp $"); 42 #endif 43 #endif /* not lint */ 44 45 #include "curses.h" 46 #include "curses_private.h" 47 48 #define SYNCH_IN {y = win->cury; x = win->curx;} 49 #define SYNCH_OUT {win->cury = y; win->curx = x;} 50 51 #ifndef _CURSES_USE_MACROS 52 53 /* 54 * addbytes -- 55 * Add the character to the current position in stdscr. 56 */ 57 int 58 addbytes(const char *bytes, int count) 59 { 60 return __waddbytes(stdscr, bytes, count, 0); 61 } 62 63 /* 64 * waddbytes -- 65 * Add the character to the current position in the given window. 66 */ 67 int 68 waddbytes(WINDOW *win, const char *bytes, int count) 69 { 70 return __waddbytes(win, bytes, count, 0); 71 } 72 73 /* 74 * mvaddbytes -- 75 * Add the characters to stdscr at the location given. 76 */ 77 int 78 mvaddbytes(int y, int x, const char *bytes, int count) 79 { 80 return mvwaddbytes(stdscr, y, x, bytes, count); 81 } 82 83 /* 84 * mvwaddbytes -- 85 * Add the characters to the given window at the location given. 86 */ 87 int 88 mvwaddbytes(WINDOW *win, int y, int x, const char *bytes, int count) 89 { 90 if (wmove(win, y, x) == ERR) 91 return ERR; 92 93 return __waddbytes(win, bytes, count, 0); 94 } 95 96 #endif 97 98 /* 99 * waddbytes -- 100 * Add the character to the current position in the given window. 101 */ 102 int 103 __waddbytes(WINDOW *win, const char *bytes, int count, attr_t attr) 104 { 105 static char blanks[] = " "; 106 int c, newx, x, y; 107 attr_t attributes; 108 __LINE *lp; 109 110 SYNCH_IN; 111 112 while (count--) { 113 c = *bytes++; 114 #ifdef DEBUG 115 __CTRACE("ADDBYTES('%c', %x) at (%d, %d)\n", c, attr, y, x); 116 #endif 117 switch (c) { 118 case '\t': 119 SYNCH_OUT; 120 if (waddbytes(win, blanks, 8 - (x % 8)) == ERR) 121 return (ERR); 122 SYNCH_IN; 123 break; 124 125 default: 126 #ifdef DEBUG 127 __CTRACE("ADDBYTES(%0.2o, %d, %d)\n", win, y, x); 128 #endif 129 130 lp = win->lines[y]; 131 if (lp->flags & __ISPASTEOL) { 132 lp->flags &= ~__ISPASTEOL; 133 newline: if (y == win->maxy - 1) { 134 if (win->flags & __SCROLLOK) { 135 SYNCH_OUT; 136 scroll(win); 137 SYNCH_IN; 138 lp = win->lines[y]; 139 x = 0; 140 } else 141 return (ERR); 142 } else { 143 y++; 144 lp = win->lines[y]; 145 x = 0; 146 } 147 if (c == '\n') 148 break; 149 } 150 151 attributes = (win->wattr | attr) & 152 (__ATTRIBUTES & ~__COLOR); 153 if (attr & __COLOR) 154 attributes |= attr & __COLOR; 155 else if (win->wattr & __COLOR) 156 attributes |= win->wattr & __COLOR; 157 #ifdef DEBUG 158 __CTRACE("ADDBYTES: 1: y = %d, x = %d, firstch = %d, lastch = %d\n", 159 y, x, *win->lines[y]->firstchp, 160 *win->lines[y]->lastchp); 161 #endif 162 if (lp->line[x].ch != c || 163 lp->line[x].attr != attributes || 164 lp->line[x].bch != win->bch || 165 lp->line[x].battr != win->battr) { 166 newx = x + win->ch_off; 167 lp->flags |= __ISDIRTY; 168 /* 169 * firstchp/lastchp are shared between 170 * parent window and sub-window. 171 */ 172 if (newx < *lp->firstchp) 173 *lp->firstchp = newx; 174 if (newx > *lp->lastchp) 175 *lp->lastchp = newx; 176 #ifdef DEBUG 177 __CTRACE("ADDBYTES: change gives f/l: %d/%d [%d/%d]\n", 178 *lp->firstchp, *lp->lastchp, 179 *lp->firstchp - win->ch_off, 180 *lp->lastchp - win->ch_off); 181 #endif 182 } 183 lp->line[x].ch = c; 184 lp->line[x].bch = win->bch; 185 lp->line[x].attr = attributes; 186 lp->line[x].battr = win->battr; 187 if (x == win->maxx - 1) 188 lp->flags |= __ISPASTEOL; 189 else 190 x++; 191 #ifdef DEBUG 192 __CTRACE("ADDBYTES: 2: y = %d, x = %d, firstch = %d, lastch = %d\n", 193 y, x, *win->lines[y]->firstchp, 194 *win->lines[y]->lastchp); 195 #endif 196 break; 197 case '\n': 198 SYNCH_OUT; 199 wclrtoeol(win); 200 SYNCH_IN; 201 if (!__NONL) 202 x = 0; 203 goto newline; 204 case '\r': 205 x = 0; 206 break; 207 case '\b': 208 if (--x < 0) 209 x = 0; 210 break; 211 } 212 } 213 SYNCH_OUT; 214 return (OK); 215 } 216