]> git.lyx.org Git - lyx.git/blob - src/TableLayout.C
Add support for compilers which do not have cname headers
[lyx.git] / src / TableLayout.C
1 #include <config.h>
2
3 #include <cstdlib>
4 #include "definitions.h"
5 #include FORMS_H_LOCATION
6 #include "layout_forms.h"
7 #include "lyx_main.h"
8 #include "lyxrc.h"
9 #include "LString.h"
10 #include "support/filetools.h"
11 #include "buffer.h"
12 #include "vspace.h"
13 #include "lyx_gui_misc.h"
14 #include "BufferView.h"
15 #include "lyxscreen.h"
16 #include "gettext.h"
17 #include "lyxtext.h"
18
19 extern void BeforeChange();
20
21 /* Prototypes */
22 extern FD_form_table_options *fd_form_table_options;
23 extern FD_form_table_extra *fd_form_table_extra;
24 extern BufferView *current_view;
25
26 static int
27     Confirmed = false,
28     ActCell;
29 // hack to keep the cursor from jumping to the end of the text in the Extra
30 // form input fields during editing. The values in LyXTable itself is changed in
31 // real-time, but we have no callbacks for the input fields, so I simply
32 // store and restore the cursor position for now. (too much of a hazzle to
33 // do it proper; we'll trash all this code in 1.1 anyway)
34     static int
35         extra_col_cursor_x, // need no y's, one-line input fields
36         extra_multicol_cursor_x;
37 // Joacim
38
39 bool UpdateLayoutTable(int flag)
40 {
41     bool update = true;
42     if (!current_view->getScreen() || !current_view->available())
43         update = false;
44     
45     if (update && current_view->currentBuffer()->text->cursor.par->table) {
46         int
47             align,
48             cell,
49             column,row;
50         char
51             buf[12];
52         string
53             pwidth, special;
54     
55         LyXTable *table = current_view->currentBuffer()->text->cursor.par->table;
56
57         cell = current_view->currentBuffer()->text->
58             NumberOfCell(current_view->currentBuffer()->text->cursor.par, 
59                          current_view->currentBuffer()->text->cursor.pos);
60         ActCell = cell;
61         column = table->column_of_cell(cell)+1;
62         fl_set_object_label(fd_form_table_options->text_warning,"");
63         Confirmed = false;
64         fl_activate_object(fd_form_table_extra->input_special_alignment);
65         fl_activate_object(fd_form_table_extra->input_special_multialign);
66         fl_activate_object(fd_form_table_options->input_column_width);
67         sprintf(buf,"%d",column);
68         fl_set_input(fd_form_table_options->input_table_column, buf);
69         fl_deactivate_object(fd_form_table_options->input_table_column);
70         row = table->row_of_cell(cell)+1;
71         sprintf(buf,"%d",row);
72         fl_set_input(fd_form_table_options->input_table_row, buf);
73         fl_deactivate_object(fd_form_table_options->input_table_row);
74         if (table->IsMultiColumn(cell))
75             fl_set_button(fd_form_table_options->radio_multicolumn, 1);
76         else
77             fl_set_button(fd_form_table_options->radio_multicolumn, 0);
78         if (table->RotateCell(cell))
79             fl_set_button(fd_form_table_options->radio_rotate_cell, 1);
80         else
81             fl_set_button(fd_form_table_options->radio_rotate_cell, 0);
82         if (table->TopLine(cell))
83             fl_set_button(fd_form_table_options->radio_border_top, 1);
84         else
85             fl_set_button(fd_form_table_options->radio_border_top, 0);
86         if (table->BottomLine(cell))
87             fl_set_button(fd_form_table_options->radio_border_bottom, 1);
88         else
89             fl_set_button(fd_form_table_options->radio_border_bottom, 0);
90         if (table->LeftLine(cell))
91             fl_set_button(fd_form_table_options->radio_border_left, 1);
92         else
93             fl_set_button(fd_form_table_options->radio_border_left, 0);
94         if (table->RightLine(cell))
95             fl_set_button(fd_form_table_options->radio_border_right, 1);
96         else
97             fl_set_button(fd_form_table_options->radio_border_right, 0);
98         align = table->GetAlignment(cell);
99         fl_set_button(fd_form_table_options->radio_align_left, 0);
100         fl_set_button(fd_form_table_options->radio_align_right, 0);
101         fl_set_button(fd_form_table_options->radio_align_center, 0);
102         special = table->GetAlignSpecial(cell,LyXTable::SET_SPECIAL_COLUMN);
103         if (flag)
104         {
105             fl_set_input(fd_form_table_extra->input_special_alignment,
106                          special.c_str());
107             fl_set_input_cursorpos(fd_form_table_extra->input_special_alignment,
108                     extra_col_cursor_x, 0); // restore the cursor
109         }
110         if (current_view->currentBuffer()->isReadonly()) 
111             fl_deactivate_object(fd_form_table_extra->input_special_alignment);
112         special = table->GetAlignSpecial(cell,LyXTable::SET_SPECIAL_MULTI);
113         if (flag)
114         {
115             fl_set_input(fd_form_table_extra->input_special_multialign,
116                          special.c_str());
117             fl_set_input_cursorpos(fd_form_table_extra->input_special_multialign,
118                     extra_multicol_cursor_x, 0); // restore the cursor
119         }
120         if (current_view->currentBuffer()->isReadonly()) 
121             fl_deactivate_object(fd_form_table_extra->input_special_multialign);
122         pwidth = table->GetPWidth(cell);
123         if (flag)
124             fl_set_input(fd_form_table_options->input_column_width,pwidth.c_str());
125         if (current_view->currentBuffer()->isReadonly()) 
126             fl_deactivate_object(fd_form_table_options->input_column_width);
127         if (!pwidth.empty()) {
128             fl_activate_object(fd_form_table_options->radio_linebreak_cell);
129             fl_set_object_lcol(fd_form_table_options->radio_linebreak_cell,
130                                FL_BLACK);
131             fl_set_button(fd_form_table_options->radio_linebreak_cell,
132                           table->Linebreaks(table->FirstVirtualCell(cell)));
133         } else {
134             fl_deactivate_object(fd_form_table_options->radio_linebreak_cell);
135             fl_set_object_lcol(fd_form_table_options->radio_linebreak_cell,
136                                FL_INACTIVE);
137             fl_set_button(fd_form_table_options->radio_linebreak_cell,0);
138         }
139         if ((!pwidth.empty() && !table->IsMultiColumn(cell)) ||
140             (align == LYX_ALIGN_LEFT))
141             fl_set_button(fd_form_table_options->radio_align_left, 1);
142         else if (align == LYX_ALIGN_RIGHT)
143             fl_set_button(fd_form_table_options->radio_align_right, 1);
144         else
145             fl_set_button(fd_form_table_options->radio_align_center, 1);
146         if (!pwidth.empty() && !table->IsMultiColumn(cell)) {
147             fl_deactivate_object(fd_form_table_options->radio_align_left);
148             fl_deactivate_object(fd_form_table_options->radio_align_right);
149             fl_deactivate_object(fd_form_table_options->radio_align_center);
150             fl_set_object_lcol(fd_form_table_options->radio_align_left,
151                                FL_INACTIVE);
152             fl_set_object_lcol(fd_form_table_options->radio_align_right,
153                                FL_INACTIVE);
154             fl_set_object_lcol(fd_form_table_options->radio_align_center,
155                                FL_INACTIVE);
156         } else {
157             fl_activate_object(fd_form_table_options->radio_align_left);
158             fl_activate_object(fd_form_table_options->radio_align_right);
159             fl_activate_object(fd_form_table_options->radio_align_center);
160             fl_set_object_lcol(fd_form_table_options->radio_align_left,
161                                FL_BLACK);
162             fl_set_object_lcol(fd_form_table_options->radio_align_right,
163                                FL_BLACK);
164             fl_set_object_lcol(fd_form_table_options->radio_align_center,
165                                FL_BLACK);
166         }
167         fl_set_button(fd_form_table_options->radio_longtable,table->IsLongTable());
168         if (table->IsLongTable()) {
169             fl_activate_object(fd_form_table_options->radio_lt_firsthead);
170             fl_activate_object(fd_form_table_options->radio_lt_head);
171             fl_activate_object(fd_form_table_options->radio_lt_foot);
172             fl_activate_object(fd_form_table_options->radio_lt_lastfoot);
173             fl_activate_object(fd_form_table_options->radio_lt_newpage);
174             fl_set_object_lcol(fd_form_table_options->radio_lt_firsthead,
175                                FL_BLACK);
176             fl_set_object_lcol(fd_form_table_options->radio_lt_head,
177                                FL_BLACK);
178             fl_set_object_lcol(fd_form_table_options->radio_lt_foot,
179                                FL_BLACK);
180             fl_set_object_lcol(fd_form_table_options->radio_lt_lastfoot,
181                                FL_BLACK);
182             fl_set_object_lcol(fd_form_table_options->radio_lt_newpage,
183                                FL_BLACK);
184             fl_set_button(fd_form_table_options->radio_lt_firsthead,
185                           table->RowOfLTFirstHead(cell));
186             fl_set_button(fd_form_table_options->radio_lt_head,
187                           table->RowOfLTHead(cell));
188             fl_set_button(fd_form_table_options->radio_lt_foot,
189                           table->RowOfLTFoot(cell));
190             fl_set_button(fd_form_table_options->radio_lt_lastfoot,
191                           table->RowOfLTLastFoot(cell));
192             fl_set_button(fd_form_table_options->radio_lt_newpage,
193                           table->LTNewPage(cell));
194         } else {
195             fl_deactivate_object(fd_form_table_options->radio_lt_firsthead);
196             fl_deactivate_object(fd_form_table_options->radio_lt_head);
197             fl_deactivate_object(fd_form_table_options->radio_lt_foot);
198             fl_deactivate_object(fd_form_table_options->radio_lt_lastfoot);
199             fl_deactivate_object(fd_form_table_options->radio_lt_newpage);
200             fl_set_button(fd_form_table_options->radio_lt_firsthead,0);
201             fl_set_button(fd_form_table_options->radio_lt_head,0);
202             fl_set_button(fd_form_table_options->radio_lt_foot,0);
203             fl_set_button(fd_form_table_options->radio_lt_lastfoot,0);
204             fl_set_button(fd_form_table_options->radio_lt_newpage,0);
205             fl_set_object_lcol(fd_form_table_options->radio_lt_firsthead,
206                                FL_INACTIVE);
207             fl_set_object_lcol(fd_form_table_options->radio_lt_head,
208                                FL_INACTIVE);
209             fl_set_object_lcol(fd_form_table_options->radio_lt_foot,
210                                FL_INACTIVE);
211             fl_set_object_lcol(fd_form_table_options->radio_lt_lastfoot,
212                                FL_INACTIVE);
213             fl_set_object_lcol(fd_form_table_options->radio_lt_newpage,
214                                FL_INACTIVE);
215         }
216         fl_set_button(fd_form_table_options->radio_rotate_table,table->RotateTable());
217     } else if (fd_form_table_options->form_table_options->visible) {
218         fl_hide_form(fd_form_table_options->form_table_options);
219     }
220     return update;
221 }
222
223 void OpenLayoutTableExtra()
224 {
225     if (fd_form_table_extra->form_table_extra->visible) {
226         fl_raise_form(fd_form_table_extra->form_table_extra);
227     } else {
228         fl_show_form(fd_form_table_extra->form_table_extra,
229                      FL_PLACE_MOUSE | FL_FREE_SIZE,FL_FULLBORDER,
230                      _("Table Extra Form"));
231     }
232 }
233
234 void MenuLayoutTable(int flag)
235 {
236     if (UpdateLayoutTable(flag)) {
237         if (fd_form_table_options->form_table_options->visible) {
238             fl_raise_form(fd_form_table_options->form_table_options);
239         }
240         else {
241             fl_show_form(fd_form_table_options->form_table_options,
242                          FL_PLACE_MOUSE | FL_FREE_SIZE,FL_FULLBORDER,
243                          _("Table Layout"));
244         }
245     }
246 }
247
248 void TableOptionsCB(FL_OBJECT *ob, long)
249 {
250     LyXTable
251         *table = 0;
252     int
253         cell,
254         s,
255         num = 0;
256     string
257         special,
258         str;
259
260     if (!current_view->available()
261         ||
262         !(table = current_view->currentBuffer()->text->cursor.par->table)) 
263       {
264         MenuLayoutTable(0);
265         return;
266       }
267     cell = current_view->currentBuffer()->text->
268         NumberOfCell(current_view->currentBuffer()->text->cursor.par, 
269                      current_view->currentBuffer()->text->cursor.pos);
270     if (ActCell != cell) {
271         MenuLayoutTable(0);
272         fl_set_object_label(fd_form_table_options->text_warning,
273                             _("Warning: Wrong Cursor position, updated window"));
274         fl_show_object(fd_form_table_options->text_warning);
275         extra_col_cursor_x=0; // would rather place it at the end, but...
276         extra_multicol_cursor_x=0;
277         return;
278     }
279     // No point in processing directives that you can't do anything with
280     // anyhow, so exit now if the buffer is read-only.
281     if (current_view->currentBuffer()->isReadonly()) {
282       MenuLayoutTable(0);
283       return;
284     }
285     
286     if (ob != fd_form_table_options->button_table_delete) {
287         fl_set_object_label(fd_form_table_options->text_warning,"");
288         Confirmed = false;
289     }
290     str = fl_get_input(fd_form_table_options->input_column_width);
291     if (!str.empty() && !isValidLength(str)) {
292         fl_set_object_label(fd_form_table_options->text_warning,
293                             _("Warning: Invalid Length (valid example: 10mm)"));
294         fl_show_object(fd_form_table_options->text_warning);
295         return;
296     }
297     if (((ob==fd_form_table_options->button_delete_row) && (table->rows<=1)) ||
298         ((ob==fd_form_table_options->button_delete_column) && (table->columns<=1)))
299         ob = fd_form_table_options->button_table_delete;
300     if (ob == fd_form_table_options->button_append_row)
301         num = LyXTable::APPEND_ROW;
302     else if (ob == fd_form_table_options->button_append_column)
303         num = LyXTable::APPEND_COLUMN;
304     else if (ob == fd_form_table_options->button_delete_row)
305         num = LyXTable::DELETE_ROW;
306     else if (ob == fd_form_table_options->button_delete_column)
307         num = LyXTable::DELETE_COLUMN;
308     else if (ob == fd_form_table_options->button_set_borders)
309         num = LyXTable::SET_ALL_LINES;
310     else if (ob == fd_form_table_options->button_unset_borders)
311         num = LyXTable::UNSET_ALL_LINES;
312     else if (ob == fd_form_table_options->radio_border_top)
313         num = LyXTable::TOGGLE_LINE_TOP;
314     else if (ob == fd_form_table_options->radio_border_bottom)
315         num = LyXTable::TOGGLE_LINE_BOTTOM;
316     else if (ob == fd_form_table_options->radio_border_left)
317         num = LyXTable::TOGGLE_LINE_LEFT;
318     else if (ob == fd_form_table_options->radio_border_right)
319         num = LyXTable::TOGGLE_LINE_RIGHT;
320     else if (ob == fd_form_table_options->radio_align_left)
321         num = LyXTable::ALIGN_LEFT;
322     else if (ob == fd_form_table_options->radio_align_right)
323         num = LyXTable::ALIGN_RIGHT;
324     else if (ob == fd_form_table_options->radio_align_center)
325         num = LyXTable::ALIGN_CENTER;
326     else if ((ob==fd_form_table_options->button_table_delete) && !Confirmed) {
327         fl_set_object_label(fd_form_table_options->text_warning,
328                             _("Confirm: press Delete-Button again"));
329         Confirmed = true;
330         return;
331     } else if ((ob == fd_form_table_options->button_table_delete) 
332                && Confirmed) {
333         num = LyXTable::DELETE_TABLE;
334         Confirmed = false;
335     } else if (ob == fd_form_table_options->radio_multicolumn)
336         num = LyXTable::MULTICOLUMN;
337     else if (ob == fd_form_table_options->radio_longtable) {
338         s=fl_get_button(fd_form_table_options->radio_longtable);
339         if (s) {
340             num = LyXTable::SET_LONGTABLE;
341             fl_activate_object(fd_form_table_options->radio_lt_firsthead);
342             fl_activate_object(fd_form_table_options->radio_lt_head);
343             fl_activate_object(fd_form_table_options->radio_lt_foot);
344             fl_activate_object(fd_form_table_options->radio_lt_lastfoot);
345             fl_activate_object(fd_form_table_options->radio_lt_newpage);
346             fl_set_button(fd_form_table_options->radio_lt_firsthead,
347                           table->RowOfLTFirstHead(cell));
348             fl_set_button(fd_form_table_options->radio_lt_head,
349                           table->RowOfLTHead(cell));
350             fl_set_button(fd_form_table_options->radio_lt_foot,
351                           table->RowOfLTFoot(cell));
352             fl_set_button(fd_form_table_options->radio_lt_lastfoot,
353                           table->RowOfLTLastFoot(cell));
354             fl_set_button(fd_form_table_options->radio_lt_firsthead,
355                           table->LTNewPage(cell));
356         } else {
357             num = LyXTable::UNSET_LONGTABLE;
358             fl_deactivate_object(fd_form_table_options->radio_lt_firsthead);
359             fl_deactivate_object(fd_form_table_options->radio_lt_head);
360             fl_deactivate_object(fd_form_table_options->radio_lt_foot);
361             fl_deactivate_object(fd_form_table_options->radio_lt_lastfoot);
362             fl_deactivate_object(fd_form_table_options->radio_lt_newpage);
363             fl_set_button(fd_form_table_options->radio_lt_firsthead,0);
364             fl_set_button(fd_form_table_options->radio_lt_firsthead,0);
365             fl_set_button(fd_form_table_options->radio_lt_firsthead,0);
366             fl_set_button(fd_form_table_options->radio_lt_firsthead,0);
367             fl_set_button(fd_form_table_options->radio_lt_firsthead,0);
368             fl_set_object_lcol(fd_form_table_options->radio_lt_firsthead,
369                                FL_INACTIVE);
370             fl_set_object_lcol(fd_form_table_options->radio_lt_head,
371                                FL_INACTIVE);
372             fl_set_object_lcol(fd_form_table_options->radio_lt_foot,
373                                FL_INACTIVE);
374             fl_set_object_lcol(fd_form_table_options->radio_lt_lastfoot,
375                                FL_INACTIVE);
376             fl_set_object_lcol(fd_form_table_options->radio_lt_newpage,
377                                FL_INACTIVE);
378         }
379     } else if (ob == fd_form_table_options->radio_rotate_table) {
380         s=fl_get_button(fd_form_table_options->radio_rotate_table);
381         if (s)
382             num = LyXTable::SET_ROTATE_TABLE;
383         else
384             num = LyXTable::UNSET_ROTATE_TABLE;
385     } else if (ob == fd_form_table_options->radio_rotate_cell) {
386         s=fl_get_button(fd_form_table_options->radio_rotate_cell);
387         if (s)
388             num = LyXTable::SET_ROTATE_CELL;
389         else
390             num = LyXTable::UNSET_ROTATE_CELL;
391     } else if (ob == fd_form_table_options->radio_linebreak_cell) {
392         num = LyXTable::SET_LINEBREAKS;
393     } else if (ob == fd_form_table_options->radio_lt_firsthead) {
394         num = LyXTable::SET_LTFIRSTHEAD;
395     } else if (ob == fd_form_table_options->radio_lt_head) {
396         num = LyXTable::SET_LTHEAD;
397     } else if (ob == fd_form_table_options->radio_lt_foot) {
398         num = LyXTable::SET_LTFOOT;
399     } else if (ob == fd_form_table_options->radio_lt_lastfoot) {
400         num = LyXTable::SET_LTLASTFOOT;
401     } else if (ob == fd_form_table_options->radio_lt_newpage) {
402         num = LyXTable::SET_LTNEWPAGE;
403     } else if (ob == fd_form_table_options->button_table_extra) {
404         OpenLayoutTableExtra();
405         return;
406     } else if (ob == fd_form_table_extra->input_special_alignment) {
407         special=fl_get_input(fd_form_table_extra->input_special_alignment);
408         int dummy;
409         fl_get_input_cursorpos(ob, &extra_col_cursor_x, &dummy);
410         num = LyXTable::SET_SPECIAL_COLUMN;
411     } else if (ob == fd_form_table_extra->input_special_multialign) {
412         special=fl_get_input(fd_form_table_extra->input_special_multialign);
413         int dummy;
414         fl_get_input_cursorpos(ob, &extra_multicol_cursor_x, &dummy);
415         num = LyXTable::SET_SPECIAL_MULTI;
416     } else
417         return;
418     if (current_view->available()){
419         current_view->getScreen()->HideCursor();
420         if (!current_view->currentBuffer()->text->selection){
421             BeforeChange(); 
422             current_view->currentBuffer()->update(-2);
423         }
424         if ((num == LyXTable::SET_SPECIAL_COLUMN) ||
425             (num == LyXTable::SET_SPECIAL_MULTI))
426             current_view->currentBuffer()->text->TableFeatures(num,special);
427         else
428             current_view->currentBuffer()->text->TableFeatures(num);
429         current_view->currentBuffer()->update(1);
430     }
431     if (num == LyXTable::DELETE_TABLE)
432         fl_hide_form(fd_form_table_options->form_table_options);
433     else
434         UpdateLayoutTable(true);
435     return;
436 }
437
438 void TableOptCloseCB(FL_OBJECT *, long)
439 {
440     fl_hide_form(fd_form_table_options->form_table_options);
441     return;
442 }
443
444 void TableSpeCloseCB(FL_OBJECT *, long)
445 {
446     fl_hide_form(fd_form_table_extra->form_table_extra);
447     return;
448 }
449
450 void SetPWidthCB(FL_OBJECT *ob, long)
451 {
452     fl_set_object_label(fd_form_table_options->text_warning,"");
453     Confirmed = false;
454     if (ob == fd_form_table_options->input_column_width) {
455         string
456             str;
457         str = fl_get_input(ob);
458         if (!str.empty() && !isValidLength(str)) {
459             fl_set_object_label(fd_form_table_options->text_warning,
460                             _("Warning: Invalid Length (valid example: 10mm)"));
461             fl_show_object(fd_form_table_options->text_warning);
462             return;
463         }
464         if (current_view->available()){
465             current_view->getScreen()->HideCursor();
466             if (!current_view->currentBuffer()->text->selection){
467                 BeforeChange(); 
468                 current_view->currentBuffer()->update(-2);
469             }
470             current_view->currentBuffer()->text->TableFeatures(LyXTable::SET_PWIDTH,str);
471             current_view->currentBuffer()->update(1);
472         }
473         MenuLayoutTable(0); // update for alignment
474     }
475 }