home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Atari FTP
/
ATARI_FTP_0693.zip
/
ATARI_FTP_0693
/
Tex
/
Tex29
/
StTeXsrc.zoo
/
src
/
pack.c
< prev
next >
Wrap
C/C++ Source or Header
|
1988-03-13
|
11KB
|
409 lines
/*
* @(#)pack.c 2.6 EPA
*
* Copyright 1987,1988 Pat J Monardo
*
* Redistribution of this file is permitted through
* the specifications in the file COPYING.
*
*
*/
#include "tex.h"
#include "scan.h"
#include "tokenstack.h"
#include "eqstack.h"
#include "evalstack.h"
#include "box.h"
#include "tfm.h"
#include "dvi.h"
#include "pack.h"
ptr adjust_tail;
val pack_begin_line;
scal total_shrink[4];
scal total_stretch[4];
#define clr_dimens() \
{d = x = 0; \
total_stretch[FILLL] = 0;\
total_stretch[FILL] = 0; \
total_stretch[FIL] = 0; \
total_stretch[NORMAL] = 0; \
total_shrink[FILLL] = 0; \
total_shrink[FILL] = 0; \
total_shrink[FIL] = 0; \
total_shrink[NORMAL] = 0;}
ptr
hpack (p, w, m)
ptr p;
scal w;
int m;
{
int b;
scal d;
fnt f;
ptr g;
scal h;
qqqq i;
gord o;
ptr q;
ptr r;
scal s;
scal x;
byte hd;
r = get_node(BOX_NODE_SIZE);
type(r) = HLIST_NODE;
subtype(r) = MIN_QUARTERWORD;
shift_amount(r) = 0;
q = r + LIST_OFFSET;
link(q) = p;
h = 0;
clr_dimens();
while (p != NULL) {
reswitch:
while (is_char_node(p)) {
f = font(p);
i = char_info(f, character(p));
hd = height_depth(i);
x += char_width(f, i);
s = char_height(f, hd);
if (s > h)
h = s;
s = char_depth(f, hd);
if (s > d)
d = s;
p = link(p);
}
if (p != NULL) {
switch (type(p))
{
case HLIST_NODE:
case VLIST_NODE:
case RULE_NODE:
case UNSET_NODE:
x += width(p);
if (type(p) >= RULE_NODE)
s = 0;
else s = shift_amount(p);
if (height(p) - s > h)
h = height(p) - s;
if (depth(p) + s > d)
d = depth(p) + s;
break;
case INS_NODE:
case MARK_NODE:
case ADJUST_NODE:
if (adjust_tail != NULL) {
while (link(q) != p)
q = link(q);
if (type(p) == ADJUST_NODE) {
link(adjust_tail) = adjust_ptr(p);
while (link(adjust_tail) != NULL)
adjust_tail = link(adjust_tail);
p = link(p);
free_node(link(q), SMALL_NODE_SIZE);
} else {
link(adjust_tail) = p;
adjust_tail = p;
p = link(p);
}
link(q) = p;
p = q;
}
break;
case WHATSIT_NODE:
break;
case GLUE_NODE:
g = glue_ptr(p);
x += width(g);
o = stretch_order(g);
total_stretch[o] += stretch(g);
o = shrink_order(g);
total_shrink[o] += shrink(g);
if (subtype(p) >= A_LEADERS) {
g = leader_ptr(p);
if (height(g) > h)
h = height(g);
if (depth(g) > d)
d = depth(g);
}
break;
case KERN_NODE:
case MATH_NODE:
x += width(p);
break;
case LIGATURE_NODE:
make_char_from_lig();
goto reswitch;
break;
default:
break;
}
p = link(p);
}
}
if (adjust_tail != NULL)
link(adjust_tail) = NULL;
height(r) = h;
depth(r) = d;
if (m == ADDITIONAL)
w += x;
width(r) = w;
x = w - x;
if (x == 0) {
glue_sign(r) = NORMAL;
glue_order(r) = NORMAL;
glue_set(r) = 0.0;
return r;
} else if (x > 0) {
get_stretch_order();
glue_order(r) = o;
glue_sign(r) = STRETCHING;
if (total_stretch[o] != 0) {
glue_set(r) = (float) x / total_stretch[o];
} else {
glue_sign(r) = NORMAL;
glue_set(r) = 0.0;
}
if (hbadness < INF_BAD && o == NORMAL && list_ptr(r) != NULL) {
b = badness(x, total_stretch[NORMAL]);
if (b > hbadness) {
print_ln();
if (b > 100)
print_nl("Underfull");
else print_nl("Loose");
print(" \\hbox (badness ");
print_int(b);
goto common_end;
}
}
return r;
} else {
get_shrink_order();
glue_order(r) = o;
glue_sign(r) = SHRINKING;
if (total_shrink[o] != 0) {
glue_set(r) = (float) -x / total_shrink[o];
} else {
glue_sign(r) = NORMAL;
glue_set(r) = 0.0;
}
if (total_shrink[o] < -x && o == NORMAL && list_ptr(r) != NULL) {
glue_set(r) = 1.0;
if (-x - total_shrink[NORMAL] > hfuzz || hbadness < 100) {
if (overfull_rule > 0 && -x - total_shrink[NORMAL] > hfuzz) {
while (link(q) != NULL)
q = link(q);
link(q) = new_rule();
width(link(q)) = overfull_rule;
}
print_ln();
print_nl("Overfull \\hbox (");
print_scaled(-x - total_shrink[NORMAL]);
print("pt too wide");
goto common_end;
}
} else if (hbadness < 100 && o == NORMAL && list_ptr(r) != NULL) {
b = badness(-x, total_shrink[NORMAL]);
if (b > hbadness) {
print_ln();
print_nl("Tight \\hbox (badness ");
print_int(b);
goto common_end;
}
}
return r;
}
common_end:
if (output_active) {
print(") has occurred while \\output is active");
} else {
if (pack_begin_line != 0) {
if (pack_begin_line > 0)
print(") in paragraph at lines ");
else print(") in alignment at lines ");
print_val(abs(pack_begin_line));
print("--");
} else print(") detected at line ");
print_val(line);
}
print_ln();
font_in_short_display = null_font;
short_display(list_ptr(r));
print_ln();
begin_diagnostic();
show_box(r);
end_diagnostic(TRUE);
return r;
}
ptr
vpackage (p, h, m, l)
ptr p;
scal h;
int m;
scal l;
{
int b;
scal d;
ptr g;
gord o;
ptr r;
scal s;
scal w;
scal x;
r = get_node(BOX_NODE_SIZE);
type(r) = VLIST_NODE;
subtype(r) = MIN_QUARTERWORD;
shift_amount(r) = 0;
list_ptr(r) = p;
w = 0;
clr_dimens();
while (p != NULL) {
if (is_char_node(p))
confusion("vpack");
switch (type(p))
{
case HLIST_NODE:
case VLIST_NODE:
case RULE_NODE:
case UNSET_NODE:
x += d + height(p);
d = depth(p);
if (type(p) >= RULE_NODE)
s = 0;
else s = shift_amount(p);
if (width(p) + s > w)
w = width(p) + s;
break;
case WHATSIT_NODE:
break;
case GLUE_NODE:
x += d;
d = 0;
g = glue_ptr(p);
x += width(g);
o = stretch_order(g);
total_stretch[o] += stretch(g);
o = shrink_order(g);
total_shrink[o] += shrink(g);
if (subtype(p) >= A_LEADERS) {
g = leader_ptr(p);
if (width(g) > w)
w = width(g);
}
break;
case KERN_NODE:
x += d + width(p);
d = 0;
break;
default:
break;
}
p = link(p);
}
width(r) = w;
if (d > l) {
x += d - l;
depth(r) = l;
} else {
depth(r) = d;
}
if (m == ADDITIONAL)
h += x;
height(r) = h;
x = h - x;
if (x == 0) {
glue_sign(r) = NORMAL;
glue_order(r) = NORMAL;
glue_set(r) = 0.0;
return r;
} else if (x > 0) {
get_stretch_order();
glue_order(r) = o;
glue_sign(r) = STRETCHING;
if (total_stretch[o] != 0) {
glue_set(r) = (float) x / total_stretch[o];
} else {
glue_sign(r) = NORMAL;
glue_set(r) = 0.0;
}
if (vbadness < INF_BAD && o == NORMAL && list_ptr(r) != NULL) {
b = badness(x, total_stretch[NORMAL]);
if (b > vbadness) {
print_ln();
if (b > 100)
print_nl("Underfull");
else print_nl("Loose");
print(" \\vbox (badness ");
print_int(b);
goto common_end;
}
}
return r;
} else {
get_shrink_order();
glue_order(r) = o;
glue_sign(r) = SHRINKING;
if (total_shrink[o] != 0) {
glue_set(r) = (float) -x / total_shrink[o];
} else {
glue_sign(r) = NORMAL;
glue_set(r) = 0.0;
}
if (total_shrink[o] < -x && o == NORMAL && list_ptr(r) != NULL) {
glue_set(r) = 1.0;
if (-x - total_shrink[NORMAL] > vfuzz || vbadness < 100) {
print_ln();
print_nl("Overfull \\vbox (");
print_scaled(-x - total_shrink[NORMAL]);
print("pt too high");
goto common_end;
}
} else if (vbadness < 100 && o == NORMAL && list_ptr(r) != NULL) {
b = badness(-x, total_shrink[NORMAL]);
if (b > vbadness) {
print_ln();
print_nl("Tight \\vbox (badness ");
print_int(b);
goto common_end;
}
}
return r;
}
common_end:
if (output_active) {
print(") has occurred while \\output is active");
} else {
if (pack_begin_line != 0) {
print(") in alignment at lines ");
print_val(abs(pack_begin_line));
print("--");
} else print(") detected at line ");
print_val(line);
print_ln();
}
begin_diagnostic();
show_box(r);
end_diagnostic(TRUE);
return r;
}