1 // $Id: Edit1.cxx 1125 2011-03-09 00:23:18Z larry $
2 //
3 // Edit1.cxx - routine for DRAWxtl V5.5 - the GUI version
4 //
5 // Coded using the FLTK 1.1.6 widget set
6 //
7 //     Larry W. Finger, Martin Kroeker and Brian Toby
8 //
9 // This module includes the majority of the edit screens for the GUI
10 //
11 // routines contained within this file:
12 //
13 //  Add_Frame_Main - add frame widget to main screen
14 //  Automation_Abort_cb - callback routine to abort automation
15 //  Automation_Edit_cb - Main window for automation of modulated structures
16 //  Automation_Go_cb - callback for starting automation
17 //  Bond_Combo_cb - updates bond distance table when atom in combo box is changed
18 //  Bond_Frame_Combo_cb - callback routine entered when frame combo box changed
19 //  Check_Box_cb - processes main page check boxes (not clipflag)
20 //  Configure_cb - callback routine to load configuration screen
21 //  Configure_Close_cb - callback routine to cancel configuration file
22 //  Configure_Save_cb - callback routine to save configuration file
23 //  Configure_MSMS_cb - callback routine to create MSMS path entry window
24 //  Configure_MSMS_loc_cb - browser window for MSMS path
25 //  Configure_Close_MSMS_cb - callback to close MSMS configuration window without saving
26 //  Configure_Save_MSMS_cb - callback to close the MSMS configuration window
27 //  ConfigurePOV_cb - callback to select path of POV executable
28 //  ConfigurePOVOptions_cb - callback to select options for POV
29 //  Edit_Arrow_cb - callback routine to create Arrow Edit screen
30 //  Edit_Arrow_Close_cb - callback routine to dismiss Arrow Edit screen
31 //  Edit_Arrow_Save_cb - callback to save (or apply) Arrow Edit changes
32 //  Edit_Bond_cb - callback routine to load the bond editing screen
33 //  Edit_Bond_Close_cb - callback routine entered when the 'Cancel' Button is pressed
34 //  Edit_Bond_Save_cb - callback routine entered when the 'Save' Button is pressed
35 //  Edit_Ellipsoid_cb - callback routine to load ellipsoid edit screen
36 //  Edit_Ellipsoid_Close_cb - callback routine from cancel button on ellipsoids screen
37 //  Edit_Ellipsoid_Save_cb - callback routine from save button on ellipsoid screen
38 //  Edit_LonePair_cb - callback routine to load lone-pair edit screen
39 //  Edit_Lone_Pair_Close_cb - callback routine called when the 'Cancel' Button is pressed
40 //  Edit_Lone_Pair_Save_cb - callback routine called when the 'Save' Button is pressed
41 //  Edit_Parmeters_Close_cb - callback from cancel button on Edit Parameter Screen
42 //  Browse_Map_File_cb - callback to select a fourier map file
43 //  Edit_Maps_cb - callback routine to load map parameter edit screen
44 //  Edit_Maps_Close_cb - callback from 'Cancel' button
45 //  Edit_Maps_Save_cb - callback from 'Save' or 'Apply' button
46 //  Edit_Parmeters_cb - callback routine for edit parameters screen
47 //  Edit_Parmeters_Save_cb - callback from save or apply button on Edit Parameter Screen
48 //  Edit_Polyhedra_cb - callback routine to load polyhedral edit screen
49 //  Load_Color_Combo - load color combo list widget
50 //  Edit_Modparms_Close_cb - callback from 'Cancel' button on modulation screen
51 //  Edit_Modparms_Change_cb - callback for immediate feedback from the modulation t spinners
52 //  Edit_Modparms_Save_cb - callback from 'Save' or 'Apply' button on modulation screen
53 //  Edit_Modparms_cb - callback routine to load modulation parameters screen
54 //  Edit_Slice_cb - callback routine to load map slice screen
55 //  Edit_Slice_Close_cb - callback routine to close map slice screen
56 //  Edit_Slice_Save_cb - callback routine to save map slice screen parameters
57 //  Modify_Occ_cb - callback entered when a line in the occupancy threshold list is selected
58 //  Occ_Combo_cb - callback associated with the atom list combo on the modulation screen
59 //  New_Occ_Input_cb - callback triggered by changes to the occupancy entry fields
60 //  New_Occ_Add_cb - callback entered when Add button for occupancy thresholds is pressed
61 //  Slice_Frame_Combo_cb - callback routine entered when the frame number combo on Edit Slice screen is changed
62 
63 #include "drawxtl.h"
64 #include "DRAWxtlViewUI.h"
65 #include "EditView.h"
66 #include "Ellipsoids.h"
67 #include "draw_ext.h"
68 #ifdef WIN32
69 #include <direct.h>
70 #else
71 #include <unistd.h>
72 #define _chdir chdir
73 #endif
74 #include <ctype.h>
75 
76 #include "DRAWxtl_proto.h"
77 
78 static int zero = 0;
79 
80 char Edit_title[128];
81 
82 char Colors_Combo[] =
83     { "\nRed\nGreen\nBlue\nYellow\nCyan\n"
84 "Magenta\nClear\nWhite\nBlack\nGray05\n"
85 "Gray10\nGray15\nGray20\nGray25\nGray30\n"
86 "Gray35\nGray40\nGray45\nGray50\nGray55\n"
87 "Gray60\nGray65\nGray70\nGray75\nGray80\n"
88 "Gray85\nGray90\nGray95\nDimGray\nDimGrey\n"
89 "Gray\nGrey\nLightGray\nLightGrey\nVLightGray\n"
90 "VLightGrey\nAquamarine\nBlueViolet\nBrown\nCadetBlue\n"
91 "Coral\nCornflowerBlue\nDarkGreen\nDarkOliveGreen\nDarkOrchid\n"
92 "DarkSlateBlue\nDarkSlateGray\nDarkSlateGrey\nDarkTurquoise\nFirebrick\n"
93 "ForestGreen\nGold\nGoldenrod\nGreenYellow\nIndianRed\n"
94 "Khaki\nLightBlue\nLightSteelBlue\nLimeGreen\nMaroon\n"
95 "MediumAquamarine\nMediumBlue\nMediumForestGreen\nMediumGoldenrod\nMediumOrchid\n"
96 "MediumSeaGreen\nMediumSlateBlue\nMediumSpringGreen\nMediumTurquoise\nMediumVioletRed\n"
97 "MidnightBlue\nNavy\nNavyBlue\nOrange\nOrangeRed\n"
98 "Orchid\nPaleGreen\nPink\nPlum\nSalmon\n"
99 "SeaGreen\nSienna\nSkyBlue\nSlateBlue\nSpringGreen\n"
100 "SteelBlue\nTan\nThistle\nTurquoise\nViolet\n"
101 "VioletRed\nWheat\nYellowGreen\nSummerSky\nRichBlue\n"
102 "Brass\nCopper\nBronze\nBronze2\nSilver\n"
103 "BrightGold\nOldGold\nFeldspar\nQuartz\nMica\n"
104 "NeonPink\nDarkPurple\nNeonBlue\nCoolCopper\nMandarinOrange\n"
105 "LightWood\nMediumWood\nDarkWood\nSpicyPink\nSemiSweetChoc\n"
106 "BakersChoc\nFlesh\nNewTan\nNewMidnightBlue\nVeryDarkBrown\n"
107 "DarkBrown\nDarkTan\nGreenCopper\nDkGreenCopper\nDustyRose\n"
108 "HuntersGreen\nScarlet\nMed_Purple\nLight_Purple\nVery_Light_Purple\n"
109 };
110 
111 #ifdef WIN32
112 const char *flu_file_chooser (const char *message, const char *pattern,
113 			      const char *filename);
114 #endif
115 
116 void
Add_Frame_Main(void)117 Add_Frame_Main (void)
118 {
119 // make frame number combo box on main screen hidden/shown as desired
120     int i;
121 
122     char string[20];
123 
124     if (drvui->max_frame > 1) {
125 	drvui->Frame_No->list.clear ();
126 	drvui->Frame_No->show ();
127 	for (i = 1; i <= drvui->max_frame; i++) {
128 	    sprintf (string, "%d", i);
129 	    drvui->Frame_No->list.add (string);
130 	}
131 	drvui->Frame_No->pop_height (20 * drvui->max_frame);
132 	drvui->Frame_No->value ("1");
133     } else {
134 	drvui->Frame_No->hide ();
135     }
136 }
137 
138 void
Arrow_Frame_Combo_cb(Fl_Widget *,void *)139 Arrow_Frame_Combo_cb (Fl_Widget *, void *)
140 {
141 // update arrow information table when the frame numver in the combo box is changed
142     int i;
143 
144     int Frame_No = 1;
145 
146     if (!drvui->table)
147 	drvui->table = (char *) zalloc (20480 * sizeof (char));
148     if (drvui->max_frame > 1)
149 	Frame_No = atoi (arrows->Frame_No->value ());
150     strcpy (drvui->table, "");
151     for (i = 0; i < drvui->nmag; i++) {	// fill in the widgets
152 	if (drvui->arrows[i].arrow_fn == Frame_No) {
153 	    char string[128];
154 
155 	    sprintf (string, "%6.3f %6.3f %6.3f %10.3f %6.3f %6.3f %10.3f %6.3f   %s\n",
156 		     drvui->arrows[i].mag_xp[0], drvui->arrows[i].mag_xp[1],
157 		     drvui->arrows[i].mag_xp[2], drvui->arrows[i].mag_xc[0],
158 		     drvui->arrows[i].mag_xc[1], drvui->arrows[i].mag_xc[2],
159 		     drvui->arrows[i].arrow_length, drvui->arrows[i].arrow_diam,
160 		     drvui->arrows[i].col_arrow);
161 	    strcat (drvui->table, string);
162 	}
163     }
164     arrows->ArrowBuffer->text (drvui->table);
165 }
166 
Automation_Abort_cb(void)167 void Automation_Abort_cb(void)
168 {
169 // callback routine to abort a running automation
170 
171     int keep;
172 
173     drvui->automation = 0;
174     keep = Automate->keeptemps->value();
175     if (!keep) {
176 	float start, end, step;
177 	int nstep, no_steps;
178 	char POV_filename[200];
179 	char string[200],string2[20];
180 
181 	strcpy(POV_filename, Automate->POV_Filename->value ());
182 	start = (float) atof (Automate->t_start->value());
183 	end = (float) atof (Automate->t_end->value());
184 	step = (float) atof (Automate->t_step->value());
185 	no_steps = (int)(((end - start) / step) + 0.5f) + 1;
186 	for (nstep = 1; nstep < no_steps; nstep++) {
187 	    strcpy(string, POV_filename);
188 	    sprintf(string2, "%.3d.pov", nstep);
189 	    strcat(string, string2);
190             if (!unlink(string)) break;
191 	    strcpy(string, POV_filename);
192 	    if (Automate->Mencoder->value() )
193 		sprintf(string2,"%dd.tga",nstep);
194 	    else
195 		sprintf(string2,"%dd.png",nstep);
196 	    strcat(string, string2);
197 	    unlink(string);
198 	}
199     }
200 
201 //    Automate->Automation_Edit_Window->hide();
202 //    delete(Automate);
203 //    Automate = NULL;
204 }
205 
Automation_Edit_cb(void)206 void Automation_Edit_cb(void)
207 {
208 // callback routine to open automation window
209     int y;
210     char string[200];
211 
212     if (!drvui->modulated) {
213 	Error_Box("Automation requires a modulated structure");
214 	return;
215     }
216     if (Automate)
217 	delete(Automate);
218     Automate = new AutomationParam;	// get new instance of automation parms
219     Automate->Automation_Edit_Window =
220 	new Fl_Window (50, 50, 410, 350, "Modulated Structure Automation");
221     Automate->Automation_Edit_Window->callback ((Fl_Callback *) Automation_Abort_cb);
222 #if !defined (WIN32) && !defined (__APPLE__)
223     Automate->Automation_Edit_Window->icon ((char *) drvui->icon);
224 #endif
225     y = 30;
226     Automate->t_start = new Fl_Input(70, y, 70, 25, "t Start");
227     Automate->t_start->align (FL_ALIGN_TOP);
228     sprintf(string, "%.3f", drvui->phaseshift[0]);
229     Automate->t_start->value(string);
230     Automate->t_end = new Fl_Input(170, y, 70, 25, "t End");
231     Automate->t_end->align (FL_ALIGN_TOP);
232     Automate->t_end->value("1.000");
233     Automate->t_step = new Fl_Input(270, y, 70, 25, "t Step");
234     Automate->t_step->align (FL_ALIGN_TOP);
235     Automate->t_step->value("0.001");
236     y += 50;
237     Automate->POV_Filename = new Fl_Input(30, y, 350, 25, "POV Basic File Name");
238     Automate->POV_Filename->align (FL_ALIGN_TOP);
239     strcpy(string, drvui->Cur_Dir);
240 #ifdef WIN32
241     strcat(string, "\\");
242 #else
243     strcat(string,"/");
244 #endif
245     strcat(string, drvui->Cur_Root);
246     Automate->POV_Filename->value (string);
247     Automate->POV_Filename->tooltip("This name will have \"xxx.pov\" appended.");
248     y += 30;
249 
250 	Fl_Group *qq = new Fl_Group (70, y, 260, 90);
251 
252 	qq->labelfont (1);
253 	qq->box (FL_THIN_UP_BOX);
254 	Automate->NoMovie = new Fl_Radio_Button (80, y + 10, 12, 12, "Prepare image files only");
255 	Automate->NoMovie->type (102);
256 	Automate->NoMovie->selection_color ((Fl_Color) 1);
257 	Automate->NoMovie->align (FL_ALIGN_RIGHT);
258 	Automate->NoMovie->set ();
259 	Automate->Mencoder = new Fl_Radio_Button (80, y + 30, 12, 12, "Create AVI using mencocder");
260 	Automate->Mencoder->type (102);
261 	Automate->Mencoder->selection_color ((Fl_Color) 1);
262 	Automate->Mencoder->align (FL_ALIGN_RIGHT);
263 	Automate->Ffmpeg = new Fl_Radio_Button (80, y + 50, 12, 12, "Create MPG using ffmpeg");
264 	Automate->Ffmpeg->type (102);
265 	Automate->Ffmpeg->selection_color ((Fl_Color) 1);
266 	Automate->Ffmpeg->align (FL_ALIGN_RIGHT);
267 	Automate->FfmpegG = new Fl_Radio_Button (80, y + 70, 12, 12, "Create animated GIF using ffmpeg");
268 	Automate->FfmpegG->type (102);
269 	Automate->FfmpegG->selection_color ((Fl_Color) 1);
270 	Automate->FfmpegG->align (FL_ALIGN_RIGHT);
271 	qq->end ();
272     y += 100;
273     Automate->keeptemps = new Fl_Check_Button(70, y, 70, 25, "Keep intermediate POV and image files");
274     y += 50;
275     Automate->width = new Fl_Input(70, y, 70, 25, "Image width");
276     Automate->width->align (FL_ALIGN_TOP);
277     Automate->height = new Fl_Input(170, y, 70, 25, "Image height");
278     Automate->height->align (FL_ALIGN_TOP);
279     Automate->fps = new Fl_Input(270, y, 70, 25, "Frames/sec");
280     Automate->fps->align (FL_ALIGN_TOP);
281     y += 50;
282     Automate->Go = new Fl_Button(270, y, 70, 25, "Go");
283     Automate->Go->callback((Fl_Callback *) Automation_Go_cb);
284     Automate->Abort = new Fl_Button(170, y, 70, 25, "Abort");
285     Automate->Abort->callback((Fl_Callback *) Automation_Abort_cb);
286     Automate->Close = new Fl_Button(70, y, 70, 25, "Close");
287     Automate->Close->callback((Fl_Callback *) Automation_Close_cb);
288     Automate->Automation_Edit_Window->show();
289 }
290 
Automation_Go_cb(void)291 void Automation_Go_cb(void)
292 {
293 // callback routine to start automation loop
294     char POV_filename[200];
295     char incpath[256];
296     char cmdbase[512],cmd[512];
297     char string[200];
298     char string2[200];
299     char format[20];
300     int nstep, no_steps;
301     int width,height,fps;
302     int keep;
303     int result;
304     int dopov;
305     int doasy;
306     int dowrl;
307     int num;
308     FILE *filetmp;
309     float start, end, step;
310 
311     doasy = doAsy;
312     dopov = doPOV;
313     dowrl = doVrml;
314     doAsy = 0;
315     doPOV = 1;
316     doVrml = 0;
317     strcpy(POV_filename, Automate->POV_Filename->value ());
318     strcpy(string, POV_filename);
319     strcat(string, ".pov");
320     filetmp = fopen(string, "w");
321     if (!filetmp) {
322 	Error_Box("Unable to write POV files in specified directory");
323 	return;
324     }
325     fclose(filetmp);
326     unlink(string);	/* remove the temporary file */
327     Progress_Window(-1, "Automation Progress", 100.0f);
328     drvui->automation = 1;
329     start = (float) atof (Automate->t_start->value());
330     end = (float) atof (Automate->t_end->value());
331     step = (float) atof (Automate->t_step->value());
332     width = atoi (Automate->width->value());
333     height = atoi (Automate->height->value());
334     fps = atoi (Automate->fps->value());
335     if (fps == 0) fps = 30;
336     keep = Automate->keeptemps->value();
337     no_steps = (int)(((end - start) / step) + 0.5f) + 1;
338     num = (int)log10((double)no_steps)+1;
339     incpath[0] = '\0';
340     if (strlen (drvui->POV_Include) > 10)
341         strcpy (incpath, drvui->POV_Include);   // make copy of colors.inc full path name
342 #ifdef WIN32
343     strcpy (cmdbase, "\"\"");       // build the command string
344     strcat (cmdbase, drvui->POV_Path);      //   for Windows
345     strcat (cmdbase, "\"");
346     strcat (cmdbase, " ");
347     strcat (cmdbase, drvui->POV_Options);
348     strcat (cmdbase, " ");
349     strcat (cmdbase, " +I\"");
350 #else
351     strcpy (cmdbase, drvui->POV_Path);      // build command string
352     strcat (cmdbase, " ");          //    for Linux
353     strcat (cmdbase, drvui->POV_Options);
354     sprintf (string2," -V -GA -GD -GF -GR -GS -GW -D -P +W%d +H%d",width,height);
355     strcat (cmdbase,string2);
356     if (Automate->Mencoder->value() )
357 	strcat(cmdbase," +FT");
358     else
359 	strcat(cmdbase," +FN");
360     strcat (cmdbase, " ");
361     if (strlen (drvui->POV_Include) > 10) {
362         strcat (cmdbase, " +HI");
363         strcat (cmdbase, drvui->POV_Include);
364         strcat (cmdbase, " ");
365     }
366 #endif
367 
368     for (nstep = 1; nstep < no_steps; nstep++) {
369 	float progress;
370 	drvui->phaseshift[0] = start + (float)nstep * step;
371 	strcpy(string, POV_filename);
372         sprintf(format,"%%.%dd.pov",num);
373 	sprintf(string2, (const char*)format, nstep);
374 	strcat(string, string2);
375 	if (Automate->Mencoder->value() )
376 	    sprintf(format," +O%%s%%.%dd.tga",num);
377 	else
378 	    sprintf(format," +O%%s%%.%dd.png",num);
379 	sprintf(string2,format,POV_filename,nstep);
380 	drvui->automate_name = string;
381 	progress = 100.0f * (float)nstep / (float)no_steps;
382 	Progress_Window(0, NULL, progress);
383 	Fl::redraw();
384 	Update_Str(0);
385 	Generate_Drawing(0);
386 	Fl::redraw();
387 	strcpy(cmd,cmdbase);
388 	strcat(cmd,string);
389 	strcat(cmd,string2);
390 	result=system(cmd);
391         if (result != 0) drvui->automation=0;
392 	if (!keep) unlink(string);
393 	if (!drvui->automation)
394 	    break;
395     }
396     Progress_Window(-2, NULL, 0.0f);
397     if (drvui->automation && !Automate->NoMovie->value()) { // if movie selected and run not already aborted
398 #ifdef WIN32
399     strcpy (cmdbase, "\"\"");       // build the command string
400     if (Automate->Mencoder->value() ) {
401 	sprintf(cmd,"%s mf://%s*.tga -mf w=%d:h=%d:fps=%d:type=tga -ovc lavc -lavcopts vcodec=mpeg4 -o %s.mpg", drvui->Mencoder_Path, POV_filename,width,height,fps,POV_filename);
402 //	sprintf(cmd,"mencoder mf://%s*.tga -mf w=%d:h=%d:fps=%d:type=tga -force-avi-aspect 1.0 -ovc copy -oac copy -o %s.mpg",POV_filename,width,height,fps,POV_filename);
403     } else if (Automate->Ffmpeg->value() ) {
404 	sprintf(cmd,"%s -r %d -f image2 -i %s%%%dd.png -s %dx%d %s.mpg", drvui->FFmpeg_Path, fps, POV_filename, num, width,height,POV_filename);
405     } else {
406 	sprintf(cmd,"%s -f image2 -pix_fmt rgb24 -r 1 -i %s%%%dd.png -s %dx%d -f gif %s.gif", drvui->FFmpeg_Path, POV_filename, num, width,height,POV_filename);
407     }
408     strcat (cmdbase,cmd);
409     strcat (cmdbase, "\"\"");
410     result = system(cmdbase);
411 #else
412     if (Automate->Mencoder->value() ) {
413 	sprintf(cmd,"%s mf://%s*.tga -mf w=%d:h=%d:fps=%d:type=tga -ovc lavc -lavcopts vcodec=mpeg4 -o %s.mpg", drvui->Mencoder_Path, POV_filename,width,height,fps,POV_filename);
414 //	sprintf(cmd,"mencoder mf://%s*.tga -mf w=%d:h=%d:fps=%d:type=tga -force-avi-aspect 1.0 -ovc copy -oac copy -o %s.mpg",POV_filename,width,height,fps,POV_filename);
415     } else if (Automate->Ffmpeg->value() ) {
416 	sprintf(cmd,"%s -r %d -f image2 -i %s%%%dd.png -s %dx%d %s.mpg", drvui->FFmpeg_Path, fps, POV_filename, num, width,height,POV_filename);
417     } else {
418 	sprintf(cmd,"%s -f image2 -pix_fmt rgb24 -r 1 -i %s%%%dd.png -s %dx%d -f gif %s.gif", drvui->FFmpeg_Path, POV_filename, num, width,height,POV_filename);
419     }
420     result = system(cmd);
421 #endif
422     if (result != 0) Error_Box("Video encoding failed");
423     }
424     if (!keep) {
425 	if (Automate->Mencoder->value() )
426 	    sprintf(format,"%%.%dd.tga",num);
427 	else
428 	    sprintf(format,"%%.%dd.png",num);
429 	for (nstep = 1; nstep < no_steps; nstep++) {
430 	    strcpy(string, POV_filename);
431 	    sprintf(string2, format, nstep);
432 	    strcat(string, string2);
433             unlink(string);
434 	}
435     }
436     drvui->automation = 0;
437     doAsy = doasy;
438     doPOV = dopov;
439     doVrml = dowrl;
440     Automate->Automation_Edit_Window->hide();
441 }
442 
Automation_Close_cb(void)443 void Automation_Close_cb(void)
444 {
445     Automate->Automation_Edit_Window->hide();
446 }
447 
448 void
Bond_Combo_cb(Fl_Widget *,void *)449 Bond_Combo_cb (Fl_Widget *, void *)
450 {
451 // update bond distance table when the atom in the combo box is changed
452     const char *atom;
453 
454     if (!drvui->table)
455 	drvui->table = (char *) zalloc (20480 * sizeof (char));
456     atom = Bonds->Bond_Combo->value ();	// get name from combo box
457     Bonds->New_Bond_From->value (atom);	// put it in the 'From' location
458     Load_Bond_Data (atom, drvui->table);
459     Bonds->Bond_Output_Buffer->text (drvui->table);
460 }
461 
462 void
Bond_Frame_Combo_cb(Fl_Widget *,void *)463 Bond_Frame_Combo_cb (Fl_Widget *, void *)
464 {
465 // routine called when the frame number is changed on the Bonds Edit Screen
466     int i, j;
467 
468     char type[5];
469 
470     char atom1[5];
471 
472     char atom2[5];
473 
474     char widget[16382];
475 
476     char atoms[100][5];
477 
478     char color[40];
479 
480     float rad, d1, d2;
481 
482     char string[100];
483 
484     int Frame_No = 1;
485 
486     if (drvui->max_frame > 1)
487 	Frame_No = atoi (Bonds->Frame_No->value ());
488     int nlist = Get_Unique_Atoms (atoms, Frame_No);	// get unique atom names in sorted list
489 
490     Bonds->Bond_Combo->list.clear ();	// clear out the old names
491     for (j = 0; j < nlist; j++) {	// add atom names in alphabetic order
492 	Bonds->Bond_Combo->list.add (atoms[j]);
493     }
494     Bonds->Bond_Combo->value (atoms[0]);	// load first one in window
495     Bond_Combo_cb (NULL, NULL);
496     widget[0] = '\0';
497     for (i = 1; i < drvui->nbond; i++) {
498 	if (drvui->bonds[i].bond_fn != Frame_No)
499 	    continue;		//skip if not for this frame
500 	strncpy (atom1, drvui->bonds[i].bond_l1, 4);
501 	strncpy (atom2, drvui->bonds[i].bond_l2, 4);
502 	atom1[4] = 0;
503 	atom2[4] = 0;
504 	for (j = 3; j >= 0; --j) {
505 	    if (atom1[j] == ' ')
506 		atom1[j] = 0;
507 	}
508 	for (j = 3; j >= 0; --j) {
509 	    if (atom2[j] == ' ')
510 		atom2[j] = 0;
511 	}
512 	rad = drvui->bonds[i].bond_size;
513 	d1 = drvui->bonds[i].bond_min;
514 	d2 = drvui->bonds[i].bond_max;
515 	strncpy (color, drvui->bonds[i].col_bond, 25);
516 	if (color[strlen (color) - 1] < ' ')
517 	    color[strlen (color) - 1] = 0;
518 	if (strlen (color) > 25)
519 	    color[25] = 0;
520 	if (drvui->bonds[i].bond_style == 0) {
521 	    strcpy (type, "bond");
522 	    sprintf (string, "%4s     %4s   %4s  %9.3f %9.3f %9.3f     %s\n", type, atom1, atom2,
523 		 rad, d1, d2, color);
524 	} else {
525 	    strcpy (type, "dash");
526 	    sprintf (string, "%4s %3d %4s   %4s  %9.3f %9.3f %9.3f     %s\n", type,
527 		drvui->bonds[i].bond_style, atom1, atom2, rad, d1, d2, color);
528 	}
529 	strcat (widget, string);
530 	Bonds->BondInstr1->show ();
531     }
532     Bonds->BondBuffer->text (widget);
533 }
534 
535 void
Browse_Map_File_cb(void)536 Browse_Map_File_cb (void)
537 {
538 // callback routine to select a map file
539 #if defined(WIN32)
540     const char *newfile =
541 	flu_file_chooser ("Select Map File", "*.*", Maps->Filename->value ());
542 #else
543     char *newfile =
544 	fl_file_chooser ("Select Map File", "*.*", Maps->Filename->value (), 1);
545 #endif
546     if (newfile) {
547 	Maps->Filename->value (newfile);
548 	ReadFourMap = 0;
549 	Map_Info.info_valid = 0;
550     }
551 }
552 
553 void
Check_Box_cb(void)554 Check_Box_cb (void)
555 {
556 // callback routine entered when a main-screen checkbox is changed
557     if (drvui->Generate_VRML1->value () != 0) {
558 	if (Vrml2)
559 	    drvui->Str_File_Changed = 1;
560 	Vrml2 = 0;
561     } else {
562 	if (!Vrml2)
563 	    drvui->Str_File_Changed = 1;
564 	Vrml2 = 1;
565     }
566     if (drvui->Orthographic_View->value () != 0) {
567 	if (M_cameras)
568 	    drvui->Str_File_Changed = 1;
569 	M_cameras = 0;
570 	gl_size = max (POV_Max[1] - POV_Min[1], POV_Max[0] - POV_Min[0]);
571     } else {
572 	if (!M_cameras)
573 	    drvui->Str_File_Changed = 1;
574 	M_cameras = 1;
575     }
576     if (drvui->Show_Vector_Triple->value () != 0) {
577 	if (!Display_axes)
578 	    drvui->Str_File_Changed = 1;
579 	Display_axes = 1;
580 	label_cell ();
581     } else {
582 	if (Display_axes)
583 	    drvui->Str_File_Changed = 1;
584 	Display_axes = 0;
585 	label_cell ();
586     }
587     Update_Str (0);		// update the 'str' file
588     Generate_Drawing (0);	// regenerate the drawing
589     Fl::redraw ();		// update the screen
590 }
591 
592 void
Configure_cb(void)593 Configure_cb (void)
594 {
595 // callback routine to display configuration screen
596     int y;
597 
598     char string[30];
599 
600     if (Configure) {
601 	Configure->ConfigWindow->show ();
602 	return;
603     }
604     Configure = new ConfigParm;	// get new instance of config parms
605     Configure->ConfigWindow =
606 	new Fl_Window (50, 50, 640, 600, "POV Configuration Window");
607     Configure->ConfigWindow->callback ((Fl_Callback *) Configure_Close_cb);
608     y = 30;
609     Configure->POVOptions = new Fl_Input (170, y, 300, 40, "POV Options");
610     Configure->POVOptions->textcolor (1);
611     Configure->POVOptions->value (drvui->POV_Options);
612     Configure->POVOptions->
613 	tooltip
614 	("+Wnum and +Hnum for size, +D for preview, +P for pause at end, +A for antialiased lines, +F for filetype (FC=TGA,FN=PNG), +L for POV library path");
615     y += 60;
616     Configure->POVPath = new Fl_Input (170, y, 300, 40, "POV program");
617     Configure->POVPath->textcolor (1);
618     Configure->POVPath->value (drvui->POV_Path);
619     Configure->POVPath->
620 	tooltip ("Enter the name and full path of the pov-ray executable here");
621     Fl_Button *a = new Fl_Button (475, y + 5, 70, 25, "Browse");
622 
623     a->callback ((Fl_Callback *) ConfigurePOV_cb);
624     y += 60;
625     Configure->POVIncludePath = new Fl_Input (170, y, 300, 40, "POV Color File");
626     Configure->POVIncludePath->textcolor (1);
627     Configure->POVIncludePath->value (drvui->POV_Include);
628     Fl_Button *b = new Fl_Button (475, y + 5, 70, 25, "Browse");
629 
630     b->callback ((Fl_Callback *) ConfigurePOVOptions_cb);
631     y += 60;
632     Configure->POVDefaultFinish = new Fl_Input (170, y, 300, 40, "POV Object Finish");
633     Configure->POVDefaultFinish->textcolor (1);
634     Configure->POVDefaultFinish->value (drvui->DefaultFinish);
635     y += 60;
636     Configure->Stereo_Base = new Fl_Input (170, y, 300, 40, "Stereo Base Separation");
637     sprintf (string, "%.3f", drvui->stereo_base);
638     Configure->Stereo_Base->value (string);
639     Configure->Stereo_Base->textcolor (1);
640     y += 60;
641     Configure->Stereo =
642 	new Fl_Check_Button (150, y, 325, 25,
643 			     "Generate stereo POV pair - StereoPOV needed");
644     if (drvui->Stereo == 1)
645 	Configure->Stereo->set ();
646     y += 30;
647     Configure->StereoMesh =
648 	new Fl_Check_Button (150, y, 325, 25,
649 			     "Generate stereo POV pair - POV 3.7 or newer needed");
650     if (drvui->Stereo == 2)
651 	Configure->StereoMesh->set ();
652     y += 30;
653     Configure->CrossEyed =
654 	new Fl_Check_Button (150, y, 175, 25, "Use \"cross-eyed\" view");
655     if (drvui->cross_eyed)
656 	Configure->CrossEyed->set ();
657 
658     y += 40;
659 
660     Configure->MencoderPath = new Fl_Input (170, y, 300, 40, "Mencoder program");
661     Configure->MencoderPath->textcolor (1);
662     Configure->MencoderPath->value (drvui->Mencoder_Path);
663     Configure->MencoderPath->
664 	tooltip ("Enter the name and full path of the mencoder program for video encoding");
665     Fl_Button *c = new Fl_Button (475, y + 5, 70, 25, "Browse");
666 
667     c->callback ((Fl_Callback *) ConfigureMencoder_cb);
668 
669     y += 60;
670     Configure->FFmpegPath = new Fl_Input (170, y, 300, 40, "FFmpeg program");
671     Configure->FFmpegPath->textcolor (1);
672     Configure->FFmpegPath->value (drvui->FFmpeg_Path);
673     Configure->FFmpegPath->
674 	tooltip ("Enter the name and full path of the ffmpeg program for video encoding");
675     Fl_Button *d = new Fl_Button (475, y + 5, 70, 25, "Browse");
676 
677     d->callback ((Fl_Callback *) ConfigureFFmpeg_cb);
678 
679     y += 60;
680     Fl_Button *o = new Fl_Button (330, y, 90, 30, "Save");
681 
682     o->callback ((Fl_Callback *) Configure_Save_cb);
683     o->tooltip ("Apply current contents of top box to drawing, then close this window.");
684     Fl_Button *p = new Fl_Button (220, y, 90, 30, "Cancel");
685 
686     p->tooltip ("Close this window and discard all changes.");
687     p->callback ((Fl_Callback *) Configure_Close_cb);
688 #if !defined (WIN32) && !defined (__APPLE__)
689     Configure->ConfigWindow->icon ((char *) drvui->icon);
690 #endif
691     Configure->ConfigWindow->end ();
692     Configure->ConfigWindow->show ();
693 }
694 
695 void
Configure_Close_cb(void)696 Configure_Close_cb (void)
697 {
698     Configure->ConfigWindow->hide ();
699 }
700 
701 void
Configure_Save_cb(void)702 Configure_Save_cb (void)
703 {
704 // callback routine to save configuration file
705 
706     char string[100];
707 
708     strcpy (drvui->POV_Options, Configure->POVOptions->value ());
709     strcpy (drvui->POV_Path, Configure->POVPath->value ());
710     strcpy (drvui->POV_Include, Configure->POVIncludePath->value ());
711     strcpy (drvui->DefaultFinish, Configure->POVDefaultFinish->value ());
712     if (Configure->Stereo->value ())
713 	drvui->Stereo = 1;
714     else if (Configure->StereoMesh->value ())
715 	drvui->Stereo = 2;
716     else
717 	drvui->Stereo = 0;
718     if (Configure->CrossEyed->value ())
719 	drvui->cross_eyed = 1;
720     else
721 	drvui->cross_eyed = 0;
722     strcpy (string, Configure->Stereo_Base->value ());
723     sscanf (string, "%f", &drvui->stereo_base);
724     strcpy (drvui->Mencoder_Path, Configure->MencoderPath->value ());
725     strcpy (drvui->FFmpeg_Path, Configure->FFmpegPath->value ());
726     WriteConfig ();
727     Configure->ConfigWindow->hide ();
728 }
729 
730 void
Configure_Misc_cb(void)731 Configure_Misc_cb (void)
732 {
733 // callback routine to display configuration screen for miscellaneous parameters
734     int y;
735 
736     if (MiscConfigure) {
737 	MiscConfigure->MiscConfigWindow->show ();
738 	return;
739     }
740     MiscConfigure = new ConfigMiscParm;	// get new instance of misc. config parms
741     MiscConfigure->MiscConfigWindow =
742 	new Fl_Window (50, 50, 400, 250, "Misc. Configuration Window");
743     MiscConfigure->MiscConfigWindow->callback ((Fl_Callback *) Configure_Misc_Close_cb);
744     y = 30;
745     MiscConfigure->LoadLast =
746 	new Fl_Check_Button (40, y, 275, 25, "Load most recently used file on startup");
747     if (strncmp (drvui->LoadOnStartup, "yes", 3) == 0)
748 	MiscConfigure->LoadLast->set ();
749     y += 30;
750     MiscConfigure->AutoLabel =
751 	new Fl_Check_Button (40, y, 275, 25, "Label atoms when importing from SHELX");
752     if (drvui->autolabel)
753 	MiscConfigure->AutoLabel->set ();
754     y += 30;
755     MiscConfigure->doVrml =
756 	new Fl_Check_Button (40, y, 275, 25, "Generate VRML file while rendering");
757     if (doVrml)
758 	MiscConfigure->doVrml->set ();
759     y += 30;
760     MiscConfigure->doPOV =
761 	new Fl_Check_Button (40, y, 275, 25, "Generate POV input file while rendering");
762     if (doPOV)
763 	MiscConfigure->doPOV->set ();
764     y += 30;
765     MiscConfigure->doAsy =
766 	new Fl_Check_Button (40, y, 275, 25, "Generate Asymptote input file while rendering");
767     if (doAsy)
768 	MiscConfigure->doAsy->set ();
769     y += 60;
770     Fl_Button *n = new Fl_Button (100, y, 90, 30, "Cancel");
771 
772     n->tooltip ("Close this window and discard all changes.");
773     n->callback ((Fl_Callback *) Configure_Misc_Close_cb);
774     Fl_Button *o = new Fl_Button (210, y, 90, 30, "Save");
775 
776     o->callback ((Fl_Callback *) Configure_Misc_Save_cb);
777     o->tooltip ("Apply current contents of top box to drawing, then close this window.");
778 #if !defined (WIN32) && !defined (__APPLE__)
779     MiscConfigure->MiscConfigWindow->icon ((char *) drvui->icon);
780 #endif
781     MiscConfigure->MiscConfigWindow->end ();
782     MiscConfigure->MiscConfigWindow->show ();
783 }
784 
785 void
Configure_Misc_Close_cb(void)786 Configure_Misc_Close_cb (void)
787 {
788     MiscConfigure->MiscConfigWindow->hide ();
789 }
790 
791 void
Configure_Misc_Save_cb(void)792 Configure_Misc_Save_cb (void)
793 {
794     if (MiscConfigure->LoadLast->value ())
795 	strcpy (drvui->LoadOnStartup, "yes");
796     else
797 	strcpy (drvui->LoadOnStartup, "no");
798     if (MiscConfigure->AutoLabel->value ())
799 	drvui->autolabel = 1;
800     else
801 	drvui->autolabel = 0;
802     if (MiscConfigure->doVrml->value ()) {
803 	doVrml = 1;
804 	drvui->Generate_VRML1->activate ();
805     } else {
806 	doVrml = 0;
807 	drvui->Generate_VRML1->deactivate ();
808     }
809     if (MiscConfigure->doPOV->value ()) {
810 	doPOV = 1;
811 	DRAWxtlViewUI::drawxtl_menu[39].activate ();
812     } else {
813 	doPOV = 0;
814 	DRAWxtlViewUI::drawxtl_menu[39].deactivate ();
815     }
816     if (MiscConfigure->doAsy->value ()) {
817 	doAsy = 1;
818     } else {
819 	doAsy = 0;
820     }
821     WriteConfig ();
822     MiscConfigure->MiscConfigWindow->hide ();
823     Generate_Drawing (0);
824 }
825 
826 void
Configure_MSMS_cb(void)827 Configure_MSMS_cb (void)
828 {
829     if (MSMSConfigure) {
830 	MSMSConfigure->MSMSConfigWindow->show ();
831 	return;
832     }
833     MSMSConfigure = new ConfigMSMSParm;	// get new instance
834     MSMSConfigure->MSMSConfigWindow =
835 	new Fl_Window (50, 50, 640, 140, "MSMS Configuration Window");
836     MSMSConfigure->MSMSConfigWindow->callback ((Fl_Callback *) Configure_Close_MSMS_cb);
837     MSMSConfigure->MSMSPath = new Fl_Input (170, 30, 300, 40, "MSMS program");
838     MSMSConfigure->MSMSPath->textcolor (1);
839     MSMSConfigure->MSMSPath->value (drvui->MSMS_Path);
840     MSMSConfigure->MSMSPath->
841 	tooltip ("Enter the name and full path of the msms executable here");
842     Fl_Button *a = new Fl_Button (475, 35, 70, 25, "Browse");
843 
844     a->callback ((Fl_Callback *) Configure_MSMS_loc_cb);
845     Fl_Button *o = new Fl_Button (330, 80, 90, 30, "Save");
846 
847     o->callback ((Fl_Callback *) Configure_Save_MSMS_cb);
848     o->tooltip ("Apply current contents of top box to drawing, then close this window.");
849     Fl_Button *p = new Fl_Button (220, 80, 90, 30, "Cancel");
850 
851     p->tooltip ("Close this window and discard all changes.");
852     p->callback ((Fl_Callback *) Configure_Close_MSMS_cb);
853 #if !defined (WIN32) && !defined (__APPLE__)
854     MSMSConfigure->MSMSConfigWindow->icon ((char *) drvui->icon);
855 #endif
856     MSMSConfigure->MSMSConfigWindow->end ();
857     MSMSConfigure->MSMSConfigWindow->show ();
858 }
859 
860 void
Configure_MSMS_loc_cb(void)861 Configure_MSMS_loc_cb (void)
862 {
863 // routine to configure MSMS exec path
864 #ifdef WIN32
865     const char *newfile =
866 	flu_file_chooser ("Select MSMS exe file", "*.exe", drvui->MSMS_Path);
867 #else
868     char *newfile = fl_file_chooser ("Select MSMS program", "*", drvui->MSMS_Path);
869 #endif
870     if (newfile) {
871 	strcpy (drvui->MSMS_Path, newfile);
872 	MSMSConfigure->MSMSPath->value (drvui->MSMS_Path);
873     }
874 }
875 
876 void
ConfigurePOV_cb(void)877 ConfigurePOV_cb (void)
878 {
879 // routine to configure POV exec path
880 #ifdef WIN32
881     const char *newfile =
882 	flu_file_chooser ("Select POVRAY exe file", "*.exe", drvui->POV_Path);
883 #else
884     char *newfile = fl_file_chooser ("Select POVRAY program", "*", drvui->POV_Path);
885 #endif
886     if (newfile) {
887 	strcpy (drvui->POV_Path, newfile);
888 	Configure->POVPath->value (drvui->POV_Path);
889     }
890 }
891 
892 void
ConfigurePOVOptions_cb(void)893 ConfigurePOVOptions_cb (void)
894 {
895 // routine to configure POV include path
896 #ifdef WIN32
897     const char *newfile =
898 	flu_file_chooser ("Select Path for POV colors.inc", "*.inc", drvui->POV_Include);
899 #else
900     char *newfile =
901 	fl_file_chooser ("Select Path for POV 'colors.inc'", "*.inc", drvui->POV_Include);
902 #endif
903     if (newfile) {
904 	strcpy (drvui->POV_Include, newfile);
905 	Configure->POVIncludePath->value (drvui->POV_Include);
906     }
907 }
908 
909 void
ConfigureMencoder_cb(void)910 ConfigureMencoder_cb (void)
911 {
912 // routine to configure mencoder exec path
913 #ifdef WIN32
914     const char *newfile =
915 	flu_file_chooser ("Select mencoder exe file", "*.exe", drvui->Mencoder_Path);
916 #else
917     char *newfile = fl_file_chooser ("Select mencoder program", "*", drvui->Mencoder_Path);
918 #endif
919     if (newfile) {
920 	strcpy (drvui->Mencoder_Path, newfile);
921 	Configure->MencoderPath->value (drvui->Mencoder_Path);
922     }
923 }
924 
925 void
ConfigureFFmpeg_cb(void)926 ConfigureFFmpeg_cb (void)
927 {
928 // routine to configure FFmpeg exec path
929 #ifdef WIN32
930     const char *newfile =
931 	flu_file_chooser ("Select FFmpeg exe file", "*.exe", drvui->FFmpeg_Path);
932 #else
933     char *newfile = fl_file_chooser ("Select FFmpeg program", "*", drvui->FFmpeg_Path);
934 #endif
935     if (newfile) {
936 	strcpy (drvui->FFmpeg_Path, newfile);
937 	Configure->FFmpegPath->value (drvui->FFmpeg_Path);
938     }
939 }
940 
941 void
Configure_Close_MSMS_cb(void)942 Configure_Close_MSMS_cb (void)
943 {
944     MSMSConfigure->MSMSConfigWindow->hide ();
945 }
946 
947 void
Configure_Save_MSMS_cb(void)948 Configure_Save_MSMS_cb (void)
949 {
950 // callback routine to save configuration file
951     strcpy (drvui->MSMS_Path, MSMSConfigure->MSMSPath->value ());
952     WriteConfig ();
953     MSMSConfigure->MSMSConfigWindow->hide ();
954 }
955 
956 void
Edit_Arrow_cb(void)957 Edit_Arrow_cb (void)
958 {
959     char widget[16382];
960     int y = 25;
961     static int one = 1;
962     int yy;
963 
964     if (!strlen (drvui->CurFile->value ())) {	// Make sure rendering enabled
965 	Error_Box ("A Structure File must be selected first.");
966 	return;
967     }
968     Save_Working_Copy ();
969     if (!arrows) {
970 	arrows = new ArrowParam;
971 
972 	{
973 	    Fl_Window *o = arrows->ArrowWindow =
974 		new Fl_Window (0, 0, 490, 500, "Edit Arrow Parameters");
975 	    o->callback ((Fl_Callback *) Edit_Arrow_Close_cb);
976 #if !defined (WIN32) && !defined (__APPLE__)
977 	    o->icon ((char *) drvui->icon);
978 #endif
979 	    {
980 		Fl_Text_Display *o = new Fl_Text_Display (250, y, 0, 0,
981 							  "  Position                   Components            Length   Diam.  Color");
982 
983 		o->labelfont (1);
984 	    }
985 	    {
986 		Fl_Text_Editor *o = new Fl_Text_Editor (20, y, 450, 80);
987 
988 		o->labelfont (1);
989 		arrows->ArrowBuffer = new Fl_Text_Buffer;
990 		strcpy (widget, "");
991 		o->buffer (arrows->ArrowBuffer);
992 	    }
993 	    arrows->ArrowBuffer->add_modify_callback ((Fl_Text_Modify_Cb) Modify_Arrow_cb,
994 						      (void *) NULL);
995 	    arrows->ArrowInstr =
996 		new Fl_Output (20, y + 90, 450, 0,
997 			       "Press 'Add' to replace "
998 			       "selected line - 'Remove' to delete it");
999 	    arrows->ArrowInstr->hide ();
1000 	    arrows->ArrowInstr->align (FL_ALIGN_BOTTOM);
1001 	    arrows->ArrowInstr1 =
1002 		new Fl_Output (20, y + 90, 450, 0,
1003 			       "Highlight text above " "or double click to edit line");
1004 	    arrows->ArrowInstr1->hide ();
1005 	    arrows->ArrowInstr1->align (FL_ALIGN_BOTTOM);
1006 	    y += 130;
1007 	    {
1008 		Fl_Text_Display *o = new Fl_Text_Display (244, y, 0, 0, "Position");
1009 
1010 		o->labelfont (1);
1011 	    }
1012 	    y += 10;
1013 	    {
1014 		Fl_Input *o = arrows->Px = new Fl_Input (110, y, 70, 25, "x");
1015 
1016 		o->labelfont (1);
1017 		o->align (FL_ALIGN_TOP);
1018 		o->callback ((Fl_Callback *) New_Arrow_Input_cb);
1019 	    }
1020 	    {
1021 		Fl_Input *o = arrows->Py = new Fl_Input (210, y, 70, 25, "y");
1022 
1023 		o->labelfont (1);
1024 		o->align (FL_ALIGN_TOP);
1025 		o->callback ((Fl_Callback *) New_Arrow_Input_cb);
1026 	    }
1027 	    {
1028 		Fl_Input *o = arrows->Pz = new Fl_Input (310, y, 70, 25, "z");
1029 
1030 		o->labelfont (1);
1031 		o->align (FL_ALIGN_TOP);
1032 		o->callback ((Fl_Callback *) New_Arrow_Input_cb);
1033 	    }
1034 	    if (drvui->max_frame > 1) {
1035 		int i;
1036 
1037 		char string[128];
1038 
1039 		Flu_Combo_List *o = arrows->Frame_No =
1040 		    new Flu_Combo_List (400, y, 75, 25, "Frame No.");
1041 		o->align (FL_ALIGN_TOP);
1042 		o->callback (Arrow_Frame_Combo_cb);
1043 		o->labelfont (1);
1044 		for (i = 1; i <= drvui->max_frame; i++) {
1045 		    sprintf (string, "%d", i);
1046 		    o->list.add (string);
1047 		}
1048 		o->pop_height (20 * drvui->max_frame);
1049 		o->value ("1");
1050 	    }
1051 	    y += 50;
1052 	    {
1053 		Fl_Text_Display *o = new Fl_Text_Display (250, y, 0, 0, "Components");
1054 
1055 		o->labelfont (1);
1056 	    }
1057 	    y += 10;
1058 	    {
1059 		Fl_Input *o = arrows->Cx = new Fl_Input (110, y, 70, 25, "x");
1060 
1061 		o->labelfont (1);
1062 		o->align (FL_ALIGN_TOP);
1063 		o->callback ((Fl_Callback *) New_Arrow_Input_cb);
1064 	    }
1065 	    {
1066 		Fl_Input *o = arrows->Cy = new Fl_Input (210, y, 70, 25, "y");
1067 
1068 		o->labelfont (1);
1069 		o->align (FL_ALIGN_TOP);
1070 		o->callback ((Fl_Callback *) New_Arrow_Input_cb);
1071 	    }
1072 	    {
1073 		Fl_Input *o = arrows->Cz = new Fl_Input (310, y, 70, 25, "z");
1074 
1075 		o->labelfont (1);
1076 		o->align (FL_ALIGN_TOP);
1077 		o->callback ((Fl_Callback *) New_Arrow_Input_cb);
1078 	    }
1079 	    y += 45;
1080 	    {
1081 		Fl_Text_Display *o =
1082 		    new Fl_Text_Display (75, y, 344, 0, "Arrow Size and Color");
1083 		o->labelfont (1);
1084 	    }
1085 	    y += 15;
1086 	    {
1087 		Fl_Input *o = arrows->Length = new Fl_Input (90, y, 70, 25, "Length");
1088 
1089 		o->labelfont (1);
1090 		o->align (FL_ALIGN_TOP);
1091 		o->callback ((Fl_Callback *) New_Arrow_Input_cb);
1092 	    }
1093 	    {
1094 		Fl_Input *o = arrows->Diameter =
1095 		    new Fl_Input (170, y, 70, 25, "Diameter");
1096 		o->labelfont (1);
1097 		o->align (FL_ALIGN_TOP);
1098 		o->callback ((Fl_Callback *) New_Arrow_Input_cb);
1099 	    }
1100 	    {
1101 		Flu_Combo_List *o = arrows->Color =
1102 		    new Flu_Combo_List (250, y, 150, 25, "Color");
1103 		o->labelfont (1);
1104 		Load_Color_Combo (o);
1105 		o->align (FL_ALIGN_TOP);
1106 		o->callback ((Fl_Callback *) New_Arrow_Input_cb);
1107 	    }
1108 	    y += 30;
1109 	    {
1110 		Fl_Button *o = arrows->AddButton = new Fl_Button (165, y, 70, 25, "Add");
1111 
1112 		o->down_box (FL_DOWN_BOX);
1113 		o->labelfont (1);
1114 		o->tooltip
1115 		    ("When active, press to transfer data in boxes to window above");
1116 		o->deactivate ();
1117 		o->callback ((Fl_Callback *) New_Arrow_Add_cb, &one);
1118 	    }
1119 	    {
1120 		Fl_Button *o = arrows->RemoveButton =
1121 		    new Fl_Button (250, y, 70, 25, "Remove");
1122 		o->down_box (FL_DOWN_BOX);
1123 		o->labelfont (1);
1124 		o->tooltip ("When active, press to remove highlighted line.");
1125 		o->deactivate ();
1126 		o->callback ((Fl_Callback *) New_Arrow_Add_cb, &zero);
1127 	    }
1128 	    y += 30;
1129 	    arrows->ArrowInstr2 = new Fl_Output (25, y, 440, 0,
1130 						 "Changes are temporary until \"Apply\" or \"Save\" is pressed.");
1131 	    arrows->ArrowInstr2->hide ();
1132 	    arrows->ArrowInstr2->align (FL_ALIGN_BOTTOM);
1133 	    y += 20;
1134 	    {
1135 		Fl_Text_Display *o = new Fl_Text_Display (248, y, 0, 0,
1136 							  "Matrix Between Magnetic and Nuclear Cells");
1137 
1138 		o->labelfont (1);
1139 	    }
1140 	    y += 15;
1141 	    {
1142 		Fl_Text_Display *o = new Fl_Text_Display (250, y, 0, 0, "Nuclear ");
1143 
1144 		o->labelfont (1);
1145 	    }
1146 	    y += 15;
1147 	    {
1148 		Fl_Text_Display *o = new Fl_Text_Display (95, y + 20, 0, 0, "Ma");
1149 
1150 		o->labelfont (1);
1151 	    }
1152 	    {
1153 		Fl_Input *o = arrows->Aa = new Fl_Input (110, y, 70, 20, "Na");
1154 
1155 		o->tooltip ("a(nuclear) component of a(magnetic)");
1156 		o->labelfont (1);
1157 		o->align (FL_ALIGN_TOP);
1158 	    }
1159 	    {
1160 		Fl_Input *o = arrows->Ab = new Fl_Input (210, y, 70, 20, "Nb");
1161 
1162 		o->tooltip ("b(nuclear) component of a(magnetic)");
1163 		o->labelfont (1);
1164 		o->align (FL_ALIGN_TOP);
1165 	    }
1166 	    {
1167 		Fl_Input *o = arrows->Ac = new Fl_Input (310, y, 70, 20, "Nc");
1168 
1169 		o->tooltip ("c(nuclear) component of a(magnetic)");
1170 		o->labelfont (1);
1171 		o->align (FL_ALIGN_TOP);
1172 	    }
1173 	    yy = y;
1174 	    {
1175 		Fl_Text_Display *o = new Fl_Text_Display (75, yy, 0, 0, "M");
1176 
1177 		o->labelfont (1);
1178 	    }
1179 	    {
1180 		Fl_Text_Display *o = new Fl_Text_Display (75, yy + 12, 0, 0, "a");
1181 
1182 		o->labelfont (1);
1183 	    }
1184 	    {
1185 		Fl_Text_Display *o = new Fl_Text_Display (75, yy + 24, 0, 0, "g");
1186 
1187 		o->labelfont (1);
1188 	    }
1189 	    {
1190 		Fl_Text_Display *o = new Fl_Text_Display (75, yy + 36, 0, 0, "n");
1191 
1192 		o->labelfont (1);
1193 	    }
1194 	    {
1195 		Fl_Text_Display *o = new Fl_Text_Display (75, yy + 48, 0, 0, "e");
1196 
1197 		o->labelfont (1);
1198 	    }
1199 	    {
1200 		Fl_Text_Display *o = new Fl_Text_Display (75, yy + 60, 0, 0, "t");
1201 
1202 		o->labelfont (1);
1203 	    }
1204 	    {
1205 		Fl_Text_Display *o = new Fl_Text_Display (75, yy + 72, 0, 0, "i");
1206 
1207 		o->labelfont (1);
1208 	    }
1209 	    {
1210 		Fl_Text_Display *o = new Fl_Text_Display (75, yy + 84, 0, 0, "c");
1211 
1212 		o->labelfont (1);
1213 	    }
1214 	    y += 20;
1215 	    {
1216 		Fl_Input *o = arrows->Ba = new Fl_Input (110, y, 70, 20, "Mb");
1217 
1218 		o->tooltip ("a(nuclear) component of b(magnetic)");
1219 		o->labelfont (1);
1220 	    }
1221 	    {
1222 		Fl_Input *o = arrows->Bb = new Fl_Input (210, y, 70, 20);
1223 
1224 		o->tooltip ("b(nuclear) component of b(magnetic)");
1225 	    }
1226 	    {
1227 		Fl_Input *o = arrows->Bc = new Fl_Input (310, y, 70, 20);
1228 
1229 		o->tooltip ("c(nuclear) component of b(magnetic)");
1230 	    }
1231 	    y += 20;
1232 	    {
1233 		Fl_Input *o = arrows->Ca = new Fl_Input (110, y, 70, 20, "Mc");
1234 
1235 		o->tooltip ("a(nuclear) component of c(magnetic)");
1236 		o->labelfont (1);
1237 	    }
1238 	    {
1239 		Fl_Input *o = arrows->Cb = new Fl_Input (210, y, 70, 20);
1240 
1241 		o->tooltip ("b(nuclear) component of c(magnetic)");
1242 	    }
1243 	    {
1244 		Fl_Input *o = arrows->Cc = new Fl_Input (310, y, 70, 20);
1245 
1246 		o->tooltip ("c(nuclear) component of c(magnetic)");
1247 	    }
1248 	    y += 30;
1249 	    {
1250 		Fl_Button *o = new Fl_Button (110, y, 70, 25, "Close");
1251 
1252 		o->down_box (FL_DOWN_BOX);
1253 		o->labelfont (1);
1254 		o->tooltip ("Close this window and discard all changes.");
1255 		o->callback ((Fl_Callback *) Edit_Arrow_Close_cb);
1256 	    }
1257 	    {
1258 		Fl_Button *o = new Fl_Button (210, y, 70, 25, "Apply");
1259 
1260 		o->down_box (FL_DOWN_BOX);
1261 		o->tooltip
1262 		    ("Apply current contents of top box to drawing, but leave this window open.");
1263 		o->labelfont (1);
1264 		o->callback ((Fl_Callback *) Edit_Arrow_Save_cb, &zero);
1265 	    }
1266 	    {
1267 		Fl_Button *o = new Fl_Button (310, y, 70, 25, "Save");
1268 
1269 		o->down_box (FL_DOWN_BOX);
1270 		o->labelfont (1);
1271 		o->tooltip
1272 		    ("Apply current contents of top box to drawing, then close this window.");
1273 		o->callback ((Fl_Callback *) Edit_Arrow_Save_cb, &one);
1274 	    }
1275 	}
1276 	arrows->ArrowWindow->end ();
1277     }
1278     Arrow_Frame_Combo_cb (NULL, NULL);
1279     arrows->ArrowInstr1->show ();
1280     if (drvui->nmag) {		// populate widgets
1281 	char string[128];
1282 
1283 	sprintf (string, "%6.3f", drvui->mag_matrix[0][0]);
1284 	arrows->Aa->value (string);
1285 	sprintf (string, "%6.3f", drvui->mag_matrix[0][1]);
1286 	arrows->Ab->value (string);
1287 	sprintf (string, "%6.3f", drvui->mag_matrix[0][2]);
1288 	arrows->Ac->value (string);
1289 	sprintf (string, "%6.3f", drvui->mag_matrix[1][0]);
1290 	arrows->Ba->value (string);
1291 	sprintf (string, "%6.3f", drvui->mag_matrix[1][1]);
1292 	arrows->Bb->value (string);
1293 	sprintf (string, "%6.3f", drvui->mag_matrix[1][2]);
1294 	arrows->Bc->value (string);
1295 	sprintf (string, "%6.3f", drvui->mag_matrix[2][0]);
1296 	arrows->Ca->value (string);
1297 	sprintf (string, "%6.3f", drvui->mag_matrix[2][1]);
1298 	arrows->Cb->value (string);
1299 	sprintf (string, "%6.3f", drvui->mag_matrix[2][2]);
1300 	arrows->Cc->value (string);
1301     }
1302     arrows->ArrowWindow->show ();
1303 }
1304 
1305 void
Edit_Arrow_Close_cb(class Fl_Button *,void *)1306 Edit_Arrow_Close_cb (class Fl_Button *, void *)
1307 {
1308     arrows->ArrowWindow->hide ();
1309     Restore_Working_Copy ();	// undo any changes
1310     Generate_Drawing (1);	// regenerate
1311 }
1312 
1313 void
Edit_Arrow_Save_cb(Fl_Button *,int * save)1314 Edit_Arrow_Save_cb (Fl_Button *, int *save)
1315 {
1316     int i = 0;
1317 
1318     char string[16382];
1319 
1320     float Px[3], Cx[3], length, diam;
1321 
1322     char color[40];
1323 
1324     int Frame_No = 1;
1325 
1326     char *selection;
1327 
1328     if (drvui->max_frame > 1)
1329 	Frame_No = atoi (arrows->Frame_No->value ());
1330 
1331     memset (color, 0, 40);
1332     drvui->Str_File_Changed = 1;
1333     selection = arrows->ArrowBuffer->text ();
1334     strcpy (string, selection);
1335     free (selection);
1336     if (strlen (string) < 10) {
1337 //      drvui->nmag = 0;
1338 	strcpy (string, "");
1339 	arrows->ArrowBuffer->text (string);
1340     } else {
1341 	while (strlen (string) > 10) {
1342 	    sscanf (string, " %f %f %f  %f %f %f %f %f %39c", &Px[0], &Px[1],
1343 		    &Px[2], &Cx[0], &Cx[1], &Cx[2], &length, &diam, color);
1344 	    int j, k;
1345 
1346 	    for (j = 0; j < 3; j++) {
1347 		drvui->arrows[i].mag_xp[j] = Px[j];
1348 		drvui->arrows[i].mag_xc[j] = Cx[j];
1349 	    }
1350 	    drvui->arrows[i].arrow_length = length;
1351 	    drvui->arrows[i].arrow_diam = diam;
1352 	    drvui->arrows[i].arrow_fn = Frame_No;
1353 	    trim_string (color, 40);
1354 	    if (!strlen (color))
1355 		strcpy (color, "Gray20");
1356 	    strcpy (drvui->arrows[i].col_arrow, color);
1357 	    i++;
1358 	    for (j = 0; j < (int) strlen (string); j++) {
1359 		if (string[j] == '\n')
1360 		    break;
1361 	    }
1362 	    for (j++, k = 0; j < (int) strlen (string); j++)
1363 		string[k++] = string[j];
1364 	    string[k] = 0;
1365 	}
1366     }
1367     drvui->nmag = i;
1368     drvui->mag_matrix[0][0] = (float) atof (arrows->Aa->value ());
1369     drvui->mag_matrix[0][1] = (float) atof (arrows->Ab->value ());
1370     drvui->mag_matrix[0][2] = (float) atof (arrows->Ac->value ());
1371     drvui->mag_matrix[1][0] = (float) atof (arrows->Ba->value ());
1372     drvui->mag_matrix[1][1] = (float) atof (arrows->Bb->value ());
1373     drvui->mag_matrix[1][2] = (float) atof (arrows->Bc->value ());
1374     drvui->mag_matrix[2][0] = (float) atof (arrows->Ca->value ());
1375     drvui->mag_matrix[2][1] = (float) atof (arrows->Cb->value ());
1376     drvui->mag_matrix[2][2] = (float) atof (arrows->Cc->value ());
1377     Update_Str (0);
1378     Generate_Drawing (0);
1379     if (*save != 3) {
1380 	Save_Working_Copy ();	// commit changes except from Add_New_Arrow
1381 	arrows->ArrowInstr2->hide ();
1382     }
1383     if (*save == 1) {
1384 	arrows->ArrowWindow->hide ();
1385     }
1386     Fl::redraw ();
1387 }
1388 
1389 void
Edit_Bond_cb(void)1390 Edit_Bond_cb (void)
1391 {
1392 // routine to create the edit bonds screen
1393     char string[100];
1394 
1395     static int one = 1;
1396 
1397     int i;
1398 
1399     int newBonds = 0;
1400 
1401     int y = 25;
1402 
1403     if (!strlen (drvui->CurFile->value ())) {	// Make sure rendering enabled
1404 	Error_Box ("A Structure File must be selected first.");
1405 	return;
1406     }
1407 /*
1408     if (!natom) {         // No atoms, no bonds...
1409         Error_Box("This structure file does not contain any atoms.");
1410         return;
1411     }
1412 */
1413     Save_Working_Copy ();
1414     if (!Bonds) {
1415 	Bonds = new BondParam;	// new instance of the bond parameters
1416 	newBonds = 1;
1417 	Bonds->Bond_Edit_Window =
1418 	    new Fl_Window (50, 50, 560, 490, "Edit Bond Parameters");
1419 	Bonds->Bond_Edit_Window->callback ((Fl_Callback *) Edit_Bond_Close_cb);
1420 	if (drvui->max_frame > 1) {
1421 	    Flu_Combo_List *o = Bonds->Frame_No =
1422 		new Flu_Combo_List (220, y, 75, 25, "Frame No.");
1423 	    o->align (FL_ALIGN_TOP);
1424 	    o->callback (Bond_Frame_Combo_cb);
1425 	    o->labelfont (1);
1426 	    for (i = 1; i <= drvui->max_frame; i++) {
1427 		sprintf (string, "%d", i);
1428 		o->list.add (string);
1429 	    }
1430 	    o->pop_height (20 * drvui->max_frame);
1431 	    o->value ("1");
1432 	}
1433 	y += 50;
1434 	Bonds->Bond_Edit = new Fl_Text_Editor (25, y, 500, 95,
1435 					       "  Type   From  To    Diameter  Min d    Max d    Color    ");
1436 	Bonds->BondBuffer = new Fl_Text_Buffer;
1437 	Bonds->BondBuffer->add_modify_callback ((Fl_Text_Modify_Cb) Modify_Bonds_cb,
1438 						(void *) NULL);
1439 	Bonds->Bond_Edit->textfont (FL_COURIER);
1440 	Bonds->Bond_Edit->textsize (12);
1441 	Bonds->Bond_Edit->buffer (Bonds->BondBuffer);
1442 	Bonds->Bond_Edit->labelfont (FL_COURIER_BOLD);
1443 	y += 95;
1444 	Bonds->BondInstr = new Fl_Output (110, y, 300, 0, "Press 'Add' to replace "
1445 					  "selected line - 'Remove' to delete it");
1446 	Bonds->BondInstr->hide ();
1447 	Bonds->BondInstr->align (FL_ALIGN_BOTTOM);
1448 	Bonds->BondInstr1 = new Fl_Output (110, y, 300, 0, "Highlight text above "
1449 					   "or double click to edit line");
1450 	Bonds->BondInstr1->hide ();
1451 	Bonds->BondInstr1->align (FL_ALIGN_BOTTOM);
1452 	y += 50;
1453 	Fl_Input *oo = Bonds->New_Bond_From = new Fl_Input (20, y, 50, 25, "From");
1454 
1455 	oo->align (FL_ALIGN_TOP);
1456 	oo->labelfont (1);
1457 	Fl_Input *op = Bonds->New_Bond_To = new Fl_Input (80, y, 50, 25, "To");
1458 
1459 	op->align (FL_ALIGN_TOP);
1460 	op->callback ((Fl_Callback *) New_Bond_Input_cb);
1461 	op->labelfont (1);
1462 	Fl_Input *oq = Bonds->New_Bond_Dia = new Fl_Input (140, y, 50, 25, "Diameter");
1463 
1464 	oq->align (FL_ALIGN_TOP);
1465 	oq->callback ((Fl_Callback *) New_Bond_Input_cb);
1466 	oq->labelfont (1);
1467 	Fl_Input *m = Bonds->New_Bond_Min = new Fl_Input (200, y, 50, 25, "Min d");
1468 
1469 	m->align (FL_ALIGN_TOP);
1470 	m->callback ((Fl_Callback *) New_Bond_Input_cb);
1471 	m->labelfont (1);
1472 	Fl_Input *os = Bonds->New_Bond_Max = new Fl_Input (260, y, 50, 25, "Max d");
1473 
1474 	os->align (FL_ALIGN_TOP);
1475 	os->callback ((Fl_Callback *) New_Bond_Input_cb);
1476 	os->labelfont (1);
1477 	Flu_Combo_List *ot = Bonds->New_Bond_Color =
1478 	    new Flu_Combo_List (320, y, 160, 25, "Color");
1479 	ot->align (FL_ALIGN_TOP);
1480 	ot->callback ((Fl_Callback *) New_Bond_Input_cb);
1481 	Load_Color_Combo (ot);
1482 	ot->labelfont (1);
1483 	Fl_Group *qq = new Fl_Group (490, y, 40, 25, "Dashed");
1484 
1485 	qq->labelfont (1);
1486 	qq->box (FL_THIN_UP_BOX);
1487 	Fl_Radio_Button *ou = Bonds->New_Bond_Style =
1488 	    new Fl_Radio_Button (490, y, 10, 25, "");
1489 	ou->callback ((Fl_Callback *) New_Bond_Input_cb);
1490 	ou->labelfont (1);
1491 	Bonds->New_Bond_Style->type (1);
1492 	Bonds->New_Bond_Style->selection_color ((Fl_Color) 1);
1493 	Bonds->New_Bond_Style->align (FL_ALIGN_RIGHT);
1494 	Fl_Input *od = Bonds->New_Bond_Dashes = new Fl_Input (500, y, 30, 25, "");
1495 	qq->end ();
1496 
1497 
1498 	od->align (FL_ALIGN_TOP);
1499 	od->callback ((Fl_Callback *) New_Bond_Input_cb);
1500 	od->labelfont (1);
1501 
1502 	y += 30;
1503 	Fl_Button *om = Bonds->New_Bond_Add = new Fl_Button (180, y, 70, 25, "Add");
1504 
1505 	om->callback ((Fl_Callback *) New_Bond_Add_cb, &zero);
1506 	om->deactivate ();
1507 	Fl_Button *mm = Bonds->New_Bond_Remove = new Fl_Button (270, y, 70, 25, "Remove");
1508 
1509 	mm->callback ((Fl_Callback *) New_Bond_Add_cb, &one);
1510 	mm->deactivate ();
1511 	y += 30;
1512 	Bonds->BondInstr2 = new Fl_Output (25, y, 470, 0,
1513 					   "Changes are temporary until \"Apply\" or \"Save\" is pressed.");
1514 	Bonds->BondInstr2->hide ();
1515 	Bonds->BondInstr2->align (FL_ALIGN_BOTTOM);
1516 	y += 40;
1517 	Fl_Text_Editor *p =
1518 	    new Fl_Text_Editor (250, y, 200, 100, "'To' Atoms & Distances");
1519 	p->textfont (FL_COURIER);
1520 	p->textsize (14);
1521 	p->align (FL_ALIGN_TOP);
1522 	p->labelfont (1);
1523 	Bonds->Bond_Output_Buffer = new Fl_Text_Buffer;
1524 	p->buffer (Bonds->Bond_Output_Buffer);
1525 	Bonds->Bond_Output_Buffer->
1526 	    add_modify_callback ((Fl_Text_Modify_Cb) Modify_Bonds_Distance_cb,
1527 				 (void *) NULL);
1528 #if !defined (WIN32) && !defined (__APPLE__)
1529 	Bonds->Bond_Edit_Window->icon ((char *) drvui->icon);
1530 #endif
1531 	Flu_Combo_List *o = Bonds->Bond_Combo =
1532 	    new Flu_Combo_List (100, y, 100, 25, "'From' Atom");
1533 	o->align (FL_ALIGN_TOP);
1534 	o->labelfont (1);
1535 	o->callback (Bond_Combo_cb);
1536 	y += 125;
1537 	Fl_Button *r = new Fl_Button (125, y, 70, 25, "Close");
1538 
1539 	r->tooltip ("Close this window and discard all changes.");
1540 	r->callback ((Fl_Callback *) Edit_Bond_Close_cb);
1541 	Fl_Button *s = new Fl_Button (325, y, 70, 25, "Save");
1542 
1543 	s->tooltip
1544 	    ("Apply current contents of top box to drawing, then close this window.");
1545 	s->callback ((Fl_Callback *) Edit_Bond_Save_cb, &one);
1546 	Fl_Button *a = new Fl_Button (225, y, 70, 25, "Apply");
1547 
1548 	a->tooltip
1549 	    ("Apply current contents of top box to drawing, but leave this window open.");
1550 	a->callback ((Fl_Callback *) Edit_Bond_Save_cb, &zero);
1551 	Bonds->Bond_Edit_Window->end ();
1552 
1553     } else {
1554 	Bonds->BondInstr->hide ();
1555 	Bonds->BondInstr1->hide ();
1556     }
1557     Bond_Frame_Combo_cb (NULL, NULL);
1558     Bonds->Bond_Edit_Window->show ();
1559 }
1560 
1561 void
Edit_Bond_Close_cb(void)1562 Edit_Bond_Close_cb (void)
1563 {
1564     Bonds->Bond_Edit_Window->hide ();
1565     Restore_Working_Copy ();	// undo any changes
1566     Generate_Drawing (1);	// regenerate
1567 }
1568 
1569 void
Edit_Bond_Save_cb(Fl_Button *,int * save)1570 Edit_Bond_Save_cb (Fl_Button *, int *save)
1571 {
1572 // callback routine when 'save' or 'apply' button is pressed on the Edit Bonds screen
1573     char type[5], atom1[5], atom2[5], color[40], widget[16382];
1574 
1575     int i = 0;
1576 
1577     unsigned int j, k;
1578 
1579     float dia, d1, d2;
1580 
1581     int Frame_No = 1;
1582 
1583     int numd;
1584 
1585     char *selection;
1586 
1587     if (drvui->max_frame > 1) {
1588 	Frame_No = atoi (Bonds->Frame_No->value ());
1589 	for (i = 1, j = 1; i < drvui->nbond; i++) {	// copy parameters for other frames to
1590 	    if (drvui->bonds[i].bond_fn != Frame_No) {	//   start of list
1591 		if ((int) j != i) {
1592 		    drvui->bonds[j].bond_fn = drvui->bonds[i].bond_fn;
1593 		    strncpy (drvui->bonds[j].col_bond, drvui->bonds[i].col_bond, 25);
1594 		    strncpy (drvui->bonds[j].bond_l1, drvui->bonds[i].bond_l1, 4);
1595 		    strncpy (drvui->bonds[j].bond_l2, drvui->bonds[i].bond_l2, 4);
1596 		    drvui->bonds[j].bond_l1[4] = '\0';
1597 		    drvui->bonds[j].bond_l2[4] = '\0';
1598 		    drvui->bonds[j].bond_max = drvui->bonds[i].bond_max;
1599 		    drvui->bonds[j].bond_min = drvui->bonds[i].bond_min;
1600 		    drvui->bonds[j].bond_size = drvui->bonds[i].bond_size;
1601 		    drvui->bonds[j].bond_style = drvui->bonds[i].bond_style;
1602 		}
1603 		j++;
1604 	    }
1605 	}
1606 	i = j - 1;
1607     }
1608     drvui->Str_File_Changed = 1;
1609     selection = Bonds->BondBuffer->text ();
1610     strcpy (widget, selection);
1611     free (selection);
1612     if (strlen (widget) < 10) {
1613 	drvui->nbond = 0;
1614 	Bonds->BondBuffer->text ("");
1615     } else {
1616 	while (strlen (widget) > 10) {
1617 	    i++;
1618 	    sscanf (widget, " %s %s %s %f %f %f %s", type, atom1, atom2, &dia, &d1, &d2,
1619 		    color);
1620 	    if (!strcmp (type, "dash")) {
1621    		j = sscanf (widget, " %s %d %s %s %f %f %f %s", type, &numd, atom1, atom2, &dia, &d1, &d2,
1622 		    color);
1623 		if (j < 4) {
1624 		    numd = 5;
1625 		    sscanf (widget, " %s %s %s %f %f %f %s", type, atom1, atom2, &dia, &d1, &d2,
1626 		    color);
1627 		}
1628 		drvui->bonds[i].bond_style = numd;
1629 	    } else
1630 		drvui->bonds[i].bond_style = 0;
1631 	    strcpy (drvui->bonds[i].bond_l1, atom1);
1632 	    strcpy (drvui->bonds[i].bond_l2, atom2);
1633 	    drvui->bonds[i].bond_size = dia;
1634 	    drvui->bonds[i].bond_min = d1;
1635 	    drvui->bonds[i].bond_max = d2;
1636 	    trim_string (color, 40);
1637 	    if (!strlen (color))
1638 		strcpy (color, "Gray20");
1639 	    strncpy (drvui->bonds[i].col_bond, color, 40);
1640 	    drvui->bonds[i].bond_fn = Frame_No;
1641 	    drvui->nbond = i + 1;
1642 	    for (j = 0; j < strlen (widget); j++) {
1643 		if (widget[j] == '\n')
1644 		    break;
1645 	    }
1646 	    for (j++, k = 0; j < strlen (widget); j++)
1647 		widget[k++] = widget[j];
1648 	    widget[k] = 0;
1649 	}
1650     }
1651     Update_Str (0);
1652     Generate_Drawing (0);
1653     if (*save != 3) {
1654 	Save_Working_Copy ();
1655 	Bonds->BondInstr2->hide ();
1656     }
1657     if (*save == 1) {
1658 	Bonds->Bond_Edit_Window->hide ();
1659     }
1660     Fl::redraw ();
1661 }
1662 
1663 void
Edit_Changed_cb(int,int nInserted,int nDeleted,int,const char *,void * v)1664 Edit_Changed_cb (int, int nInserted, int nDeleted, int, const char *, void *v)
1665 {
1666     char title[128];
1667 
1668     Fl_Window *w = (Fl_Window *) v;
1669 
1670     if ((nInserted || nDeleted) && !Edit_loading) {
1671 	Edit_changed = 1;
1672 	strcpy (title, Edit_title);
1673 	strcat (title, " (modified)");
1674 	w->label (title);
1675     }
1676 }
1677 
1678 void
Edit_Ellipsoid_cb(void)1679 Edit_Ellipsoid_cb (void)
1680 {
1681 // Callback routine to show the Ellipsoid Parameter screen and load the widgets on that page
1682     char string[100];
1683 
1684     int i, j;
1685 
1686     char atom[5];
1687 
1688     char color[40];
1689 
1690     char widget[16382];
1691 
1692     if (!strlen (drvui->CurFile->value ())) {	// Make sure rendering enabled
1693 	Error_Box ("A Structure File must be selected first.");
1694 	return;
1695     }
1696 /*
1697     if (!natom) {         // No atoms, no ellipsoids...
1698         Error_Box("This structure file does not contain any atoms.");
1699         return;
1700     }
1701 */
1702     Save_Working_Copy ();
1703     if (!ellipsoids) {
1704 	ellipsoids = new Ellipsoids;	// Create the screen
1705 #if !defined (WIN32) && !defined (__APPLE__)
1706 	ellipsoids->Ellips_Window->icon ((char *) drvui->icon);
1707 #endif
1708 	ellipsoids->Color_Combo->list.add ("");
1709 	ellipsoids->Color_Combo->value ("");
1710 	Load_Color_Combo (ellipsoids->Color_Combo);
1711 	ellipsoids->show ();	// show it
1712 	drvui->frame_no = min (drvui->frame_no, drvui->max_frame);
1713 	set_tf_status ();	// set the flags
1714 	sprintf (string, "%5.2f", drvui->Ellipsoid_Prob);	// load the ellipsoid probability widget
1715 	ellipsoids->Probability->value (string);
1716 	ellipsoids->Probability->take_focus ();	// set this widget with focus
1717 	ellipsoids->Probability->position (0);
1718 	ellipsoids->Probability->mark (strlen (ellipsoids->Probability->value ()));
1719 	if (drvui->do_ellipsoids)
1720 	    ellipsoids->Show_Ellipsoids->set ();	// Show ellipsoids checkbox set
1721 	if (drvui->El_Cutout) {
1722 	    ellipsoids->Use_Cutouts->set ();	// cutout check box
1723 	    if (!strlen (drvui->Cutout_color))
1724 		strcpy (drvui->Cutout_color, "Gray20");
1725 	    ellipsoids->Cutout_Color->value (drvui->Cutout_color);	// Cutout Color widget
1726 	} else {
1727 	    ellipsoids->Cutout_Color->deactivate ();
1728 	}
1729 	ellipsoids->Axis_Color->value (drvui->Ellipaxis_color);	// Load ellipsoid axis color
1730 	sprintf (string, "%6.2f", drvui->Ellipaxis_width);
1731 	ellipsoids->Axis_Width->value (string);	// and width
1732 	ellipsoids->Atom_Combo->list.add ("");
1733 	ellipsoids->Atom_Combo->value ("");
1734 	for (i = 0; i < natom; i++) {
1735 	    if (drvui->atoms[i].atom_fn != drvui->frame_no)
1736 		continue;
1737 	    if (drvui->atoms[i].TF_status > 0) {
1738 		strcpy (string, drvui->atoms[i].atom_l);
1739 		while (strlen (string) < 4)
1740 		    strcat (string, " ");
1741 		sprintf (widget, "%4s%2d", string, drvui->atoms[i].sv_atom_n);
1742 		ellipsoids->Atom_Combo->list.add (widget);
1743 	    }
1744 	}
1745 	for (i = 0; i < natom; i++) {
1746 	    if (drvui->atoms[i].atom_fn != drvui->frame_no)
1747 		continue;
1748 	    if (drvui->atoms[i].TF_status > 0) {
1749 		int j, haveit;
1750 
1751 		haveit = 0;
1752 		for (j = 0; j < i; j++)
1753 		    if (drvui->atoms[j].TF_status &&
1754 			check_atom_name (drvui->atoms[i].atom_l, drvui->atoms[j].atom_l))
1755 			haveit = 1;
1756 		if (haveit == 1)
1757 		    continue;
1758 		strcpy (string, drvui->atoms[i].atom_l);
1759 		while (strlen (string) < 4)
1760 		    strcat (string, " ");
1761 		sprintf (widget, "%4s *", string);
1762 		ellipsoids->Atom_Combo->list.add (widget);
1763 	    }
1764 	}
1765 	widget[0] = '\0';
1766 	for (i = 1; i < drvui->n_ellips; i++) {
1767 	    if (drvui->ellips[i].ell_type < 1000)
1768 		continue;	// skip for npd or not displayed
1769 	    memset (atom, 0, 5);
1770 	    strncpy (atom, drvui->ellips[i].ellips_l, 4);
1771 	    atom[4] = 0;
1772 	    for (j = 3; j >= 0; --j) {
1773 		if (atom[j] == ' ')
1774 		    atom[j] = 0;
1775 	    }
1776 	    j = drvui->ellips[i].save_el_number;
1777 	    memset (color, 0, 40);
1778 	    memset (string, 0, 100);
1779 	    strncpy (color, drvui->ellips[i].ellips_col, 39);
1780 	    trim_string (color, 40);
1781 	    if (!strlen (color))
1782 		strcpy (color, "Gray20");
1783 	    if (j == -1) {
1784 		int haveit = 0;
1785 
1786 		for (j = 1; j < i; j++) {
1787 		    if (check_atom_name
1788 			(drvui->ellips[i].ellips_l, drvui->ellips[j].ellips_l))
1789 			haveit = 1;
1790 		}
1791 		if (haveit == 0)
1792 		    sprintf (string, "%4s   *   %s\n", atom, color);
1793 
1794 	    } else
1795 		sprintf (string, "%4s %3d   %s\n", atom, j, color);
1796 	    strcat (widget, string);
1797 	}
1798 	ellipsoids->ColorInputBuf->text (widget);
1799     }
1800     ellipsoids->Ellips_Window->show ();
1801 }
1802 
1803 void
Edit_Ellipsoid_Close_cb(Fl_Button *,void *)1804 Edit_Ellipsoid_Close_cb (Fl_Button *, void *)
1805 {
1806 // callback from close button on ellipsoids screen
1807     drvui->destroy |= ELLIPSOID;
1808     ellipsoids->Ellips_Window->hide ();
1809     Restore_Working_Copy ();	// undo any changes
1810     Generate_Drawing (1);	// regenerate
1811 }
1812 
1813 void
Edit_Ellipsoid_Save_cb(Fl_Button *,int * save)1814 Edit_Ellipsoid_Save_cb (Fl_Button *, int *save)
1815 {
1816 // callback routine when 'save' or 'apply' button is pressed on the Ellipsoids Parameter screen
1817     char atom[5], color[40], widget[16382], num[4];
1818 
1819     int i;
1820 
1821     int j, k;
1822 
1823     char string[128];
1824 
1825     char *selection;
1826 
1827     drvui->Str_File_Changed = 1;
1828     for (i = 1; i < drvui->n_ellips; i++)
1829 	drvui->ellips[i].ell_type = 1;
1830     drvui->Ellipsoid_Prob = (float) atof (ellipsoids->Probability->value ());
1831     selection = ellipsoids->ColorInputBuf->text ();
1832     strcpy (widget, selection);
1833     free (selection);
1834     while (strlen (widget) > 10) {
1835 	sscanf (widget, "%s %s %20s", atom, num, color);
1836 	while (strlen (atom) < 4)
1837 	    strcat (atom, " ");
1838 	if (strstr (num, "*"))
1839 	    j = -1;
1840 	else
1841 	    j = atoi (num);
1842 	for (i = 1; i < drvui->n_ellips; i++) {
1843 	    if (check_atom_name (drvui->ellips[i].ellips_l, atom) &&
1844 		(j == drvui->ellips[i].ellips_n || j == -1)) {
1845 		trim_string (color, 40);
1846 		if (!strlen (color))
1847 		    strcpy (color, "Gray20");
1848 		strcpy (drvui->ellips[i].ellips_col, color);	/* copy color */
1849 		drvui->ellips[i].ell_type = 1001;
1850 		drvui->ellips[i].save_el_number = j;
1851 	    }
1852 	}
1853 	for (j = 0; j < (int) strlen (widget); j++) {
1854 	    if (widget[j] == '\n')
1855 		break;
1856 	}
1857 	for (j++, k = 0; j < (int) strlen (widget); j++)
1858 	    widget[k++] = widget[j];
1859 	widget[k] = 0;
1860     }
1861     if (ellipsoids->Use_Cutouts->value () != 0) {
1862 	drvui->El_Cutout = 1;
1863 	strcpy (string, ellipsoids->Cutout_Color->value ());
1864 	if (!strlen (string))
1865 	    strcpy (string, "Gray20");
1866 	trim_string (string, 40);
1867 	strcpy (drvui->Cutout_color, string);
1868 	strcpy (string, ellipsoids->Axis_Color->value ());	// Get ellipsoid axis color
1869 	trim_string (string, 40);
1870 	if (!strlen (string))
1871 	    strcpy (string, "Gray20");
1872 	strcpy (drvui->Ellipaxis_color, string);
1873     } else {
1874 	strcpy (drvui->Cutout_color, "");
1875 	drvui->El_Cutout = 0;
1876     }
1877     if (ellipsoids->Show_Ellipsoids->value () != 0)
1878 	drvui->do_ellipsoids = 1;
1879     else
1880 	drvui->do_ellipsoids = 0;
1881     drvui->Ellipaxis_width = (float) atof (ellipsoids->Axis_Width->value ());
1882     Update_Str (0);
1883     Generate_Drawing (0);
1884     if (*save != 3) {
1885 	Save_Working_Copy ();
1886 	ellipsoids->Instr2->hide ();
1887     }
1888     if (*save == 1) {
1889 	ellipsoids->Ellips_Window->hide ();
1890     }
1891     Fl::redraw ();		// update the screen
1892 }
1893 
1894 void
Edit_LonePair_cb(void)1895 Edit_LonePair_cb (void)
1896 {
1897 // Callback routine to show the Lone-Pair Parameter screen and load the widgets on that page
1898     char string[100];
1899 
1900     static int one = 1;
1901 
1902     static int zero = 0;
1903 
1904     int i;
1905 
1906     int y = 50;
1907 
1908     if (!strlen (drvui->CurFile->value ())) {	// Make sure rendering enabled
1909 	Error_Box ("A Structure File must be selected first.");
1910 	return;
1911     }
1912 /*
1913     if (!natom) {         // No atoms, no lone-pairs...
1914         Error_Box("This structure file does not contain any atoms.");
1915         return;
1916     }
1917 */
1918     Save_Working_Copy ();
1919     if (!LonePairs) {
1920 	LonePairs = new LonePairParam;	// new instance of the lone-pair parameters
1921 	LonePairs->LonePair_Edit_Window =
1922 	    new Fl_Window (50, y, 520, 350, "Edit Lone-Pair Parameters");
1923 	LonePairs->LonePair_Edit_Window->
1924 	    callback ((Fl_Callback *) Edit_Lone_Pair_Close_cb);
1925 	if (drvui->max_frame > 1) {
1926 	    Flu_Combo_List *o = LonePairs->Frame_No = new Flu_Combo_List (220, y - 25, 75,
1927 									  25,
1928 									  "Frame No.");
1929 	    o->align (FL_ALIGN_TOP);
1930 	    o->callback (LonePair_Frame_Combo_cb);
1931 	    o->labelfont (1);
1932 	    for (i = 1; i <= drvui->max_frame; i++) {
1933 		sprintf (string, "%d", i);
1934 		o->list.add (string);
1935 	    }
1936 	    o->pop_height (20 * drvui->max_frame);
1937 	    o->value ("1");
1938 	}
1939 	y += 25;
1940 	LonePairs->LonePair_Edit = new Fl_Text_Editor (25, y, 460, 75,
1941 						       "From  #e  Height   Rad 1   Rad 2    Color        ");
1942 	LonePairs->LonePairBuffer = new Fl_Text_Buffer;
1943 	LonePairs->LonePairBuffer->
1944 	    add_modify_callback ((Fl_Text_Modify_Cb) Modify_LonePair_cb, (void *) NULL);
1945 	LonePairs->LonePair_Edit->textfont (FL_COURIER);
1946 	LonePairs->LonePair_Edit->textsize (12);
1947 	LonePairs->LonePair_Edit->buffer (LonePairs->LonePairBuffer);
1948 	LonePairs->LonePair_Edit->labelfont (FL_COURIER_BOLD);
1949 	y += 85;
1950 	LonePairs->LonePairInst = new Fl_Output (135, y, 250, 0, "Press 'Add' to replace "
1951 						 "selected line - 'Remove' to delete it");
1952 	LonePairs->LonePairInst->hide ();
1953 	LonePairs->LonePairInst->align (FL_ALIGN_BOTTOM);
1954 	LonePairs->LonePairInst1 = new Fl_Output (135, y, 250, 0, "Highlight text above "
1955 						  "or double click to edit line");
1956 	LonePairs->LonePairInst1->hide ();
1957 	LonePairs->LonePairInst1->align (FL_ALIGN_BOTTOM);
1958 	y += 40;
1959 	Flu_Combo_List *o = LonePairs->LonePair_Combo =
1960 	    new Flu_Combo_List (20, y, 50, 25, "From");
1961 	o->align (FL_ALIGN_TOP);
1962 	o->labelfont (1);
1963 	o->callback (Lone_Pair_Combo_cb);
1964 	Fl_Input *op = LonePairs->Number = new Fl_Input (80, y, 50, 25, "No. Elec.");
1965 
1966 	op->align (FL_ALIGN_TOP);
1967 	op->labelfont (1);
1968 	op->callback (Lone_Pair_Combo_cb);
1969 	Fl_Input *oq = LonePairs->Height = new Fl_Input (140, y, 50, 25, "Height");
1970 
1971 	oq->align (FL_ALIGN_TOP);
1972 	oq->labelfont (1);
1973 	oq->callback (Lone_Pair_Combo_cb);
1974 	Fl_Input *m = LonePairs->Radius1 = new Fl_Input (200, y, 50, 25, "Rad. 1");
1975 
1976 	m->align (FL_ALIGN_TOP);
1977 	m->labelfont (1);
1978 	Fl_Input *os = LonePairs->Radius2 = new Fl_Input (260, y, 50, 25, "Rad. 2");
1979 
1980 	os->align (FL_ALIGN_TOP);
1981 	os->labelfont (1);
1982 	os->callback (Lone_Pair_Combo_cb);
1983 	Flu_Combo_List *ot = LonePairs->LonePair_Color =
1984 	    new Flu_Combo_List (320, y, 160, 25, "Color");
1985 	ot->align (FL_ALIGN_TOP);
1986 	Load_Color_Combo (ot);
1987 	ot->labelfont (1);
1988 	ot->callback (Lone_Pair_Combo_cb);
1989 	y += 30;
1990 	Fl_Button *om = LonePairs->LonePair_Add = new Fl_Button (180, y, 70, 25, "Add");
1991 
1992 	om->callback ((Fl_Callback *) New_Lone_Pair_Add_cb, &one);
1993 	om->deactivate ();
1994 	Fl_Button *pm = LonePairs->LonePair_Remove =
1995 	    new Fl_Button (270, y, 70, 25, "Remove");
1996 	pm->callback ((Fl_Callback *) New_Lone_Pair_Add_cb, &zero);
1997 	pm->deactivate ();
1998 	y += 30;
1999 	LonePairs->LonePairInst2 = new Fl_Output (25, y, 470, 0,
2000 						  "Changes are temporary until \"Apply\" or \"Save\" is pressed.");
2001 	LonePairs->LonePairInst2->hide ();
2002 	LonePairs->LonePairInst2->align (FL_ALIGN_BOTTOM);
2003 	y += 30;
2004 	Fl_Button *r = new Fl_Button (125, y, 70, 25, "Close");
2005 
2006 	r->tooltip ("Close this window and discard all changes.");
2007 	r->callback ((Fl_Callback *) Edit_Lone_Pair_Close_cb);
2008 	Fl_Button *s = new Fl_Button (325, y, 70, 25, "Save");
2009 
2010 	s->tooltip
2011 	    ("Apply current contents of top box to drawing, then close this window.");
2012 	s->callback ((Fl_Callback *) Edit_Lone_Pair_Save_cb, &one);
2013 	Fl_Button *a = new Fl_Button (225, y, 70, 25, "Apply");
2014 
2015 	a->tooltip
2016 	    ("Apply current contents of top box to drawing, but leave this window open.");
2017 	a->callback ((Fl_Callback *) Edit_Lone_Pair_Save_cb, &zero);
2018 #if !defined (WIN32) && !defined (__APPLE__)
2019 	LonePairs->LonePair_Edit_Window->icon ((char *) drvui->icon);
2020 #endif
2021 	LonePairs->LonePair_Edit_Window->end ();
2022     }
2023     LonePair_Frame_Combo_cb (NULL, NULL);
2024     LonePairs->LonePair_Edit_Window->show ();
2025 }
2026 
2027 void
Edit_Lone_Pair_Close_cb(void)2028 Edit_Lone_Pair_Close_cb (void)
2029 {
2030     drvui->destroy |= LONEPAIR;
2031     LonePairs->LonePair_Edit_Window->hide ();
2032     Restore_Working_Copy ();
2033     Generate_Drawing (1);
2034 }
2035 
2036 void
Edit_Lone_Pair_Save_cb(Fl_Button *,int * save)2037 Edit_Lone_Pair_Save_cb (Fl_Button *, int *save)
2038 {
2039 // callback routine when 'save' or 'apply' button is pressed on the Edit Lone Pairs screen
2040     char atom[4], color[40], widget[16382];
2041 
2042     int i = 0;
2043 
2044     int no = 0;
2045 
2046     unsigned int j, k;
2047 
2048     float height, d1, d2;
2049 
2050     int Frame_No = 1;
2051 
2052     char *selection;
2053 
2054     if (drvui->max_frame > 1) {
2055 	Frame_No = atoi (LonePairs->Frame_No->value ());
2056 	for (i = 1, j = 1; i < drvui->ncone; i++) {	// copy parameters for other frames to
2057 	    if (drvui->cones[i].cone_fn != Frame_No) {	//   start of list
2058 		if ((int) j != i) {
2059 		    drvui->cones[j].cone_height = drvui->cones[i].cone_height;
2060 		    drvui->cones[j].cone_fn = drvui->cones[i].cone_fn;
2061 		    strncpy (drvui->cones[j].col_cone, drvui->cones[i].col_cone, 25);
2062 		    strncpy (drvui->cones[j].cone_l1, drvui->cones[i].cone_l1, 4);
2063 		    drvui->cones[j].cone_max = drvui->cones[i].cone_max;
2064 		    drvui->cones[j].cone_min = drvui->cones[i].cone_min;
2065 		}
2066 		j++;
2067 	    }
2068 	}
2069 	i = j - 1;
2070     }
2071 
2072     drvui->Str_File_Changed = 1;
2073     selection = LonePairs->LonePairBuffer->text ();
2074     strcpy (widget, selection);
2075     free (selection);
2076     if (strlen (widget) < 10) {
2077 	i = 0;
2078 	strcpy (widget, "");
2079 	LonePairs->LonePairBuffer->text (widget);
2080     } else {
2081 	while (strlen (widget) > 10) {
2082 	    i++;
2083 	    sscanf (widget, " %s %d %f %f %f %s", atom, &no, &height, &d1, &d2, color);
2084 	    strncpy (drvui->cones[i].cone_l1, atom, 4);
2085 	    drvui->cones[i].numlonepairs = no;
2086 	    drvui->cones[i].cone_height = height;
2087 	    drvui->cones[i].cone_min = d1;
2088 	    drvui->cones[i].cone_max = d2;
2089 	    trim_string (color, 40);
2090 	    if (!strlen (color))
2091 		strcpy (color, "Gray20");
2092 	    strcpy (drvui->cones[i].col_cone, color);
2093 	    drvui->cones[i].cone_fn = Frame_No;
2094 	    for (j = 0; j < strlen (widget); j++) {
2095 		if (widget[j] == '\n')
2096 		    break;
2097 	    }
2098 	    for (j++, k = 0; j < strlen (widget); j++)
2099 		widget[k++] = widget[j];
2100 	    widget[k] = 0;
2101 	}
2102     }
2103     drvui->ncone = i + 1;
2104     Update_Str (0);
2105     Generate_Drawing (0);
2106     if (*save != 3) {
2107 	Save_Working_Copy ();
2108 	LonePairs->LonePairInst2->hide ();
2109     }
2110     if (*save == 1) {
2111 	LonePairs->LonePair_Edit_Window->hide ();
2112     }
2113     Fl::redraw ();
2114 }
2115 
2116 void
Edit_Maps_cb(void)2117 Edit_Maps_cb (void)
2118 {
2119 // Callback routine to show the Map Parameter screen and load the widgets on that page
2120     char string[128];
2121     static int one = 1;
2122     int y;
2123     int i;
2124     int wh;
2125     char widget[2048];
2126     char type[6];
2127 
2128     if (!strlen (drvui->CurFile->value ())) {	// Make sure rendering enabled
2129 	Error_Box ("A Structure File must be selected first.");
2130 	return;
2131     }
2132     Save_Working_Copy ();
2133     if (!Maps) {
2134 	char title[30];
2135 
2136 	if (drvui->Fourier2d)
2137 	    strcpy (title, "Edit 2D Map parameters");
2138 	else
2139 	    strcpy (title, "Edit 3D Map Parameters");
2140 	Maps = new MapsParam;	// new instance of the map parameters
2141 
2142 	wh = 550;
2143 	if (drvui->modulated)
2144 	    wh += 55;
2145 	if (drvui->max_frame > 1)
2146 	    wh += 60;
2147 	Maps->Maps_Edit_Window = new Fl_Window (50, 50, 500, wh, title);
2148 
2149 	Maps->Maps_Edit_Window->callback ((Fl_Callback *) Edit_Maps_Close_cb);
2150 	y = 30;
2151 	if (drvui->max_frame > 1) {
2152 	    Maps->Frame_No =
2153 		new Flu_Combo_List (220, y, 75, 25, "Frame No.");
2154 	    Maps->Frame_No->align (FL_ALIGN_TOP);
2155 	    Maps->Frame_No->callback (Maps_Frame_Combo_cb);
2156 	    Maps->Frame_No->labelfont (1);
2157 	    for (i = 1; i <= drvui->max_frame; i++) {
2158 		sprintf (string, "%d", i);
2159 		Maps->Frame_No->list.add (string);
2160 	    }
2161 	    Maps->Frame_No->pop_height (20 * drvui->max_frame);
2162 	    Maps->Frame_No->value ("1");
2163             y += 50;
2164 	}
2165 	Maps->Filename = new Fl_Output (10, y, 260, 25, "Map Filename");
2166 	Maps->Filename->align (FL_ALIGN_TOP);
2167 	Maps->Filename->color ((Fl_Color) 17);
2168 	Maps->Filename->labelfont (FL_COURIER_BOLD);
2169 
2170 	Maps->Map_Browse = new Fl_Button (280, y, 70, 25, "Browse");
2171 	Maps->Map_Browse->tooltip ("Browse for new Fourier file.");
2172 	Maps->Map_Browse->callback ((Fl_Callback *) Browse_Map_File_cb);
2173 
2174 	Maps->MapType = new Flu_Combo_List (360, y, 130, 25, "File Type");
2175 	Maps->MapType->align (FL_ALIGN_TOP);
2176 	Maps->MapType->list.add ("GSAS - grd");
2177 	Maps->MapType->list.add ("JANA - stf");
2178 	Maps->MapType->list.add ("WIEN - w2k");
2179 	Maps->MapType->list.add ("VASP - vsp");
2180 	Maps->MapType->list.add ("FullProf - flp");
2181 	Maps->MapType->list.add ("CIF FoFc - fcf");
2182 	Maps->MapType->list.add ("O Format - dn6");
2183 	Maps->MapType->list.add ("JANA FoFc - m80");
2184 	Maps->MapType->list.add ("Exciting - exc");
2185 	Maps->MapType->list.add ("JANA - m81");
2186 	Maps->MapType->list.add ("XCrysDen - xsf");
2187 	Maps->MapType->pop_height (120);
2188 	Maps->MapType->labelfont (FL_COURIER_BOLD);
2189 	Maps->MapType->color ((Fl_Color) 17);
2190 	Maps->MapType->callback ((Fl_Callback *) MapType_cb);
2191 
2192 	y += 40;
2193 	Maps->Map_Info = new Fl_Button (20, y - 10, 110, 25, "Show Map Info");
2194 	Maps->Map_Info->tooltip ("Display header information from Fourier file.");
2195 	Maps->Map_Info->callback ((Fl_Callback *) Map_Info_cb);
2196 
2197 	Maps->MapCalc = new Fl_Button (20, y + 25, 110, 25, "Save Calc Map");
2198 	Maps->MapCalc->tooltip ("Save Calculated 'fcf' Map in 'grd' format");
2199 	Maps->MapCalc->callback ((Fl_Callback *) Write_Map_cb);
2200 	Maps->MapCalcType = new Flu_Combo_List (20, y + 70, 110, 25, "Calc Type");
2201 	Maps->MapCalcType->align (FL_ALIGN_TOP);
2202 	Maps->MapCalcType->list.add ("Fo");
2203 	Maps->MapCalcType->list.add ("Fc");
2204 	Maps->MapCalcType->list.add ("Fo-Fc");
2205 	Maps->MapCalcType->list.add ("2Fo-Fc");
2206 	Maps->MapCalcType->list.add ("Fo2");
2207 	Maps->MapCalcType->pop_height (80);
2208 	Maps->MapCalcType->color ((Fl_Color) 17);
2209 	if (Map_Info.map_type == 0)
2210 	    Maps->MapCalcType->value ("Fo");
2211 	else if (Map_Info.map_type == 1)
2212 	    Maps->MapCalcType->value ("Fc");
2213 	else if (Map_Info.map_type == 2)
2214 	    Maps->MapCalcType->value ("Fo-Fc");
2215 	else if (Map_Info.map_type == 3)
2216 	    Maps->MapCalcType->value ("2Fo-Fc");
2217 	else if (Map_Info.map_type == 4)
2218 	    Maps->MapCalcType->value ("Fo2");
2219 
2220 	Maps->Resolution = new Fl_Input (20, y + 110, 110, 25, "Resolution");
2221 	Maps->Resolution->align (FL_ALIGN_TOP);
2222 	sprintf(widget, "%i", Map_Info.res);
2223 	Maps->Resolution->value(widget);
2224 
2225 	y += 15;
2226 	strcpy (widget, "");
2227 	Maps->MapsBuffer = new Fl_Text_Buffer;
2228 	Maps->MapsBuffer->add_modify_callback ((Fl_Text_Modify_Cb) Modify_Maps_cb,
2229 					       (void *) NULL);
2230 	if (!drvui->Fourier2d) {
2231 	    Fl_Text_Editor *o =
2232 		new Fl_Text_Editor (150, y, 300, 120, "Level     Type     Color     ");
2233 	    o->labelfont (FL_COURIER_BOLD);
2234 	    o->textfont (FL_COURIER);
2235 	    o->buffer (Maps->MapsBuffer);
2236 	} else {
2237 	    Fl_Text_Editor *o =
2238 		new Fl_Text_Editor (150, y, 300, 120, "Lower    Step   Upper Color ");
2239 	    o->labelfont (FL_COURIER_BOLD);
2240 	    o->textfont (FL_COURIER);
2241 	    o->buffer (Maps->MapsBuffer);
2242 	}
2243 	Maps->MapsInstr = new Fl_Output (20, y + 130, 450, 0, "Press 'Add' to replace "
2244 					 "selected line - 'Remove' to delete it");
2245 	Maps->MapsInstr->hide ();
2246 	Maps->MapsInstr->align (FL_ALIGN_BOTTOM);
2247 	Maps->MapsInstr1 = new Fl_Output (70, y + 130, 450, 0, "Highlight text above "
2248 					  "or double click to edit line");
2249 	Maps->MapsInstr1->align (FL_ALIGN_BOTTOM);
2250 	y += 160;
2251 	if (!drvui->Fourier2d) {
2252 	    Maps->Level = new Fl_Input (80, y, 70, 25, "Contour Level");
2253 	    Maps->Level->align (FL_ALIGN_BOTTOM);
2254 	    Maps->Level->callback ((Fl_Callback *) New_Map_Input_cb);
2255 	    Maps->Type = new Flu_Combo_List (170, y, 90, 25, "Type");
2256 	    Maps->Type->align (FL_ALIGN_BOTTOM);
2257 	    Maps->Type->callback ((Fl_Callback *) New_Map_Input_cb);
2258 	    Maps->Type->list.add ("mesh");
2259 	    Maps->Type->list.add ("solid");
2260 	    Maps->Type->pop_height (40);
2261 	} else {
2262 	    Maps->Level = new Fl_Input (40, y, 70, 25, "Lower");
2263 	    Maps->Level->align (FL_ALIGN_BOTTOM);
2264 	    Maps->Level->callback ((Fl_Callback *) New_Map_Input_cb);
2265 	    Maps->Step = new Fl_Input (120, y, 70, 25, "Step");
2266 	    Maps->Step->align (FL_ALIGN_BOTTOM);
2267 	    Maps->Step->callback ((Fl_Callback *) New_Map_Input_cb);
2268 	    Maps->Top = new Fl_Input (200, y, 70, 25, "Upper");
2269 	    Maps->Top->align (FL_ALIGN_BOTTOM);
2270 	    Maps->Top->callback ((Fl_Callback *) New_Map_Input_cb);
2271 	}
2272 	Maps->Color = new Flu_Combo_List (280, y, 160, 25, "Color");
2273 	Load_Color_Combo (Maps->Color);
2274 	Maps->Color->align (FL_ALIGN_TOP);
2275 	Maps->Color->callback ((Fl_Callback *) New_Map_Input_cb);
2276 	Load_Color_Combo (Maps->Color);
2277 	Maps->Color->align (FL_ALIGN_BOTTOM);
2278 	y += 45;
2279 	Fl_Button *om;
2280 
2281 	Fl_Button *mm;
2282 
2283 	om = Maps->Add_Button = new Fl_Button (180, y, 70, 25, "Add");
2284 	om->callback ((Fl_Callback *) New_Map_Add_cb, &one);
2285 	om->tooltip ("When active, press to transfer data in boxes to window above");
2286 	om->deactivate ();
2287 	mm = Maps->Remove_Button = new Fl_Button (270, y, 70, 25, "Remove");
2288 	mm->callback ((Fl_Callback *) New_Map_Add_cb, &zero);
2289 	mm->tooltip ("When active, press to remove highlighted line.");
2290 	mm->deactivate ();
2291 	y += 30;
2292 	Maps->MapsInstr2 = new Fl_Output (25, y, 450, 0,
2293 					  "Changes are temporary until \"Apply\" or \"Save\" is pressed.");
2294 	Maps->MapsInstr2->hide ();
2295 	Maps->MapsInstr2->align (FL_ALIGN_BOTTOM);
2296 	y += 30;
2297 	Maps->XMin = new Fl_Input (80, y, 100, 25, "XMin");
2298 	Maps->XMin->align (FL_ALIGN_BOTTOM);
2299 	Maps->XMin->color ((Fl_Color) 17);
2300 	Maps->YMin = new Fl_Input (200, y, 100, 25, "YMin");
2301 	Maps->YMin->align (FL_ALIGN_BOTTOM);
2302 	Maps->YMin->color ((Fl_Color) 17);
2303 	Maps->ZMin = new Fl_Input (320, y, 100, 25, "ZMin");
2304 	Maps->ZMin->align (FL_ALIGN_BOTTOM);
2305 	Maps->ZMin->color ((Fl_Color) 17);
2306 	y += 55;
2307 	Maps->XMax = new Fl_Input (80, y, 100, 25, "XMax");
2308 	Maps->XMax->align (FL_ALIGN_BOTTOM);
2309 	Maps->XMax->color ((Fl_Color) 17);
2310 	Maps->YMax = new Fl_Input (200, y, 100, 25, "YMax");
2311 	Maps->YMax->align (FL_ALIGN_BOTTOM);
2312 	Maps->YMax->color ((Fl_Color) 17);
2313 	Maps->ZMax = new Fl_Input (320, y, 100, 25, "ZMax");
2314 	Maps->ZMax->align (FL_ALIGN_BOTTOM);
2315 	Maps->ZMax->color ((Fl_Color) 17);
2316 	y += 55;
2317 	if (drvui->modulated) {
2318 	    Maps->X4 = new Flu_Spinner (110, y, 50, 25, "x4");
2319 	    Maps->X4->value (x4Val);
2320 	    Maps->X4->minimum (Map_Info.x4lim[0]);
2321 	    Maps->X4->maximum (Map_Info.x4lim[1]);
2322 	    Maps->X4->step (x4step);
2323 	    Maps->X4->callback ((Fl_Callback *) Edit_Maps_Save_cb, &zero);
2324 	    if (x4step < 0.001)
2325 		Maps->X4->deactivate ();
2326 	    Maps->X5 = new Flu_Spinner (230, y, 50, 25, "x5");
2327 	    Maps->X5->value (x5Val);
2328 	    Maps->X5->minimum (Map_Info.x5lim[0]);
2329 	    Maps->X5->maximum (Map_Info.x5lim[1]);
2330 	    Maps->X5->step (x5step);
2331 	    Maps->X5->callback ((Fl_Callback *) Edit_Maps_Save_cb, &zero);
2332 	    if (x5step < 0.001)
2333 		Maps->X5->deactivate ();
2334 	    Maps->X6 = new Flu_Spinner (350, y, 50, 25, "x6");
2335 	    Maps->X6->value (x6Val);
2336 	    Maps->X6->minimum (Map_Info.x6lim[0]);
2337 	    Maps->X6->maximum (Map_Info.x6lim[1]);
2338 	    Maps->X6->step (x6step);
2339 	    Maps->X6->callback ((Fl_Callback *) Edit_Maps_Save_cb, &zero);
2340 	    if (x6step < 0.001)
2341 		Maps->X6->deactivate ();
2342 	    y += 55;
2343 	}
2344 	Fl_Button *q = new Fl_Button (195, y, 130, 25, "Edit 2D Map Slice");
2345 	q->tooltip("Choose 2D slice through arbitrary pplane");
2346 	q->callback((Fl_Callback *) Edit_Slice_cb);
2347 	y += 45;
2348 
2349 	Fl_Button *r = new Fl_Button (125, y, 70, 25, "Close");
2350 	r->tooltip ("Close this window and discard all changes.");
2351 	r->callback ((Fl_Callback *) Edit_Maps_Close_cb);
2352 	Fl_Button *s = new Fl_Button (325, y, 70, 25, "Save");
2353 
2354 	s->tooltip
2355 	    ("Apply current contents of top box to drawing, then close this window.");
2356 	s->callback ((Fl_Callback *) Edit_Maps_Save_cb, &one);
2357 	Fl_Button *a = new Fl_Button (225, y, 70, 25, "Apply");
2358 
2359 	a->tooltip
2360 	    ("Apply current contents of top box to drawing, but leave this window open.");
2361 	a->callback ((Fl_Callback *) Edit_Maps_Save_cb, &zero);
2362 #if !defined (WIN32) && !defined (__APPLE__)
2363 	Maps->Maps_Edit_Window->icon ((char *) drvui->icon);
2364 #endif
2365     }
2366     strcpy (widget, "");
2367     for (i = 1; i <= drvui->numOfFourierContours; i++) {	// fill in the widgets
2368 	if (!drvui->Fourier2d) {
2369 	    if (drvui->fourier[i].FourierContourSolid)
2370 		strcpy (type, "solid");
2371 	    else
2372 		strcpy (type, "mesh ");
2373 	    sprintf (string, "%8.3f     %6s    %s\n",
2374 		     drvui->fourier[i].FourierContourLevel, type,
2375 		     drvui->fourier[i].FourierContourColor);
2376 	} else {
2377 	    sprintf (string, "%7.3f %7.3f %7.3f %s\n",
2378 		     drvui->fourier[i].FourierContourLevel,
2379 		     drvui->fourier[i].FourierContourStep,
2380 		     drvui->fourier[i].FourierContourTop,
2381 		     drvui->fourier[i].FourierContourColor);
2382 	}
2383 	strcat (widget, string);
2384     }
2385     Maps->MapsBuffer->text (widget);
2386     if (ReadFourMap) {
2387 	if (FourierMapType == 1)
2388 	    Maps->MapType->value ("GSAS - grd");
2389 	if (FourierMapType == 2)
2390 	    Maps->MapType->value ("JANA - stf");
2391 	if (FourierMapType == 3)
2392 	    Maps->MapType->value ("WIEN - w2k");
2393 	if (FourierMapType == 4)
2394 	    Maps->MapType->value ("VASP - vsp");
2395 	if (FourierMapType == 5)
2396 	    Maps->MapType->value ("FullProf - flp");
2397 	if (FourierMapType == 6)
2398 	    Maps->MapType->value ("CIF FoFc - fcf");
2399 	if (FourierMapType == 7)
2400 	    Maps->MapType->value ("O Format - dn6");
2401 	if (FourierMapType == 8)
2402 	    Maps->MapType->value ("JANA FoFc - m80");
2403 	if (FourierMapType == 9)
2404 	    Maps->MapType->value ("Exciting - exc");
2405 	if (FourierMapType == 10)
2406 	    Maps->MapType->value ("JANA - m81");
2407 	if (FourierMapType == 11)
2408 	    Maps->MapType->value ("XCrysDen - xsf");
2409 	Maps->Filename->value (FourierFileName);
2410 	Maps_Frame_Combo_cb (NULL, NULL);
2411     }
2412     Maps->MapsInstr1->show ();
2413 
2414     Maps->Maps_Edit_Window->end ();
2415     Maps->Maps_Edit_Window->show ();
2416     MapType_cb ();
2417 }
2418 
2419 void
Edit_Maps_Close_cb(void)2420 Edit_Maps_Close_cb (void)
2421 {
2422     Maps->Maps_Edit_Window->~Fl_Window ();	// this window needs to be deleted
2423     delete (Maps->Maps_Edit_Window);	// not just killed (2d/3d nature might change)
2424     delete (Maps->MapsBuffer);
2425     delete (Maps);
2426     Maps = NULL;
2427     Restore_Working_Copy ();	// undo any changes
2428     Generate_Drawing (1);	// regenerate
2429 }
2430 
2431 void
Edit_Maps_Save_cb(Fl_Button *,int * save)2432 Edit_Maps_Save_cb (Fl_Button *, int *save)
2433 {
2434 // callback routine when 'save' or 'apply' button is pressed on the Edit Maps screen
2435     char type[5], color[40], widget[16382];
2436 
2437     unsigned int j, k;
2438 
2439     int i = 0;
2440 
2441     int Frame_No = 1;
2442 
2443     float level, step, top;
2444 
2445     char *selection = Maps->MapsBuffer->text ();
2446 
2447     if (drvui->max_frame > 1)
2448 	Frame_No = atoi (Maps->Frame_No->value ());
2449 
2450     strcpy (widget, selection);
2451     free (selection);
2452     if (strlen (widget) < 10) {
2453 	drvui->numOfFourierContours = 0;
2454 	strcpy (widget, "");
2455 	Maps->MapsBuffer->text (widget);
2456     } else {
2457 	while (strlen (widget) > 10) {
2458 	    i++;
2459 	    if (drvui->Fourier2d)
2460 		sscanf (widget, "%f %f %f %s", &level, &step, &top, color);
2461 	    else
2462 		sscanf (widget, "%f %s %s", &level, type, color);
2463 	    trim_string (color, 40);
2464 	    if (!strlen (color))
2465 		strcpy (color, "Gray20");
2466 	    drvui->fourier[i].FourierContourLevel = level;
2467 	    if (!drvui->Fourier2d) {
2468 		if (strncmp (type, "mesh", 4) == 0)
2469 		    drvui->fourier[i].FourierContourSolid = 0;
2470 		else
2471 		    drvui->fourier[i].FourierContourSolid = 1;
2472 	    } else {
2473 		drvui->fourier[i].FourierContourStep = step;
2474 		drvui->fourier[i].FourierContourTop = top;
2475 	    }
2476 	    strcpy (drvui->fourier[i].FourierContourColor, color);
2477 	    drvui->numOfFourierContours = i;
2478 	    for (j = 0; j < strlen (widget); j++) {
2479 		if (widget[j] == '\n')
2480 		    break;
2481 	    }
2482 	    for (j++, k = 0; j < strlen (widget); j++)
2483 		widget[k++] = widget[j];
2484 	    widget[k] = 0;
2485 	}
2486     }
2487     strcpy (widget, Maps->Filename->value ());
2488     if (strcmp (widget, FourierFileName)) {
2489 	strcpy (FourierFileName, widget);	// File name changed
2490 	if (FourierPt) {
2491 	    free (FourierPt);
2492 	    FourierPt = NULL;
2493 	}
2494     }
2495     if (!strcmp (Maps->MapType->value (), "GSAS - grd"))
2496 	FourierMapType = 1;
2497     if (!strcmp (Maps->MapType->value (), "JANA - stf"))
2498 	FourierMapType = 2;
2499     if (!strcmp (Maps->MapType->value (), "WIEN - w2k"))
2500 	FourierMapType = 3;
2501     if (!strcmp (Maps->MapType->value (), "VASP - vsp"))
2502 	FourierMapType = 4;
2503     if (!strcmp (Maps->MapType->value (), "FullProf - flp"))
2504 	FourierMapType = 5;
2505     if (!strcmp (Maps->MapType->value (), "CIF FoFc - fcf"))
2506 	FourierMapType = 6;
2507     if (!strcmp (Maps->MapType->value (), "O Format - dn6"))
2508 	FourierMapType = 7;
2509     if (!strcmp (Maps->MapType->value (), "JANA FoFc - m80"))
2510 	FourierMapType = 8;
2511     if (!strcmp (Maps->MapType->value (), "Exciting - exc"))
2512 	FourierMapType = 9;
2513     if (!strcmp (Maps->MapType->value (), "JANA - m81"))
2514 	FourierMapType = 10;
2515     if (!strcmp (Maps->MapType->value (), "XCrysDen - xsf"))
2516 	FourierMapType = 11;
2517     sscanf (Maps->XMin->value (), "%f", &drvui->frames[Frame_No].map_lim[0]);
2518     sscanf (Maps->YMin->value (), "%f", &drvui->frames[Frame_No].map_lim[1]);
2519     sscanf (Maps->ZMin->value (), "%f", &drvui->frames[Frame_No].map_lim[2]);
2520     sscanf (Maps->XMax->value (), "%f", &drvui->frames[Frame_No].map_lim[3]);
2521     sscanf (Maps->YMax->value (), "%f", &drvui->frames[Frame_No].map_lim[4]);
2522     sscanf (Maps->ZMax->value (), "%f", &drvui->frames[Frame_No].map_lim[5]);
2523     if (FourierMapType == 6 || FourierMapType == 8) {
2524 	if (const char *temp = Maps->MapCalcType->value ()) {
2525 	    int i = 0;
2526 
2527 	    if (!strcmp (temp, "Fo"))
2528 		i = 0;
2529 	    else if (!strcmp (temp, "Fc"))
2530 		i = 1;
2531 	    else if (!strcmp (temp, "Fo-Fc"))
2532 		i = 2;
2533 	    else if (!strcmp (temp, "2Fo-Fc"))
2534 		i = 3;
2535 	    if (i != Map_Info.map_type) {
2536 		Map_Info.map_type = i;
2537 		Map_Info.info_valid = 0;
2538 		if (FourierPt) {
2539 		    free (FourierPt);
2540 		    FourierPt = NULL;
2541 		}
2542 	    }
2543 	}
2544     }
2545     i = Map_Info.res;
2546     sscanf (Maps->Resolution->value (), "%i", &Map_Info.res);
2547     if (Map_Info.res <= 0) {
2548 	Map_Info.res = 1;
2549 	Maps->Resolution->value("1");
2550     }
2551     if ((int)i != Map_Info.res) {
2552  	if (FourierPt) {
2553 	    free (FourierPt);
2554 	    FourierPt = NULL;
2555 	}
2556     }
2557     if (drvui->modulated) {
2558 	if (x4step > 0.0f)
2559 	    drvui->frames[Frame_No].map_lim[6] = (float) Maps->X4->value ();
2560 	if (x5step > 0.0f)
2561 	    drvui->frames[Frame_No].map_lim[7] = (float) Maps->X5->value ();
2562 	if (x6step > 0.0f)
2563 	    drvui->frames[Frame_No].map_lim[8] = (float) Maps->X6->value ();
2564     }
2565     drvui->Str_File_Changed = 1;
2566     if (*save != 3) {
2567 	Save_Working_Copy ();
2568 	Maps->MapsInstr2->hide ();
2569     }
2570     if (*save == 1) {
2571 	Fl::delete_widget (Maps->Maps_Edit_Window);
2572 //      Maps->Maps_Edit_Window->~Fl_Window();         // this window needs to be deleted
2573 //      delete(Maps->Maps_Edit_Window);               // not just killed (2d/3d nature might change)
2574 //      delete(Maps->MapsBuffer);
2575 	delete (Maps);
2576 	Maps = NULL;
2577     }
2578     Update_Str (0);
2579     Generate_Drawing (0);
2580     Fl::redraw ();
2581 }
2582 
2583 void
Edit_Parmeters_cb(void)2584 Edit_Parmeters_cb (void)
2585 {
2586 // Callback routine to show the Edit Parameter screen and load the widgets on that page
2587     char string[40];
2588 
2589     if (!strlen (drvui->CurFile->value ())) {	// Make sure rendering enabled
2590 	Error_Box ("A Structure File must be selected first.");
2591 	return;
2592     }
2593     if (!edtprm) {
2594 	edtprm = new EditScreen;	// Create the screen
2595 	if (!Omit->nomits) {
2596 	    edtprm->ClearLastOmit->deactivate ();
2597 	    edtprm->ClearOmit->deactivate ();
2598 	}
2599 #if !defined (WIN32) && !defined (__APPLE__)
2600 	edtprm->editWindow->icon ((char *) drvui->icon);
2601 #endif
2602 	edtprm->show ();	// show it
2603     }
2604     sprintf (string, "%6.1f", printdist);	// load the bond limit distance widget
2605     edtprm->List->value (string);
2606     sprintf (string, "%5.2f", Magnification);	// Magnification widget
2607     edtprm->Magnification->value (string);
2608     if (drvui->noshadow)
2609 	edtprm->NoShadow->set ();
2610     if (Labels == 0)
2611 	edtprm->NoLabels->set ();
2612     if (domolcomp) {
2613 	sprintf (string, "%5.2f", drvui->mol_d);
2614 	edtprm->Mol_Comp_Dist->value (string);	// Molecule completion stuff
2615 	edtprm->MolCompButton->set ();	// set check button
2616     }
2617     sprintf (string, "%6.3f", DepthCue);
2618     edtprm->DepthCue->value (string);	// Depth Cue widget
2619     Load_Color_Combo (edtprm->Cell_Edge_Color);
2620     edtprm->Cell_Edge_Color->value (drvui->col_cell);	// load cell axis line color
2621     sprintf (string, "%6.3f", rad_cell);
2622     edtprm->Cell_Edge_Width->value (string);	//   and width
2623     sprintf (string, "%6.2f", drvui->polylimit);	// load polyhedral limit
2624     edtprm->Poly_Limit->value (string);
2625     sprintf (string, "%7.2f", drvui->Phong_Value);	// load phong value
2626     edtprm->Phong_Refl->value (string);
2627     sprintf (string, "%7.0f", drvui->Phong_Size);	//  and size
2628     edtprm->Phong_Size->value (string);
2629     sprintf (string, "%6.2f", drvui->ambient);	// load default POV ambient,
2630     edtprm->Ambient_Finish->value (string);
2631     sprintf (string, "%6.2f", drvui->diffuse);	// diffuse,
2632     edtprm->Diffuse_Finish->value (string);
2633     sprintf (string, "%6.2f", drvui->specular);	// specular finish and
2634     edtprm->Specular_Finish->value (string);
2635     sprintf (string, "%6.2f", drvui->roughness);	// surface roughness
2636     edtprm->Finish_Roughness->value (string);
2637     strcpy (string, drvui->col_bg);	// load background color
2638     Load_Color_Combo (edtprm->Background_Color);
2639     edtprm->Background_Color->value (string);
2640     sprintf (string, "%.3f", drvui->label_scale);
2641     edtprm->Label_Scale->value (string);
2642     edtprm->editWindow->show ();
2643 }
2644 
2645 void
Edit_Parmeters_Close_cb(Fl_Button *,void *)2646 Edit_Parmeters_Close_cb (Fl_Button *, void *)
2647 {
2648 // callback routine when the 'close' button is pushed
2649     edtprm->editWindow->hide ();	// hide the window
2650     Fl::redraw ();		// update the screen
2651 }
2652 
2653 void
Edit_Parmeters_Save_cb(Fl_Button *,int * tosave)2654 Edit_Parmeters_Save_cb (Fl_Button *, int *tosave)
2655 {
2656 // callback routine when 'save' or 'apply' button is pressed on the Edit Parameter screen
2657 
2658     Magnification = (float) atof (edtprm->Magnification->value ());	// extract data from widgets
2659     printdist = (float) atof (edtprm->List->value ());
2660     DepthCue = (float) atof (edtprm->DepthCue->value ());
2661     drvui->label_scale = (float) atof (edtprm->Label_Scale->value ());
2662     strcpy (drvui->col_cell, edtprm->Cell_Edge_Color->value ());
2663     trim_string (drvui->col_cell, 39);
2664     if (!strlen (drvui->col_cell))
2665 	strcpy (drvui->col_cell, "White");
2666     rad_cell = (float) atof (edtprm->Cell_Edge_Width->value ());
2667     drvui->polylimit = (float) atof (edtprm->Poly_Limit->value ());
2668     drvui->Phong_Value = (float) atof (edtprm->Phong_Refl->value ());
2669     drvui->Phong_Size = (float) atof (edtprm->Phong_Size->value ());
2670     drvui->ambient = (float) atof (edtprm->Ambient_Finish->value ());
2671     drvui->diffuse = (float) atof (edtprm->Diffuse_Finish->value ());
2672     drvui->specular = (float) atof (edtprm->Specular_Finish->value ());
2673     drvui->roughness = (float) atof (edtprm->Finish_Roughness->value ());
2674     strcpy (drvui->col_bg, edtprm->Background_Color->value ());
2675     trim_string (drvui->col_bg, 39);
2676     if (!strlen (drvui->col_bg))
2677 	strcpy (drvui->col_bg, "White");
2678     drvui->noshadow = 0;
2679     if (edtprm->NoShadow->value ())
2680 	drvui->noshadow = 1;
2681     Labels = 1;
2682     if (edtprm->NoLabels->value ()) {
2683 	int i, j = 1, k, l;
2684 
2685 	Labels = 0;
2686 	for (i = 1; i < drvui->nlabel; i++) {
2687 	    if (!strcmp (drvui->labels[i].label_label, "a"))
2688 		drvui->labels[i].label_fn = 0;
2689 	    if (!strcmp (drvui->labels[i].label_label, "b"))
2690 		drvui->labels[i].label_fn = 0;
2691 	    if (!strcmp (drvui->labels[i].label_label, "c"))
2692 		drvui->labels[i].label_fn = 0;
2693 	    if (!strcmp (drvui->labels[i].label_label, "o"))
2694 		drvui->labels[i].label_fn = 0;
2695 	    if (!strcmp (drvui->labels[i].label_label, "triple_vect"))
2696 		drvui->labels[i].label_fn = 0;
2697 	}
2698 	for (i = 1; i < drvui->nlabel; i++) {
2699 	    if (drvui->labels[i].label_fn > 0)
2700 		j++;
2701 	    if (j != i) {
2702 		l = j;
2703 		for (k = i + 1; k < drvui->nlabel; k++) {
2704 		    drvui->labels[l].label_fn = drvui->labels[k].label_fn;
2705 		    strcpy (drvui->labels[l].label_label, drvui->labels[k].label_label);
2706 		    drvui->labels[l].label_x[0] = drvui->labels[k].label_x[0];
2707 		    drvui->labels[l].label_x[1] = drvui->labels[k].label_x[1];
2708 		    drvui->labels[l++].label_x[2] = drvui->labels[k].label_x[2];
2709 		}
2710 	    }
2711 	}
2712 	drvui->nlabel = j;
2713     } else {
2714 	label_cell ();
2715     }
2716     if (edtprm->MolCompButton->value () != 0) {
2717 	float temp;
2718 
2719 	temp = (float) atof (edtprm->Mol_Comp_Dist->value ());
2720 	if (temp > 3.5f) {
2721 	    char string[100];
2722 
2723 	    sprintf (string, "A molecular completion distance of %5.2f is very\n"
2724 		     "large. Are you sure you wish to continue?", temp);
2725 	    if (!fl_choice (string, "No", "Yes", NULL))
2726 		return;
2727 	}
2728 	drvui->mol_d = temp;
2729 	domolcomp = 1;
2730     } else {
2731 	drvui->mol_d = 0.0;
2732 	domolcomp = 0;
2733     }
2734     if (edtprm->ClearOmit->value () != 0) {
2735 	Omit->nomits = 0;	// dump the omit list if ClearOmit button checked
2736 	edtprm->ClearOmit->value (0);    // and disarm the checkbutton afterwards
2737 	edtprm->ClearLastOmit->deactivate ();
2738 	edtprm->ClearOmit->deactivate ();
2739     }
2740     drvui->Str_File_Changed = 1;
2741     Update_Str (0);		// update the 'str' file
2742     Generate_Drawing (0);	// regenerate the drawing
2743     if (*tosave) {
2744 	edtprm->editWindow->hide ();	// hide the window if 'save'
2745     }
2746     Fl::redraw ();		// update the screen
2747 }
2748 
2749 void
Edit_Polyhedra_cb(void)2750 Edit_Polyhedra_cb (void)
2751 {
2752 // callback routine to load polyhedra edit screen
2753     char string[100];
2754 
2755     static int one = 1;
2756 
2757     static int zero = 0;
2758 
2759     int i;
2760 
2761     int y = 5;
2762 
2763     if (!strlen (drvui->CurFile->value ())) {	// Make sure rendering enabled
2764 	Error_Box ("A Structure File must be selected first.");
2765 	return;
2766     }
2767 /*
2768     if (!natom) {         // No atoms, no polyhedra...
2769         Error_Box("This structure file does not contain any atoms.");
2770         return;
2771     }
2772 */
2773     Save_Working_Copy ();
2774     if (!Polyhedra) {
2775 	Polyhedra = new PolyParam;	// new instance of the polyhedra parameters
2776 	Polyhedra->Polyhedra_Edit_Window =
2777 	    new Fl_Window (50, 0, 560, 560, "Edit Polyhedral/Plane Parameters");
2778 	Polyhedra->Polyhedra_Edit_Window->
2779 	    callback ((Fl_Callback *) Edit_Polyhedra_Close_cb);
2780 	if (drvui->max_frame > 1) {
2781 	    Flu_Combo_List *o = Polyhedra->Frame_No =
2782 		new Flu_Combo_List (220, y, 75, 25, "Frame No.");
2783 	    o->align (FL_ALIGN_TOP);
2784 	    o->callback (Polyhedra_Frame_Combo_cb);
2785 	    o->labelfont (1);
2786 	    for (i = 1; i <= drvui->max_frame; i++) {
2787 		sprintf (string, "%d", i);
2788 		o->list.add (string);
2789 	    }
2790 	    o->pop_height (20 * drvui->max_frame);
2791 	    o->value ("1");
2792 	}
2793 	y += 50;
2794 	Polyhedra->Polyhedra_Edit = new Fl_Text_Editor (25, y, 450, 95,
2795 							"     Type    From   To   Min d   Max d    Color          ");
2796 	Polyhedra->PolyhedraBuffer = new Fl_Text_Buffer;
2797 	Polyhedra->PolyhedraBuffer->
2798 	    add_modify_callback ((Fl_Text_Modify_Cb) Modify_Polyhedra_cb, (void *) NULL);
2799 	Polyhedra->Polyhedra_Edit->textfont (FL_COURIER);
2800 	Polyhedra->Polyhedra_Edit->textsize (12);
2801 	Polyhedra->Polyhedra_Edit->buffer (Polyhedra->PolyhedraBuffer);
2802 	Polyhedra->Polyhedra_Edit->labelfont (FL_COURIER_BOLD);
2803 	y += 105;
2804 	Polyhedra->PolyInstr = new Fl_Output (135, y, 250, 0, "Press 'Add' to replace "
2805 					      "selected line - 'Remove' to delete it");
2806 	Polyhedra->PolyInstr->hide ();
2807 	Polyhedra->PolyInstr->align (FL_ALIGN_BOTTOM);
2808 	Polyhedra->PolyInstr1 = new Fl_Output (135, y, 250, 0, "Highlight text above "
2809 					       "or double click to edit line");
2810 	Polyhedra->PolyInstr1->hide ();
2811 	Polyhedra->PolyInstr1->align (FL_ALIGN_BOTTOM);
2812 	y += 40;
2813 	Polyhedra->New_Polyhedra_From = new Fl_Input (20, y, 50, 25, "From");
2814 	Polyhedra->New_Polyhedra_From->align (FL_ALIGN_TOP);
2815 	Polyhedra->New_Polyhedra_From->labelfont (1);
2816 	Fl_Input *op = Polyhedra->New_Polyhedra_To = new Fl_Input (80, y, 50, 25, "To");
2817 
2818 	op->align (FL_ALIGN_TOP);
2819 	op->callback ((Fl_Callback *) New_Polyhedra_Input_cb);
2820 	op->labelfont (1);
2821 	Fl_Input *m = Polyhedra->New_Polyhedra_Min =
2822 	    new Fl_Input (140, y, 50, 25, "Min d");
2823 	m->align (FL_ALIGN_TOP);
2824 	m->callback ((Fl_Callback *) New_Polyhedra_Input_cb);
2825 	m->labelfont (1);
2826 	Fl_Input *os = Polyhedra->New_Polyhedra_Max =
2827 	    new Fl_Input (200, y, 50, 25, "Max d");
2828 	os->align (FL_ALIGN_TOP);
2829 	os->callback ((Fl_Callback *) New_Polyhedra_Input_cb);
2830 	os->labelfont (1);
2831 	Flu_Combo_List *ot = Polyhedra->New_Polyhedra_Color =
2832 	    new Flu_Combo_List (260, y, 160, 25, "Color");
2833 	ot->align (FL_ALIGN_TOP);
2834 	ot->callback ((Fl_Callback *) New_Polyhedra_Input_cb);
2835 	ot->labelfont (1);
2836 	Load_Color_Combo (ot);
2837 	Fl_Input *ou = Polyhedra->New_Polyhedra_Transp =
2838 	    new Fl_Input (430, y, 50, 25, "Transp.");
2839 	ou->callback ((Fl_Callback *) New_Polyhedra_Input_cb);
2840 	ou->align (FL_ALIGN_TOP);
2841 	ou->labelfont (1);
2842 	y += 40;
2843 	Polyhedra->Edge_Radius = new Fl_Input (150, y, 100, 25, "Edge Radius");
2844 	Polyhedra->Edge_Radius->align (FL_ALIGN_TOP);
2845 	Polyhedra->Edge_Radius->labelfont (1);
2846 	Polyhedra->Edge_Color = new Flu_Combo_List (270, y, 120, 25, "Edge Color");
2847 	Polyhedra->Edge_Color->align (FL_ALIGN_TOP);
2848 	Polyhedra->Edge_Color->labelfont (1);
2849 	Load_Color_Combo (Polyhedra->Edge_Color);
2850 	Polyhedra->Edge_Color->value (drvui->col_edge);
2851 	sprintf (string, "%6.3f", drvui->rad_edge);
2852 	Polyhedra->Edge_Radius->value (string);
2853 	y += 40;
2854 	Fl_Button *om = Polyhedra->New_Polyhedra_Add =
2855 	    new Fl_Button (180, y, 70, 25, "Add");
2856 	om->callback ((Fl_Callback *) New_Polyhedra_Add_cb, &one);
2857 	om->tooltip ("When active, press to transfer data in boxes to window above");
2858 	om->deactivate ();
2859 	Fl_Button *mm = Polyhedra->New_Polyhedra_Remove =
2860 	    new Fl_Button (270, y, 70, 25, "Remove");
2861 	mm->callback ((Fl_Callback *) New_Polyhedra_Add_cb, &zero);
2862 	mm->tooltip ("When active, press to remove highlighted line.");
2863 	mm->deactivate ();
2864 	y += 30;
2865 	Polyhedra->PolyInstr2 = new Fl_Output (25, y, 470, 0,
2866 					       "Changes are temporary until \"Apply\" or \"Save\" is pressed.");
2867 	Polyhedra->PolyInstr2->hide ();
2868 	Polyhedra->PolyInstr2->align (FL_ALIGN_BOTTOM);
2869 	y += 40;
2870 	Fl_Group *qq = new Fl_Group (30, y, 150, 90, "Polyhedra/Plane Type");
2871 
2872 	qq->labelfont (1);
2873 	qq->box (FL_THIN_UP_BOX);
2874 	Polyhedra->Polysz = new Fl_Radio_Button (40, y + 10, 12, 12, "Polysz (PS) Style");
2875 	Polyhedra->Polysz->type (102);
2876 	Polyhedra->Polysz->selection_color ((Fl_Color) 1);
2877 	Polyhedra->Polysz->align (FL_ALIGN_RIGHT);
2878 	Polyhedra->Polysz->set ();
2879 	Polyhedra->Polyvert =
2880 	    new Fl_Radio_Button (40, y + 30, 12, 12, "Polyvert (PV) Style");
2881 	Polyhedra->Polyvert->type (102);
2882 	Polyhedra->Polyvert->selection_color ((Fl_Color) 1);
2883 	Polyhedra->Polyvert->align (FL_ALIGN_RIGHT);
2884 	Polyhedra->Polyshell =
2885 	    new Fl_Radio_Button (40, y + 50, 12, 12, "Shell (SH) Style");
2886 	Polyhedra->Polyshell->type (102);
2887 	Polyhedra->Polyshell->selection_color ((Fl_Color) 1);
2888 	Polyhedra->Polyshell->align (FL_ALIGN_RIGHT);
2889 	Polyhedra->Plane = new Fl_Radio_Button (40, y + 70, 12, 12, "Plane (PL) Style");
2890 	Polyhedra->Plane->type (102);
2891 	Polyhedra->Plane->selection_color ((Fl_Color) 1);
2892 	Polyhedra->Plane->align (FL_ALIGN_RIGHT);
2893 	qq->end ();
2894 	Flu_Combo_List *o = Polyhedra->Polyhedra_Combo =
2895 	    new Flu_Combo_List (200, y, 100, 25, "'From' Atom");
2896 	o->align (FL_ALIGN_TOP);
2897 	o->labelfont (1);
2898 	o->callback (Polyhedra_Combo_cb);
2899 	Fl_Text_Editor *p =
2900 	    new Fl_Text_Editor (310, y, 200, 100, "'To' Atoms & Distances");
2901 	p->textfont (FL_COURIER);
2902 	p->textsize (14);
2903 	p->align (FL_ALIGN_TOP);
2904 	p->labelfont (1);
2905 	Polyhedra->Polyhedra_Output_Buffer = new Fl_Text_Buffer;
2906 	Polyhedra->Polyhedra_Output_Buffer->
2907 	    add_modify_callback ((Fl_Text_Modify_Cb) Modify_Polyhedra_Distance_cb,
2908 				 (void *) NULL);
2909 	p->buffer (Polyhedra->Polyhedra_Output_Buffer);
2910 	y += 120;
2911 	Polyhedra->Def_Edge_Radius = new Fl_Input (145, y, 100, 25, "Default Edge Radius");
2912 	Polyhedra->Def_Edge_Radius->align (FL_ALIGN_TOP);
2913 	Polyhedra->Def_Edge_Radius->labelfont (1);
2914 	Polyhedra->Def_Edge_Color = new Flu_Combo_List (275, y, 120, 25, "Default Edge Color");
2915 	Polyhedra->Def_Edge_Color->align (FL_ALIGN_TOP);
2916 	Polyhedra->Def_Edge_Color->labelfont (1);
2917 	Load_Color_Combo (Polyhedra->Def_Edge_Color);
2918 	Polyhedra->Def_Edge_Color->value (drvui->col_edge);
2919 	sprintf (string, "%6.3f", drvui->rad_edge);
2920 	Polyhedra->Def_Edge_Radius->value (string);
2921 #if !defined (WIN32) && !defined (__APPLE__)
2922 	Polyhedra->Polyhedra_Edit_Window->icon ((char *) drvui->icon);
2923 #endif
2924 	y += 35;
2925 	Fl_Button *r = new Fl_Button (125, y, 70, 25, "Close");
2926 
2927 	r->tooltip ("Close this window and discard all changes.");
2928 	r->callback ((Fl_Callback *) Edit_Polyhedra_Close_cb);
2929 	Fl_Button *a = new Fl_Button (225, y, 70, 25, "Apply");
2930 
2931 	a->tooltip
2932 	    ("Apply current contents of top box to drawing, but leave this window open.");
2933 	a->callback ((Fl_Callback *) Edit_Polyhedra_Save_cb, &zero);
2934 	Fl_Button *s = new Fl_Button (325, y, 70, 25, "Save");
2935 
2936 	s->tooltip
2937 	    ("Apply current contents of top box to drawing, then close this window.");
2938 	s->callback ((Fl_Callback *) Edit_Polyhedra_Save_cb, &one);
2939 	Polyhedra->Polyhedra_Edit_Window->end ();
2940     }
2941     Polyhedra_Frame_Combo_cb (NULL, NULL);
2942     Polyhedra->Polyhedra_Edit_Window->show ();
2943 }
2944 
2945 void
Load_Color_Combo(Flu_Combo_List * ot)2946 Load_Color_Combo (Flu_Combo_List * ot)
2947 {
2948     int j, k = strlen (Colors_Combo), l = 0;
2949 
2950     char string[20];
2951 
2952     FILE *colinc;
2953 
2954     if (ot->list.size () > 1)
2955 	return;
2956 
2957     // look for private colors.inc file first
2958     colinc = NULL;
2959     if (strlen (drvui->POV_Include) > 10) {
2960 	colinc = fopen (drvui->POV_Include, "r");
2961     }
2962     if (!colinc) {
2963 	char* a, b[30];
2964 	char POV_incpath[255] = "\0";
2965 	strncpy (b, drvui->POV_Options, 29);
2966 	b[29] = '\0';
2967 	a = strstr (b, "+L");
2968 	if (a != NULL) {
2969 	    sscanf (a + 2, "%s", POV_incpath);
2970 	    if (POV_incpath != NULL) {
2971 		strcat (POV_incpath, "/colors.inc");
2972 		colinc = fopen (POV_incpath, "r");
2973 		if (colinc) {
2974 		    strcpy (drvui->POV_Include, POV_incpath);
2975 		    WriteConfig ();
2976 		}
2977 	    }
2978 	}
2979     }
2980     if (colinc != NULL) { // load color names from private colors.inc file
2981 	char line[80];
2982 	char keyword[20], thecolor[20];
2983 	float thered,thegreen,theblue;
2984 
2985 	while (!feof (colinc)) {
2986 	    if (fgets (line, 80, colinc) == NULL)
2987 		continue;
2988 	    if (!strstr (line, "#declare") || strstr(line,"Colors_Inc"))
2989 		continue;
2990 	    sscanf (line, "%s %s = color red %f green %f blue %f", keyword, thecolor,
2991 		    &thered, &thegreen, &theblue);
2992 	    ot->list.add(thecolor);
2993 	}
2994 	fclose (colinc);
2995     } else {  // colors.inc not given, use built-in color list corresponding to povray 3.6
2996 
2997 	for (j = 0; j < k; j++) {
2998 	    if (Colors_Combo[j] != '\n') {
2999 		string[l++] = Colors_Combo[j];
3000 	    } else {
3001 		string[l++] = 0;
3002 		l = 0;
3003 		ot->list.add (string);
3004 	    }
3005 	}
3006     }
3007     ot->pop_height (300);
3008 }
3009 
3010 
3011 
3012 void
Edit_Modparms_Close_cb()3013 Edit_Modparms_Close_cb ()
3014 {
3015     Modparms->Mods_Edit_Window->hide ();
3016 
3017     drvui->modulated = Modparms->saved_avg;
3018     if (drvui->modulated == -1)
3019 	Modparms->Mod_average->set ();
3020     else
3021 	Modparms->Mod_average->clear ();
3022     for (int i = 0; i < 3; i++)
3023 	drvui->phaseshift[i] = Modparms->saved_t[i];
3024     Modparms->Mod_t0->value (drvui->phaseshift[0]);
3025     Modparms->Mod_t1->value (drvui->phaseshift[1]);
3026     Modparms->Mod_t2->value (drvui->phaseshift[2]);
3027     if (Modparms->Mod_average->value () != 0) {
3028 	Modparms->Mod_t0->deactivate ();
3029 	Modparms->Mod_t1->deactivate ();
3030 	Modparms->Mod_t2->deactivate ();
3031     } else {
3032 	Modparms->Mod_t0->activate ();
3033 	if (drvui->no_cell_vec > 1)
3034 	    Modparms->Mod_t1->activate ();
3035 	if (drvui->no_cell_vec > 2)
3036 	    Modparms->Mod_t2->activate ();
3037     }
3038 
3039     drvui->Str_File_Changed = 1;
3040     Update_Str (0);		// update the 'str' file
3041     Generate_Drawing (1);	// regenerate
3042     Fl::redraw ();		// update the screen
3043 }
3044 
3045 void
Edit_Modparms_Change_cb()3046 Edit_Modparms_Change_cb ()
3047 {
3048     if (Modparms->Mod_average->value () != 0) {
3049 	drvui->modulated = -1;
3050 	Modparms->Mod_t0->deactivate ();
3051 	Modparms->Mod_t1->deactivate ();
3052 	Modparms->Mod_t2->deactivate ();
3053     } else {
3054 	drvui->modulated = 1;
3055 	Modparms->Mod_t0->activate ();
3056 	if (drvui->no_cell_vec > 1)
3057 	    Modparms->Mod_t1->activate ();
3058 	if (drvui->no_cell_vec > 2)
3059 	    Modparms->Mod_t2->activate ();
3060     }
3061 
3062     drvui->phaseshift[0] = (float) Modparms->Mod_t0->value ();
3063     drvui->phaseshift[1] = (float) Modparms->Mod_t1->value ();
3064     drvui->phaseshift[2] = (float) Modparms->Mod_t2->value ();
3065 
3066     drvui->Str_File_Changed = 1;
3067     Update_Str (0);		// update the 'str' file
3068     Generate_Drawing (0);
3069     Fl::redraw ();
3070 }
3071 
3072 void
Edit_Modparms_Save_cb(Fl_Button *,int * save)3073 Edit_Modparms_Save_cb (Fl_Button *, int *save)
3074 {
3075     int i, j, k, n;
3076 
3077     float d1, d2;
3078 
3079     char atom1[5], numb[5], widget[16382];
3080 
3081     if (Modparms->Mod_average->value () != 0) {
3082 	drvui->modulated = -1;
3083 	Modparms->Mod_t0->deactivate ();
3084 	Modparms->Mod_t1->deactivate ();
3085 	Modparms->Mod_t2->deactivate ();
3086     } else {
3087 	drvui->modulated = 1;
3088 	Modparms->Mod_t0->activate ();
3089 	if (drvui->no_cell_vec > 1)
3090 	    Modparms->Mod_t1->activate ();
3091 	if (drvui->no_cell_vec > 2)
3092 	    Modparms->Mod_t2->activate ();
3093     }
3094     drvui->phaseshift[0] = (float) Modparms->Mod_t0->value ();
3095     drvui->phaseshift[1] = (float) Modparms->Mod_t1->value ();
3096     drvui->phaseshift[2] = (float) Modparms->Mod_t2->value ();
3097     Modparms->saved_avg = drvui->modulated;
3098     for (i = 0; i < 3; i++)
3099 	Modparms->saved_t[i] = drvui->phaseshift[i];
3100 
3101     for (j = 0; j < natom; j++) {
3102 	drvui->atoms[j].occupancy = 1.;
3103 	drvui->atoms[j].min_occ = 0.;
3104     }
3105     char *selection = Modparms->Occ_Buffer->text ();
3106 
3107     strcpy (widget, selection);
3108     free (selection);
3109     if (strlen (widget) < 10) {
3110 	strcpy (widget, "");
3111 	Modparms->Occ_Buffer->text (widget);
3112     } else {
3113 	while (strlen (widget) > 10) {
3114 	    memset (atom1, 0, 5);
3115 	    (void) sscanf (widget, "%4c %s %f %f", atom1, numb, &d1, &d2);
3116 	    if (strstr (numb, "*"))
3117 		n = -1;
3118 	    else
3119 		(void) sscanf (numb, "%d", &n);
3120 	    for (j = 0; j < natom; j++) {
3121 		if (check_atom_name (atom1, drvui->atoms[j].atom_l) &&
3122 		    (n == -1 || n == drvui->atoms[j].sv_atom_n)) {
3123 		    drvui->atoms[j].occupancy = d1;
3124 		    drvui->atoms[j].min_occ = d2;
3125 		    break;
3126 		}
3127 	    }
3128 	    for (j = 0; j < (int) strlen (widget); j++) {
3129 		if (widget[j] == '\n')
3130 		    break;
3131 	    }
3132 	    for (j++, k = 0; j < (int) strlen (widget); j++)
3133 		widget[k++] = widget[j];
3134 	    widget[k] = 0;
3135 	}
3136     }
3137     drvui->Str_File_Changed = 1;
3138     Update_Str (0);		// update the 'str' file
3139     Generate_Drawing (0);	// regenerate the drawing
3140 
3141     if (*save)
3142 	Modparms->Mods_Edit_Window->hide ();	// hide the window if 'save'
3143     Fl::redraw ();		// update the screen
3144 }
3145 
3146 void
Edit_Modparms_cb(void)3147 Edit_Modparms_cb (void)
3148 {
3149 // Callback routine to show the Modulation Options screen and load the widgets on that page
3150     static int one = 1;
3151 
3152     static int zero = 0;
3153 
3154     char string[10], buffer[40];
3155 
3156     int i, y;
3157 
3158     if (!strlen (drvui->CurFile->value ())) {	// Make sure rendering enabled
3159 	Error_Box ("A Structure File must be selected first.");
3160 	return;
3161     }
3162     if (drvui->modulated == 0) {	// Make sure we have a modulated structure
3163 	Error_Box ("This Structure does not appear to be modulated.");
3164 	return;
3165     }
3166     if (!Modparms) {
3167 	Modparms = new ModParam;	// new instance of the modulation parameters
3168 	Modparms->Mods_Edit_Window =
3169 	    new Fl_Window (50, 50, 360, 500, "Edit Modulation Parameters");
3170 	Modparms->Mods_Edit_Window->callback ((Fl_Callback *) Edit_Modparms_Close_cb);
3171 	y = 30;
3172 	Modparms->Mod_average =
3173 	    new Fl_Check_Button (70, y, 225, 25, "Display average structure only");
3174 	if (drvui->modulated == -1)
3175 	    Modparms->Mod_average->set ();
3176 	Modparms->Mod_average->callback ((Fl_Callback *) Edit_Modparms_Change_cb);
3177 	y += 35;
3178 	Modparms->Mod_t0 =
3179 	    new Flu_Spinner (220, y, 100, 25, "Phase shift t (1st direction)");
3180 	Modparms->Mod_t0->value (drvui->phaseshift[0]);
3181 	Modparms->Mod_t0->callback ((Fl_Callback *) Edit_Modparms_Change_cb);
3182 	y += 35;
3183 	Modparms->Mod_t1 =
3184 	    new Flu_Spinner (220, y, 100, 25, "Phase shift t (2nd direction)");
3185 	Modparms->Mod_t1->value (drvui->phaseshift[1]);
3186 	Modparms->Mod_t1->callback ((Fl_Callback *) Edit_Modparms_Change_cb);
3187 	y += 35;
3188 	Modparms->Mod_t2 =
3189 	    new Flu_Spinner (220, y, 100, 25, "Phase shift t (3rd direction)");
3190 	Modparms->Mod_t2->value (drvui->phaseshift[2]);
3191 	Modparms->Mod_t2->callback ((Fl_Callback *) Edit_Modparms_Change_cb);
3192 
3193 	if (Modparms->Mod_average->value () != 0) {
3194 	    Modparms->Mod_t0->deactivate ();
3195 	    Modparms->Mod_t1->deactivate ();
3196 	    Modparms->Mod_t2->deactivate ();
3197 	}
3198 	if (drvui->no_cell_vec < 2)
3199 	    Modparms->Mod_t1->deactivate ();
3200 	if (drvui->no_cell_vec < 3)
3201 	    Modparms->Mod_t2->deactivate ();
3202 	y += 65;
3203 
3204 	Modparms->Occ_Edit = new Fl_Text_Editor (25, y, 310, 80,
3205 						 "Atom     Occupancy     Minimum");
3206 	Modparms->Occ_Buffer = new Fl_Text_Buffer;
3207 	for (i = 0; i < natom; i++) {
3208 	    if (drvui->atoms[i].min_occ > 0.) {
3209 		sprintf (buffer, "%4s%2d %15.3f %15.3f\n", drvui->atoms[i].atom_l,
3210 			 drvui->atoms[i].sv_atom_n, drvui->atoms[i].occupancy,
3211 			 drvui->atoms[i].min_occ);
3212 		Modparms->Occ_Buffer->append (buffer);
3213 	    }
3214 	}
3215 	Modparms->Occ_Buffer->add_modify_callback ((Fl_Text_Modify_Cb) Modify_Occ_cb,
3216 						   (void *) NULL);
3217 	y += 85;
3218 	Modparms->Occ_Instr = new Fl_Output (0, y, 400, 0, "Press 'Add' to replace "
3219 					     "line - 'Remove' to delete");
3220 	Modparms->Occ_Instr->hide ();
3221 	Modparms->Occ_Instr->align (FL_ALIGN_BOTTOM);
3222 	Modparms->Occ_Instr1 = new Fl_Output (0, y, 400, 0,
3223 					      "Highlight or double-click text above to edit");
3224 	Modparms->Occ_Instr1->hide ();
3225 	Modparms->Occ_Instr1->align (FL_ALIGN_BOTTOM);
3226 	Modparms->Occ_Edit->textfont (FL_COURIER);
3227 	Modparms->Occ_Edit->textsize (12);
3228 	Modparms->Occ_Edit->buffer (Modparms->Occ_Buffer);
3229 	Modparms->Occ_Edit->labelfont (FL_COURIER_BOLD);
3230 	y += 40;
3231 	Flu_Combo_List *o = Modparms->Occ_Combo =
3232 	    new Flu_Combo_List (35, y, 100, 25, "Atom");
3233 	o->align (FL_ALIGN_TOP);
3234 	o->callback (Occ_Combo_cb);
3235 	o->labelfont (1);
3236 	for (i = 0; i < natom; i++)
3237 	    if (drvui->atoms[i].occ_ismod != 0) {
3238 		memset (string, 0, 10);
3239 		sprintf (string, "%4s%2d", drvui->atoms[i].atom_l,
3240 			 drvui->atoms[i].sv_atom_n);
3241 		Modparms->Occ_Combo->list.add (string);
3242 	    }
3243 	Fl_Input *oa = Modparms->New_Occ_Avg = new Fl_Input (155, y, 60, 25, "Avg. occ.");
3244 
3245 	oa->align (FL_ALIGN_TOP);
3246 	oa->callback ((Fl_Callback *) New_Occ_Input_cb);
3247 	oa->labelfont (1);
3248 	Fl_Input *om = Modparms->New_Occ_Min = new Fl_Input (235, y, 60, 25, "Min. occ.");
3249 
3250 	om->align (FL_ALIGN_TOP);
3251 	om->callback ((Fl_Callback *) New_Occ_Input_cb);
3252 	om->labelfont (1);
3253 	y += 30;
3254 	Fl_Button *oba = Modparms->New_Occ_Add = new Fl_Button (105, y, 70, 25, "Add");
3255 
3256 	oba->callback ((Fl_Callback *) New_Occ_Add_cb, &one);
3257 	oba->tooltip ("When active, press to transfer data in boxes to window above");
3258 	oba->deactivate ();
3259 	Fl_Button *obr = Modparms->New_Occ_Remove =
3260 	    new Fl_Button (195, y, 70, 25, "Remove");
3261 	obr->callback ((Fl_Callback *) New_Occ_Add_cb, &zero);
3262 	obr->tooltip ("When active, press to remove highlighted line.");
3263 	obr->deactivate ();
3264 
3265 	y += 45;
3266 	Fl_Button *q = new Fl_Button (125, y, 130, 25, "Movie generation");
3267 	q->tooltip("Choose parameters for POVray movie generation from t1 sampling");
3268 	q->callback((Fl_Callback *) Automation_Edit_cb);
3269 
3270 	y += 45;
3271 	Fl_Button *r = new Fl_Button (50, y, 70, 25, "Close");
3272 
3273 	r->tooltip ("Close this window and discard all changes.");
3274 	r->callback ((Fl_Callback *) Edit_Modparms_Close_cb);
3275 	Fl_Button *a = new Fl_Button (150, y, 70, 25, "Apply");
3276 
3277 	a->tooltip ("Apply current settings to drawing, but leave this window open.");
3278 	a->callback ((Fl_Callback *) Edit_Modparms_Save_cb, &zero);
3279 	Fl_Button *s = new Fl_Button (250, y, 70, 25, "Save");
3280 
3281 	s->tooltip ("Apply current settings to drawing, then close this window.");
3282 	s->callback ((Fl_Callback *) Edit_Modparms_Save_cb, &one);
3283 
3284 #if !defined (WIN32) && !defined (__APPLE__)
3285 	Modparms->Mods_Edit_Window->icon ((char *) drvui->icon);
3286 #endif
3287 
3288 	Modparms->Mods_Edit_Window->end ();
3289     }
3290     Modparms->saved_avg = drvui->modulated;
3291     for (i = 0; i < 3; i++)
3292 	Modparms->saved_t[i] = drvui->phaseshift[i];
3293     Modparms->Mods_Edit_Window->show ();
3294 }
3295 
3296 void
Edit_Slice_cb(void)3297 Edit_Slice_cb (void)
3298 {
3299 // Callback routine to show the Map Slice screen and load the widgets on that page
3300     static int one = 1;
3301     static int zero = 0;
3302     int y = 30, x;
3303 
3304     if (!strlen (drvui->CurFile->value ())) {	// Make sure rendering enabled
3305 	Error_Box ("A Structure File must be selected first.");
3306 	return;
3307     }
3308     Save_Working_Copy ();
3309 //    Maps->Maps_Edit_Window->hide();
3310     if (!Slice) {
3311 	Slice = new SliceParam;	// new instance of the slice parameters
3312 	Slice->Slice_Edit_Window =
3313 	    new Fl_Window (100, 100, 400, 340, "Edit Map Slice Parameters");
3314 #if !defined (WIN32) && !defined (__APPLE__)
3315 	Slice->Slice_Edit_Window->icon ((char *) drvui->icon);
3316 #endif
3317 	if (drvui->max_frame > 1) {
3318 	    int i;
3319 	    char string[128];
3320 
3321 	    Flu_Combo_List *o = Slice->Frame_No =
3322 			        new Flu_Combo_List (65, y, 75, 25, "Frame No.");
3323 	    o->align (FL_ALIGN_TOP);
3324 	    o->callback (Slice_Frame_Combo_cb);
3325 	    o->labelfont (0);
3326 	    for (i = 1; i <= drvui->max_frame; i++) {
3327 		sprintf (string, "%d", i);
3328 		o->list.add (string);
3329 	    }
3330 	    o->pop_height (20 * drvui->max_frame);
3331 	    o->value ("1");
3332 	    x = 265;
3333 	} else {
3334 	    x = 165;
3335 	}
3336 	Fl_Text_Display *mh = new Fl_Text_Display (x, y, 70, 0,
3337 						  "Contour Type for Slice");
3338 	mh->labelfont(0);
3339 	Fl_Input *mi = Slice->New_type =
3340 	    new Fl_Input (x, y, 70, 25, "");
3341 	mi->align (FL_ALIGN_BOTTOM);
3342 	mi->tooltip("Choices for type:  1 - Contoured slice,"
3343 		    "    2 - Solid slice from blue to red,"
3344 		    "    3 - Solid slice from black to white");
3345 	y += 70;
3346 	Fl_Text_Display *m = new Fl_Text_Display (0, y, 400, 0,
3347 						  "Point in Plane of Slice");
3348 	m->labelfont(0);
3349 	Fl_Input *ma = Slice->New_x =
3350 	    new Fl_Input (65, y + 5, 70, 25, "x");
3351 	ma->align (FL_ALIGN_BOTTOM);
3352 	ma->tooltip ("Point (in fractional coordinates) through which slice passes");
3353 	Fl_Input *mb = Slice->New_y =
3354 	    new Fl_Input (165, y + 5, 70, 25, "y");
3355 	mb->align (FL_ALIGN_BOTTOM);
3356 	mb->tooltip ("Point (in fractional coordinates) through which slice passes");
3357 	Fl_Input *mc = Slice->New_z =
3358 	    new Fl_Input (265, y + 5, 70, 25, "z");
3359 	mc->align (FL_ALIGN_BOTTOM);
3360 	mc->tooltip ("Point (in fractional coordinates) through which slice passes");
3361 	y += 75;
3362 	Fl_Text_Display *md = new Fl_Text_Display (0, y, 400, 0,
3363 						  "Normal to Plane of Slice");
3364 	md->labelfont(0);
3365 	Fl_Input *me = Slice->New_nx =
3366 	    new Fl_Input (65, y + 5, 70, 25, "nx");
3367 	me->align (FL_ALIGN_BOTTOM);
3368 	Fl_Input *mf = Slice->New_ny =
3369 	    new Fl_Input (165, y + 5, 70, 25, "ny");
3370 	mf->align (FL_ALIGN_BOTTOM);
3371 	Fl_Input *mg = Slice->New_nz =
3372 	    new Fl_Input (265, y + 5, 70, 25, "nz");
3373 	mg->align (FL_ALIGN_BOTTOM);
3374 
3375 	y += 65;
3376 	Fl_Check_Button *sc = Slice->Legend = new Fl_Check_Button (140,y,35,25, "Display Legend");
3377 	sc->align (FL_ALIGN_RIGHT);
3378 
3379 	y += 45;
3380 	Fl_Button *r = new Fl_Button (65, y, 70, 25, "Close");
3381 
3382 	r->tooltip ("Close this window and discard all changes.");
3383 	r->callback ((Fl_Callback *) Edit_Slice_Close_cb);
3384 	Fl_Button *a = new Fl_Button (165, y, 70, 25, "Apply");
3385 	a->tooltip
3386 	    ("Apply current contents of top box to drawing, but leave this window open.");
3387 	a->callback ((Fl_Callback *) Edit_Slice_Save_cb, &zero);
3388 	Fl_Button *s = new Fl_Button (265, y, 70, 25, "Save");
3389 	s->tooltip
3390 	    ("Apply current contents of top box to drawing, then close this window.");
3391 	s->callback ((Fl_Callback *) Edit_Slice_Save_cb, &one);
3392 	Slice->Slice_Edit_Window->end ();
3393     }
3394     Slice_Frame_Combo_cb(NULL, NULL);
3395     Slice->Slice_Edit_Window->show ();
3396 }
3397 
3398 void
Edit_Slice_Close_cb(void)3399 Edit_Slice_Close_cb (void)
3400 {
3401 // callback routine when the 'close' button is pushed
3402     Slice->Slice_Edit_Window->hide ();	// hide the window
3403     Fl::redraw ();		// update the screen
3404 }
3405 
3406 void
Edit_Slice_Save_cb(Fl_Button *,int * save)3407 Edit_Slice_Save_cb (Fl_Button *, int *save)
3408 {
3409 // callback routine when 'save' or 'apply' button is pressed on the Edit Slice screen
3410     int Frame_No = 1;
3411 
3412     if (drvui->max_frame > 1)
3413 	Frame_No = atoi (Slice->Frame_No->value ());
3414 
3415     drvui->Str_File_Changed = 1;
3416     drvui->frames[Frame_No].mapslice[0] = (float) atof (Slice->New_x->value ());
3417     drvui->frames[Frame_No].mapslice[1] = (float) atof (Slice->New_y->value ());
3418     drvui->frames[Frame_No].mapslice[2] = (float) atof (Slice->New_z->value ());
3419     drvui->frames[Frame_No].mapnorm[0] = (float) atof (Slice->New_nx->value ());
3420     drvui->frames[Frame_No].mapnorm[1] = (float) atof (Slice->New_ny->value ());
3421     drvui->frames[Frame_No].mapnorm[2] = (float) atof (Slice->New_nz->value ());
3422     drvui->frames[Frame_No].slice = atoi (Slice->New_type->value ());
3423     ShowMapLegend = Slice->Legend->value();
3424     Update_Str (0);
3425     Generate_Drawing (0);
3426     Save_Working_Copy ();
3427     if (*save == 1) {
3428 	Slice->Slice_Edit_Window->hide ();
3429     }
3430     Fl::redraw ();
3431 }
3432 
3433 void
Modify_Occ_cb(Fl_Widget *,void *)3434 Modify_Occ_cb (Fl_Widget *, void *)
3435 {
3436     char atom[10], value[8], string[40];
3437 
3438     float avg, min;
3439 
3440     int start, end, n;
3441 
3442     const char *selection;
3443 
3444     if (!Modparms->Occ_Buffer->selected ()) {
3445 	Modparms->Occ_Combo->value ("");
3446 	Modparms->New_Occ_Avg->value ("");
3447 	Modparms->New_Occ_Min->value ("");
3448 	Modparms->New_Occ_Add->deactivate ();
3449 	return;
3450     }
3451     memset (atom, 0, 10);
3452     Modparms->Occ_Buffer->selection_position (&start, &end);
3453     selection = Modparms->Occ_Buffer->line_text (start);
3454     Modparms->Occ_Instr1->hide ();
3455     Modparms->Occ_Instr->show ();
3456     if (strlen (selection) == 0)
3457 	return;			// user clicked on empty line by mistake
3458     sscanf (selection, "%s %s %f %f", atom, string, &avg, &min);
3459     while (strlen (atom) < 4)
3460 	strcat (atom, " ");
3461     free ((char *) selection);
3462     if (strstr (string, "*"))
3463 	n = -1;
3464     else
3465 	(void) sscanf (string, "%d", &n);
3466     if (strlen (atom) && isalpha (atom[0])) {
3467 	strcpy (string, atom);
3468 	if (n < 0)
3469 	    strcpy (value, " *");
3470 	else
3471 	    sprintf (value, "%2d", n);
3472 	strcat (string, value);
3473 	Modparms->Occ_Combo->value (string);
3474 	sprintf (value, "%2.3f", avg);
3475 	Modparms->New_Occ_Avg->value (value);
3476 	sprintf (value, "%2.3f", min);
3477 	Modparms->New_Occ_Min->value (value);
3478 	Modparms->New_Occ_Add->activate ();
3479 	Modparms->New_Occ_Remove->activate ();
3480 
3481 	New_Occ_Input_cb (NULL, NULL);
3482     }
3483     return;
3484 }
3485 
3486 void
Occ_Combo_cb(Fl_Widget *,void *)3487 Occ_Combo_cb (Fl_Widget *, void *)
3488 {
3489     Modparms->New_Occ_Avg->value ("1.0");
3490     Modparms->New_Occ_Add->activate ();
3491 }
3492 
3493 void
New_Occ_Input_cb(Fl_Widget *,void *)3494 New_Occ_Input_cb (Fl_Widget *, void *)
3495 {
3496     int n;
3497 
3498     char atom[5], number[5];
3499 
3500 // callback routine to make 'Add' new occupancy limit button active whenever all
3501 //  required fields are non-blank
3502     if (atof (Modparms->New_Occ_Min->value ()) == 0.0)
3503 	return;
3504     Modparms->New_Occ_Add->activate ();
3505     (void) sscanf (Modparms->Occ_Combo->value (), "%s %s", atom, number);
3506     if (strstr (number, "*")) {
3507 	n = -1;
3508     } else {
3509 	(void) sscanf (number, "%d", &n);
3510     }
3511     while (strlen (atom) < 4)
3512 	strcat (atom, " ");
3513 }
3514 
3515 void
New_Occ_Add_cb(Fl_Widget *,int * action)3516 New_Occ_Add_cb (Fl_Widget *, int *action)
3517 {
3518     char string[100];
3519 
3520     int start, end;
3521 
3522     float avg, min;
3523 
3524     char atom1[10];
3525 
3526     char *selection = NULL;
3527 
3528     avg = (float) atof (Modparms->New_Occ_Avg->value ());
3529     min = (float) atof (Modparms->New_Occ_Min->value ());
3530 
3531 //    Modparms->OccInstr2->show();
3532 
3533     strcpy (atom1, Modparms->Occ_Combo->value ());
3534     if (Modparms->Occ_Buffer->selected ()) {
3535 	Modparms->Occ_Buffer->selection_position (&start, &end);
3536 	selection = Modparms->Occ_Buffer->line_text (start);
3537 	if (*action != 1)
3538 	    Modparms->Occ_Buffer->remove (Modparms->Occ_Buffer->line_start (start),
3539 					  Modparms->Occ_Buffer->line_end (end) + 1);
3540     }
3541     if (*action == 1) {
3542 	sprintf (string, "%6s %15.3f %15.3f\n", atom1, avg, min);
3543 	if (selection)
3544 	    Modparms->Occ_Buffer->replace (Modparms->Occ_Buffer->line_start (start),
3545 					   Modparms->Occ_Buffer->line_end (end) + 1,
3546 					   string);
3547 	else
3548 	    Modparms->Occ_Buffer->append (string);
3549     }
3550     free ((char *) selection);
3551     Modparms->New_Occ_Avg->value ("");
3552     Modparms->New_Occ_Min->value ("");
3553     Modparms->Occ_Combo->value ("");
3554     Modparms->New_Occ_Add->deactivate ();
3555     Modparms->New_Occ_Remove->deactivate ();
3556     Modparms->Occ_Instr->hide ();
3557     Modparms->Occ_Instr1->show ();
3558 }
3559 
3560 void
Maps_Frame_Combo_cb(Fl_Widget *,void *)3561 Maps_Frame_Combo_cb (Fl_Widget *, void *)
3562 {
3563 // update fourier map data when the frame number in the combo box is changed
3564     char string[10];
3565 
3566     int Frame_No = 1;
3567 
3568     if (drvui->max_frame > 1)
3569 	Frame_No = atoi (Maps->Frame_No->value ());
3570 
3571 	sprintf (string, "%.3f", drvui->frames[Frame_No].map_lim[0]);
3572 	Maps->XMin->value (string);
3573 	sprintf (string, "%.3f", drvui->frames[Frame_No].map_lim[3]);
3574 	Maps->XMax->value (string);
3575 	sprintf (string, "%.3f", drvui->frames[Frame_No].map_lim[1]);
3576 	Maps->YMin->value (string);
3577 	sprintf (string, "%.3f", drvui->frames[Frame_No].map_lim[4]);
3578 	Maps->YMax->value (string);
3579 	sprintf (string, "%.3f", drvui->frames[Frame_No].map_lim[2]);
3580 	Maps->ZMin->value (string);
3581 	sprintf (string, "%.3f", drvui->frames[Frame_No].map_lim[5]);
3582 	Maps->ZMax->value (string);
3583 }
3584 
3585 void
Slice_Frame_Combo_cb(Fl_Widget *,void *)3586 Slice_Frame_Combo_cb (Fl_Widget *, void *)
3587 {
3588 // routine called when the frame number is changed on the Slice Edit Screen
3589     char string[10];
3590     int Frame_No = 1;
3591 
3592     if (drvui->max_frame > 1)
3593 	Frame_No = atoi (Slice->Frame_No->value ());
3594     sprintf(string, "%.5f", drvui->frames[Frame_No].mapslice[0]);
3595     Slice->New_x->value(string);
3596     sprintf(string, "%.5f", drvui->frames[Frame_No].mapslice[1]);
3597     Slice->New_y->value(string);
3598     sprintf(string, "%.5f", drvui->frames[Frame_No].mapslice[2]);
3599     Slice->New_z->value(string);
3600     sprintf(string, "%.5f", drvui->frames[Frame_No].mapnorm[0]);
3601     Slice->New_nx->value(string);
3602     sprintf(string, "%.5f", drvui->frames[Frame_No].mapnorm[1]);
3603     Slice->New_ny->value(string);
3604     sprintf(string, "%.5f", drvui->frames[Frame_No].mapnorm[2]);
3605     Slice->New_nz->value(string);
3606     sprintf(string, "%i", drvui->frames[Frame_No].slice);
3607     Slice->New_type->value(string);
3608     Slice->Legend->value(ShowMapLegend);
3609 }
3610 
3611