output: Support decimal and mixed alignment,
[pspp] / src / output / table.h
1 /* PSPP - a program for statistical analysis.
2    Copyright (C) 1997, 1998, 1999, 2000, 2009, 2013, 2014 Free Software Foundation, Inc.
3
4    This program is free software: you can redistribute it and/or modify
5    it under the terms of the GNU General Public License as published by
6    the Free Software Foundation, either version 3 of the License, or
7    (at your option) any later version.
8
9    This program is distributed in the hope that it will be useful,
10    but WITHOUT ANY WARRANTY; without even the implied warranty of
11    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12    GNU General Public License for more details.
13
14    You should have received a copy of the GNU General Public License
15    along with this program.  If not, see <http://www.gnu.org/licenses/>. */
16
17 #ifndef OUTPUT_TABLE_H
18 #define OUTPUT_TABLE_H 1
19
20 /* Tables.
21
22 .  A table is a rectangular grid of cells.  Cells can be joined to form larger
23    cells.  Rows and columns can be separated by rules of various types.  Rows
24    at the top and bottom of a table and columns at the left and right edges of
25    a table can be designated as headers, which means that if the table must be
26    broken across more than one page, those rows or columns are repeated on each
27    page.
28
29    Every table is an instance of a particular table class that is responsible
30    for keeping track of cell data.  By far the most common table class is
31    struct tab_table (see output/tab.h).  This header also declares some other
32    kinds of table classes, near the end of the file.
33
34    A table is not itself an output_item, and thus a table cannot by itself be
35    used for output, but they can be embedded inside struct table_item (see
36    table-item.h) for that purpose. */
37
38 #include <stdbool.h>
39 #include <stdint.h>
40 #include <stddef.h>
41
42 struct casereader;
43 struct fmt_spec;
44 struct pool;
45 struct table_item;
46 struct variable;
47
48 /* A table axis.
49
50    Many table-related declarations use 2-element arrays in place of "x" and "y"
51    variables.  This reduces code duplication significantly, because much table
52    code treats rows and columns the same way.
53
54    A lot of code that uses these enumerations assumes that the two values are 0
55    and 1, so don't change them to other values. */
56 enum table_axis
57   {
58     TABLE_HORZ,
59     TABLE_VERT,
60     TABLE_N_AXES
61   };
62
63 struct cell_color
64   {
65     uint8_t alpha, r, g, b;
66   };
67
68 #define CELL_COLOR(r, g, b) (struct cell_color) { 255, r, g, b }
69 #define CELL_COLOR_BLACK CELL_COLOR (0, 0, 0)
70 #define CELL_COLOR_WHITE CELL_COLOR (255, 255, 255)
71
72 static inline bool
73 cell_color_equal (const struct cell_color *a, const struct cell_color *b)
74 {
75   return a->alpha == b->alpha && a->r == b->r && a->g == b->g && a->b == b->b;
76 }
77
78 void cell_color_dump (const struct cell_color *);
79
80 enum table_stroke
81   {
82     TABLE_STROKE_NONE,
83     TABLE_STROKE_SOLID,
84     TABLE_STROKE_DASHED,
85     TABLE_STROKE_THICK,
86     TABLE_STROKE_THIN,
87     TABLE_STROKE_DOUBLE,
88     TABLE_N_STROKES,
89   };
90
91 const char *table_stroke_to_string (enum table_stroke);
92
93 struct table_border_style
94   {
95     enum table_stroke stroke;
96     struct cell_color color;
97   };
98
99 #define TABLE_BORDER_STYLE_INITIALIZER { TABLE_STROKE_SOLID, CELL_COLOR_BLACK }
100
101 enum table_halign
102   {
103     TABLE_HALIGN_RIGHT,
104     TABLE_HALIGN_LEFT,
105     TABLE_HALIGN_CENTER,
106     TABLE_HALIGN_MIXED,
107     TABLE_HALIGN_DECIMAL
108   };
109
110 const char *table_halign_to_string (enum table_halign);
111
112 enum table_valign
113   {
114     TABLE_VALIGN_TOP,
115     TABLE_VALIGN_CENTER,
116     TABLE_VALIGN_BOTTOM,
117   };
118
119 const char *table_valign_to_string (enum table_valign);
120
121 struct cell_style
122   {
123     enum table_halign halign;
124     enum table_valign valign;
125     double decimal_offset;       /* In 1/96" units. */
126     char decimal_char;           /* Either '.' or ','. */
127     int margin[TABLE_N_AXES][2]; /* In 1/96" units. */
128   };
129
130 #define CELL_STYLE_INITIALIZER { CELL_STYLE_INITIALIZER__ }
131 #define CELL_STYLE_INITIALIZER__                                \
132         .margin = { [TABLE_HORZ][0] = 8, [TABLE_HORZ][1] = 11,  \
133                     [TABLE_VERT][0] = 1, [TABLE_VERT][1] = 1 }
134
135 void cell_style_dump (const struct cell_style *);
136
137 struct font_style
138   {
139     bool bold, italic, underline, markup;
140     struct cell_color fg[2], bg[2];
141     char *typeface;
142     int size;
143   };
144
145 #define FONT_STYLE_INITIALIZER { FONT_STYLE_INITIALIZER__ }
146 #define FONT_STYLE_INITIALIZER__                                        \
147         .fg = { [0] = CELL_COLOR_BLACK, [1] = CELL_COLOR_BLACK},        \
148         .bg = { [0] = CELL_COLOR_WHITE, [1] = CELL_COLOR_WHITE},
149
150 void font_style_copy (struct font_style *, const struct font_style *);
151 void font_style_uninit (struct font_style *);
152 void font_style_dump (const struct font_style *);
153
154 struct area_style
155   {
156     struct cell_style cell_style;
157     struct font_style font_style;
158   };
159
160 #define AREA_STYLE_INITIALIZER { AREA_STYLE_INITIALIZER__ }
161 #define AREA_STYLE_INITIALIZER__                \
162        .cell_style = CELL_STYLE_INITIALIZER,    \
163        .font_style = FONT_STYLE_INITIALIZER
164
165 struct area_style *area_style_clone (struct pool *, const struct area_style *);
166 void area_style_copy (struct area_style *, const struct area_style *);
167 void area_style_uninit (struct area_style *);
168 void area_style_free (struct area_style *);
169
170 /* Properties of a table cell. */
171 enum
172   {
173     TAB_NONE = 0,
174     TAB_EMPH       = 1 << 0,    /* Emphasize cell contents. */
175     TAB_FIX        = 1 << 1,    /* Use fixed font. */
176     TAB_MARKUP     = 1 << 2,    /* Text contains Pango markup. */
177     TAB_NUMERIC    = 1 << 3,    /* Cell contents are numeric. */
178     TAB_ROTATE     = 1 << 4,    /* Rotate cell contents 90 degrees. */
179
180     /* Bits with values (1 << TAB_FIRST_AVAILABLE) and higher are
181        not used, so they are available for subclasses to use as
182        they wish. */
183     TAB_FIRST_AVAILABLE = 5
184   };
185
186 /* Styles for the rules around table cells. */
187 enum
188   {
189     TAL_NONE = TABLE_STROKE_NONE,
190 #define TAL_0 TAL_NONE
191     TAL_SOLID = TABLE_STROKE_SOLID,
192 #define TAL_1 TAL_SOLID
193     TAL_DASHED = TABLE_STROKE_DASHED,
194     TAL_THICK = TABLE_STROKE_THICK,
195     TAL_THIN = TABLE_STROKE_THIN,
196     TAL_DOUBLE = TABLE_STROKE_DOUBLE,
197 #define TAL_2 TAL_DOUBLE
198   };
199
200 /* Given line styles A and B (each one of the TAL_* enumeration constants
201    above), returns a line style that "combines" them, that is, that gives a
202    reasonable line style choice for a rule for different reasons should have
203    both styles A and B.
204
205    Used especially for pasting tables together (see table_paste()). */
206 static inline int table_rule_combine (int a, int b)
207 {
208   return a > b ? a : b;
209 }
210
211 /* A table. */
212 struct table
213   {
214     const struct table_class *klass;
215
216     /* Table size.
217
218        n[TABLE_HORZ]: Number of columns.
219        n[TABLE_VERT]: Number of rows. */
220     int n[TABLE_N_AXES];
221
222     /* Table headers.
223
224        Rows at the top and bottom of a table and columns at the left and right
225        edges of a table can be designated as headers.  If the table must be
226        broken across more than one page for output, headers rows and columns
227        are repeated on each page.
228
229        h[TABLE_HORZ][0]: Left header columns.
230        h[TABLE_HORZ][1]: Right header columns.
231        h[TABLE_VERT][0]: Top header rows.
232        h[TABLE_VERT][1]: Bottom header rows. */
233     int h[TABLE_N_AXES][2];
234
235     /* Reference count.  A table may be shared between multiple owners,
236        indicated by a reference count greater than 1.  When this is the case,
237        the table must not be modified. */
238     int ref_cnt;
239   };
240
241 /* Reference counting. */
242 struct table *table_ref (const struct table *);
243 void table_unref (struct table *);
244 bool table_is_shared (const struct table *);
245 struct table *table_unshare (struct table *);
246
247 /* Returns the number of columns or rows, respectively, in T. */
248 static inline int table_nc (const struct table *t)
249         { return t->n[TABLE_HORZ]; }
250 static inline int table_nr (const struct table *t)
251         { return t->n[TABLE_VERT]; }
252
253 /* Returns the number of left, right, top, or bottom headers, respectively, in
254    T.  */
255 static inline int table_hl (const struct table *t)
256         { return t->h[TABLE_HORZ][0]; }
257 static inline int table_hr (const struct table *t)
258         { return t->h[TABLE_HORZ][1]; }
259 static inline int table_ht (const struct table *t)
260         { return t->h[TABLE_VERT][0]; }
261 static inline int table_hb (const struct table *t)
262         { return t->h[TABLE_VERT][1]; }
263
264 /* Set headers. */
265 void table_set_hl (struct table *, int hl);
266 void table_set_hr (struct table *, int hr);
267 void table_set_ht (struct table *, int ht);
268 void table_set_hb (struct table *, int hb);
269 \f
270 /* Table classes. */
271
272 /* Simple kinds of tables. */
273 struct table *table_from_string (enum table_halign, const char *);
274 struct table *table_from_variables (unsigned int options,
275                                     struct variable **, size_t);
276 struct table *table_from_casereader (const struct casereader *,
277                                      size_t column,
278                                      const char *heading,
279                                      const struct fmt_spec *);
280
281 /* Combining tables. */
282 struct table *table_paste (struct table *, struct table *,
283                            enum table_axis orientation);
284 struct table *table_hpaste (struct table *left, struct table *right);
285 struct table *table_vpaste (struct table *top, struct table *bottom);
286
287 /* Taking subsets of tables. */
288 struct table *table_select (struct table *, int rect[TABLE_N_AXES][2]);
289 struct table *table_select_slice (struct table *, enum table_axis,
290                                   int z0, int z1, bool add_headers);
291 struct table *table_select_columns (struct table *,
292                                     int x0, int x1, bool add_headers);
293 struct table *table_select_rows (struct table *,
294                                  int y0, int y1, bool add_headers);
295
296 /* Miscellaneous table operations. */
297 struct table *table_transpose (struct table *);
298
299 #endif /* output/table.h */