]> Creatis software - creaImageIO.git/blob - src/creaImageIOWxTreeView.cpp
correction of minor bugs: quotes and last slice in first place
[creaImageIO.git] / src / creaImageIOWxTreeView.cpp
1 #include <creaImageIOWxTreeView.h>
2 #include <creaImageIOGimmickView.h>
3 #include <creaImageIOSystem.h>
4 #include <wx/splitter.h>
5 #include <wx/gdicmn.h>
6 #include <boost/date_time/gregorian/gregorian.hpp>
7 #include <creaImageIOGimmick.h>
8 #ifdef _DEBUG
9 #define new DEBUG_NEW
10 #endif
11 //=====================================================================
12 namespace creaImageIO
13 {
14
15   //=====================================================================
16 }
17 //=====================================================================
18
19 //=====================================================================
20 ///Comparing function for ordering algorithm. Takes parameters as strings.
21 int wxCALLBACK CompareFunctionStrings(long item1, long item2, long sortData)
22 {       
23   creaImageIO::ItemData* data1 = (creaImageIO::ItemData*)item1;
24   creaImageIO::ItemData* data2 = (creaImageIO::ItemData*)item2;
25
26   const std::string& s1(*(data1->attr));
27   const std::string& s2(*(data2->attr));
28   if(sortData==1)
29     {
30       // inverse the order
31       if (s1 < s2)
32         return 1;
33       if (s1 > s2)
34         return -1;
35       
36       return 0;
37     }
38   else
39     {
40       if (s1 < s2)
41         return -1;
42       if (s1 > s2)
43         return 1;
44       
45       return 0;
46       
47     }
48 }
49 //=====================================================================
50
51 //=====================================================================
52 ///Comparing function for ordering algorithm. Takes parameters as ints.
53 int wxCALLBACK CompareFunctionInts(long item1, long item2, long sortData)
54 {       
55   creaImageIO::ItemData* data1 = (creaImageIO::ItemData*)item1;
56   creaImageIO::ItemData* data2 = (creaImageIO::ItemData*)item2;
57
58   const std::string& s1(*(data1->attr));
59   const std::string& s2(*(data2->attr));
60
61   int val1=atoi(s1.c_str());
62   int val2=atoi(s2.c_str());
63
64   if(sortData==1)
65     {
66       // inverse the order
67       if (val1 < val2)
68         return 1;
69       if (val1 > val2)
70         return -1;
71       
72       return 0;
73     }
74   else
75     {
76       if (val1 < val2)
77         return -1;
78       if (val1 > val2)
79         return 1;
80
81       return 0;
82       
83     }
84   
85 }
86
87 //=====================================================================
88
89
90 //=====================================================================
91 namespace creaImageIO
92 {
93   //=====================================================================
94   // CTor
95   WxTreeView::WxTreeView(TreeHandler* handler,
96                          GimmickView* gimmick,
97                          wxWindow* parent,
98                          const wxWindowID id)
99     : wxPanel(parent,id),
100       TreeView(handler, gimmick)
101   {
102     GimmickDebugMessage(1,"WxTreeView::WxTreeView"
103                         <<std::endl);
104
105     
106     // Split part below toolbar into notebook for views and panel
107     // for preview, messages...
108     // TO DO : Splitter
109     //    mSplitter = new wxSplitterWindow( this , -1);
110
111     // Global sizer
112     msizer = new wxBoxSizer(wxHORIZONTAL);
113     
114     int ctrl_style = wxLC_REPORT | wxLC_VRULES;
115     int col_style = wxLIST_FORMAT_LEFT;
116
117     // Creating the ListCtrl for the levels > 0 (not for Root level)
118     for (int i = 0;
119          i < handler->GetTree().GetNumberOfLevels() -1;
120          ++i)
121       {
122         GimmickDebugMessage(5,"Creating view for level "<<i
123                             <<std::endl);
124         LevelType level;
125         level.SelectedUpToDate = true;
126         level.SortColumn = 0;
127
128         // If the first level : parent = this
129         wxWindow* sparent = this;
130         // else parent = last splitter
131         if (i>0) 
132                 sparent = mLevelList[i-1].wxSplitter;
133
134         level.wxSplitter = new wxSplitterWindow( sparent , -1);
135         if(i!=0)
136         {
137         level.wxSplitter->Show(false);
138         }
139         //          level.wxSplitter->SetMinimumPaneSize(100);
140         
141         wxListCtrl* ctrl = new wxListCtrl(level.wxSplitter,
142                                           i,
143                                           wxDefaultPosition, 
144                                           wxDefaultSize,
145                                           ctrl_style);
146         level.wxCtrl = ctrl;
147         level.wxSplitter->Initialize(ctrl);
148    
149         // Create the columns : one for each attribute of the level
150         int col = 0;
151         std::string title;
152
153         tree::LevelDescriptor::AttributeDescriptorListType::const_iterator a;
154         for (a  = handler->GetTree().GetAttributeDescriptorList(i+1).begin();
155              a != handler->GetTree().GetAttributeDescriptorList(i+1).end();
156              ++a)
157
158 {
159         
160             GimmickDebugMessage(5,"Creating column "<<col<<" : "
161                                 <<a->GetName()
162                                 <<std::endl);
163             
164             if(a->GetFlags()!=creaImageIO::tree::AttributeDescriptor::PRIVATE)
165               {
166                 
167                 if(a->GetName()=="UNKNOWN")
168                   {
169                     title = "#";
170                     title += handler->GetTree().GetLevelDescriptor(i+1).GetName();
171                     if (title[title.size()-1]!='s')
172                       title += "s";
173                     
174                   }
175                 else
176                   {
177                     title=a->GetName();
178                   }
179                   std::string temp = a->GetKey();
180                   if (temp.compare("ID") != 0)
181                   {
182                 
183                 ctrl->InsertColumn(col, 
184                                    crea::std2wx(title),
185                                    col_style);
186                 col++;
187                   }
188                 level.key.push_back(a->GetKey());
189               }
190                 
191           }
192           
193         mLevelList.push_back(level);
194       }
195     
196 #if wxUSE_MENUS
197
198          // Column Menu
199     menu =new wxMenu;
200         wxMenuItem* m1=menu->Append(wxID_ANY, _T("&Sort ascending"));
201         wxMenuItem* m2=menu->Append(wxID_ANY, _T("&Sort descending"));
202         wxMenuItem* m3=menu->Append(wxID_ANY, _T("&Filter"));
203         mAscendingID=m1->GetId();
204         mDescendingID=m2->GetId();
205         mFilterID=m3->GetId();
206         Connect( mAscendingID, wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(WxTreeView::OnPopupSort) );
207         Connect( mDescendingID, wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(WxTreeView::OnPopupSort) );
208         Connect( mFilterID, wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(WxTreeView::OnPopupFilter) );
209
210
211         ////SubMenuItem EXPORT
212         subExportMenu = new wxMenu;
213         wxMenuItem *subExp1 = subExportMenu->Append(wxID_ANY, _T("&Export to Storage"));
214         Connect( subExp1->GetId(), wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(WxTreeView::OnExportToStorage) );
215
216         //ItemMenu
217         menuItem =new wxMenu;
218
219
220         wxMenuItem* m2Item=menuItem->Append(wxID_ANY, _T("&Local Copy"));
221         wxMenuItem* m3Item=menuItem->Append(wxID_ANY, _T("&Edit Fields"));
222         wxMenuItem* m4Item=menuItem->Append(wxID_ANY, _T("&Display Dicom Tags"));
223         menuItem->AppendSubMenu(subExportMenu, wxT("&Export"));
224
225 #if defined(USE_GDCM_ANOM)
226         wxMenuItem* m1Item=menuItem->Append(wxID_ANY, _T("&Anonymize"));
227         mAnonymizingID=m1Item->GetId();
228         Connect( mAnonymizingID, wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(WxTreeView::OnAnonymize) );
229 #endif
230         mLocalCopyID=m2Item->GetId();
231         mEditFieldID=m3Item->GetId();
232         mDumpID=m4Item->GetId();
233         
234         
235         Connect( mLocalCopyID, wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(WxTreeView::OnLocalCopy) );
236         Connect( mEditFieldID, wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(WxTreeView::OnEditField) );
237         Connect( mDumpID, wxEVT_COMMAND_MENU_SELECTED, wxCommandEventHandler(WxTreeView::OnDumpTags) );
238         
239
240         
241 #endif // wxUSE_MENUS
242         /// Initialize the first level splitter
243           
244         msizer->Add( mLevelList[0].wxSplitter ,1, wxGROW  ,0);
245         //      mColumnSelected=1;
246         mLastSelected=0;
247         mLastLevel=0;
248         //      mDirection=true;
249
250         mIgnoreSelectedChanged = false;
251
252         //CreateColorPalette();
253     UpdateLevel(1);
254
255     SetSizer( msizer );     
256     SetAutoLayout(true);
257     Layout();
258
259   }
260   //=====================================================================
261
262   //=====================================================================
263   /// Destructor
264   WxTreeView::~WxTreeView()
265   {
266     GimmickDebugMessage(1,"WxTreeView::~WxTreeView"
267                         <<std::endl);
268         delete menu;
269         delete menuItem;
270
271   }
272   //=====================================================================
273   
274   
275   
276   //=====================================================================
277   const std::vector<tree::Node*>& WxTreeView::GetSelected(int level)
278   {
279           std::vector<tree::Node*>& sel = mLevelList[0].Selected;
280     //  if (GetSelectedUpToDate(level)) 
281     int l = level - 1;
282     // the selection of upper level
283         if(mLevelList.size() == level -1)
284                  sel = mLevelList.back().Selected;
285         else
286                   sel=  mLevelList[l].Selected;
287         if (sel.size() > 0)
288         {
289                 sel.clear();
290         }
291           if (level == 1) 
292       {
293         sel.push_back(GetTreeHandler()->GetTree().GetTree());
294       }
295           else if (level < mLevelList.size()+2 ) 
296     {
297                 long item = -1;
298                 for ( ;; )
299                 {
300                         item = GetCtrl(l-1)->GetNextItem(item,
301                                                                                  wxLIST_NEXT_ALL,
302                                                                                  wxLIST_STATE_SELECTED);
303                         if ( item == -1 )
304                                 break;
305                         long adr = GetCtrl(l-1)->GetItemData(item);
306                         tree::Node* n = ((ItemData*)adr)->node;
307                         /* FCY 18-04-2011: don't understand the real purpose of these lines,
308                          if uncomment add last frame in first place 
309                                 if(mLastSelected==item)
310                         {
311                                 std::vector<tree::Node*>::iterator it;
312                                 it = sel.begin();
313                                 it = sel.insert ( it , n );
314                         }
315                         else
316                         {*/
317                                 
318                                 sel.push_back(n);
319                         //}                     
320                         
321                 }
322                 /*int n = GetCtrl(l-1)->GetItemCount();
323                 for (int i = 0; i<n; i++)
324                 {
325                         std::cout<<GetCtrl(l-1)->GetItemState(i,wxLIST_STATE_SELECTED)<<std::endl;
326                         if ( GetCtrl(l-1)->GetItemState(i,wxLIST_STATE_SELECTED))
327                         {
328                                 long adr = GetCtrl(l-1)->GetItemData(i);
329                                 tree::Node* n = ((ItemData*)adr)->node;
330                                 if(mLastSelected==i)
331                                 {
332                                         std::vector<tree::Node*>::iterator it;
333                                         it = sel.begin();
334                                         it = sel.insert ( it , n );
335                                 }
336                                 else
337                                 {
338                                         
339                                         sel.push_back(n);
340                                 }
341                         }
342               }*/
343           }
344         else
345         {
346                 // NOTHING
347         }   
348          
349     //    return mLevelList[level-1].Selected;
350     return sel;
351   }
352
353   //=====================================================================
354   
355   //=====================================================================
356   ///Removes selected nodes on last selected level
357    // NOT SPECIFIC 
358   void WxTreeView::RemoveSelected(std::string &i_save)
359   {
360          bool erase=false;
361          
362          unsigned int tempLevel = mLastLevel;
363     mLastLevel+=1;
364     const std::vector<tree::Node*>& sel=GetSelected(mLastLevel+1);
365         // if no selection, no remove action.
366     if(sel.size() != 0)
367         {
368         
369             std::stringstream out;
370             std::string levelName=GetTreeHandler()->GetTree().GetLevelDescriptor(mLastLevel).GetName();
371             out<<"Delete ";
372             out<<sel.size();
373             if(sel.size()>1&&levelName.at(levelName.size()-1)!='s')
374               {
375                 out<<" "<<levelName;
376                 out<<"s?";
377               }
378             else
379               {
380                 out<<" "<<GetTreeHandler()->GetTree().GetLevelDescriptor(mLastLevel).GetName()<<"?";
381               }
382             if (wxMessageBox(crea::std2wx(out.str()),
383                              _T("Remove Files"),
384                              wxYES_NO,this ) == wxYES)
385               {
386                 erase = true;
387               }
388             if(erase)
389                   {
390             GetGimmickView()->modifyValidationSignal(false);
391                     bool needRefresh=false;
392                     std::vector<tree::Node*>::const_iterator i;
393                     for (i=sel.begin(); i!=sel.end(); ++i)
394                       {
395                         GimmickMessage(1,
396                                        "deleting '"
397                                        <<(*i)->GetLabel()
398                                        <<"'"<<mLastLevel
399                                        <<std::endl);
400                         if((*i)->GetParent()->GetNumberOfChildren()<2)
401                           {
402                             needRefresh=true;
403                           }
404                           //tree::Node* n = new (tree::Node*)(*i);
405                           GetTreeHandler()->LoadChildren((*i),4);
406                           GetGimmickView()->AddIgnoreFile(*i);
407                           GetTreeHandler()->Remove(*i);
408                       }
409                     
410                     if(needRefresh && mLastLevel>1)
411                       {
412                         UpdateLevel(mLastLevel-2);
413                       }
414                     else if(mLastLevel>1)
415                       {
416                         UpdateLevel(mLastLevel-1);
417                       }
418                     else
419                       {
420                         UpdateLevel(mLastLevel);
421                       }
422                   }
423         }
424         else
425         {
426                 // no need to incremente level
427                 mLastLevel = tempLevel;
428         }
429     
430         if (erase && mLastLevel == 1 && i_save == "0")
431         {
432         
433                 RemoveAlertDlg *dial = new RemoveAlertDlg(this,  crea::std2wx("Remove files"), wxSize(370,100));
434                 //dial->ShowModal();
435                 if (dial->ShowModal() == wxID_OK)
436                 {
437                         i_save = dial->isChecked() == false? "0" : "1";
438                 }
439                 
440         }
441   }
442   
443   
444   //=====================================================================
445   /// Updates a level of the view (adds or removes children, etc.)
446   void WxTreeView::UpdateLevel( int level )
447   {
448     GimmickDebugMessage(1,
449                         GetTreeHandler()->GetTree().GetLabel()
450                         <<"WxTreeView::UpdateLevel(level "
451                         <<level
452                         <<")"
453                         <<std::endl);
454     
455     wxBusyCursor busy;
456     RecursiveUpdateLevel(level);
457     int i;
458     for (i=0; i<level-1; i++)
459       {
460         if (!GetSplitter(i)->IsSplit()) 
461           GetSplitter(i)->SplitVertically(  GetCtrl(i), GetSplitter(i+1),
462                                             100 );
463       }
464     if (GetSplitter(i)->IsSplit()) GetSplitter(i)->Unsplit();    
465     
466   }
467   //=====================================================================
468   
469   //=====================================================================
470   /// Recursive method called upon by UpdateLevel to refresh all windows
471   void WxTreeView::RecursiveUpdateLevel( int level )
472   {
473     GimmickDebugMessage(1,
474                         GetTreeHandler()->GetTree().GetLabel()
475                         <<"WxTreeView::RecursiveUpdateLevel(level "
476                         <<level
477                         <<")"<<std::endl);
478     
479     
480     const std::vector<tree::Node*>& sel(GetSelected(level));
481     
482     int l = level - 1;
483     
484     // to speed up inserting we hide the control temporarily
485     GetCtrl(l)->Hide();
486     GetCtrl(l)->DeleteAllItems();
487     
488     std::vector<tree::Node*>::const_iterator i;
489     
490     for (i=sel.begin(); i!=sel.end(); ++i)
491       {
492         GimmickDebugMessage(1,
493                             "adding children of '"
494                             <<(*i)->GetLabel()
495                             <<"'"
496                             <<std::endl);
497         int _id=0;
498         
499         //Adds items and sets their attributes 
500         
501         GetTreeHandler()->LoadChildren(*i,1);
502         tree::Node::ChildrenListType::reverse_iterator j;
503         for (j = (*i)->GetChildrenList().rbegin(); 
504              j!= (*i)->GetChildrenList().rend(); 
505              ++j)
506           {
507             GimmickDebugMessage(1,
508                                 "adding children "
509                                 <<(*j)->GetLabel()
510                                 <<"'"
511                                 <<std::endl);
512             
513             wxListItem item;
514             item.SetMask(wxLIST_MASK_STATE | 
515                          wxLIST_MASK_TEXT |
516                          //                      wxLIST_MASK_IMAGE |
517                          wxLIST_MASK_DATA |
518                          //                      wxLIST_MASK_WIDTH |
519                          wxLIST_MASK_FORMAT
520                          );
521             
522                 ItemData* data = new ItemData();
523             data->node = *j;
524             data->id = _id;
525                 
526             item.SetId(_id);
527             item.SetData(data);
528
529             _id++;
530             GetCtrl(l)->InsertItem(item);
531             
532             //Setting attributes
533             for (int k=0; k<GetCtrl(l)->GetColumnCount(); ++k)                          
534               {
535                 std::string val;
536                 //  Temporary correction : it works but no explanation about the problem FCY
537                 
538                 if(k==0 && level <3)
539                 {
540                   val = (*j)->GetAttribute("NumberOfChildren");
541                 }
542                 else
543                   val = (*j)->GetAttribute(mLevelList[l].key[k]);
544                 if(((*j)->GetAttributeDescriptor(mLevelList[l].key[k])).isDateEntry()) // Date
545                   {
546                     //                                    std::cout << "["<<val<< "]" << std::endl;
547                     std::string valtmp(val);
548                     try
549                       {
550                         boost::gregorian::date d1(boost::gregorian::from_undelimited_string(val));                                 
551                         val = to_iso_extended_string(d1);
552                       }
553                     catch (...)
554                       {
555                         val =  valtmp;
556                       }
557                     //                                    std::cout << "["<<val<< "]" << std::endl;     
558                   }
559                 else if(((*j)->GetAttributeDescriptor(mLevelList[l].key[k])).isTimeEntry()) // Time
560                   {
561                     if ((val.size()>6) && 
562                         (val != "" || val != " "))
563                       val = val.substr(0,2) + " : " 
564                         + val.substr(2,2) + " : " 
565                         + val.substr(4,2);
566                   }
567                 else
568                   {
569                     if (val.size()==0) val = "?";
570                   }
571                 if (val.size()==0) val = "X";
572                 item.SetText( crea::std2wx(val));
573                 item.SetColumn(k);
574                   
575                   GetCtrl(l)->SetItem(item);
576                   }
577                 item.Clear();
578             
579           }
580       }
581     
582     SortLevel(l);
583     GetCtrl(l)->Show();
584   }
585   //=====================================================================
586   
587   
588   //================================================================
589   void WxTreeView::OnItemDeSelected(wxListEvent& event)
590   { 
591     GimmickDebugMessage(1,
592                         GetTreeHandler()->GetTree().GetLabel()
593                         <<" WxTreeView::OnItemDeselected"<<std::endl);
594     // retrieve the level
595     wxObject* obj = event.GetEventObject();   
596     unsigned int level = 0;
597     for (level = 0; level<mLevelList.size(); ++level)
598       {
599         if ( GetCtrl(level) == obj ) break;
600       } 
601     SetSelectedUpToDate(level,false);
602     // to allow a first selection in images TreeView
603     if (level==mLevelList.size()-1) 
604       OnItemSelected(event);
605   }
606   //================================================================
607   
608   //================================================================
609   void WxTreeView::OnItemSelected(wxListEvent& event)
610   { 
611           
612     GimmickDebugMessage(1,
613                         GetTreeHandler()->GetTree().GetLabel()
614                         <<" WxTreeView::OnItemSelected"<<std::endl);
615
616     if (mIgnoreSelectedChanged) 
617       {
618         GimmickDebugMessage(1,
619                             " mIgnoreSelectedChanged true: returning"
620                             <<std::endl);
621         return;
622       }
623     
624
625     
626     wxListItem info;
627     info.m_itemId = event.m_itemIndex;
628     mLastSelected = event.m_itemIndex;
629     // retrieve the level
630     wxObject* obj = event.GetEventObject();   
631     unsigned int level = 0;
632     for (level = 0; level<mLevelList.size(); ++level)
633       {
634         if ( GetCtrl(level) == obj ) break;
635       }
636         mLastLevel=level;
637     GimmickDebugMessage(1,
638                         " Level "<<level+1
639                         <<std::endl);
640     
641     // Update the children level (if selection not at last level)
642     if (level<mLevelList.size()-1) 
643       {
644                 
645         UpdateLevel( level + 2 ); 
646         // Reset the viewer setting the default image
647         GetGimmickView()->ClearSelection();
648       }
649     // Select all images if the selection is at series level
650     if (level==mLevelList.size()-2) 
651                 SelectAll(level+1);
652     // Validate selected images if the selection is at image level
653     if (level==(mLevelList.size()-1)) //&&mProcess) 
654       {
655         if(event.GetEventType()==wxEVT_COMMAND_LIST_ITEM_SELECTED)
656           {
657                   ValidateSelectedImages (true);
658           }
659         else
660           {
661                   ValidateSelectedImages (false);
662           }
663       }
664     
665   }
666   //================================================================
667
668   //================================================================
669   void WxTreeView::SelectAll(int level)
670   {
671     long item = -1;
672     //    int level=mLevelList.size()-1;
673     for ( ;; )
674       {
675         item = GetCtrl(level)->GetNextItem(item,
676                                            wxLIST_NEXT_ALL);
677         if ( item == -1 )
678           break;
679         
680         if(item==(GetCtrl(level)->GetItemCount()-1))
681           {
682             mIgnoreSelectedChanged = false;//mProcess=true;
683           }
684         else
685           {
686             mIgnoreSelectedChanged = true;//    mProcess=false;
687           }
688         GetCtrl(level)->SetItemState(item,wxLIST_STATE_SELECTED, wxLIST_MASK_STATE 
689                                      | wxLIST_MASK_TEXT |wxLIST_MASK_IMAGE | wxLIST_MASK_DATA | wxLIST_MASK_WIDTH | wxLIST_MASK_FORMAT);
690       }
691   }
692
693   //================================================================
694   //================================================================
695
696   void WxTreeView::OnColClick(wxListEvent& event)
697   { 
698     mColumnSelected = event.m_col;
699     wxPoint clientpt;
700     clientpt.x = wxGetMousePosition().x - this->GetScreenPosition().x;
701     clientpt.y = wxGetMousePosition().y - this->GetScreenPosition().y;
702     senderCtrl = event.GetEventObject(); 
703     unsigned int level = 0;
704     for (level = 0; level<mLevelList.size(); ++level)
705       {
706         if ( GetCtrl(level) == senderCtrl ) break;
707       }
708     PopupMenu(menu, clientpt);
709     
710   }
711
712    //================================================================
713   //================================================================
714
715   void WxTreeView::OnItemMenu(wxListEvent &event)
716   {
717          wxPoint clientpt;
718     clientpt.x = wxGetMousePosition().x - this->GetScreenPosition().x;
719     clientpt.y = wxGetMousePosition().y - this->GetScreenPosition().y;
720     senderCtrl = event.GetEventObject();
721     unsigned int level = 0;
722     for (level = 0; level<mLevelList.size(); ++level)
723       {
724                 if ( GetCtrl(level) == senderCtrl ) break;
725       }
726           long* ptr=0;
727           int flag;
728           mLastRightLevel=level;
729           mLastRightSelected=GetCtrl(level)->HitTest(wxPoint(0,clientpt.y-8),flag,ptr);
730     PopupMenu(menuItem, clientpt);
731     
732   }
733   
734   //================================================================
735   //================================================================
736
737   void WxTreeView::OnPopupFilter(wxCommandEvent& event)
738   {
739     wxBusyCursor busy;
740     GimmickDebugMessage(7,
741                         "WxTreeView::OnEndLabelEdit" 
742                         <<std::endl);
743     unsigned int level = 0;
744     for (level = 0; level<mLevelList.size(); ++level)
745       {
746         if ( GetCtrl(level) == senderCtrl ) break;
747       }
748     std::string filter = crea::wx2std(wxGetTextFromUser(_T("Enter the filter to apply"), _T("Filter On Column")));
749     
750     std::string att;
751     
752     long it = -1;
753     UpdateLevel(level+1);
754     
755     std::vector<long> items;
756     bool in=false;
757     int del=0;
758     for ( ;; )
759       {
760         it = GetCtrl(level)->GetNextItem(it,
761                                          wxLIST_NEXT_ALL);
762         if ( it == -1 )
763           break;
764         
765         long adr = GetCtrl(level)->GetItemData(it);
766         tree::Node* nod = ((ItemData*)adr)->node;
767         att=(*nod).GetAttribute(mLevelList[level].key[mColumnSelected]);
768         
769         
770         if(att.find(filter)>900)
771           {
772             
773             if(!in)
774               {
775                 in=true;
776               }
777             else
778               {
779                 del+=1;
780               }
781             
782             items.push_back(it-del);
783           }
784         
785       }
786     std::vector<long>::iterator iter;
787     for(iter=items.begin();iter!=items.end();++iter)
788       {
789         GetCtrl(level)->DeleteItem(*iter);
790       }
791     GetGimmickView()->ClearSelection();
792   }
793   //================================================================
794   
795   //================================================================
796   void WxTreeView::OnPopupSort(wxCommandEvent& event)
797   {
798     wxBusyCursor busy;
799     unsigned int level = 0;
800     for (level = 0; level<mLevelList.size(); ++level)
801       {
802         if ( GetCtrl(level) == senderCtrl ) break;
803       }
804     mLevelList[level].SortColumn = mColumnSelected;
805
806     if(event.GetId()==mAscendingID)
807       {
808         mLevelList[level].SortAscending = true;
809       }
810     else if(event.GetId()==mDescendingID)
811       {
812         mLevelList[level].SortAscending = false;
813       }
814           
815     SortLevel(level);
816   }
817   //================================================================
818
819   void WxTreeView::OnAnonymizer(wxCommandEvent &event)
820   {
821            wxBusyCursor busy;
822            std::vector<std::string> filesname;
823            std::vector<tree::Node*> nodes;
824 //         nodes.push_back(((ItemData*)GetCtrl(mLastRightLevel)->GetItemData(mLastRightSelected))->node);
825            if(nodes.size() != 0)
826            {
827                    GetFilenamesAsString(nodes,filesname);
828                 //   GetGimmickView()->Anonymize(filesname,0);
829            }
830         
831   }
832
833   //================================================================
834   void WxTreeView::OnLocalCopy(wxCommandEvent& event)
835   {
836     wxBusyCursor busy;
837     
838         unsigned int tempLevel = mLastLevel;
839     mLastLevel+=1;
840     const std::vector<tree::Node*>& sel=GetSelected(mLastLevel+1);
841         
842     if(sel.size() != 0)
843         {
844             bool copy=false;
845             std::stringstream out;
846             std::string levelName=GetTreeHandler()->GetTree().GetLevelDescriptor(mLastLevel).GetName();
847             out<<"Copy ";
848             out<<sel.size();
849             if(sel.size()>1&&levelName.at(levelName.size()-1)!='s')
850               {
851                 out<<" "<<levelName;
852                 out<<"s to .creaImageIO?";
853               }
854             else
855               {
856                 out<<" "<<GetTreeHandler()->GetTree().GetLevelDescriptor(mLastLevel).GetName()<<" to .creaImageIO?";
857               }
858             if (wxMessageBox(crea::std2wx(out.str()),
859                              _T("Remove Files"),
860                              wxYES_NO,this ) == wxYES)
861               {
862                 copy = true;
863               }
864             if(copy)
865                   {
866                         std::vector<std::string> s;
867                         GetFilenamesAsString(sel,s);
868             GetGimmickView()->CopyFiles(s);
869                   }
870         }
871         else
872         {
873                 mLastLevel = tempLevel;
874         }
875     
876     
877   }
878   //================================================================
879
880    //================================================================
881   void WxTreeView::OnEditField(wxCommandEvent& event)
882   {
883         if(mLastRightSelected!=-1)
884         {
885     tree::Node* node=((ItemData*)GetCtrl(mLastRightLevel)->GetItemData(mLastRightSelected))->node;
886         tree::LevelDescriptor::AttributeDescriptorListType::const_iterator a;
887         std::vector<std::string> names;
888         std::vector<std::string> keys;
889         for (a  = GetTreeHandler()->GetTree().GetAttributeDescriptorList(mLastRightLevel+1).begin();
890              a != GetTreeHandler()->GetTree().GetAttributeDescriptorList(mLastRightLevel+1).end();
891              ++a)
892         {
893                 if(a->GetFlags()==creaImageIO::tree::AttributeDescriptor::EDITABLE)
894             {
895                         names.push_back(a->GetName());
896                         keys.push_back(a->GetKey());
897                 }
898         }
899         GetGimmickView()->CreateEditFieldsDialog(node,names,keys);
900         }
901   }
902
903   //================================================================
904
905   //================================================================
906
907   void WxTreeView::OnExportToStorage(wxCommandEvent &event)
908   {
909         std::vector<std::string> filesname;
910         std::vector<tree::Node*> nodes;
911         nodes.push_back(((ItemData*)GetCtrl(mLastRightLevel)->GetItemData(mLastRightSelected))->node);
912         GetFilenamesAsString(nodes,filesname);
913         GetGimmickView()->ExportToStorage(filesname);
914   }
915
916   //================================================================
917
918   //================================================================
919
920   void WxTreeView::OnDumpTags(wxCommandEvent &event)
921   {
922           if(mLastRightSelected!=-1)
923         {
924                 tree::Node* node=((ItemData*)GetCtrl(mLastRightLevel)->GetItemData(mLastRightSelected))->node;
925                 tree::LevelDescriptor::AttributeDescriptorListType::const_iterator a;
926                 std::vector<std::string> names;
927                 std::vector<std::string> keys;
928                 for (a  = GetTreeHandler()->GetTree().GetAttributeDescriptorList(mLastRightLevel+1).begin();
929                          a != GetTreeHandler()->GetTree().GetAttributeDescriptorList(mLastRightLevel+1).end();
930                          ++a)
931                         {
932                                 if(a->GetKey()=="FullFileName")
933                                 {
934                                         GetGimmickView()->DumpTags(node->GetAttribute("FullFileName"));
935                                         return;
936                                 }
937                         }
938           }
939   }
940   
941
942   //================================================================
943
944   //================================================================
945   void WxTreeView::SortLevel(int level)
946   {       
947     GimmickDebugMessage(1,
948                         "WxTreeView::SortLevel(" 
949                         <<level<<")"
950                         <<std::endl);  
951     //Obtain the column name and the level that needs to be organized
952     
953     //    int l = level - 1;
954     //Sets the data for the items to be sorted
955     //    std::string att;
956     unsigned int ty=0;
957     int nbselected = 0;
958     int n = GetCtrl(level)->GetItemCount();
959     for (int i = 0; i < n; i++)
960       {
961         
962         //Gets current item data
963         ItemData* data = (ItemData*)GetCtrl(level)->GetItemData(i);
964         
965         //Extracts the node and the type of attribute   
966         tree::Node* nod = data->node;
967         if(i==0)
968           {
969             (*nod).GetAttributeDescriptor
970               (mLevelList[level].key[mLevelList[level].SortColumn])
971               .DecodeType( ty );
972           }
973         //Obtains the organizing attribute
974         data->attr = & (*nod).GetAttribute
975           (mLevelList[level].key[mLevelList[level].SortColumn]);
976         //Selected ?
977         data->selected = false;
978         if (GetCtrl(level)->GetItemState(i,wxLIST_STATE_SELECTED)>0)
979           {
980             data->selected = true;
981             nbselected++;
982           }
983
984       } 
985     GimmickDebugMessage(1,
986                         "WxTreeView::OnSort : " 
987                         <<nbselected<<" selected before sorting"
988                         <<std::endl);  
989
990     mIgnoreSelectedChanged = true; 
991     // 
992     if (mLevelList[level].SortAscending)
993       {
994         
995         if(ty==1)
996           {
997             GetCtrl(level)->SortItems(CompareFunctionInts, 0);
998           }
999         else
1000           {
1001             GetCtrl(level)->SortItems(CompareFunctionStrings, 0);
1002           }
1003         
1004       }
1005     else
1006       {
1007         if(ty==1)
1008           {
1009             GetCtrl(level)->SortItems(CompareFunctionInts, 1);
1010           }
1011         else
1012           {
1013             GetCtrl(level)->SortItems(CompareFunctionStrings, 1);
1014           }
1015       }
1016  
1017
1018     // Reselects the unselected 
1019     n = GetCtrl(level)->GetItemCount();
1020     int after = 0;
1021     for (int i = 0; i < n; i++)
1022       {
1023         
1024         //Gets current item data
1025         ItemData* data = (ItemData*)GetCtrl(level)->GetItemData(i);
1026   
1027         //  long item = -1;
1028         //    for ( ;; )
1029         //      {
1030         //      item = GetCtrl(level)->GetNextItem(item,wxLIST_NEXT_ALL);
1031         //      if ( item == -1 ) break;
1032         //Gets current item data
1033         //      ItemData* data = (ItemData*)GetCtrl(level)->GetItemData(item);
1034         // was selected ?
1035         
1036         if (data->selected)
1037           {
1038             nbselected--;
1039             if (nbselected==0)
1040               {
1041                 // if it is the last one we must process the selection
1042                 mIgnoreSelectedChanged = false;
1043               }
1044             GetCtrl(level)->SetItemState(i,
1045                                          wxLIST_STATE_SELECTED, 
1046                                          wxLIST_MASK_STATE 
1047                                          | wxLIST_MASK_TEXT 
1048                                          | wxLIST_MASK_IMAGE 
1049                                          | wxLIST_MASK_DATA 
1050                                          | wxLIST_MASK_WIDTH 
1051                                          | wxLIST_MASK_FORMAT);   
1052           }
1053         if (GetCtrl(level)->GetItemState(i,wxLIST_STATE_SELECTED)>0)
1054           {
1055             after++;
1056           }
1057
1058         
1059       }
1060     mIgnoreSelectedChanged = false; 
1061      GimmickDebugMessage(1,
1062                         "WxTreeView::SortLevel : " 
1063                         <<after<<" selected after sorting"
1064                         <<std::endl);  
1065   
1066   }
1067   //================================================================
1068
1069   
1070   //================================================================
1071   void WxTreeView::ValidateSelectedImages(bool isSelection)
1072   {
1073     GimmickDebugMessage(7,
1074                         "WxTreeView::ValidateSelectedImages" 
1075                         <<std::endl);
1076     const std::vector<tree::Node*>& sel(GetSelected(mLevelList.size()+1));
1077     GetGimmickView()->OnSelectionChange(sel,
1078                                         isSelection,(mLastSelected-1),
1079                                         !mIgnoreSelectedChanged);
1080  
1081   }
1082   //================================================================
1083
1084
1085   //================================================================
1086   void WxTreeView::GetNodes(std::vector<tree::Node*>& nodes, bool direction)
1087   {
1088         long item = mLastSelected;
1089         int level=mLevelList.size()-1;
1090         //Gets current item data
1091         long adr = GetCtrl(level)->GetItemData(item);
1092         //Extracts the node
1093         tree::Node* nod = ((ItemData*)adr)->node;
1094     for ( ;; )
1095     {
1096                 if(direction)
1097                 {
1098                         item = GetCtrl(level)->GetNextItem(item,
1099                                      wxLIST_NEXT_ABOVE);
1100                 }
1101                 else
1102                 {
1103                         item = GetCtrl(level)->GetNextItem(item,
1104                                      wxLIST_NEXT_BELOW);
1105                 }
1106         if ( item == -1 || item==0  )
1107                 {
1108             break;
1109                 }
1110                 if(GetCtrl(level)->GetItemState(item, wxLIST_STATE_SELECTED)==0 )
1111                 {
1112
1113                         adr = GetCtrl(level)->GetItemData(item);
1114                         nod = ((ItemData*)adr)->node;
1115                         nodes.push_back(nod);
1116                 }
1117     }
1118
1119   }
1120   //================================================================
1121    //=================================================
1122   void WxTreeView::OnKeyDown(wxListEvent &event)
1123   {
1124           if(event.GetKeyCode() == WXK_DELETE)
1125           {
1126                    wxBusyCursor busy;
1127                    std::string temp = "0";
1128                    RemoveSelected(temp);
1129                    GetGimmickView()->ClearSelection();
1130           }
1131                   
1132   }
1133   //================================================================
1134
1135   //================================================================
1136   // Should be in another place : not specific !
1137   void WxTreeView::GetSelectedAsString(std::vector<std::string>&s)
1138   {
1139     int level=mLevelList.size();
1140     const std::vector<tree::Node*>& sel=GetSelected(level+1);
1141     std::vector<tree::Node*>::const_iterator i;
1142     
1143     for (i=sel.begin(); i!=sel.end(); ++i)
1144       {
1145         std::string filename=(*i)->GetAttribute("FullFileName");
1146         s.push_back(filename);
1147       }
1148   }
1149
1150
1151
1152   //================================================================
1153   void WxTreeView::GetFilenamesAsString(const std::vector<tree::Node*>& nodes, std::vector<std::string>&s)
1154   {
1155     std::vector<tree::Node*>::const_iterator i;
1156     
1157     for (i=nodes.begin(); i!=nodes.end(); ++i)
1158       {
1159                   if((*i)->GetLevel()<mLevelList.size())
1160                   {
1161                          GetTreeHandler()->LoadChildren(*i,0);
1162                          GetFilenamesAsString((*i)->GetChildrenList(),s);
1163                   }
1164                   else
1165                   {
1166                         std::string filename=(*i)->GetAttribute("FullFileName");
1167                         s.push_back(filename);
1168                   }
1169       }
1170   }
1171
1172    //================================================================
1173
1174    //================================================================
1175   void WxTreeView::GetAttributes(std::vector<std::string>& areShown, std::vector<std::string>& notShown, int level)
1176   {
1177           areShown.clear();
1178           notShown.clear();
1179         tree::LevelDescriptor::AttributeDescriptorListType::const_iterator a;
1180         for (a  = GetTreeHandler()->GetTree().GetAttributeDescriptorList(level).begin();
1181              a != GetTreeHandler()->GetTree().GetAttributeDescriptorList(level).end();
1182              ++a)
1183         {
1184                 if(a->GetFlags()==creaImageIO::tree::AttributeDescriptor::EDITABLE && IsAttributeVisible(a->GetName(),level))
1185             {
1186                         areShown.push_back(a->GetName());
1187                 }
1188         }
1189         notShown=mLevelList[level-1].notShownAtts;
1190   }
1191
1192   //================================================================
1193   void WxTreeView::SetNonVisibleAttributes(const std::vector<std::string>& notShown, int nlevel)
1194   {
1195         mLevelList[nlevel].notShownAtts=notShown;
1196   }
1197
1198   //================================================================
1199    void WxTreeView::CreateCtrl(std::vector<std::string>& notShown, int nlevel)
1200   {
1201         int ctrl_style = wxLC_REPORT | wxLC_VRULES;
1202     int col_style = wxLIST_FORMAT_LEFT;
1203         LevelType level;
1204         mLevelList[nlevel].SelectedUpToDate = true;
1205         mLevelList[nlevel].SortColumn = 0;
1206         mLevelList[nlevel].key.clear();
1207         
1208         mLevelList[nlevel].wxCtrl = new wxListCtrl(mLevelList[nlevel].wxSplitter,
1209                                           nlevel,
1210                                           wxDefaultPosition, 
1211                                           wxDefaultSize,
1212                                           ctrl_style);
1213         wxWindow* oldWin=mLevelList[nlevel].wxSplitter->GetWindow1();
1214         mLevelList[nlevel].wxSplitter->ReplaceWindow(oldWin,mLevelList[nlevel].wxCtrl);
1215         mLevelList[nlevel].wxSplitter->Initialize(mLevelList[nlevel].wxCtrl);
1216    
1217         // Create the columns : one for each attribute of the level
1218         int col = 0;
1219         std::string title;
1220
1221         tree::LevelDescriptor::AttributeDescriptorListType::const_iterator a;
1222         for (a  = GetTreeHandler()->GetTree().GetAttributeDescriptorList(nlevel+1).begin();
1223              a != GetTreeHandler()->GetTree().GetAttributeDescriptorList(nlevel+1).end();
1224              ++a)
1225
1226         {   
1227             if(a->GetFlags()!=creaImageIO::tree::AttributeDescriptor::PRIVATE && IsAttributeVisible(a->GetName(),nlevel+1))
1228               {
1229                   title=a->GetName();
1230                   std::string temp = a->GetKey();
1231                   if (temp.compare("ID") != 0)
1232                   {
1233                         mLevelList[nlevel].wxCtrl->InsertColumn(col, 
1234                                         crea::std2wx(title),
1235                                         col_style);
1236                         col++;
1237                   }
1238                 mLevelList[nlevel].key.push_back(a->GetKey());
1239               }
1240                 
1241           }
1242         oldWin->Destroy();
1243         UpdateLevel(1);
1244         }
1245
1246    //================================================================
1247   bool WxTreeView::IsAttributeVisible(const std::string& val, int level)
1248   {
1249           std::vector<std::string> ns=mLevelList[level-1].notShownAtts;
1250           std::vector<std::string>::iterator it;
1251           bool found=false;
1252           for(it=ns.begin();it!=ns.end()&&!found;++it)
1253           {
1254                   if(val.compare(*it)==0)
1255                   {
1256                           found=true;
1257                   }
1258           }
1259           return !found;
1260   }
1261  //================================================================
1262   //================================================================
1263
1264         RemoveAlertDlg::RemoveAlertDlg(wxWindow *parent, 
1265                                        wxString title,    
1266                                        const wxSize& size)
1267  :   wxDialog( parent, 
1268                   wxID_ANY, 
1269                   title,
1270                   wxDefaultPosition,
1271                   size,
1272                   wxDEFAULT_DIALOG_STYLE)
1273         {
1274             wxBoxSizer *topsizer = new wxBoxSizer(wxVERTICAL);
1275
1276                 //std::string out("To reload deleted patient, you should synchronize your database before.");  // JPR
1277                 //wxTextCtrl *text = new wxTextCtrl(this, wxID_ANY,crea::std2wx(out),wxDefaultPosition, wxSize(500,20));
1278                 wxTextCtrl *text = new wxTextCtrl(this, wxID_ANY,
1279                                         _T("To reload deleted patient, you should synchronize your database before."),
1280                                         wxDefaultPosition, wxSize(650,20));  // 650 vs 500 ? // JPRx
1281                 mcheck = new wxCheckBox(this, 5478, _T("Do not display this warning again!"));
1282                 Connect( mcheck->GetId(), wxEVT_COMMAND_CHECKBOX_CLICKED , (wxObjectEventFunction) &RemoveAlertDlg::onCheck ); 
1283                 wxSizer* buttonsSizer = this->CreateSeparatedButtonSizer(wxOK|wxCANCEL);
1284                 
1285                 topsizer->Add(text);
1286                 topsizer->Add(mcheck,0,wxGROW);
1287                 topsizer->Add(buttonsSizer,0,wxGROW);
1288                 SetSizer(topsizer, true);
1289                 mSave = false;
1290                 Layout();
1291         }
1292         RemoveAlertDlg::~RemoveAlertDlg(){};
1293         bool RemoveAlertDlg::isChecked()
1294         {
1295                 return mSave;
1296         }
1297         void RemoveAlertDlg::onCheck(wxCommandEvent &Event)
1298         {
1299                 mSave = mcheck->IsChecked();
1300         }
1301         
1302
1303   //================================================================
1304   //================================================================
1305   BEGIN_EVENT_TABLE(WxTreeView, wxPanel)   
1306   /*
1307     EVT_SIZE(MyFrame::OnSize)
1308
1309     EVT_MENU(LIST_QUIT, MyFrame::OnQuit)
1310     EVT_MENU(LIST_ABOUT, MyFrame::OnAbout)
1311     EVT_MENU(LIST_LIST_VIEW, MyFrame::OnListView)
1312     EVT_MENU(LIST_REPORT_VIEW, MyFrame::OnReportView)
1313     EVT_MENU(LIST_ICON_VIEW, MyFrame::OnIconView)
1314     EVT_MENU(LIST_ICON_TEXT_VIEW, MyFrame::OnIconTextView)
1315     EVT_MENU(LIST_SMALL_ICON_VIEW, MyFrame::OnSmallIconView)
1316     EVT_MENU(LIST_SMALL_ICON_TEXT_VIEW, MyFrame::OnSmallIconTextView)
1317     EVT_MENU(LIST_VIRTUAL_VIEW, MyFrame::OnVirtualView)
1318     EVT_MENU(LIST_SMALL_VIRTUAL_VIEW, MyFrame::OnSmallVirtualView)
1319
1320     EVT_MENU(LIST_FOCUS_LAST, MyFrame::OnFocusLast)
1321     EVT_MENU(LIST_TOGGLE_FIRST, MyFrame::OnToggleFirstSel)
1322     EVT_MENU(LIST_DESELECT_ALL, MyFrame::OnDeselectAll)
1323     EVT_MENU(LIST_SELECT_ALL, MyFrame::OnSelectAll)
1324     EVT_MENU(LIST_DELETE, MyFrame::OnDelete)
1325     EVT_MENU(LIST_ADD, MyFrame::OnAdd)
1326     EVT_MENU(LIST_EDIT, MyFrame::OnEdit)
1327     EVT_MENU(LIST_DELETE_ALL, MyFrame::OnDeleteAll)
1328     EVT_MENU(LIST_SORT, MyFrame::OnSort)
1329     EVT_MENU(LIST_SET_FG_COL, MyFrame::OnSetFgColour)
1330     EVT_MENU(LIST_SET_BG_COL, MyFrame::OnSetBgColour)
1331     EVT_MENU(LIST_TOGGLE_MULTI_SEL, MyFrame::OnToggleMultiSel)
1332     EVT_MENU(LIST_SHOW_COL_INFO, MyFrame::OnShowColInfo)
1333     EVT_MENU(LIST_SHOW_SEL_INFO, MyFrame::OnShowSelInfo)
1334     EVT_MENU(LIST_FREEZE, MyFrame::OnFreeze)
1335     EVT_MENU(LIST_THAW, MyFrame::OnThaw)
1336     EVT_MENU(LIST_TOGGLE_LINES, MyFrame::OnToggleLines)
1337     EVT_MENU(LIST_MAC_USE_GENERIC, MyFrame::OnToggleMacUseGeneric)
1338
1339     EVT_UPDATE_UI(LIST_SHOW_COL_INFO, MyFrame::OnUpdateShowColInfo)
1340     EVT_UPDATE_UI(LIST_TOGGLE_MULTI_SEL, MyFrame::OnUpdateToggleMultiSel)
1341 END_EVENT_TABLE()
1342
1343 BEGIN_EVENT_TABLE(MyListCtrl, wxListCtrl)
1344     EVT_LIST_BEGIN_DRAG(LIST_CTRL, MyListCtrl::OnBeginDrag)
1345     EVT_LIST_BEGIN_RDRAG(LIST_CTRL, MyListCtrl::OnBeginRDrag)
1346         
1347     EVT_LIST_BEGIN_LABEL_EDIT(-1, WxTreeView::OnBeginLabelEdit)
1348     EVT_LIST_END_LABEL_EDIT(-1, WxTreeView::OnEndLabelEdit)
1349         
1350     EVT_LIST_DELETE_ITEM(LIST_CTRL, MyListCtrl::OnDeleteItem)
1351     EVT_LIST_DELETE_ALL_ITEMS(LIST_CTRL, MyListCtrl::OnDeleteAllItems)
1352 #if WXWIN_COMPATIBILITY_2_4
1353     EVT_LIST_GET_INFO(LIST_CTRL, MyListCtrl::OnGetInfo)
1354     EVT_LIST_SET_INFO(LIST_CTRL, MyListCtrl::OnSetInfo)
1355 #endif
1356   */
1357     EVT_LIST_KEY_DOWN(-1, WxTreeView::OnKeyDown)
1358     EVT_LIST_ITEM_SELECTED(-1, WxTreeView::OnItemSelected)
1359         EVT_LIST_ITEM_RIGHT_CLICK(-1, WxTreeView::OnItemMenu)
1360     EVT_LIST_ITEM_DESELECTED(-1, WxTreeView::OnItemDeSelected)
1361         /*
1362     EVT_LIST_KEY_DOWN(LIST_CTRL, MyListCtrl::OnListKeyDown)
1363     EVT_LIST_ITEM_ACTIVATED(LIST_CTRL, MyListCtrl::OnActivated)
1364     EVT_LIST_ITEM_FOCUSED(LIST_CTRL, MyListCtrl::OnFocused)
1365 */
1366     EVT_LIST_COL_RIGHT_CLICK(-1, WxTreeView::OnColClick)
1367         
1368     EVT_LIST_COL_CLICK(-1, WxTreeView::OnColClick)
1369
1370         //EVT_LEFT_DOWN(WxTreeView::OnMouseClick)
1371         /*
1372     EVT_LIST_COL_BEGIN_DRAG(LIST_CTRL, MyListCtrl::OnColBeginDrag)
1373     EVT_LIST_COL_DRAGGING(LIST_CTRL, MyListCtrl::OnColDragging)
1374     EVT_LIST_COL_END_DRAG(LIST_CTRL, MyListCtrl::OnColEndDrag)
1375
1376     EVT_LIST_CACHE_HINT(LIST_CTRL, MyListCtrl::OnCacheHint)
1377
1378 #if USE_CONTEXT_MENU
1379     EVT_CONTEXT_MENU(MyListCtrl::OnContextMenu)
1380 #endif
1381     EVT_CHAR(MyListCtrl::OnChar)
1382
1383     EVT_RIGHT_DOWN(MyListCtrl::OnRightClick)
1384   */
1385 END_EVENT_TABLE()
1386   
1387 } // EO namespace creaImageIO
1388