updated .gitignore for .configs/
[ede] / explorer / src / ExplorerWindow.ec
index 5a5b37f..54a6a6a 100644 (file)
-public import "ecere"
+import "Explorer"
+import "IconBag"
+import "ToolBar"
 
-private:
-define guiApp = ((GuiApplication)__thisModule);
-define selectionColor = guiApp.currentSkin.selectionColor; //Color { 10, 36, 106 };
+#ifdef _DEBUG
+   define title = "Ecere Explorer (Debug)";
+#else
+   define title = "Ecere Explorer";
+#endif
 
-static char * iconNames[] = 
+/*
+define backgroundColor = Color { 30, 40, 50 }; //Color { 20, 20, 60 };
+define foregroundColor = lightGray; //white;
+define selectionColor = lightYellow;
+define selectionText = Color { 20, 30, 40 };
+define toolBarBackgroundColor = backgroundColor;//white; //Color { 240, 240, 250 };
+define toolBarForegroundColor = foregroundColor;//white; //Color { 240, 240, 250 };
+*/
+define backgroundColor = beige;//white; //Color { 128, 145, 175 }; //200, 224, 224 }; //lightGray;
+define foregroundColor = black;
+define selectionColor = app.currentSkin.selectionColor;
+define selectionText = app.currentSkin.selectionText;
+define toolBarBackgroundColor = backgroundColor;//white; //Color { 240, 240, 250 };
+define toolBarForegroundColor = foregroundColor;//white; //Color { 240, 240, 250 };
+
+enum ExplorerToolId
 {
-   "<:ecere>tango/16x16/mimetypes/file-x-generic.png",         /*none*/
-
-   "<:ecere>tango/16x16/mimetypes/file-x-generic.png",         /*normalFile*/
-   "<:ecere>tango/16x16/mimetypes/text-ews-work.png",          /*ewsFile*/
-   "<:ecere>tango/16x16/mimetypes/text-epj-assembly.png",      /*epjFile*/
-   "<:ecere>tango/16x16/mimetypes/text-ec-source.png",         /*ecFile*/
-   "<:ecere>tango/16x16/mimetypes/text-eh-header.png",         /*ehFile*/
-   "<:ecere>tango/16x16/mimetypes/text-c-source.png",          /*cFile*/
-   "<:ecere>tango/16x16/mimetypes/text-h-header.png",          /*hFile*/
-   "<:ecere>tango/16x16/mimetypes/text-cpp-source.png",        /*cppFile*/
-   "<:ecere>tango/16x16/mimetypes/text-hpp-header.png",        /*hppFile*/
-   "<:ecere>tango/16x16/mimetypes/text-x-generic.png",         /*textFile*/
-   "<:ecere>tango/16x16/mimetypes/text-html.png",              /*webFile*/
-   "<:ecere>tango/16x16/mimetypes/image-x-generic.png",        /*pictureFile*/
-   "<:ecere>tango/16x16/status/audio-volume-high.png",         /*soundFile*/
-   "<:ecere>tango/16x16/mimetypes/package-x-generic.png",      /*archiveFile*/
-   "<:ecere>tango/16x16/mimetypes/package-x-software.png",     /*packageFile*/
-   "<:ecere>tango/16x16/mimetypes/package-x-optical-disc.png", /*opticalMediaImageFile*/
-
-   "<:ecere>tango/16x16/places/folder.png",
-   "<:ecere>tango/16x16/status/folder-open.png",
-   "<:ecere>tango/16x16/devices/computer.png",
-   "<:ecere>tango/16x16/devices/drive-harddisk.png",
-   "<:ecere>tango/16x16/places/folder-remote.png",
-   "<:ecere>tango/16x16/devices/media-optical.png",
-   "<:ecere>tango/16x16/devices/drive-removable-media.png",
-   "<:ecere>tango/16x16/devices/media-floppy.png",
-   "<:ecere>tango/16x16/places/network-workgroup.png",
-   "<:ecere>tango/16x16/places/network-server.png",
-   "<:ecere>tango/16x16/places/folder-remote.png",
-
-   "<:ecere>tango/16x16/mimetypes/package-x-generic.png",      /*treeLoader*/
-   "<:ecere>tango/16x16/places/start-here.png"                 /*lineNumbers*/
+   none,
+   newWindow, goBack, goForward, goUp, goHome,
+   newFile, newFolder,
+   browse,
+   panelTree, panelSearch,
+   addressBar,
+   refresh,
+   viewList, viewDetails, viewIcons, viewCards, viewShowcase, viewTree, viewCustom,
+   previewPictures,
+
+   searchInFileName,
+   inFileNameMatchCase,
+   inFileNameMatchWord,
+   searchInFileContent,
+   inFileContentMatchCase,
+   inFileContentMatchWord,
+   searchInSubDirs,
+   searchStart,
+   searchStop,
+
+   hasHeader
 };
 
