Jspice3
mfbtext.c
Go to the documentation of this file.
1 /*************************************************************************
2  MFB graphics and miscellaneous library
3  Copyright (c) Stephen R. Whiteley 1992
4  Author: Stephen R. Whiteley
5  *************************************************************************/
6 
7 #include "mfb.h"
8 #include "mfbP.h"
9 #include <dos.h>
10 
11 static Xl,Yl, Xu = 0x7fff, Yu = 0x7fff;
12 
13 #ifdef __STDC__
14 static void mode1_render_text(char*,int,int,int,int);
15 static void mode2_render_text(char*,int,int,int,int);
16 static int setcode(int);
17 static void xform_cell(unsigned short*,unsigned short*,int,int,int,int);
18 #else
19 static void mode1_render_text();
20 static void mode2_render_text();
21 static int setcode();
22 static void xform_cell();
23 #endif
24 
25 
26 void
27 MFBSetTextClip(xl,yl,xu,yu)
28 
29 /* set up a clipping window for text */
30 int xl,yl,xu,yu;
31 {
32  Xl = xl;
33  Yl = yl;
34  Xu = xu;
35  Yu = yu;
36 }
37 
38 
39 void
40 MFBTextBB(string,len,hei)
41 
42 char *string;
43 int *len,*hei;
44 {
45  *len = 0;
46  *hei = 0;
47  if (string == NULL) return;
48  *len = strlen(string)*pc.charwidth;
49  *hei = pc.charheight;
50 }
51 
52 
53 void
54 MFBText(s,x,y,r)
55 
56 char *s;
57 int x, y, r;
58 {
59  if (pc.mfbMODE & 2)
60  mode2_render_text(s,x,y,r,1);
61  else
62  mode1_render_text(s,x,y,r,1);
63 }
64 
65 
66 void
67 MFBScaledText(s,x,y,r,sc)
68 
69 char *s;
70 int x,y,r,sc;
71 {
72  if (pc.mfbMODE & 2)
73  mode2_render_text(s,x,y,r,sc);
74  else
75  mode1_render_text(s,x,y,r,sc);
76 }
77 
78 
79 static void
80 mode1_render_text(text,x,y,degrees,scale)
81 
82 char *text;
83 int x, y, degrees, scale;
84 
85 /* Print the text, where each pixel expands to a (scale X scale) pixel field.
86  * Supports fonts up to 16 X 16.
87  * Assumes bit field in degrees:
88  * 0x8: mirror x
89  * 0x4: mirror y
90  * 0x3: 0-no rotation, 1-90, 2-180, 3-270
91  *
92  * if > 15, assume rotation in degrees: 90,180,270.
93  *
94  * For mode 1 (16 colors).
95  */
96 
97 {
98  int i, j, k, l, tx;
99  int next, next1, bwidth, cwidth;
100  int fheight, fwidth;
101  int ynow, xw, cx, xn, bcnt;
102  unsigned short rotbuf[16], *ctab;
103  unsigned short z, z1, imask;
104  unsigned char cbuf, omask;
105  unsigned char mask[22];
106  vidmptr rgen;
107  char *str0, *str1;
108  union { unsigned short color2; unsigned char c[2]; } c;
109 
110  if (scale < 1 || scale > 10) return;
111  if (text == NULL) return;
112 
113  if (degrees >= 90) degrees /= 90;
114 
115  c.c[0] = pc.curcolor;
116  c.c[1] = c.c[0];
117 
118  outpw(0x3ce,0x0b05); /* read mode 1, write mode 3 */
119  outpw(0x3ce,0x0007); /* clear color dont care reg */
120  outpw(0x3ce,c.color2 & 0xff00); /* set/reset */
121  outpw(0x3ce,pc.alumode); /* set alu mode */
122 
123  if (degrees & 1) {
124  fheight = pc.charwidth;
125  fwidth = pc.charheight;
126  cwidth = fwidth*scale;
127  if (degrees & 2) {
128  if (!(degrees & 4))
129  y -= strlen(text)*fheight*scale;
130  if (degrees & 8)
131  x -= cwidth;
132  }
133  else {
134  if (!(degrees & 8))
135  x -= cwidth;
136  if (degrees & 4)
137  y -= strlen(text)*fheight*scale;
138  }
139  }
140  else {
141  fheight = pc.charheight;
142  fwidth = pc.charwidth;
143  next1 = pc.bytpline*fheight*scale;
144  cwidth = fwidth*scale;
145  if (degrees & 2) {
146  if (!(degrees & 8))
147  x -= strlen(text)*cwidth;
148  if (!(degrees & 4))
149  y -= fheight*scale;
150  }
151  else {
152  if (degrees & 8)
153  x -= strlen(text)*cwidth;
154  if (degrees & 4)
155  y -= fheight*scale;
156  }
157  }
158  degrees = setcode(degrees);
159 
160  rgen = pc.base + (long) ((x >> 3) + (pc.ysize-1-y)*pc.bytpline);
161  cx = x & 7;
162  xn = cx + cwidth;
163  bwidth = xn >> 3;
164  next = pc.bytpline + bwidth;
165  str0 = text;
166  str1 = text + strlen(text);
167 
168  while (str0 != str1) {
169  if (x + cwidth < Xl || x > Xu) {
170  if (degrees & 4) break;
171  if (degrees & 8)
172  str1--;
173  else
174  str0++;
175  }
176  else {
177  memset(mask,0xff,bwidth+1);
178  if (x < Xl) {
179  z = (Xl >> 3) - (x >> 3);
180  memset(mask,0,z);
181  mask[z] >>= (Xl & 7);
182  }
183  if (Xu < x + cwidth) {
184  z = (Xu >> 3) - (x >> 3) + 1;
185  memset(mask+z,0,bwidth+1-z);
186  mask[z-1] <<= 8 - (Xu & 7);
187  }
188 
189  if (degrees & 8) {
190  if ((tx = (*--str1 & 0x7f) - ' ') < 0) tx = 0;
191  }
192  else
193  if ((tx = (*str0++ & 0x7f) - ' ') < 0) tx = 0;
194 
195  ctab = pc.chartab + tx*pc.charheight;
196  xform_cell(rotbuf,ctab,fwidth,fheight,degrees,fwidth);
197  ctab = rotbuf + fheight - 1;
198 
199  if (scale > 1) {
200  ynow = y;
201  for (i = fheight; i; i--,ctab--) {
202  for (j = scale; j; j--) {
203  if (ynow >= Yl && ynow <= Yu) {
204  cbuf = 0;
205  omask = 0x80 >> cx;
206  imask = 0x8000;
207  bcnt = 0;
208  for (k = fwidth; k; k--) {
209  for (l = scale; l; l--) {
210  if (imask & *ctab) cbuf |= omask;
211  if (!(omask >>= 1)) {
212  omask = 0x80;
213  cbuf &= mask[bcnt++];
214  mfb_trash = *rgen;
215  *rgen++ = cbuf;
216  cbuf = 0;
217 
218  }
219  }
220  imask >>= 1;
221  }
222  if (omask != 0x80) {
223  mfb_trash = *rgen;
224  *rgen = cbuf;
225  }
226  }
227  else
228  rgen += bwidth;
229  rgen -= next;
230  ynow++;
231  }
232  }
233  if (degrees & 4) {
234  y += fheight*scale;
235  continue;
236  }
237  rgen += next1;
238  }
239  else {
240  ynow = y;
241  for (i = fheight; i; i--, ctab--) {
242  if (ynow >= Yl && ynow <= Yu) {
243  imask = *ctab >> cx;
244  mfb_trash = *rgen;
245  *rgen = (*((char *) &imask + 1) & mask[0]);
246  if (bwidth) {
247  rgen++;
248  mfb_trash = *rgen;
249  *rgen = ((char) imask & mask[1]);
250  }
251  if (bwidth & 2) {
252  rgen++;
253  mfb_trash = *rgen;
254  *rgen =
255  ((char) (*ctab << (8 - cx)) & mask[2]);
256  }
257  }
258  else
259  rgen += bwidth;
260  rgen -= next;
261  ynow++;
262  }
263  if (degrees & 4) {
264  y += fheight;
265  continue;
266  }
267  rgen += next1;
268  }
269  }
270  next -= bwidth;
271  rgen += bwidth;
272  cx = xn & 7;
273  xn = cx + cwidth;
274  bwidth = xn >> 3;
275  next += bwidth;
276  x += cwidth;
277  }
278  outpw(0x3ce,0xff07);
279  outpw(0x3ce,0x5);
280 }
281 
282 
283 #ifndef __GNUC__
284 
285 
286 static void
287 mode2_render_text(text,x,y,degrees,scale)
288 
289 /* Print text, 256 color modes. Supports up to 16 X 16 fonts */
290 char *text;
291 int x, y, degrees, scale;
292 {
293 
294 
295  int i, ii, j, k, tx, next;
296  int xnow, ynow;
297  long next1;
298  int fheight, fwidth;
299  unsigned short rotbuf[16], *ctab, mask;
300  union {long l; unsigned short o[2];} p;
301  unsigned char cbuf;
302  char *str0, *str1;
303  union { unsigned short color2; unsigned char c[2]; } c;
304 
305  outpw(0x3ce,0xff08); /* set bit mask */
306  outpw(0x3ce,pc.alumode); /* set alu mode */
307 
308  c.c[0] = pc.curcolor;
309 
310  if (scale < 1 || scale > 10) return;
311  if (text == NULL) return;
312 
313  if (degrees >= 90) degrees /= 90;
314 
315  cbuf = inp(0x3cd);
316  cbuf |= (cbuf << 4);
317  if (degrees & 1) {
318  fheight = pc.charwidth;
319  fwidth = pc.charheight;
320  next1 = 0;
321  if (degrees & 2) {
322  if (!(degrees & 4))
323  y -= strlen(text)*fheight*scale;
324  if (degrees & 8)
325  x -= fwidth*scale;
326  }
327  else {
328  if (!(degrees & 8))
329  x -= fwidth*scale;
330  if (degrees & 4)
331  y -= strlen(text)*fheight*scale;
332  }
333  }
334  else {
335  fheight = pc.charheight;
336  fwidth = pc.charwidth;
337  next1 = (pc.xsize*fheight + fwidth)*scale;
338  if (degrees & 2) {
339  if (!(degrees & 8))
340  x -= strlen(text)*fwidth*scale;
341  if (!(degrees & 4))
342  y -= fheight*scale;
343  }
344  else {
345  if (degrees & 8)
346  x -= strlen(text)*fwidth*scale;
347  if (degrees & 4)
348  y -= fheight*scale;
349  }
350  }
351  degrees = setcode(degrees);
352 
353  p.l = x + (long) (pc.ysize-y-1)*pc.xsize;
354  next = pc.xsize + fwidth*scale;
355  str0 = text;
356  str1 = text + strlen(text);
357  while (str0 != str1) {
358 
359  if (degrees & 8) {
360  if ((tx = (*--str1 & 0x7f) - ' ') < 0) tx = 0;
361  }
362  else
363  if ((tx = (*str0++ & 0x7f) - ' ') < 0) tx = 0;
364 
365  ctab = pc.chartab + tx*pc.charheight;
366  xform_cell(rotbuf,ctab,fwidth,fheight,degrees,fwidth);
367  ctab = rotbuf + fheight - 1;
368 
369  ynow = y;
370  for (i = fheight; i; i--, ctab--) {
371  for (j = scale; j; j--) {
372  if (ynow >= Yl && ynow <= Yu) {
373  xnow = x;
374  for (mask = 0x8000,ii = fwidth; ii; mask >>= 1,ii--) {
375  for (k = scale; k; k--) {
376  if (xnow >= Xl && xnow <= Xu) {
377  if (*ctab & mask) {
378  if (cbuf != p.o[1]) {
379  cbuf = p.o[1];
380  cbuf |= (cbuf << 4);
381  outp(0x3cd,cbuf);
382  }
383  if (pc.alumode != 3)
384  mfb_trash = *(pc.base + p.o[0]);
385  *(pc.base + p.o[0]) = c.c[0];
386  }
387  }
388  p.l++;
389  xnow++;
390  }
391  }
392  }
393  else
394  p.l += fwidth*scale;
395  p.l -= next;
396  ynow++;
397  }
398  }
399  if (degrees & 4) {
400  y += fheight*scale;
401  continue;
402  }
403  x += fwidth*scale;
404  p.l += next1;
405  }
406 }
407 
408 
409 #else /* __GNUC__ */
410 
411 
412 static void
413 mode2_render_text(text,x,y,degrees,scale)
414 
415 /* Print text, 256 color modes. Supports up to 16 X 16 fonts */
416 char *text;
417 int x, y, degrees, scale;
418 {
419 
420 
421  int i, ii, j, k, tx, next;
422  int xnow, ynow;
423  long next1;
424  int fheight, fwidth;
425  unsigned short rotbuf[16], *ctab, mask;
426  char *str0, *str1;
427  union { unsigned short color2; unsigned char c[2]; } c;
428  vidmptr rgen;
429 
430  outpw(0x3ce,0xff08); /* set bit mask */
431  outpw(0x3ce,pc.alumode); /* set alu mode */
432 
433  c.c[0] = pc.curcolor;
434 
435  if (scale < 1 || scale > 10) return;
436  if (text == NULL) return;
437 
438  if (degrees >= 90) degrees /= 90;
439 
440  if (degrees & 1) {
441  fheight = pc.charwidth;
442  fwidth = pc.charheight;
443  next1 = 0;
444  if (degrees & 2) {
445  if (!(degrees & 4))
446  y -= strlen(text)*fheight*scale;
447  if (degrees & 8)
448  x -= fwidth*scale;
449  }
450  else {
451  if (!(degrees & 8))
452  x -= fwidth*scale;
453  if (degrees & 4)
454  y -= strlen(text)*fheight*scale;
455  }
456  }
457  else {
458  fheight = pc.charheight;
459  fwidth = pc.charwidth;
460  next1 = (pc.xsize*fheight + fwidth)*scale;
461  if (degrees & 2) {
462  if (!(degrees & 8))
463  x -= strlen(text)*fwidth*scale;
464  if (!(degrees & 4))
465  y -= fheight*scale;
466  }
467  else {
468  if (degrees & 8)
469  x -= strlen(text)*fwidth*scale;
470  if (degrees & 4)
471  y -= fheight*scale;
472  }
473  }
474  degrees = setcode(degrees);
475 
476  rgen = pc.base + x + (long) (pc.ysize-y-1)*pc.xsize;
477  next = pc.xsize + fwidth*scale;
478  str0 = text;
479  str1 = text + strlen(text);
480  while (str0 != str1) {
481 
482  if (degrees & 8) {
483  if ((tx = (*--str1 & 0x7f) - ' ') < 0) tx = 0;
484  }
485  else
486  if ((tx = (*str0++ & 0x7f) - ' ') < 0) tx = 0;
487 
488  ctab = pc.chartab + tx*pc.charheight;
489  xform_cell(rotbuf,ctab,fwidth,fheight,degrees,fwidth);
490  ctab = rotbuf + fheight - 1;
491 
492  ynow = y;
493  for (i = fheight; i; i--, ctab--) {
494  for (j = scale; j; j--) {
495  if (ynow >= Yl && ynow <= Yu) {
496  xnow = x;
497  for (mask = 0x8000,ii = fwidth; ii; mask >>= 1,ii--) {
498  for (k = scale; k; k--) {
499  if (xnow >= Xl && xnow <= Xu) {
500  if (*ctab & mask) {
501  if (rgen >= pc.base) {
502  if (pc.alumode != 3)
503  mfb_trash = *rgen;
504  *rgen = c.c[0];
505  }
506  }
507  }
508  rgen++;
509  xnow++;
510  }
511  }
512  }
513  else
514  rgen += fwidth*scale;
515  rgen -= next;
516  ynow++;
517  }
518  }
519  if (degrees & 4) {
520  y += fheight*scale;
521  continue;
522  }
523  x += fwidth*scale;
524  rgen += next1;
525  }
526 }
527 
528 #endif /* __GNUC__ */
529 
530 static int
532 
533 int deg;
534 {
535  /*
536  * returned bit field:
537  * 0x8: load text backward
538  * 0x4: rotation
539  * 0x2: reverse y data
540  * 0x1: reverse x data
541  *
542  * Assumes input bit field:
543  * 0x8: mirror x
544  * 0x4: mirror y
545  * 0x3: 0-no rotation, 1-90, 2-180, 3-270
546  */
547 
548  int mx = 0,my = 0;
549  int rotn;
550  int xf = 0;
551 
552  rotn = deg & 3;
553  if (deg & 8) mx = 1;
554  if (deg & 4) my = 1;
555 
556  if ((mx && rotn == 0) || (!mx && rotn == 2) ||
557  (my && rotn == 1) || (!my && rotn == 3))
558  xf |= 8;
559  if (rotn & 1)
560  xf |= 4;
561  if ((my && (rotn == 0 || rotn == 1)) ||
562  (!my && (rotn == 2 || rotn == 3)))
563  xf |= 2;
564  if ((mx && (rotn == 0 || rotn == 3)) ||
565  (!mx && (rotn == 1 || rotn == 2)))
566  xf |= 1;
567  return (xf);
568 }
569 
570 
571 static void
572 xform_cell(out,in,w,h,code,shift)
573 
574 unsigned short *out,*in;
575 int w,h,code,shift;
576 {
577  int i, j, k, l;
578 
579  for (i = 0; i < h; i++) {
580  k = ((code & 2) ? h-i-1 : i);
581  if (code & 4) {
582  for (j = 0,out[i] = 0; j < w; j++) {
583  l = ((code & 1) ? (w-j-1) : j);
584  out[i] |= ((in[j] >> k) & 1) << l;
585  }
586  }
587  else {
588  if (code & 1)
589  for (j = 0,out[i] = 0; j < w; j++)
590  out[i] |= ((in[k] >> j) & 1) << (w-j-1);
591  else
592  out[i] = in[k];
593  }
594  }
595  if (shift)
596  for (i = 0,j = 16-shift; i < h; i++)
597  out[i] <<= j;
598 }
static void mode1_render_text()
int charwidth
Definition: mfbp.h:65
unsigned short * chartab
Definition: mfbp.h:63
Definition: cddefs.h:119
static complex ii
Definition: vectors.c:19
static Xl
Definition: mfbtext.c:11
int mfbMODE
Definition: mfbp.h:41
FILE * p
Definition: proc2mod.c:48
static Yu
Definition: mfbtext.c:11
char mfb_trash
Definition: mfbopen.c:15
Definition: cddefs.h:169
static void xform_cell()
Definition: cddefs.h:312
void MFBSetTextClip(int xl, int yl, int xu, int yu)
Definition: mfbtext.c:27
void MFBTextBB(char *string, int *len, int *hei)
Definition: mfbtext.c:40
Definition: cddefs.h:215
static Xu
Definition: mfbtext.c:11
char * vidmptr
Definition: mfbp.h:17
int ysize
Definition: mfbp.h:54
void MFBText(char *s, int x, int y, int r)
Definition: mfbtext.c:54
vidmptr base
Definition: mfbp.h:38
void MFBScaledText(char *s, int x, int y, int r, int sc)
Definition: mfbtext.c:67
#define NULL
Definition: spdefs.h:121
int charheight
Definition: mfbp.h:64
int alumode
Definition: mfbp.h:56
static double c
Definition: vectors.c:16
static void mode2_render_text()
Definition: cddefs.h:142
int xsize
Definition: mfbp.h:53
Definition: cddefs.h:177
int bytpline
Definition: mfbp.h:39
Definition: cddefs.h:162
static Yl
Definition: mfbtext.c:11
int curcolor
Definition: mfbp.h:46
struct mfbpc pc
Definition: mfbopen.c:14
static int setcode()