1 1.26 christos /* $NetBSD: border.c,v 1.26 2024/12/25 15:35:29 christos Exp $ */ 2 1.2 blymn 3 1.2 blymn /* 4 1.2 blymn * Copyright (c) 2000 The NetBSD Foundation, Inc. 5 1.2 blymn * All rights reserved. 6 1.2 blymn * 7 1.2 blymn * This code is derived from software contributed to The NetBSD Foundation 8 1.2 blymn * by Julian Coleman. 9 1.2 blymn * 10 1.2 blymn * Redistribution and use in source and binary forms, with or without 11 1.2 blymn * modification, are permitted provided that the following conditions 12 1.2 blymn * are met: 13 1.2 blymn * 1. Redistributions of source code must retain the above copyright 14 1.2 blymn * notice, this list of conditions and the following disclaimer. 15 1.2 blymn * 2. Redistributions in binary form must reproduce the above copyright 16 1.2 blymn * notice, this list of conditions and the following disclaimer in the 17 1.2 blymn * documentation and/or other materials provided with the distribution. 18 1.2 blymn * 19 1.2 blymn * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 20 1.2 blymn * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21 1.2 blymn * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22 1.2 blymn * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23 1.2 blymn * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 1.2 blymn * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 1.2 blymn * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26 1.2 blymn * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27 1.2 blymn * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28 1.2 blymn * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29 1.2 blymn * POSSIBILITY OF SUCH DAMAGE. 30 1.2 blymn */ 31 1.6 blymn 32 1.6 blymn #include <sys/cdefs.h> 33 1.6 blymn #ifndef lint 34 1.26 christos __RCSID("$NetBSD: border.c,v 1.26 2024/12/25 15:35:29 christos Exp $"); 35 1.6 blymn #endif /* not lint */ 36 1.2 blymn 37 1.10 blymn #include <stdlib.h> 38 1.10 blymn #include <string.h> 39 1.10 blymn 40 1.2 blymn #include "curses.h" 41 1.2 blymn #include "curses_private.h" 42 1.2 blymn 43 1.4 blymn #ifndef _CURSES_USE_MACROS 44 1.4 blymn 45 1.4 blymn /* 46 1.4 blymn * border -- 47 1.10 blymn * Draw a border around stdscr using the specified 48 1.4 blymn * delimiting characters. 49 1.4 blymn */ 50 1.4 blymn int 51 1.4 blymn border(chtype left, chtype right, chtype top, chtype bottom, chtype topleft, 52 1.4 blymn chtype topright, chtype botleft, chtype botright) 53 1.4 blymn { 54 1.4 blymn return wborder(stdscr, left, right, top, bottom, topleft, topright, 55 1.10 blymn botleft, botright); 56 1.4 blymn } 57 1.4 blymn 58 1.4 blymn #endif 59 1.4 blymn 60 1.2 blymn /* 61 1.2 blymn * wborder -- 62 1.2 blymn * Draw a border around the given window using the specified delimiting 63 1.2 blymn * characters. 64 1.2 blymn */ 65 1.2 blymn int 66 1.4 blymn wborder(WINDOW *win, chtype left, chtype right, chtype top, chtype bottom, 67 1.4 blymn chtype topleft, chtype topright, chtype botleft, chtype botright) 68 1.2 blymn { 69 1.13 drochner #ifndef HAVE_WCHAR 70 1.2 blymn int endy, endx, i; 71 1.2 blymn __LDATA *fp, *lp; 72 1.2 blymn 73 1.25 blymn if (__predict_false(win == NULL)) 74 1.26 christos return ERR; 75 1.25 blymn 76 1.7 jdc if (!(left & __CHARTEXT)) 77 1.7 jdc left |= ACS_VLINE; 78 1.7 jdc if (!(right & __CHARTEXT)) 79 1.7 jdc right |= ACS_VLINE; 80 1.7 jdc if (!(top & __CHARTEXT)) 81 1.7 jdc top |= ACS_HLINE; 82 1.7 jdc if (!(bottom & __CHARTEXT)) 83 1.7 jdc bottom |= ACS_HLINE; 84 1.7 jdc if (!(topleft & __CHARTEXT)) 85 1.7 jdc topleft |= ACS_ULCORNER; 86 1.7 jdc if (!(topright & __CHARTEXT)) 87 1.7 jdc topright |= ACS_URCORNER; 88 1.7 jdc if (!(botleft & __CHARTEXT)) 89 1.7 jdc botleft |= ACS_LLCORNER; 90 1.7 jdc if (!(botright & __CHARTEXT)) 91 1.7 jdc botright |= ACS_LRCORNER; 92 1.2 blymn 93 1.21 blymn __CTRACE(__CTRACE_INPUT, "wborder: window 0x%p\n", win); 94 1.9 jdc __CTRACE(__CTRACE_INPUT, "wborder: left = %c, 0x%x\n", 95 1.9 jdc left & __CHARTEXT, left & __ATTRIBUTES); 96 1.9 jdc __CTRACE(__CTRACE_INPUT, "wborder: right = %c, 0x%x\n", 97 1.9 jdc right & __CHARTEXT, right & __ATTRIBUTES); 98 1.9 jdc __CTRACE(__CTRACE_INPUT, "wborder: top = %c, 0x%x\n", 99 1.9 jdc top & __CHARTEXT, top & __ATTRIBUTES); 100 1.9 jdc __CTRACE(__CTRACE_INPUT, "wborder: bottom = %c, 0x%x\n", 101 1.9 jdc bottom & __CHARTEXT, bottom & __ATTRIBUTES); 102 1.9 jdc __CTRACE(__CTRACE_INPUT, "wborder: topleft = %c, 0x%x\n", 103 1.9 jdc topleft & __CHARTEXT, topleft & __ATTRIBUTES); 104 1.9 jdc __CTRACE(__CTRACE_INPUT, "wborder: topright = %c, 0x%x\n", 105 1.9 jdc topright & __CHARTEXT, topright & __ATTRIBUTES); 106 1.9 jdc __CTRACE(__CTRACE_INPUT, "wborder: botleft = %c, 0x%x\n", 107 1.9 jdc botleft & __CHARTEXT, botleft & __ATTRIBUTES); 108 1.9 jdc __CTRACE(__CTRACE_INPUT, "wborder: botright = %c, 0x%x\n", 109 1.9 jdc botright & __CHARTEXT, botright & __ATTRIBUTES); 110 1.2 blymn 111 1.8 jdc /* Merge window and background attributes */ 112 1.3 jdc left |= (left & __COLOR) ? (win->wattr & ~__COLOR) : win->wattr; 113 1.8 jdc left |= (left & __COLOR) ? (win->battr & ~__COLOR) : win->battr; 114 1.3 jdc right |= (right & __COLOR) ? (win->wattr & ~__COLOR) : win->wattr; 115 1.8 jdc right |= (right & __COLOR) ? (win->battr & ~__COLOR) : win->battr; 116 1.3 jdc top |= (top & __COLOR) ? (win->wattr & ~__COLOR) : win->wattr; 117 1.8 jdc top |= (top & __COLOR) ? (win->battr & ~__COLOR) : win->battr; 118 1.3 jdc bottom |= (bottom & __COLOR) ? (win->wattr & ~__COLOR) : win->wattr; 119 1.8 jdc bottom |= (bottom & __COLOR) ? (win->battr & ~__COLOR) : win->battr; 120 1.3 jdc topleft |= (topleft & __COLOR) ? (win->wattr & ~__COLOR) : win->wattr; 121 1.8 jdc topleft |= (topleft & __COLOR) ? (win->battr & ~__COLOR) : win->battr; 122 1.3 jdc topright |= (topright & __COLOR) ? (win->wattr & ~__COLOR) : win->wattr; 123 1.8 jdc topright |= (topright & __COLOR) ? (win->battr & ~__COLOR) : win->battr; 124 1.3 jdc botleft |= (botleft & __COLOR) ? (win->wattr & ~__COLOR) : win->wattr; 125 1.8 jdc botleft |= (botleft & __COLOR) ? (win->battr & ~__COLOR) : win->battr; 126 1.3 jdc botright |= (botright & __COLOR) ? (win->wattr & ~__COLOR) : win->wattr; 127 1.8 jdc botright |= (botright & __COLOR) ? (win->battr & ~__COLOR) : win->battr; 128 1.2 blymn 129 1.2 blymn endx = win->maxx - 1; 130 1.2 blymn endy = win->maxy - 1; 131 1.12 roy fp = win->alines[0]->line; 132 1.12 roy lp = win->alines[endy]->line; 133 1.2 blymn 134 1.2 blymn /* Sides */ 135 1.2 blymn for (i = 1; i < endy; i++) { 136 1.12 roy win->alines[i]->line[0].ch = (wchar_t) left & __CHARTEXT; 137 1.12 roy win->alines[i]->line[0].attr = (attr_t) left & __ATTRIBUTES; 138 1.12 roy win->alines[i]->line[endx].ch = (wchar_t) right & __CHARTEXT; 139 1.12 roy win->alines[i]->line[endx].attr = (attr_t) right & __ATTRIBUTES; 140 1.2 blymn } 141 1.2 blymn for (i = 1; i < endx; i++) { 142 1.2 blymn fp[i].ch = (wchar_t) top & __CHARTEXT; 143 1.2 blymn fp[i].attr = (attr_t) top & __ATTRIBUTES; 144 1.2 blymn lp[i].ch = (wchar_t) bottom & __CHARTEXT; 145 1.2 blymn lp[i].attr = (attr_t) bottom & __ATTRIBUTES; 146 1.2 blymn } 147 1.2 blymn 148 1.2 blymn /* Corners */ 149 1.18 blymn if (!(win->maxy == LINES && win->maxx == COLS && 150 1.2 blymn (win->flags & __SCROLLOK) && (win->flags & __SCROLLWIN))) { 151 1.2 blymn fp[0].ch = (wchar_t) topleft & __CHARTEXT; 152 1.2 blymn fp[0].attr = (attr_t) topleft & __ATTRIBUTES; 153 1.2 blymn fp[endx].ch = (wchar_t) topright & __CHARTEXT; 154 1.2 blymn fp[endx].attr = (attr_t) topright & __ATTRIBUTES; 155 1.2 blymn lp[0].ch = (wchar_t) botleft & __CHARTEXT; 156 1.2 blymn lp[0].attr = (attr_t) botleft & __ATTRIBUTES; 157 1.2 blymn lp[endx].ch = (wchar_t) botright & __CHARTEXT; 158 1.2 blymn lp[endx].attr = (attr_t) botright & __ATTRIBUTES; 159 1.10 blymn } 160 1.23 blymn __touchwin(win, 0); 161 1.17 roy return OK; 162 1.13 drochner #else /* HAVE_WCHAR */ 163 1.13 drochner cchar_t ls, rs, ts, bs, tl, tr, bl, br; 164 1.13 drochner cchar_t *lsp, *rsp, *tsp, *bsp, *tlp, *trp, *blp, *brp; 165 1.13 drochner 166 1.14 blymn #define S(in, out, def) \ 167 1.13 drochner if (in & __CHARTEXT) { \ 168 1.13 drochner __cursesi_chtype_to_cchar(in, &out); \ 169 1.14 blymn } else { \ 170 1.14 blymn memcpy(&out, def, sizeof(cchar_t)); \ 171 1.14 blymn out.attributes |= in & __ATTRIBUTES; \ 172 1.14 blymn } \ 173 1.14 blymn out##p = &out; 174 1.14 blymn 175 1.14 blymn S(left, ls, WACS_VLINE); 176 1.14 blymn S(right, rs, WACS_VLINE); 177 1.14 blymn S(top, ts, WACS_HLINE); 178 1.14 blymn S(bottom, bs, WACS_HLINE); 179 1.14 blymn S(topleft, tl, WACS_ULCORNER); 180 1.14 blymn S(topright, tr, WACS_URCORNER); 181 1.14 blymn S(botleft, bl, WACS_LLCORNER); 182 1.14 blymn S(botright, br, WACS_LRCORNER); 183 1.13 drochner #undef S 184 1.13 drochner return wborder_set(win, lsp, rsp, tsp, bsp, tlp, trp, blp, brp); 185 1.13 drochner #endif /* HAVE_WCHAR */ 186 1.10 blymn } 187 1.10 blymn 188 1.10 blymn int border_set(const cchar_t *ls, const cchar_t *rs, const cchar_t *ts, 189 1.10 blymn const cchar_t *bs, const cchar_t *tl, const cchar_t *tr, 190 1.10 blymn const cchar_t *bl, const cchar_t *br) 191 1.10 blymn { 192 1.10 blymn #ifndef HAVE_WCHAR 193 1.10 blymn return ERR; 194 1.10 blymn #else 195 1.10 blymn return wborder_set(stdscr, ls, rs, ts, bs, tl, tr, bl, br); 196 1.10 blymn #endif /* HAVE_WCHAR */ 197 1.10 blymn } 198 1.10 blymn 199 1.10 blymn int wborder_set(WINDOW *win, const cchar_t *ls, const cchar_t *rs, 200 1.10 blymn const cchar_t *ts, const cchar_t *bs, 201 1.10 blymn const cchar_t *tl, const cchar_t *tr, 202 1.10 blymn const cchar_t *bl, const cchar_t *br) 203 1.10 blymn { 204 1.10 blymn #ifndef HAVE_WCHAR 205 1.10 blymn return ERR; 206 1.10 blymn #else 207 1.10 blymn int endy, endx, i, j, k, cw, pcw, tlcw, blcw, trcw, brcw; 208 1.10 blymn cchar_t left, right, bottom, top, topleft, topright, botleft, botright; 209 1.10 blymn nschar_t *np, *tnp; 210 1.10 blymn 211 1.25 blymn if (__predict_false(win == NULL)) 212 1.25 blymn return ERR; 213 1.25 blymn 214 1.17 roy if (ls && wcwidth(ls->vals[0])) 215 1.17 roy memcpy(&left, ls, sizeof(cchar_t)); 216 1.10 blymn else 217 1.17 roy memcpy(&left, WACS_VLINE, sizeof(cchar_t)); 218 1.17 roy if (rs && wcwidth( rs->vals[0])) 219 1.17 roy memcpy(&right, rs, sizeof(cchar_t)); 220 1.10 blymn else 221 1.17 roy memcpy(&right, WACS_VLINE, sizeof(cchar_t)); 222 1.17 roy if (ts && wcwidth( ts->vals[0])) 223 1.17 roy memcpy(&top, ts, sizeof(cchar_t)); 224 1.10 blymn else 225 1.17 roy memcpy( &top, WACS_HLINE, sizeof(cchar_t)); 226 1.17 roy if (bs && wcwidth( bs->vals[0])) 227 1.17 roy memcpy(&bottom, bs, sizeof(cchar_t)); 228 1.10 blymn else 229 1.17 roy memcpy(&bottom, WACS_HLINE, sizeof(cchar_t)); 230 1.17 roy if (tl && wcwidth(tl->vals[0])) 231 1.17 roy memcpy( &topleft, tl, sizeof(cchar_t)); 232 1.10 blymn else 233 1.17 roy memcpy(&topleft, WACS_ULCORNER, sizeof(cchar_t)); 234 1.17 roy if (tr && wcwidth( tr->vals[0])) 235 1.17 roy memcpy(&topright, tr, sizeof(cchar_t)); 236 1.10 blymn else 237 1.17 roy memcpy(&topright, WACS_URCORNER, sizeof( cchar_t )); 238 1.17 roy if (bl && wcwidth( bl->vals[0])) 239 1.17 roy memcpy(&botleft, bl, sizeof(cchar_t)); 240 1.10 blymn else 241 1.17 roy memcpy(&botleft, WACS_LLCORNER, sizeof(cchar_t)); 242 1.17 roy if (br && wcwidth( br->vals[0])) 243 1.17 roy memcpy(&botright, br, sizeof(cchar_t)); 244 1.10 blymn else 245 1.17 roy memcpy(&botright, WACS_LRCORNER, sizeof(cchar_t)); 246 1.10 blymn 247 1.21 blymn __CTRACE(__CTRACE_INPUT, "wborder_set: window 0x%p\n", win); 248 1.10 blymn __CTRACE(__CTRACE_INPUT, "wborder_set: left = %c, 0x%x\n", 249 1.10 blymn left.vals[0], left.attributes ); 250 1.10 blymn __CTRACE(__CTRACE_INPUT, "wborder_set: right = %c, 0x%x\n", 251 1.10 blymn right.vals[0], right.attributes ); 252 1.10 blymn __CTRACE(__CTRACE_INPUT, "wborder_set: top = %c, 0x%x\n", 253 1.10 blymn top.vals[0], top.attributes ); 254 1.10 blymn __CTRACE(__CTRACE_INPUT, "wborder_set: bottom = %c, 0x%x\n", 255 1.10 blymn bottom.vals[0], bottom.attributes ); 256 1.10 blymn __CTRACE(__CTRACE_INPUT, "wborder_set: topleft = %c, 0x%x\n", 257 1.10 blymn topleft.vals[0], topleft.attributes ); 258 1.10 blymn __CTRACE(__CTRACE_INPUT, "wborder_set: topright = %c, 0x%x\n", 259 1.10 blymn topright.vals[0], topright.attributes ); 260 1.10 blymn __CTRACE(__CTRACE_INPUT, "wborder_set: botleft = %c, 0x%x\n", 261 1.10 blymn botleft.vals[0], botleft.attributes ); 262 1.10 blymn __CTRACE(__CTRACE_INPUT, "wborder_set: botright = %c, 0x%x\n", 263 1.10 blymn botright.vals[0], botright.attributes ); 264 1.10 blymn 265 1.10 blymn /* Merge window attributes */ 266 1.10 blymn left.attributes |= (left.attributes & __COLOR) ? 267 1.10 blymn (win->wattr & ~__COLOR) : win->wattr; 268 1.15 jdc left.attributes |= (left.attributes & __COLOR) ? 269 1.15 jdc (win->battr & ~__COLOR) : win->battr; 270 1.10 blymn right.attributes |= (right.attributes & __COLOR) ? 271 1.10 blymn (win->wattr & ~__COLOR) : win->wattr; 272 1.15 jdc right.attributes |= (right.attributes & __COLOR) ? 273 1.15 jdc (win->battr & ~__COLOR) : win->battr; 274 1.10 blymn top.attributes |= (top.attributes & __COLOR) ? 275 1.10 blymn (win->wattr & ~__COLOR) : win->wattr; 276 1.15 jdc top.attributes |= (top.attributes & __COLOR) ? 277 1.15 jdc (win->battr & ~__COLOR) : win->battr; 278 1.10 blymn bottom.attributes |= (bottom.attributes & __COLOR) ? 279 1.10 blymn (win->wattr & ~__COLOR) : win->wattr; 280 1.15 jdc bottom.attributes |= (bottom.attributes & __COLOR) ? 281 1.15 jdc (win->battr & ~__COLOR) : win->battr; 282 1.10 blymn topleft.attributes |= (topleft.attributes & __COLOR) ? 283 1.10 blymn (win->wattr & ~__COLOR) : win->wattr; 284 1.15 jdc topleft.attributes |= (topleft.attributes & __COLOR) ? 285 1.15 jdc (win->battr & ~__COLOR) : win->battr; 286 1.10 blymn topright.attributes |= (topright.attributes & __COLOR) ? 287 1.10 blymn (win->wattr & ~__COLOR) : win->wattr; 288 1.15 jdc topright.attributes |= (topright.attributes & __COLOR) ? 289 1.15 jdc (win->battr & ~__COLOR) : win->battr; 290 1.10 blymn botleft.attributes |= (botleft.attributes & __COLOR) ? 291 1.10 blymn (win->wattr & ~__COLOR) : win->wattr; 292 1.15 jdc botleft.attributes |= (botleft.attributes & __COLOR) ? 293 1.15 jdc (win->battr & ~__COLOR) : win->battr; 294 1.10 blymn botright.attributes |= (botright.attributes & __COLOR) ? 295 1.10 blymn (win->wattr & ~__COLOR) : win->wattr; 296 1.15 jdc botright.attributes |= (botright.attributes & __COLOR) ? 297 1.15 jdc (win->battr & ~__COLOR) : win->battr; 298 1.10 blymn 299 1.10 blymn endx = win->maxx - 1; 300 1.10 blymn endy = win->maxy - 1; 301 1.10 blymn 302 1.10 blymn /* Sides */ 303 1.10 blymn for (i = 1; i < endy; i++) { 304 1.10 blymn /* left border */ 305 1.17 roy cw = wcwidth(left.vals[0]); 306 1.13 drochner if (cw < 0) 307 1.13 drochner cw = 1; 308 1.10 blymn for ( j = 0; j < cw; j++ ) { 309 1.17 roy win->alines[i]->line[j].ch = left.vals[0]; 310 1.24 blymn win->alines[i]->line[j].cflags &= ~CA_BACKGROUND; 311 1.12 roy win->alines[i]->line[j].attr = left.attributes; 312 1.12 roy np = win->alines[i]->line[j].nsp; 313 1.10 blymn if (np) { 314 1.17 roy while (np) { 315 1.10 blymn tnp = np->next; 316 1.17 roy free(np); 317 1.10 blymn np = tnp; 318 1.10 blymn } 319 1.12 roy win->alines[i]->line[j].nsp = NULL; 320 1.10 blymn } 321 1.17 roy if (j) 322 1.22 blymn win->alines[i]->line[j].wcols = -j; 323 1.10 blymn else { 324 1.22 blymn win->alines[i]->line[j].wcols = cw; 325 1.17 roy if (left.elements > 1) { 326 1.10 blymn for (k = 1; k < left.elements; k++) { 327 1.16 christos np = malloc(sizeof(nschar_t)); 328 1.10 blymn if (!np) 329 1.10 blymn return ERR; 330 1.10 blymn np->ch = left.vals[ k ]; 331 1.12 roy np->next = win->alines[i]->line[j].nsp; 332 1.12 roy win->alines[i]->line[j].nsp 333 1.10 blymn = np; 334 1.10 blymn } 335 1.10 blymn } 336 1.10 blymn } 337 1.10 blymn } 338 1.22 blymn for (j = cw; win->alines[i]->line[j].wcols < 0; j++) { 339 1.10 blymn __CTRACE(__CTRACE_INPUT, 340 1.10 blymn "wborder_set: clean out partial char[%d]", j); 341 1.23 blymn win->alines[i]->line[j].ch = win->bch; 342 1.24 blymn win->alines[i]->line[j].cflags |= CA_BACKGROUND; 343 1.10 blymn if (_cursesi_copy_nsp(win->bnsp, 344 1.12 roy &win->alines[i]->line[j]) == ERR) 345 1.10 blymn return ERR; 346 1.22 blymn win->alines[i]->line[j].wcols = 1; 347 1.10 blymn } 348 1.10 blymn /* right border */ 349 1.17 roy cw = wcwidth(right.vals[0]); 350 1.13 drochner if (cw < 0) 351 1.13 drochner cw = 1; 352 1.22 blymn pcw = win->alines[i]->line[endx - cw].wcols; 353 1.10 blymn for ( j = endx - cw + 1; j <= endx; j++ ) { 354 1.17 roy win->alines[i]->line[j].ch = right.vals[0]; 355 1.24 blymn win->alines[i]->line[j].cflags &= ~CA_BACKGROUND; 356 1.12 roy win->alines[i]->line[j].attr = right.attributes; 357 1.12 roy np = win->alines[i]->line[j].nsp; 358 1.10 blymn if (np) { 359 1.17 roy while (np) { 360 1.10 blymn tnp = np->next; 361 1.17 roy free(np); 362 1.10 blymn np = tnp; 363 1.10 blymn } 364 1.12 roy win->alines[i]->line[j].nsp = NULL; 365 1.10 blymn } 366 1.17 roy if (j == endx - cw + 1) { 367 1.22 blymn win->alines[i]->line[j].wcols = cw; 368 1.17 roy if (right.elements > 1) { 369 1.10 blymn for (k = 1; k < right.elements; k++) { 370 1.16 christos np = malloc(sizeof(nschar_t)); 371 1.10 blymn if (!np) 372 1.10 blymn return ERR; 373 1.10 blymn np->ch = right.vals[ k ]; 374 1.12 roy np->next = win->alines[i]->line[j].nsp; 375 1.12 roy win->alines[i]->line[j].nsp 376 1.10 blymn = np; 377 1.10 blymn } 378 1.10 blymn } 379 1.10 blymn } else 380 1.22 blymn win->alines[i]->line[j].wcols = 381 1.22 blymn endx - cw + 1 - j; 382 1.10 blymn } 383 1.17 roy if (pcw != 1) { 384 1.10 blymn __CTRACE(__CTRACE_INPUT, 385 1.10 blymn "wborder_set: clean out partial chars[%d:%d]", 386 1.20 rin endx - cw + pcw, endx - cw); 387 1.10 blymn k = pcw < 0 ? endx -cw + pcw : endx - cw; 388 1.17 roy for (j = endx - cw; j >= k; j--) { 389 1.23 blymn win->alines[i]->line[j].ch = win->bch; 390 1.24 blymn win->alines[i]->line[j].cflags |= CA_BACKGROUND; 391 1.10 blymn if (_cursesi_copy_nsp(win->bnsp, 392 1.12 roy &win->alines[i]->line[j]) == ERR) 393 1.10 blymn return ERR; 394 1.12 roy win->alines[i]->line[j].attr = win->battr; 395 1.22 blymn win->alines[i]->line[j].wcols = 1; 396 1.10 blymn } 397 1.10 blymn } 398 1.10 blymn } 399 1.17 roy tlcw = wcwidth(topleft.vals[0]); 400 1.13 drochner if (tlcw < 0) 401 1.13 drochner tlcw = 1; 402 1.17 roy blcw = wcwidth(botleft.vals[0]); 403 1.13 drochner if (blcw < 0) 404 1.13 drochner blcw = 1; 405 1.17 roy trcw = wcwidth(topright.vals[0]); 406 1.13 drochner if (trcw < 0) 407 1.13 drochner trcw = 1; 408 1.17 roy brcw = wcwidth(botright.vals[0]); 409 1.13 drochner if (brcw < 0) 410 1.13 drochner brcw = 1; 411 1.10 blymn /* upper border */ 412 1.17 roy cw = wcwidth(top.vals[0]); 413 1.13 drochner if (cw < 0) 414 1.13 drochner cw = 1; 415 1.17 roy for (i = tlcw; i <= min( endx - cw, endx - trcw); i += cw) { 416 1.17 roy for (j = 0; j < cw; j++) { 417 1.17 roy win->alines[0]->line[i + j].ch = top.vals[0]; 418 1.24 blymn win->alines[0]->line[i + j].cflags &= ~CA_BACKGROUND; 419 1.17 roy win->alines[0]->line[i + j].attr = top.attributes; 420 1.17 roy np = win->alines[0]->line[i + j].nsp; 421 1.10 blymn if (np) { 422 1.17 roy while (np) { 423 1.10 blymn tnp = np->next; 424 1.17 roy free(np); 425 1.10 blymn np = tnp; 426 1.10 blymn } 427 1.17 roy win->alines[0]->line[i + j].nsp = NULL; 428 1.10 blymn } 429 1.17 roy if (j) 430 1.22 blymn win->alines[ 0 ]->line[ i + j ].wcols = -j; 431 1.10 blymn else { 432 1.22 blymn win->alines[ 0 ]->line[ i + j ].wcols = cw; 433 1.10 blymn if ( top.elements > 1 ) { 434 1.17 roy for (k = 1; k < top.elements; k++) { 435 1.16 christos np = malloc(sizeof(nschar_t)); 436 1.10 blymn if (!np) 437 1.10 blymn return ERR; 438 1.17 roy np->ch = top.vals[k]; 439 1.12 roy np->next = win->alines[0]->line[i + j].nsp; 440 1.12 roy win->alines[0]->line[i + j].nsp 441 1.10 blymn = np; 442 1.10 blymn } 443 1.10 blymn } 444 1.10 blymn } 445 1.10 blymn } 446 1.10 blymn } 447 1.17 roy while (i <= endx - trcw) { 448 1.23 blymn win->alines[0]->line[i].ch = win->bch; 449 1.24 blymn win->alines[0]->line[i].cflags |= CA_BACKGROUND; 450 1.10 blymn if (_cursesi_copy_nsp(win->bnsp, 451 1.12 roy &win->alines[0]->line[i]) == ERR) 452 1.10 blymn return ERR; 453 1.17 roy win->alines[0]->line[i].attr = win->battr; 454 1.22 blymn win->alines[0]->line[i].wcols = 1; 455 1.10 blymn i++; 456 1.10 blymn } 457 1.10 blymn /* lower border */ 458 1.17 roy for (i = blcw; i <= min( endx - cw, endx - brcw); i += cw) { 459 1.17 roy for (j = 0; j < cw; j++) { 460 1.17 roy win->alines[endy]->line[i + j].ch = bottom.vals[0]; 461 1.24 blymn win->alines[endy]->line[i + j].cflags &= ~CA_BACKGROUND; 462 1.12 roy win->alines[endy]->line[i + j].attr = bottom.attributes; 463 1.17 roy np = win->alines[endy]->line[i + j].nsp; 464 1.10 blymn if (np) { 465 1.17 roy while (np) { 466 1.10 blymn tnp = np->next; 467 1.17 roy free(np); 468 1.10 blymn np = tnp; 469 1.10 blymn } 470 1.17 roy win->alines[endy]->line[i + j].nsp = NULL; 471 1.10 blymn } 472 1.17 roy if (j) 473 1.22 blymn win->alines[endy]->line[i + j].wcols = -j; 474 1.10 blymn else { 475 1.22 blymn win->alines[endy]->line[i + j].wcols = cw; 476 1.17 roy if (bottom.elements > 1) { 477 1.17 roy for (k = 1; k < bottom.elements; k++) { 478 1.16 christos np = malloc(sizeof(nschar_t)); 479 1.16 christos if (!np) 480 1.10 blymn return ERR; 481 1.10 blymn np->ch = bottom.vals[ k ]; 482 1.12 roy np->next = win->alines[endy]->line[i + j].nsp; 483 1.12 roy win->alines[endy]->line[i + j].nsp = np; 484 1.10 blymn } 485 1.10 blymn } 486 1.10 blymn } 487 1.10 blymn } 488 1.10 blymn } 489 1.17 roy while (i <= endx - brcw) { 490 1.23 blymn win->alines[endy]->line[i].ch = win->bch; 491 1.24 blymn win->alines[endy]->line[i].cflags |= CA_BACKGROUND; 492 1.10 blymn if (_cursesi_copy_nsp(win->bnsp, 493 1.12 roy &win->alines[endy]->line[i]) == ERR) 494 1.10 blymn return ERR; 495 1.17 roy win->alines[endy]->line[i].attr = win->battr; 496 1.22 blymn win->alines[endy]->line[i].wcols = 1; 497 1.10 blymn i++; 498 1.10 blymn } 499 1.10 blymn 500 1.10 blymn /* Corners */ 501 1.18 blymn if (!(win->maxy == LINES && win->maxx == COLS && 502 1.10 blymn (win->flags & __SCROLLOK) && (win->flags & __SCROLLWIN))) { 503 1.17 roy for (i = 0; i < tlcw; i++) { 504 1.17 roy win->alines[0]->line[i].ch = topleft.vals[0]; 505 1.24 blymn win->alines[0]->line[i].cflags &= ~CA_BACKGROUND; 506 1.17 roy win->alines[0]->line[i].attr = topleft.attributes; 507 1.17 roy np = win->alines[0]->line[i].nsp; 508 1.10 blymn if (np) { 509 1.17 roy while (np) { 510 1.10 blymn tnp = np->next; 511 1.17 roy free(np); 512 1.10 blymn np = tnp; 513 1.10 blymn } 514 1.17 roy win->alines[0]->line[i].nsp = NULL; 515 1.10 blymn } 516 1.17 roy if (i) 517 1.22 blymn win->alines[0]->line[i].wcols = -i; 518 1.10 blymn else { 519 1.22 blymn win->alines[0]->line[i].wcols = tlcw; 520 1.17 roy if (topleft.elements > 1) { 521 1.17 roy for (k = 1; k < topleft.elements; k++) 522 1.17 roy { 523 1.16 christos np = malloc(sizeof(nschar_t)); 524 1.10 blymn if (!np) 525 1.10 blymn return ERR; 526 1.17 roy np->ch = topleft.vals[k]; 527 1.17 roy np->next = win->alines[0]->line[i].nsp; 528 1.17 roy win->alines[0]->line[i].nsp = np; 529 1.10 blymn } 530 1.10 blymn } 531 1.10 blymn } 532 1.10 blymn } 533 1.17 roy for (i = endx - trcw + 1; i <= endx; i++) { 534 1.17 roy win->alines[0]->line[i].ch = topright.vals[0]; 535 1.24 blymn win->alines[0]->line[i].cflags &= ~CA_BACKGROUND; 536 1.17 roy win->alines[0]->line[i].attr = topright.attributes; 537 1.17 roy np = win->alines[0]->line[i].nsp; 538 1.10 blymn if (np) { 539 1.17 roy while (np) { 540 1.10 blymn tnp = np->next; 541 1.17 roy free(np); 542 1.10 blymn np = tnp; 543 1.10 blymn } 544 1.17 roy win->alines[0]->line[i].nsp = NULL; 545 1.10 blymn } 546 1.17 roy if (i == endx - trcw + 1) { 547 1.22 blymn win->alines[0]->line[i].wcols = trcw; 548 1.17 roy if (topright.elements > 1) { 549 1.17 roy for (k = 1; k < topright.elements;k ++) 550 1.17 roy { 551 1.16 christos np = malloc(sizeof(nschar_t)); 552 1.10 blymn if (!np) 553 1.10 blymn return ERR; 554 1.17 roy np->ch = topright.vals[k]; 555 1.12 roy np->next = win->alines[0]->line[i].nsp; 556 1.17 roy win->alines[ 0 ]->line[i].nsp = np; 557 1.10 blymn } 558 1.10 blymn } 559 1.10 blymn } else 560 1.22 blymn win->alines[0]->line[i].wcols = 561 1.22 blymn endx - trcw + 1 - i; 562 1.10 blymn } 563 1.17 roy for (i = 0; i < blcw; i++) { 564 1.17 roy win->alines[endy]->line[i].ch = botleft.vals[0]; 565 1.24 blymn win->alines[endy]->line[i].cflags &= ~CA_BACKGROUND; 566 1.17 roy win->alines[endy]->line[i].attr = botleft.attributes; 567 1.12 roy np = win->alines[ endy ]->line[i].nsp; 568 1.10 blymn if (np) { 569 1.17 roy while (np) { 570 1.10 blymn tnp = np->next; 571 1.17 roy free(np); 572 1.10 blymn np = tnp; 573 1.10 blymn } 574 1.17 roy win->alines[endy]->line[i].nsp = NULL; 575 1.10 blymn } 576 1.17 roy if (i) 577 1.22 blymn win->alines[endy]->line[i].wcols = -i; 578 1.10 blymn else { 579 1.22 blymn win->alines[endy]->line[i].wcols = blcw; 580 1.17 roy if (botleft.elements > 1) { 581 1.17 roy for (k = 1; k < botleft.elements; k++) { 582 1.16 christos np = malloc(sizeof(nschar_t)); 583 1.10 blymn if (!np) 584 1.10 blymn return ERR; 585 1.10 blymn np->ch = botleft.vals[ k ]; 586 1.12 roy np->next = win->alines[endy]->line[i].nsp; 587 1.17 roy win->alines[endy]->line[i].nsp = np; 588 1.10 blymn } 589 1.10 blymn } 590 1.10 blymn } 591 1.10 blymn } 592 1.17 roy for (i = endx - brcw + 1; i <= endx; i++) { 593 1.17 roy win->alines[endy]->line[i].ch = botright.vals[0]; 594 1.24 blymn win->alines[endy]->line[i].cflags &= ~CA_BACKGROUND; 595 1.17 roy win->alines[endy]->line[i].attr = botright.attributes; 596 1.17 roy np = win->alines[endy]->line[i].nsp; 597 1.10 blymn if (np) { 598 1.17 roy while (np) { 599 1.10 blymn tnp = np->next; 600 1.17 roy free(np); 601 1.10 blymn np = tnp; 602 1.10 blymn } 603 1.17 roy win->alines[endy]->line[i].nsp = NULL; 604 1.10 blymn } 605 1.17 roy if (i == endx - brcw + 1) { 606 1.22 blymn win->alines[endy]->line[i].wcols = brcw; 607 1.17 roy if (botright.elements > 1) { 608 1.17 roy for (k = 1; k < botright.elements; k++){ 609 1.16 christos np = malloc(sizeof(nschar_t)); 610 1.10 blymn if (!np) 611 1.10 blymn return ERR; 612 1.17 roy np->ch = botright.vals[k]; 613 1.12 roy np->next = win->alines[endy]->line[i].nsp; 614 1.17 roy win->alines[endy]->line[i].nsp = np; 615 1.10 blymn } 616 1.10 blymn } 617 1.10 blymn } else 618 1.22 blymn win->alines[endy]->line[i].wcols = 619 1.22 blymn endx - brcw + 1 - i; 620 1.10 blymn } 621 1.2 blymn } 622 1.23 blymn __touchwin(win, 0); 623 1.17 roy return OK; 624 1.10 blymn #endif /* HAVE_WCHAR */ 625 1.2 blymn } 626