-public class FileSystemToolWindow : public Window
+class ExplorerWindow : Window
 {
-   BitmapResource icons[FileItemType];
+   text = title;
+   background = backgroundColor;
+   borderStyle = sizable;
+   hasMaximize = true;
+   hasMinimize = true;
+   hasClose = true;
+   hasMenuBar = true;
+   //tabCycle = true;
+   size = { 840, 480 };
+   minClientSize = { 600, 300 };
+   nativeDecorations = true;
+   tabCycle = true;
+
+   /*
+   bool userMode;
+   bool clipboard;
+
+   int treeSplit;
+   int searchSplit;
+   
+   ExplorerToolId lastViewId;
+*/
+
+   bool treeInitialized;
+   int historyIndex;
+   Array<HistoryItem> history { };
+
+
+   menu = Menu { };
+   
+   Menu fileMenu { menu, "File", f };
+   Menu windowMenu { menu, "Window", w };
+      MenuItem itemNewWindow
+      {
+         windowMenu, "New Window", n;
+         
+         bool NotifySelect(MenuItem selection, Modifiers mods)
+         {
+            ExplorerWindow { }.Create();
+            return true;
+         }
+      };
+
+   IconBag<ExplorerToolId> iconBag
+   {
+      //window = guiApp.desktop;
+      window = this;
+      alphaBlend = true;
+      iconNames =
+      [
+         "<:ecere>emblems/unreadable.png",         /* none */
+
+         "<:ecere>actions/windowNew.png",          /* newWindow */
+         "<:ecere>actions/goPrevious.png",         /* goBack */
+         "<:ecere>actions/goNext.png",             /* goForward */
+         "<:ecere>actions/goUp.png",               /* goUp */
+         "<:ecere>actions/goHome.png",             /* goHome */
+         "<:ecere>mimeTypes/file.png",             /* newFile */
+         "<:ecere>actions/folderNew.png",          /* newFolder */
+
+         ":browse.png",                            /* browse */
+
+         ":panel-tree.png",                        /* panelTree */
+         "<:ecere>actions/editFind.png",           /* panelSearch */
+
+         "",                                       /* addressBar */
+
+         "<:ecere>actions/viewRefresh.png",        /* refresh */
+
+         ":view-list.png",                         /* viewList */
+         ":view-details.png",                      /* viewDetails */
+         ":view-icons.png",                        /* viewIcons */
+         ":view-cards.png",                        /* viewCards */
+         ":view-showcase-right.png",               /* viewShowcase */
+         ":panel-tree.png",                        /* viewTree */
+         ":view-custom.png",                       /* viewCustom */
+         
+         "<:ecere>mimeTypes/image.png",            /* previewPictures */
+
+         "",                                       /* searchInFileName */
+         "<:ecere>emblems/unreadable.png",         /* inFileNameMatchCase */
+         "<:ecere>emblems/unreadable.png",         /* inFileNameMatchWord */
+         "",                                       /* searchInFileContent */
+         "<:ecere>emblems/unreadable.png",         /* inFileContentMatchCase */
+         "<:ecere>emblems/unreadable.png",         /* inFileContentMatchWord */
+         ":browse.png",                            /* searchInSubDirs */
+         "<:ecere>actions/editFind.png",           /* searchStart */
+         "<:ecere>emblems/unreadable.png",         /* searchStop */
+         "<:ecere>emblems/unreadable.png"          /* hasHeader */
+      ];
+   };
+
+   Stacker stack
+   {
+      this;
+      gap = 0;
+      direction = vertical;
+      background = backgroundColor;
+      opacity = 0.0f;
+      tabCycle = true;
+
+      anchor = { left = 0, top = 0, right = 0, bottom = 0 };
+      //moveable = false;
+   };
+
+   ToolBar/*<ExplorerToolId>*/ toolBar
+   {
+      stack, this;
+      size = { h = 32 };
+      //moveable = false;
+      borderStyle = none;
+      background = toolBarBackgroundColor;
+      tabCycle = true;
+
+      iconBag = iconBag;
+
+      void NotifyToolClick(ToolButton button)
+      {
+         ExplorerToolId id = (ExplorerToolId)button.id;
+         switch(id)
+         {
+            case none:
+               break;
+            case newWindow:
+               ExplorerWindow { }.Create();
+               break;
+            case goBack:
+            case goForward:
+               historyIndex += id == goBack ? -1 : 1;
+               GoToHistoryIndex(false, false, false);
+               break;
+            case goHome:
+            {
+               char * home = getenv("HOME");
+               if(home && home[0] && FileExists(home).isDirectory)
+                  GoTo(home, false, false);
+               break;
+            }
+            case goUp:
+            {
+               char * path = view.path;
+               char * newPath = new char[strlen(path)+1];
+               StripLastDirectory(path, newPath);
+               if(!newPath[0])
+               {
+                  newPath[0] = '/';
+                  newPath[1] = 0;
+               }
+               GoTo(newPath, false, false);
+               delete newPath;
+               break;
+            }
+            case newFile:
+               if(CreateNewFileDialog { master = this, parent = parent, currentDirectory = view.path }.Modal() == ok )
+                  Refresh();
+               break;
+            case newFolder:
+               if(CreateDirectoryDialog { master = this, parent = parent, currentDirectory = view.path }.Modal() == ok )
+                  Refresh();
+               break;
+            case panelTree:
+               SearchStop();
+               //ToggleSearchMode(false);
+               tree.visible = button.checked;
+               split.visible = button.checked;
+               if(button.checked)
+               {
+                  split.rightPane = view;
+                  view.anchor = { top = 0, bottom = 0, right = 0 };
+                  GoTo(addressBar.path, false, false);
+                  ReadyTree();
+               }
+               else
+               {
+                  split.rightPane = null;
+                  view.anchor = { left = 2, top = 0, bottom = 0, right = 0 };
+               }
+               //search.visible = !button.checked;
+               panels.size = { panels.size.w, panels.size.h }; // TOFIX : another Stacker fix needed
+               break;
+            case panelSearch:
+               ToggleSearchMode(button.checked);
+
+               //tree.visible = false; //!button.checked;
+               //split.visible = false; //!button.checked;
+               if(button.checked)
+               {
+                  /*split.rightPane = view;
+                  view.anchor = { top = 0, bottom = 0, right = 0 };*/
+                  //split.rightPane = null;
+                  //view.anchor = { left = 2, top = 0, bottom = 0, right = 0 };
+
+                  //SearchStart();
+                  searchInFileName.Activate();
+               }
+               else
+               {
+                  //split.rightPane = null;
+                  //view.anchor = { left = 2, top = 0, bottom = 0, right = 0 };
+
+                  GoTo(addressBar.path, false, false);
+               }
+               //panels.size = { panels.size.w, panels.size.h }; // TOFIX : another Stacker fix needed
+               break;
+            case refresh:
+               Refresh();
+               break;
+            case previewPictures:
+               view.previewPictures = button.checked;
+               view.Refresh();
+               break;
+            case viewList:
+               view.details = false;
+               view.treeBranches = false;
+               view.Refresh();
+               break;
+            case viewDetails:
+               view.details = true;
+               view.treeBranches = false;
+               view.Refresh();
+               break;
+            case viewIcons:
+            case viewCards:
+               //SwitchViews(toolId);
+               view.details = false;
+               view.treeBranches = false;
+               view.Refresh();
+               break;
+            case viewShowcase:
+               view.preview = button.checked;
+               view.Refresh();
+               break;
+            case viewTree:
+               view.treeBranches = button.checked;
+               view.Refresh();
+               break;
+            case hasHeader:
+               view.hasHeader ^= true;
+               break;
+         }
+         view.Activate();
+      }
+   };
+
+   Window { toolBar, size = { w = 8 }, inactive = true };
+   ToolButton goBack { toolBar, this, id = ExplorerToolId::goBack, hotKey = { left, alt = true }, disabled = true };
+   Window { toolBar, size = { w = 2 }, inactive = true };
+   ToolButton goForward { toolBar, this, id = ExplorerToolId::goForward, hotKey = { right, alt = true }, disabled = true };
+   Window { toolBar, size = { w = 2 }, inactive = true };
+   ToolButton refresh { toolBar, this, id = ExplorerToolId::refresh, hotKey = { r, ctrl = true } };
+   Window { toolBar, size = { w = 2 }, inactive = true };
+   ToolButton goHome { toolBar, this, id = ExplorerToolId::goHome, hotKey = { h, ctrl = true } };
+   Window { toolBar, size = { w = 8 }, inactive = true };
+   PathBox addressBar
+   {
+      toolBar, this;
+      size = { 300, 22 }, id = ExplorerToolId::addressBar;
+      typeExpected = directory;
+      borderStyle = deep;
+      background = toolBarBackgroundColor;
+      foreground = toolBarForegroundColor;
+      selectionColor = selectionColor;
+      selectionText = selectionText;
+
+      bool OnKeyDown(Key key, unichar ch)
+      {
+         if((SmartKey)key == enter)
+         {
+            // how to make enter effect a modification
+            // how to implement in PathBox
+         }
+         return true;
+      }
+
+      bool NotifyModified(PathBox pathBox)
+      {
+         GoTo(pathBox.path, false, false);
+         return true;
+      }
+   };
+   FlipStacker { toolBar, spring = previous };
+   Window { toolBar, size = { w = 8 }, inactive = true };
+   ToolButton newFile { toolBar, this, id = ExplorerToolId::newFile, hotKey = { n, ctrl = true } };
+   Window { toolBar, size = { w = 2 }, inactive = true };
+   ToolButton newFolder { toolBar, this, id = ExplorerToolId::newFolder, hotKey = { d, ctrl = true } };
+   Window { toolBar, size = { w = 8 }, inactive = true };
+   ToolButton goUp { toolBar, this, id = ExplorerToolId::goUp, hotKey = { up, alt = true } };
+   Window { toolBar, size = { w = 8 }, inactive = true };
+   //GroupToggleToolButton selectedPanel;
+   ToggleToolButton panelTree   { toolBar, this, id = ExplorerToolId::panelTree, hotKey = { t, ctrl = true }/*, selected = &selectedPanel*//*, checked = true*/ };
+   ToggleToolButton panelSearch { toolBar, this, id = ExplorerToolId::panelSearch, hotKey = { f, ctrl = true }/*, selected = &selectedPanel*/ };
+   //selectedPanel = panelTree;
+   Window { toolBar, size = { w = 8 }, inactive = true };
+   /*OptionToolButton selectedView;
+   OptionToolButton viewList     { toolBar, this, id = ExplorerToolId::viewList, selected = &selectedView, checked = true };
+   OptionToolButton viewDetails  { toolBar, this, id = ExplorerToolId::viewDetails, selected = &selectedView };
+   OptionToolButton viewIcons    { toolBar, this, id = ExplorerToolId::viewIcons, selected = &selectedView };
+   OptionToolButton viewTiles    { toolBar, this, id = ExplorerToolId::viewCards, selected = &selectedView };
+   OptionToolButton viewShowcase { toolBar, this, id = ExplorerToolId::viewShowcase, selected = &selectedView };
+   OptionToolButton viewTree     { toolBar, this, id = ExplorerToolId::viewTree, selected = &selectedView };
+   selectedView = viewList;*/
+   //ToggleToolButton viewList     { toolBar, this, id = ExplorerToolId::viewList, checked = true };
+   ToggleToolButton viewDetails  { toolBar, this, id = ExplorerToolId::viewDetails };
+   //ToggleToolButton viewIcons    { toolBar, this, id = ExplorerToolId::viewIcons };
+   //ToggleToolButton viewTiles    { toolBar, this, id = ExplorerToolId::viewCards };
+   ToggleToolButton viewShowcase { toolBar, this, id = ExplorerToolId::viewShowcase };
+   ToggleToolButton viewTree     { toolBar, this, id = ExplorerToolId::viewTree };
+   Window { toolBar, size = { w = 8 }, inactive = true };
+   ToggleToolButton previewPictures { toolBar, this, id = ExplorerToolId::previewPictures };
+
+   Window { toolBar, size = { w = 8 }, inactive = true };
+   ToolButton hasHeader { toolBar, this, id = ExplorerToolId::hasHeader };
+   Window { toolBar, size = { w = 8 }, inactive = true };
+   ToolButton newWindow { toolBar, this, id = ExplorerToolId::newWindow, hotKey = { w, ctrl = true } };
+   Window { toolBar, size = { w = 8 }, inactive = true };
+
+
+   /*void OnDestroy()
+   {
+      iconBag.window = null;
+      delete iconBag;
+   }*/
+
+   bool OnLoadGraphics()
+   {
+      iconBag.Load();
+      return true;
+   }
+
+   void OnUnloadGraphics()
+   {
+      iconBag.Unload();
+   }
+
+   Stacker panels
+   {
+      stack, this;
+      gap = 0;
+      direction = horizontal;
+      opacity = 0.0f;
+      tabCycle = true;
+
+      anchor.left = 0;
+      //anchor.bottom = 0;
+      anchor.right = 0;
+
+      //size = { h = 400 };
+   };
+
+   FlipStacker flipStack { stack, spring = previous };
+
+   //Window searchSpace { stack, size = { h = 32 }, background = toolBarBackgroundColor, inactive = true, opacity = 0.0f };
+
+   ToolBar/*<ExplorerToolId>*/ searchBar
+   {
+      stack, this;
+      size = { h = 32 };
+      visible = false;
+      //moveable = false;
+      borderStyle = none;
+      background = toolBarBackgroundColor;
+      tabCycle = true;
+      iconBag = iconBag;
+
+      void NotifyToolClick(ToolButton button)
+      {
+         ExplorerToolId id = (ExplorerToolId)button.id;
+         switch(id)
+         {
+            case none:
+               break;
+            case searchStart:
+               SearchStart();
+               break;
+            case searchStop:
+               SearchStop();
+               break;
+         }
+         view.Activate();
+      }
+   };
+
+
+   Window { searchBar, size = { w = 8 }, inactive = true };
+   Label { searchBar, this, labeledWindow = searchInFileName};
+   Window { searchBar, size = { w = 2 }, inactive = true };
+   EditBox searchInFileName
+   {
+      searchBar, this;
+      size = { 200, 22 }, id = ExplorerToolId::searchInFileName;
+      borderStyle = deep;
+      background = toolBarBackgroundColor;
+      foreground = toolBarForegroundColor;
+      selectionColor = selectionColor;
+      selectionText = selectionText;
+      text = "File Name:";
+
+      bool NotifyKeyDown(EditBox editBox, Key key, unichar ch)
+      {
+         if((SmartKey)key == enter)
+            SearchStart();
+         return true;
+      }
+
+      /*bool NotifyActivate(Window window, bool active, Window previous)
+      {
+         if(active)
+         {
+            toolBar.focusHolder = window;
+         }
+         return true;
+      }*/
+   };
+   Window { searchBar, size = { w = 2 }, inactive = true };
+#ifndef __WIN32__
+   ToggleToolButton inFileNameMatchCase { searchBar, this, id = ExplorerToolId::inFileNameMatchCase };
+#endif
+   ToggleToolButton inFileNameMatchWord { searchBar, this, id = ExplorerToolId::inFileNameMatchWord };
+   Window { searchBar, size = { w = 8 }, inactive = true };
+   Label { searchBar, this, labeledWindow = searchInFileContent};
+   Window { searchBar, size = { w = 2 }, inactive = true };
+   EditBox searchInFileContent
+   {
+      searchBar, this;
+      size = { 200, 22 }, id = ExplorerToolId::searchInFileContent;
+      borderStyle = deep;
+      background = toolBarBackgroundColor;
+      foreground = toolBarForegroundColor;
+      selectionColor = selectionColor;
+      selectionText = selectionText;
+      text = "File Content:";
+
+      bool NotifyKeyDown(EditBox editBox, Key key, unichar ch)
+      {
+         if((SmartKey)key == enter)
+            SearchStart();
+         return true;
+      }
+
+      /*bool NotifyActivate(Window window, bool active, Window previous)
+      {
+         if(active)
+            toolBar.focusHolder = window;
+         return true;
+      }*/
+   };
+   FlipStacker { searchBar, spring = previous };
+   ToggleToolButton inFileContentMatchCase { searchBar, this, id = ExplorerToolId::inFileContentMatchCase };
+   ToggleToolButton inFileContentMatchWord { searchBar, this, id = ExplorerToolId::inFileContentMatchWord };
+   Window { searchBar, size = { w = 8 }, inactive = true };
+   ToggleToolButton searchInSubDirs { searchBar, this, id = ExplorerToolId::searchInSubDirs, checked = true };
+   Window { searchBar, size = { w = 8 }, inactive = true };
+   ToolButton searchStart { searchBar, this, id = ExplorerToolId::searchStart, hotKey = { s, ctrl = true } };
+   Window { searchBar, size = { w = 8 }, inactive = true };
+   ToolButton searchStop { searchBar, this, id = ExplorerToolId::searchStop, hotKey = { escape }, disabled = true; };
+   Window { searchBar, size = { w = 8 }, inactive = true };
+
+
+
+   //Window { searchBar, size = { h = 1 } };
+
+   /*SearchPanel searchPanel
+   {
+      panels, this;
+   };*/
+
+   /*Window hack
+   {
+      panels, this;
+      anchor.top = 0;
+      anchor.bottom = 0;
+      anchor.right = 0;
+      borderStyle = none;
+      background = backgroundColor;
+   };*/
+
+   /*Tree*/FileSystemBox tree//;
+   {
+      panels, this;
+      size = { w = 240 };
+      borderStyle = none;
+      background = backgroundColor;
+      foreground = foregroundColor;
+      selectionColor = selectionColor;
+      selectionText = selectionText;
+      visible = false;
+      anchor.top = 0;
+      anchor.bottom = 0;
+      //anchor = { left = 0, top = 0, bottom = 0 };
+
+      treeBranches = true;
+      foldersOnly = true;
+      autoLoad = false;
+
+      bool NotifyNodeSelect(FileSystemBox box, FileSystemBoxSelection selection)
+      {
+         if(treeInitialized)
+         {
+            FileSystemNode node = selection.node;
+            if(node)
+            {
+               char p[MAX_LOCATION];
+               node.GetPath(p);
+               GoTo(node.path, false, true);
+            }
+         }
+         return true;
+      }
+
+      /*bool NotifyActivate(Window window, bool active, Window previous)
+      {
+         if(active)
+            toolBar.focusHolder = window;
+         return true;
+      }*/
+   };
+
+   PaneSplitter split
+   {
+      panels, this;
+      visible = false;
+      leftPane = tree;//, rightPane = view;
+      split = 300;
+   };
+
+   FileSystemBox view
+   {
+      panels, this;
+      borderStyle = none;
+      background = backgroundColor;
+      foreground = foregroundColor;
+      selectionColor = selectionColor;
+      selectionText = selectionText;
+      anchor.top = 0;
+      anchor.bottom = 0;
+      anchor.right = 0;
+      //anchor = { left = 2, top = 0, bottom = 0, right = 0 };
+
+      locationBox = addressBar;
+      navigateFolders = true;
+      multiSelect = true;
+      autoLoad = false;
+
+      bool NotifyNodeOpen(FileSystemBox box, FileSystemBoxSelection selection)
+      {
+         FileSystemNode node = selection.node;
+         if(node)
+         {
+            if(node.type.isFile)
+            {
+               char path[MAX_LOCATION];
+            #ifndef __WIN32__
+               char command[MAX_LOCATION];
+               node.GetPath(path);
+               /*_FileType t = node.type;
+               if(t == ewsFile || t == epjFile ||
+                     t == ecFile || t == ehFile ||
+                     t == cppFile || t == hppFile ||
+                     t == cFile || t == hFile ||
+                     t == textFile || t == webFile)*/
+                  sprintf(command, "gnome-open \"%s\"", path);
+               /*else
+                  sprintf(command, "%s", path);*/
+               Execute(command);
+            #else
+               node.GetPath(path);
+               ShellOpen(path);
+            #endif
+            }
+            else if(node.type.isFolder)
+               GoTo(node.path, true, false);
+         }
+         UpdateHistoryItem(selection);
+         return true;
+      }
+
+      bool NotifyNodeSelect(FileSystemBox box, FileSystemBoxSelection selection)
+      {
+         UpdateHistoryItem(selection);
+         return true;
+      }
+
+      /*bool NotifyActivate(Window window, bool active, Window previous)
+      {
+         if(active)
+            toolBar.focusHolder = window;
+         return true;
+      }*/
+   };
+
+   FileSystemSearch searchThread
+   {
+      owner = this, fsb = view, tree = tree/*, searchPanel = this*/;
+
+      /*bool ExplorerWindow::NotifyUpdateSearchLocation(FileSystemSearch search, char * location)
+      {
+         char string[MAX_LOCATION + 2048];
+         sprintf(string, "%s (Searching %s)", title, location);
+         PrintLn(string); //view.results.text = string;
+         text = string;
+         return true;
+      }*/
+
+      bool ExplorerWindow::NotifySearchTerminated(FileSystemSearch search)
+      {
+         searchStop.disabled = true;
+         return true;
+      }
+   };
+
+   void ToggleSearchMode(bool inSearch)
+   {
+      SearchStop();
+      //search.visible = inSearch;
+      //panelSearch.checked = inSearch; // <------ this is toggling panelSearch even though it shouldn't
+      //searchSpace.visible = !inSearch;
+      searchBar.visible = inSearch;
+      history[historyIndex].inSearch = inSearch;
+      size = { size.w, size.h };
+      view.pathColumn = inSearch;
+      /*if(inSearch)
+         searchThread.InitResults();*/
+      if(inSearch && /*(*/searchInFileName.contents[0]/* || searchInFileContents.contents[0])*/)
+         SearchStart();
+   }
+
+   void ReadyTree()
+   {
+      if(tree.visible)
+      {
+         if(!treeInitialized)
+         {
+            tree.path = "/"; // this should be available as a parameter
+            treeInitialized = true;
+         }
+         tree.SelectLocation(view.path);
+      }
+   }
+
+   void Refresh()
+   {
+      if(searchBar.visible)
+         SearchStart();
+      else
+      {
+         if(tree.visible)
+            tree.Refresh();
+         view.Refresh();
+      }
+   }
+
+   void GoTo(char * location, bool viewIsAtLocation, bool treeIsAtLocation)
+   {
+      HistoryItem item = null;
+      if(!history.count || fstrcmp(history[historyIndex].path, location))
+      {
+         int c;
+         for(c = 0; c < history.count; c++)
+            if(!fstrcmp(history[c].path, location))
+               break;
+         if(c == history.count)
+         {
+            item = { path = CopyString(location) };
+            if(history.count)
+            {
+               while(historyIndex < history.count-1)
+               {
+                  delete history[history.count-1].path;
+                  history.count--;
+               }
+            }
+            history.Add(item);
+            historyIndex = history.count-1;
+         }
+         else
+            historyIndex = c;
+      }
+      GoToHistoryIndex(viewIsAtLocation, treeIsAtLocation, item != null);
+   }
+
+   void GoToHistoryIndex(bool viewIsAtLocation, bool treeIsAtLocation, bool updateHistoryItem)
+   {
+      HistoryItem item = history[historyIndex];
+
+      goBack.disabled = historyIndex == 0;
+      goForward.disabled = historyIndex == history.count-1;
+      goUp.disabled = !fstrcmp(item.path, "/");
+
+      if(!viewIsAtLocation)
+      {
+         if(item.inSearch != panelSearch.checked)
+         {
+            ToggleSearchMode(item.inSearch);
+            if(item.inSearch)
+               SearchStart();
+         }
+         if(!item.inSearch)
+         /*{
+            //SearchStart();
+         }
+         else*/
+         {
+            view.path = item.path;
+            item.holdRecordingSelection = true;
+            view.SelectMultipleByPath(item.selection);
+         }
+      }
+      if(tree.visible && !treeIsAtLocation)
+         tree.SelectLocation(item.path);
+
+      if(updateHistoryItem)
+         UpdateHistoryItem(view.selection);
+   }
 
-   FileSystemToolWindow()
+   void UpdateHistoryItem(FileSystemBoxSelection selection)
    {
-      FileItemType c;
-      for(c = 0; c < FileItemType::enumSize; c++)
+      HistoryItem item = history[historyIndex];
+
+      if(!item.holdRecordingSelection)
       {
-         icons[c] = BitmapResource { iconNames[c], alphaBlend = true };
-         AddResource(icons[c]);
+         if(selection.node || (selection.nodes && selection.nodes.count))
+         {
+            item.selection.Free();
+            if(selection.nodes.count)
+            {
+               for(node : selection.nodes)
+                  item.selection.Add(CopyString(node.path));
+            }
+            else if(selection.node)
+               item.selection.Add(CopyString(selection.node.path));
+         }
       }
+      else
+         item.holdRecordingSelection = false;
+   }
+
+   void SearchStart()
+   {
+      SearchStop();
+      searchThread.active = true;
+
+      searchThread.optionSubdirs = searchInSubDirs.checked == true;
+      searchThread.optionTree = view.treeBranches; //(options.subdirs.checked && options.tree.checked);
+      searchThread.optionBrowser = tree.visible; //(options.subdirs.checked && options.browser.checked);
+#ifndef __WIN32__
+      searchThread.optionNameMatchCase = inFileNameMatchCase.checked;
+#else
+      searchThread.optionNameMatchCase = false;
+#endif
+      searchThread.optionNameMatchWord = inFileNameMatchWord.checked;
+      searchThread.optionContentMatchCase = inFileContentMatchCase.checked;
+      searchThread.optionContentMatchWord = inFileContentMatchWord.checked;
+
+      strcpy(searchThread.location, view.path);
+      strcpy(searchThread.nameSearch, searchInFileName.contents);
+      strcpy(searchThread.contentSearch, searchInFileContent.contents);
+
+      //actions.startStop.text = "Stop Search";
+      //actions.clear.disabled = false;
+      //view.results.Clear();
+      //view.results.hasHeader = !searchThread.optionTree;
+      //view.results.treeBranches = searchThread.optionTree;
+      //view.browser.Clear();
+      //ToggleBrowserDisplay(searchThread.optionBrowser);
+
+      //view.browser.text = "Browser";
+      /*{
+         char string[MAX_LOCATION + 2048];
+         sprintf(string, "%s (Searching %s)", title, view.path);
+         //PrintLn(string); //view.results.text = string;
+         text = string;
+      }*/
+      searchThread.InitResults();
+      searchThread.Create();
+      searchStop.disabled = false;
+      //Update(null);
    }
+
+   bool SearchStop()
+   {
+      if(searchThread.active)
+      {
+         searchThread.terminate = true;
+         //searchStop.disabled = true;
+         app.Unlock();
+            searchThread.Wait();
+         app.Lock();
+         return true;
+      }
+      return false;
+   }
+
+   /*ExplorerSearch search
+   {
+      deep, this;
+      visible = false;
+      tabCycle = true;
+      size = Size { 624, 268 };
+      anchor = Anchor { left = 0, top = 0, bottom = 0 };
+   };
+
+   ExplorerViewSearch results;*/
+
+   /*Window viewHolder
+   {
+      parent = deep, master = this;
+      tabCycle = true;
+      anchor = Anchor { top = 0, bottom = 0, right = 0 };
+   };*/
+
+   // Preview / Showcase
+   /*PreviewArea previewArea
+   {
+      panels, this;
+   };*/
+
+   //FlipStacker flipPanels { panels, spring = previous };
+
+   /*bool TreeNotifyBranchSelect(ExplorerTree tree, ExplorerFileBranch branch)
+   {
+      if(branch)
+      {
+         char path[MAX_LOCATION];
+         branch.GetPath(path);
+         toolBar.addressBar.contents = path;
+         view.Load(branch);
+      }
+      return true;
+   }*/
+   
+   /*bool ViewNotifyItemOpen(ExplorerView view, ExplorerFileItem item)
+   {
+      ExplorerFileBranch branch = tree.branch;
+      if(item && branch)
+      {
+         if(item.type.isFolderType)
+         {
+            ExplorerFileBranch child;
+            
+            if(!branch.loaded || !branch.childrenLoaded)
+               BranchLoad(branch, tree.tree);
+
+            for(child = branch.children.first; child; child = child.next)
+               if(!strcmp(child.name, item.name))
+                  break;
+            
+            if(child)
+            {
+               if(branch.row.collapsed)
+                  child.row.collapsed = true;
+               child.EnsureVisible(false);
+               tree.Select(child);
+            }
+         }
+         else
+         {
+            char path[MAX_LOCATION];
+            branch.GetPath(path);
+            PathCat(path, item.name);
+            ShellOpen(path);
+         }
+      }
+   }*/
+
+   /*void SwitchViews(ExplorerToolId viewId)
+   {
+      ExplorerFileBranch branch = tree.branch;
+      view.Destroy(0);
+      switch(viewId)
+      {
+         case viewList:     view = ExplorerViewList     { parent = viewHolder, master = this }; break;
+         case viewDetails:  view = ExplorerViewDetails  { parent = viewHolder, master = this }; break;
+         case viewIcons:    view = ExplorerViewIcons    { parent = viewHolder, master = this }; break;
+         case viewCards:    view = ExplorerViewCards    { parent = viewHolder, master = this }; break;
+         case viewShowcase: view = ExplorerViewShowcase { parent = viewHolder, master = this }; break;
+      }
+      view.tabCycle = true;
+      view.previewPictures = toolBar.previewPictures.checked;
+      view.anchor = Anchor { left = 0, top = 0, bottom = 0, right = 0 };
+      view.NotifyItemOpen = ViewNotifyItemOpen;
+      view.Create();
+      view.Load(branch);
+      lastViewId = viewId;
+   }*/
+
+   /*void SearchLocation(char * location)
+   {
+      GoTo(location);
+      search.location.editBox.contents = location;
+   }*/
+
+   bool OnPostCreate()
+   {
+      //userMode = true;
+      addressBar.path = view.path;
+      ReadyTree();
+      return true;
+   }
+
+   bool OnClose(bool parentClosing)
+   {
+      SearchStop();
+      return true;
+   }
+
+   /*ExplorerWindow()
+   {
+      userMode = false;
+
+      treeSplit = 300;
+      searchSplit = 200;
+
+      view = ExplorerViewList
+      {
+         parent = viewHolder, master = this;
+         tabCycle = true;
+         previewPictures = toolBar.previewPictures.checked;
+         anchor = Anchor { left = 0, top = 0, bottom = 0, right = 0 };
+         NotifyItemOpen = ViewNotifyItemOpen;
+      };
+      lastViewId = viewList;
+      
+      tree.Load();
+      view.Load(tree.root);
+   }*/
+
+   /*void InitTree()
+   {
+   }*/
+
+   /*void InitSearch()
+   {
+   }*/
 }
 
+//class TreeFileSystemBox : FileSystemBox { }
+
+class HistoryItem
+{
+   char * path;
+   bool holdRecordingSelection;
+   bool inSearch;
+   Array<String> selection { };
+
+   ~HistoryItem()
+   {
+      delete path;
+   }
+}