root/trunk/FRII/cartwheel-interface/PairView.cc

Revision 144, 11.8 kB (checked in by t, 2 years ago)

include FL/ instead of Fl/

Line 
1 /*
2  * This file is part of the FamilyRelations II source distribution.
3  *
4  * FamilyRelations II is part of the FamilyJewels package for comparative
5  * sequence analysis: http://family.caltech.edu/.
6  *
7  * Contact author: C. Titus Brown, titus@caltech.edu.
8  *
9  * This program and all associated source code files are Copyright (C) 2003,
10  * 2004 the California Institute of Technology, Pasadena, CA, 91125 USA.  It
11  * is under the Lesser GNU Public License; please see the included
12  * LICENSE.txt file for more information, or contact Titus directly.
13  *
14  */
15
16 #include "PairView.hh"
17 #include <FL/Fl_Menu_Item.H>
18 #include <FL/Fl_Menu_Button.H>
19 #include <FL/fl_ask.H>
20 #include "MotifSearchView.hh"
21 #include "SingleView.hh"
22
23 #include <iostream>
24 #include <vector>
25
26 #include <FL/Fl.H>
27 #include <FL/Fl_Window.H>
28 #include <FL/Fl_Double_Window.H>
29 #include <FL/Fl_Tabs.H>
30 #include <FL/Fl_Button.H>
31 #include <FL/Fl_Check_Button.H>
32 #include <FL/Fl_Tile.H>
33 #include <FL/Fl_Pack.H>
34 #include <FL/Fl_Menu_Bar.H>
35 #include <FL/Fl_Menu_Item.H>
36 #include <FL/Fl_Menu_Button.H>
37 #include <FL/Fl_Scroll.H>
38
39 #include "ParsedSingleAnalysis.hh"
40 #include "ParsedPairwiseAnalysis.hh"
41 #include "parsed_analyses.hh"
42
43 #include "SeqcompMappingContainer.hh"
44 #include "SimpleMappingContainer.hh"
45 #include "BlastMappingContainer.hh"
46 #include "PairwiseMappingView.hh"
47 #include "DotPlotMappingView.hh"
48 #include "TripleMappingView.hh"
49 #include "SeqcompThresholdSlider.hh"
50 #include "SimpleFeaturesContainer.hh"
51 #include "SequenceView.hh"
52 #include "HorizontalSequenceView.hh"
53
54 #include "BlastFeaturesContainer.hh"
55 #include "BlastThresholdSlider.hh"
56 #include "SequenceZoomCoordinator.hh"
57 #include "TextLabel.hh"
58 #include "SlavedHorizontalSequenceView.hh"
59 #include "TextSequenceView.hh"
60 #include "ColorPatch.hh"
61
62 #include "SearchPlug.hh"
63
64 #define N_ROTATING_COLORS 5
65 static Fl_Color rotating_colors[N_ROTATING_COLORS] =
66      { FL_RED, FL_BLUE, FL_GREEN, FL_CYAN, FL_MAGENTA };
67
68 // forward-declare callback to pop up the menu attached to the sequence bar.
69 static int toplevel_sequence_popup_menu(gui::SequenceView * seq_view,
70                                         int x, int y, void * passthru);
71
72 // menu item callbacks:
73 static void new_cb(Fl_Widget * w, void * p);
74 static void close_cb(Fl_Widget * w, void * p);
75 static void quit_cb(Fl_Widget * w, void * p);
76
77 static Fl_Menu_Item menuitems[] = {
78   { "&File",              0, 0, 0, FL_SUBMENU },
79      { "&New analysis window", FL_CTRL + 'n', new_cb, 0 },
80      { "&Close analysis window", FL_CTRL + 'w', close_cb, 0 },
81      { "E&xit", FL_CTRL + 'q', quit_cb, 0 },
82      { 0 },
83   { 0 }
84 };
85
86 PairView::PairView(iff::PairAnalysisGroup* g, unsigned int w, unsigned int h) :
87   Fl_Double_Window(w, h)
88 {
89   _parent_window = NULL;
90
91   int controls_x;
92   int controls_y;
93   int controls_width;
94
95   Fl_Color color;
96
97   //
98   // Get the two sequences.
99   //
100
101   iff::Sequence* top_seq = g->get_top_group()->sequence();
102   iff::Sequence* bot_seq = g->get_bot_group()->sequence();
103
104   //
105   // Set up the window a bit.
106   //
107
108   window_name = std::string("Pairwise comparison: ");
109  
110   std::string top_trunc(top_seq->name(), 0, 12);
111   if (top_seq->name().length() > 12) {
112     top_trunc += "...";
113   }
114   std::string bot_trunc(bot_seq->name(), 0, 12);
115   if (bot_seq->name().length() > 12) {
116     bot_trunc += "...";
117   }
118
119   window_name += top_trunc + " against " + bot_trunc;
120   this->label(window_name.c_str());
121
122   this->color(FL_WHITE);
123   this->end();
124
125   //
126   // Create the basic views in the center.
127   //
128
129   Fl_Group* view1 = new Fl_Group(0, 60, 480, 570);
130   Fl_Group* view2 = new Fl_Group(0, 60, 480, 570);
131
132   //
133   // Also create the sidebar that contains controls for the comparisons.
134   //
135
136   Fl_Scroll * cmp_scroll = new Fl_Scroll(485, 60, 212, 570);
137   cmp_scroll->label("Comparisons");
138   cmp_scroll->color(FL_WHITE);
139
140   //
141   // Create the two main views.
142   //
143
144   gui::PairwiseMappingView* pair_view1;
145   gui::DotPlotMappingView* pair_view2;
146
147   pair_view1 = new gui::PairwiseMappingView(0, 60, 485, 570,
148                                             top_seq->name(),
149                                             top_seq->sequence(),
150                                             bot_seq->name(),
151                                             bot_seq->sequence());
152   view1->add(pair_view1);
153   view1->label("Pair View");
154   view1->color(FL_WHITE);
155
156   pair_view2 = new gui::DotPlotMappingView(0, 60, 485, 570,
157                                            top_seq->name(),
158                                            top_seq->sequence(),
159                                            bot_seq->name(),
160                                            bot_seq->sequence());
161   view2->add(pair_view2);
162   view2->label("Dot Plot");
163   view2->color(FL_WHITE);
164
165   //
166   // Now run through all of the feature lists & add control widgets to
167   // the sidebar.
168   //
169
170   controls_x = 485 + 5;
171   controls_y = 60;
172   controls_width = 210 - 20;
173
174   // get the feature lists
175   std::vector<iff::FeatureList*> comparisons = g->get_feature_lists();
176
177   unsigned int color_n = 0;
178   for (unsigned int i = 0; i < comparisons.size(); i++) {
179     iff::FeatureList* fl = comparisons[i];
180     ParsedPairwiseAnalysis * pair_analysis = make_pairwise_analysis(fl, pair_view1);
181
182     if (pair_analysis == NULL) continue;
183
184     gui::MappingContainer * map = pair_analysis->get_mapping_container();
185
186     color = rotating_colors[color_n % N_ROTATING_COLORS];
187     color_n++;
188
189     map->color(color);
190
191     pair_view1->add_map(map);
192     pair_view2->add_map(map);
193
194     pair_analysis->add_control_panel(cmp_scroll, controls_x, controls_y,
195                                      controls_width);
196   }
197
198   // Create two SequenceZoomCoordinators to coordinate the zooms between
199   // the sequences for maps 1 & 2.
200
201   gui::SequenceZoomCoordinator* top_coord = new gui::SequenceZoomCoordinator();
202   gui::SequenceZoomCoordinator* bot_coord = new gui::SequenceZoomCoordinator();
203
204   // First add the dotplot in...
205   pair_view2->top_zoom_coordinator(top_coord);
206   pair_view2->bot_zoom_coordinator(bot_coord);
207
208   //////////////////////
209
210   //
211   // Run through all of the feature lists on the top/bottom sequences.
212   //
213
214   Fl_Group* top_scroll = new Fl_Scroll(485, 60, 212, 570);
215   top_scroll->color(FL_WHITE);
216   top_scroll->label("Top");
217
218   iff::SingleAnalysisGroup* top = g->get_top_group();
219   gui::SequenceView * top_view1 = pair_view1->get_top_seq_view();
220   gui::SequenceView * top_view2 = pair_view2->get_top_seq_view();
221
222   top_view1->popup_menu_handler(toplevel_sequence_popup_menu, top);
223   top_view2->popup_menu_handler(toplevel_sequence_popup_menu, top);
224
225 #if 0
226   for (unsigned int i = 0; i < plugs.size(); i++) {
227     SearchPlug * p = plugs[i];
228     p->add_view(top_view1);
229     p->add_view(top_view2);
230   }
231 #endif // 0
232
233   top_view1->zoom_coordinator(top_coord);
234   top_view2->zoom_coordinator(top_coord);
235
236   // Top group stuff.
237
238   std::vector<iff::FeatureList*> featureLists = top->get_feature_lists();
239
240   color_n = 0;
241
242   controls_y = 60;
243   for (unsigned int i = 0; i < featureLists.size(); i++) {
244     iff::FeatureList* fl = featureLists[i];
245     ParsedSingleAnalysis * single_analysis = make_single_analysis(fl,
246                                                                   top_view1);
247     if (single_analysis == NULL) continue;
248
249     gui::FeaturesContainer* cont;
250     cont = single_analysis->get_features_container();
251
252     color = rotating_colors[color_n % N_ROTATING_COLORS];
253     color_n++;
254
255     cont->color(color);
256
257     top_view1->add_feature_list(cont);
258     top_view2->add_feature_list(cont);
259
260     single_analysis->add_control_panel(top_scroll, controls_x, controls_y,
261                                        controls_width);
262   }
263
264   //
265   // Transfer over the bottom group stuff, too.
266   //
267
268   Fl_Group* bot_scroll = new Fl_Scroll(485, 60, 212, 570);
269   bot_scroll->label("Bottom");
270   bot_scroll->color(FL_WHITE);
271
272   iff::SingleAnalysisGroup* bot = g->get_bot_group();
273   gui::SequenceView * bot_view1 = pair_view1->get_bot_seq_view();
274   gui::SequenceView * bot_view2 = pair_view2->get_bot_seq_view();
275
276   bot_view1->popup_menu_handler(toplevel_sequence_popup_menu, bot);
277   bot_view2->popup_menu_handler(toplevel_sequence_popup_menu, bot);
278
279 #if 0
280   for (unsigned int i = 0; i < plugs.size(); i++) {
281     SearchPlug * p = plugs[i];
282     p->add_view(bot_view1);
283     p->add_view(bot_view2);
284   }
285 #endif // 0
286
287   bot_view1->zoom_coordinator(bot_coord);
288   bot_view2->zoom_coordinator(bot_coord);
289
290   featureLists = bot->get_feature_lists();
291
292   controls_y = 60;
293   for (unsigned int i = 0; i < featureLists.size(); i++) {
294     iff::FeatureList* fl = featureLists[i];
295     ParsedSingleAnalysis * single_analysis = make_single_analysis(fl,
296                                                                   bot_view1);
297     if (single_analysis == NULL) continue;
298
299     gui::FeaturesContainer* cont;
300     cont = single_analysis->get_features_container();
301
302     color = rotating_colors[color_n % N_ROTATING_COLORS];
303     color_n++;
304
305     cont->color(color);
306
307     bot_view1->add_feature_list(cont);
308     bot_view2->add_feature_list(cont);
309
310     single_analysis->add_control_panel(bot_scroll, controls_x, controls_y,
311                                        controls_width);
312   }
313
314   //
315   // Finalize everything.
316   //
317
318   // Menu bar
319
320   Fl_Menu_Bar *m = new Fl_Menu_Bar(0, 0, w, 30);
321   m->copy(menuitems);
322   m->user_data(this);           // attach the PairView to the menu bar for cb
323
324   this->add(m);
325
326   // Add the two different pairwise views.
327   Fl_Tabs* view_tabs = new Fl_Tabs(0, 30, 480, 600);
328   view_tabs->add(view1);
329   view_tabs->add(view2);
330
331   view1->selection_color(FL_LIGHT1);
332   view2->selection_color(FL_LIGHT1);
333   view_tabs->selection_color(FL_WHITE);
334   view_tabs->color(FL_WHITE);
335
336   this->add(view_tabs);
337   //this->resizable(view_tabs);
338
339   // default to dotplot view for the moment.
340   view_tabs->value(view2);
341
342   // Also add the sidebar views.
343   Fl_Box* ctrl_tabs_box = new Fl_Box(480, 30, 220, 600);
344   ctrl_tabs_box->box(FL_UP_BOX);
345   ctrl_tabs_box->color(FL_WHITE);
346
347   Fl_Tabs* ctrl_tabs = new Fl_Tabs(482, 30, 212, 600);
348   ctrl_tabs->add(cmp_scroll);
349   ctrl_tabs->add(top_scroll);
350   ctrl_tabs->add(bot_scroll);
351
352   cmp_scroll->selection_color(FL_LIGHT1);
353   top_scroll->selection_color(FL_LIGHT1);
354   bot_scroll->selection_color(FL_LIGHT1);
355   ctrl_tabs->selection_color(FL_WHITE);
356   ctrl_tabs->color(FL_WHITE);
357
358   this->add(ctrl_tabs_box);
359   this->add(ctrl_tabs);
360
361   resizable(this);
362 }
363
364 //////////////
365
366 //
367 // popup_menu -- display a popup menu
368 //
369
370 static Fl_Menu_Item _popup[] = {
371   {"&view features", 0, 0 },
372   {"&zoom", 0, 0 },
373   {"&unzoom", 0, 0 },
374   {"&copy sequence", 0, 0 },
375   {"search for &motifs...", 0, 0 },
376   { 0 }
377 };
378
379 static int toplevel_sequence_popup_menu(gui::SequenceView * seq_view,
380                                         int x, int y, void * passthru)
381 {
382   Fl_Menu_Button * w = new Fl_Menu_Button(0, 0, 100, 300);
383   gui::MotifSearchView * motif_view;
384   SingleView * new_view;
385   iff::SingleAnalysisGroup * group = (iff::SingleAnalysisGroup *) passthru;
386
387   x = Fl::event_x();
388   y = Fl::event_y();
389
390   w->copy(_popup);
391
392   // I don't know why I have to do this, exactly, but there's some weird
393   // code in Fl_Menu that runs through and systematically screws up the
394   // position of the popup.  So I'm setting it manually.
395
396   const Fl_Menu_Item * m = w->menu()->popup(x, y, w->label(), NULL, w);
397   if (m != NULL) {      // picked an item
398     w->picked(m);
399     int v = w->value();
400     switch(v) {
401     case 0:
402       new_view = new SingleView(group, 600, 400);
403       new_view->show();
404       break;
405     case 1:                     // zoom
406       seq_view->zoom();
407       break;
408     case 2:                     // unzoom
409       seq_view->unzoom();
410       break;
411     case 3:                     // copy selected or displayed region
412       seq_view->copy_to_clipboard();
413       break;
414     case 4:                     // bring up motif search window
415       motif_view = new gui::MotifSearchView(seq_view);
416       break;
417     default:
418       break;
419     }
420   }
421   delete w;
422
423   return 1;
424 }
425
426 //
427 // menu bar callbacks
428 //
429
430 // unhide parent (==> new analysis?)
431 static void new_cb(Fl_Widget * w, void * p)
432 {
433   Fl_Menu_Bar * m = (Fl_Menu_Bar *) w;
434   PairView * pv = (PairView *) m->user_data();
435
436   Fl_Window * parent = pv->parent_window();
437   if (parent != NULL) {
438     parent->show();
439   } else {
440     fl_alert("I'm sorry, I have no way of bringing up a new analysis.");
441   }
442 }
443
444 // close?
445 static void close_cb(Fl_Widget * w, void * p)
446 {
447   Fl_Menu_Bar * m = (Fl_Menu_Bar *) w;
448   Fl_Window * win = (Fl_Window *) m->user_data();
449   win->hide();
450 }
451
452 // quit?
453 static void quit_cb(Fl_Widget * w, void * p)
454 {
455   int choice = fl_choice("Close all windows and exit?",
456                              "No", "Yes", 0);
457   if (choice == 1) {
458     exit(0);
459   }
460 }
Note: See TracBrowser for help on using the browser.