(function() {
  var $, AddDialog, BufferedProcess, CompositeDisposable, CopyDialog, Directory, DirectoryView, FileView, LocalStorage, Minimatch, MoveDialog, TreeView, View, fs, path, shell, toggleConfig, _, _ref, _ref1,
    __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; },
    __hasProp = {}.hasOwnProperty,
    __extends = function(child, parent) { for (var key in parent) { if (__hasProp.call(parent, key)) child[key] = parent[key]; } function ctor() { this.constructor = child; } ctor.prototype = parent.prototype; child.prototype = new ctor(); child.__super__ = parent.prototype; return child; },
    __indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (i in this && this[i] === item) return i; } return -1; };

  path = require('path');

  shell = require('shell');

  _ = require('underscore-plus');

  _ref = require('atom'), BufferedProcess = _ref.BufferedProcess, CompositeDisposable = _ref.CompositeDisposable;

  _ref1 = require('atom-space-pen-views'), $ = _ref1.$, View = _ref1.View;

  fs = require('fs-plus');

  AddDialog = null;

  MoveDialog = null;

  CopyDialog = null;

  Minimatch = null;

  Directory = require('./directory');

  DirectoryView = require('./directory-view');

  FileView = require('./file-view');

  LocalStorage = window.localStorage;

  toggleConfig = function(keyPath) {
    return atom.config.set(keyPath, !atom.config.get(keyPath));
  };

  module.exports = TreeView = (function(_super) {
    __extends(TreeView, _super);

    function TreeView() {
      this.onStylesheetsChanged = __bind(this.onStylesheetsChanged, this);
      this.resizeTreeView = __bind(this.resizeTreeView, this);
      this.resizeStopped = __bind(this.resizeStopped, this);
      this.resizeStarted = __bind(this.resizeStarted, this);
      return TreeView.__super__.constructor.apply(this, arguments);
    }

    TreeView.prototype.panel = null;

    TreeView.content = function() {
      return this.div({
        "class": 'tree-view-resizer tool-panel',
        'data-show-on-right-side': atom.config.get('tree-view.showOnRightSide')
      }, (function(_this) {
        return function() {
          _this.div({
            "class": 'tree-view-scroller',
            outlet: 'scroller'
          }, function() {
            return _this.ol({
              "class": 'tree-view full-menu list-tree has-collapsable-children focusable-panel',
              tabindex: -1,
              outlet: 'list'
            });
          });
          return _this.div({
            "class": 'tree-view-resize-handle',
            outlet: 'resizeHandle'
          });
        };
      })(this));
    };

    TreeView.prototype.initialize = function(state) {
      this.disposables = new CompositeDisposable;
      this.focusAfterAttach = false;
      this.roots = [];
      this.scrollLeftAfterAttach = -1;
      this.scrollTopAfterAttach = -1;
      this.selectedPath = null;
      this.ignoredPatterns = [];
      this.handleEvents();
      process.nextTick((function(_this) {
        return function() {
          var onStylesheetsChanged;
          _this.onStylesheetsChanged();
          onStylesheetsChanged = _.debounce(_this.onStylesheetsChanged, 100);
          _this.disposables.add(atom.styles.onDidAddStyleElement(onStylesheetsChanged));
          _this.disposables.add(atom.styles.onDidRemoveStyleElement(onStylesheetsChanged));
          return _this.disposables.add(atom.styles.onDidUpdateStyleElement(onStylesheetsChanged));
        };
      })(this));
      this.updateRoots(state.directoryExpansionStates);
      this.selectEntry(this.roots[0]);
      if (state.selectedPath) {
        this.selectEntryForPath(state.selectedPath);
      }
      this.focusAfterAttach = state.hasFocus;
      if (state.scrollTop) {
        this.scrollTopAfterAttach = state.scrollTop;
      }
      if (state.scrollLeft) {
        this.scrollLeftAfterAttach = state.scrollLeft;
      }
      this.attachAfterProjectPathSet = state.attached && _.isEmpty(atom.project.getPaths());
      if (state.width > 0) {
        this.width(state.width);
      }
      if (state.attached) {
        return this.attach();
      }
    };

    TreeView.prototype.attached = function() {
      if (this.focusAfterAttach) {
        this.focus();
      }
      if (this.scrollLeftAfterAttach > 0) {
        this.scroller.scrollLeft(this.scrollLeftAfterAttach);
      }
      if (this.scrollTopAfterAttach > 0) {
        return this.scrollTop(this.scrollTopAfterAttach);
      }
    };

    TreeView.prototype.detached = function() {
      return this.resizeStopped();
    };

    TreeView.prototype.serialize = function() {
      var _ref2;
      return {
        directoryExpansionStates: new (function(roots) {
          var root, _i, _len;
          for (_i = 0, _len = roots.length; _i < _len; _i++) {
            root = roots[_i];
            this[root.directory.path] = root.directory.serializeExpansionState();
          }
          return this;
        })(this.roots),
        selectedPath: (_ref2 = this.selectedEntry()) != null ? _ref2.getPath() : void 0,
        hasFocus: this.hasFocus(),
        attached: this.panel != null,
        scrollLeft: this.scroller.scrollLeft(),
        scrollTop: this.scrollTop(),
        width: this.width()
      };
    };

    TreeView.prototype.deactivate = function() {
      var root, _i, _len, _ref2;
      _ref2 = this.roots;
      for (_i = 0, _len = _ref2.length; _i < _len; _i++) {
        root = _ref2[_i];
        root.directory.destroy();
      }
      this.disposables.dispose();
      if (this.panel != null) {
        return this.detach();
      }
    };

    TreeView.prototype.handleEvents = function() {
      this.on('dblclick', '.tree-view-resize-handle', (function(_this) {
        return function() {
          return _this.resizeToFitContent();
        };
      })(this));
      this.on('click', '.entry', (function(_this) {
        return function(e) {
          if (e.target.classList.contains('entries')) {
            return;
          }
          if (!(e.shiftKey || e.metaKey || e.ctrlKey)) {
            return _this.entryClicked(e);
          }
        };
      })(this));
      this.on('mousedown', '.entry', (function(_this) {
        return function(e) {
          return _this.onMouseDown(e);
        };
      })(this));
      this.on('mousedown', '.tree-view-resize-handle', (function(_this) {
        return function(e) {
          return _this.resizeStarted(e);
        };
      })(this));
      atom.commands.add(this.element, {
        'core:move-up': this.moveUp.bind(this),
        'core:move-down': this.moveDown.bind(this),
        'core:page-up': (function(_this) {
          return function() {
            return _this.pageUp();
          };
        })(this),
        'core:page-down': (function(_this) {
          return function() {
            return _this.pageDown();
          };
        })(this),
        'core:move-to-top': (function(_this) {
          return function() {
            return _this.scrollToTop();
          };
        })(this),
        'core:move-to-bottom': (function(_this) {
          return function() {
            return _this.scrollToBottom();
          };
        })(this),
        'tree-view:expand-directory': (function(_this) {
          return function() {
            return _this.expandDirectory();
          };
        })(this),
        'tree-view:recursive-expand-directory': (function(_this) {
          return function() {
            return _this.expandDirectory(true);
          };
        })(this),
        'tree-view:collapse-directory': (function(_this) {
          return function() {
            return _this.collapseDirectory();
          };
        })(this),
        'tree-view:recursive-collapse-directory': (function(_this) {
          return function() {
            return _this.collapseDirectory(true);
          };
        })(this),
        'tree-view:open-selected-entry': (function(_this) {
          return function() {
            return _this.openSelectedEntry(true);
          };
        })(this),
        'tree-view:open-selected-entry-right': (function(_this) {
          return function() {
            return _this.openSelectedEntryRight();
          };
        })(this),
        'tree-view:open-selected-entry-left': (function(_this) {
          return function() {
            return _this.openSelectedEntryLeft();
          };
        })(this),
        'tree-view:open-selected-entry-up': (function(_this) {
          return function() {
            return _this.openSelectedEntryUp();
          };
        })(this),
        'tree-view:open-selected-entry-down': (function(_this) {
          return function() {
            return _this.openSelectedEntryDown();
          };
        })(this),
        'tree-view:move': (function(_this) {
          return function() {
            return _this.moveSelectedEntry();
          };
        })(this),
        'tree-view:copy': (function(_this) {
          return function() {
            return _this.copySelectedEntries();
          };
        })(this),
        'tree-view:cut': (function(_this) {
          return function() {
            return _this.cutSelectedEntries();
          };
        })(this),
        'tree-view:paste': (function(_this) {
          return function() {
            return _this.pasteEntries();
          };
        })(this),
        'tree-view:copy-full-path': (function(_this) {
          return function() {
            return _this.copySelectedEntryPath(false);
          };
        })(this),
        'tree-view:show-in-file-manager': (function(_this) {
          return function() {
            return _this.showSelectedEntryInFileManager();
          };
        })(this),
        'tree-view:open-in-new-window': (function(_this) {
          return function() {
            return _this.openSelectedEntryInNewWindow();
          };
        })(this),
        'tree-view:copy-project-path': (function(_this) {
          return function() {
            return _this.copySelectedEntryPath(true);
          };
        })(this),
        'tool-panel:unfocus': (function(_this) {
          return function() {
            return _this.unfocus();
          };
        })(this),
        'tree-view:toggle-vcs-ignored-files': function() {
          return toggleConfig('tree-view.hideVcsIgnoredFiles');
        },
        'tree-view:toggle-ignored-names': function() {
          return toggleConfig('tree-view.hideIgnoredNames');
        },
        'tree-view:remove-project-folder': (function(_this) {
          return function(e) {
            return _this.removeProjectFolder(e);
          };
        })(this)
      });
      [0, 1, 2, 3, 4, 5, 6, 7, 8].forEach((function(_this) {
        return function(index) {
          return atom.commands.add(_this.element, "tree-view:open-selected-entry-in-pane-" + (index + 1), function() {
            return _this.openSelectedEntryInPane(index);
          });
        };
      })(this));
      this.disposables.add(atom.workspace.onDidChangeActivePaneItem((function(_this) {
        return function() {
          return _this.selectActiveFile();
        };
      })(this)));
      this.disposables.add(atom.project.onDidChangePaths((function(_this) {
        return function() {
          return _this.updateRoots();
        };
      })(this)));
      this.disposables.add(atom.config.onDidChange('tree-view.hideVcsIgnoredFiles', (function(_this) {
        return function() {
          return _this.updateRoots();
        };
      })(this)));
      this.disposables.add(atom.config.onDidChange('tree-view.hideIgnoredNames', (function(_this) {
        return function() {
          return _this.updateRoots();
        };
      })(this)));
      this.disposables.add(atom.config.onDidChange('core.ignoredNames', (function(_this) {
        return function() {
          if (atom.config.get('tree-view.hideIgnoredNames')) {
            return _this.updateRoots();
          }
        };
      })(this)));
      this.disposables.add(atom.config.onDidChange('tree-view.showOnRightSide', (function(_this) {
        return function(_arg) {
          var newValue;
          newValue = _arg.newValue;
          return _this.onSideToggled(newValue);
        };
      })(this)));
      return this.disposables.add(atom.config.onDidChange('tree-view.sortFoldersBeforeFiles', (function(_this) {
        return function() {
          return _this.updateRoots();
        };
      })(this)));
    };

    TreeView.prototype.toggle = function() {
      if (this.isVisible()) {
        return this.detach();
      } else {
        return this.show();
      }
    };

    TreeView.prototype.show = function() {
      this.attach();
      return this.focus();
    };

    TreeView.prototype.attach = function() {
      if (_.isEmpty(atom.project.getPaths())) {
        return;
      }
      return this.panel != null ? this.panel : this.panel = atom.config.get('tree-view.showOnRightSide') ? atom.workspace.addRightPanel({
        item: this
      }) : atom.workspace.addLeftPanel({
        item: this
      });
    };

    TreeView.prototype.detach = function() {
      this.scrollLeftAfterAttach = this.scroller.scrollLeft();
      this.scrollTopAfterAttach = this.scrollTop();
      LocalStorage['tree-view:cutPath'] = null;
      LocalStorage['tree-view:copyPath'] = null;
      this.panel.destroy();
      this.panel = null;
      return this.unfocus();
    };

    TreeView.prototype.focus = function() {
      return this.list.focus();
    };

    TreeView.prototype.unfocus = function() {
      return atom.workspace.getActivePane().activate();
    };

    TreeView.prototype.hasFocus = function() {
      return this.list.is(':focus') || document.activeElement === this.list[0];
    };

    TreeView.prototype.toggleFocus = function() {
      if (this.hasFocus()) {
        return this.unfocus();
      } else {
        return this.show();
      }
    };

    TreeView.prototype.entryClicked = function(e) {
      var entry, isRecursive, _ref2, _ref3;
      entry = e.currentTarget;
      isRecursive = e.altKey || false;
      switch ((_ref2 = (_ref3 = e.originalEvent) != null ? _ref3.detail : void 0) != null ? _ref2 : 1) {
        case 1:
          this.selectEntry(entry);
          if (entry instanceof FileView) {
            this.openSelectedEntry(false);
          }
          if (entry instanceof DirectoryView) {
            entry.toggleExpansion(isRecursive);
          }
          break;
        case 2:
          if (entry instanceof FileView) {
            this.unfocus();
          } else if (DirectoryView) {
            entry.toggleExpansion(isRecursive);
          }
      }
      return false;
    };

    TreeView.prototype.resizeStarted = function() {
      $(document).on('mousemove', this.resizeTreeView);
      return $(document).on('mouseup', this.resizeStopped);
    };

    TreeView.prototype.resizeStopped = function() {
      $(document).off('mousemove', this.resizeTreeView);
      return $(document).off('mouseup', this.resizeStopped);
    };

    TreeView.prototype.resizeTreeView = function(_arg) {
      var pageX, which, width;
      pageX = _arg.pageX, which = _arg.which;
      if (which !== 1) {
        return this.resizeStopped();
      }
      if (atom.config.get('tree-view.showOnRightSide')) {
        width = $(document.body).width() - pageX;
      } else {
        width = pageX;
      }
      return this.width(width);
    };

    TreeView.prototype.resizeToFitContent = function() {
      this.width(1);
      return this.width(this.list.outerWidth());
    };

    TreeView.prototype.loadIgnoredPatterns = function() {
      var error, ignoredName, ignoredNames, _i, _len, _ref2, _results;
      this.ignoredPatterns.length = 0;
      if (!atom.config.get('tree-view.hideIgnoredNames')) {
        return;
      }
      if (Minimatch == null) {
        Minimatch = require('minimatch').Minimatch;
      }
      ignoredNames = (_ref2 = atom.config.get('core.ignoredNames')) != null ? _ref2 : [];
      if (typeof ignoredNames === 'string') {
        ignoredNames = [ignoredNames];
      }
      _results = [];
      for (_i = 0, _len = ignoredNames.length; _i < _len; _i++) {
        ignoredName = ignoredNames[_i];
        if (ignoredName) {
          try {
            _results.push(this.ignoredPatterns.push(new Minimatch(ignoredName, {
              matchBase: true,
              dot: true
            })));
          } catch (_error) {
            error = _error;
            _results.push(console.warn("Error parsing ignore pattern (" + ignoredName + "): " + error.message));
          }
        }
      }
      return _results;
    };

    TreeView.prototype.updateRoots = function(expansionStates) {
      var directory, oldExpansionStates, projectPath, root, _i, _len, _ref2;
      if (expansionStates == null) {
        expansionStates = {};
      }
      oldExpansionStates = {};
      _ref2 = this.roots;
      for (_i = 0, _len = _ref2.length; _i < _len; _i++) {
        root = _ref2[_i];
        oldExpansionStates[root.directory.path] = root.directory.serializeExpansionState();
        root.directory.destroy();
        root.remove();
      }
      this.loadIgnoredPatterns();
      this.roots = (function() {
        var _j, _len1, _ref3, _ref4, _ref5, _results;
        _ref3 = atom.project.getPaths();
        _results = [];
        for (_j = 0, _len1 = _ref3.length; _j < _len1; _j++) {
          projectPath = _ref3[_j];
          directory = new Directory({
            name: path.basename(projectPath),
            fullPath: projectPath,
            symlink: false,
            isRoot: true,
            expansionState: (_ref4 = (_ref5 = expansionStates[projectPath]) != null ? _ref5 : oldExpansionStates[projectPath]) != null ? _ref4 : {
              isExpanded: true
            },
            ignoredPatterns: this.ignoredPatterns
          });
          root = new DirectoryView();
          root.initialize(directory);
          this.list[0].appendChild(root);
          _results.push(root);
        }
        return _results;
      }).call(this);
      if (this.attachAfterProjectPathSet) {
        this.attach();
        return this.attachAfterProjectPathSet = false;
      }
    };

    TreeView.prototype.getActivePath = function() {
      var _ref2;
      return (_ref2 = atom.workspace.getActivePaneItem()) != null ? typeof _ref2.getPath === "function" ? _ref2.getPath() : void 0 : void 0;
    };

    TreeView.prototype.selectActiveFile = function() {
      var activeFilePath;
      if (activeFilePath = this.getActivePath()) {
        return this.selectEntryForPath(activeFilePath);
      } else {
        return this.deselect();
      }
    };

    TreeView.prototype.revealActiveFile = function() {
      var activeFilePath, activePathComponents, centeringOffset, currentPath, directory, entry, pathComponent, relativePath, rootPath, _i, _j, _len, _len1, _ref2, _results;
      if (_.isEmpty(atom.project.getPaths())) {
        return;
      }
      this.attach();
      this.focus();
      if (!(activeFilePath = this.getActivePath())) {
        return;
      }
      relativePath = null;
      rootPath = null;
      _ref2 = atom.project.getDirectories();
      for (_i = 0, _len = _ref2.length; _i < _len; _i++) {
        directory = _ref2[_i];
        if (directory.contains(activeFilePath)) {
          rootPath = directory.getPath();
          relativePath = directory.relativize(activeFilePath);
          break;
        }
      }
      if (relativePath == null) {
        return;
      }
      activePathComponents = relativePath.split(path.sep);
      currentPath = rootPath;
      _results = [];
      for (_j = 0, _len1 = activePathComponents.length; _j < _len1; _j++) {
        pathComponent = activePathComponents[_j];
        currentPath += path.sep + pathComponent;
        entry = this.entryForPath(currentPath);
        if (entry instanceof DirectoryView) {
          _results.push(entry.expand());
        } else {
          centeringOffset = (this.scrollBottom() - this.scrollTop()) / 2;
          this.selectEntry(entry);
          _results.push(this.scrollToEntry(entry, centeringOffset));
        }
      }
      return _results;
    };

    TreeView.prototype.copySelectedEntryPath = function(relativePath) {
      var pathToCopy;
      if (relativePath == null) {
        relativePath = false;
      }
      if (pathToCopy = this.selectedPath) {
        if (relativePath) {
          pathToCopy = atom.project.relativize(pathToCopy);
        }
        return atom.clipboard.write(pathToCopy);
      }
    };

    TreeView.prototype.entryForPath = function(entryPath) {
      var bestMatchEntry, bestMatchLength, entry, entryLength, _i, _len, _ref2, _ref3;
      bestMatchEntry = null;
      bestMatchLength = 0;
      _ref2 = this.list[0].querySelectorAll('.entry');
      for (_i = 0, _len = _ref2.length; _i < _len; _i++) {
        entry = _ref2[_i];
        if (entry.isPathEqual(entryPath)) {
          return entry;
        }
        entryLength = entry.getPath().length;
        if (((_ref3 = entry.directory) != null ? _ref3.contains(entryPath) : void 0) && entryLength > bestMatchLength) {
          bestMatchEntry = entry;
          bestMatchLength = entryLength;
        }
      }
      return bestMatchEntry;
    };

    TreeView.prototype.selectEntryForPath = function(entryPath) {
      return this.selectEntry(this.entryForPath(entryPath));
    };

    TreeView.prototype.moveDown = function(event) {
      var selectedEntry;
      event.stopImmediatePropagation();
      selectedEntry = this.selectedEntry();
      if (selectedEntry != null) {
        if (selectedEntry instanceof DirectoryView) {
          if (this.selectEntry(selectedEntry.entries.children[0])) {
            this.scrollToEntry(this.selectedEntry());
            return;
          }
        }
        selectedEntry = $(selectedEntry);
        while (!this.selectEntry(selectedEntry.next('.entry')[0])) {
          selectedEntry = selectedEntry.parents('.entry:first');
          if (!selectedEntry.length) {
            break;
          }
        }
      } else {
        this.selectEntry(this.roots[0]);
      }
      return this.scrollToEntry(this.selectedEntry());
    };

    TreeView.prototype.moveUp = function(event) {
      var previousEntry, selectedEntry, _ref2, _ref3;
      event.stopImmediatePropagation();
      selectedEntry = this.selectedEntry();
      if (selectedEntry != null) {
        selectedEntry = $(selectedEntry);
        if (previousEntry = this.selectEntry(selectedEntry.prev('.entry')[0])) {
          if (previousEntry instanceof DirectoryView) {
            this.selectEntry(_.last(previousEntry.entries.children));
          }
        } else {
          this.selectEntry((_ref2 = selectedEntry.parents('.directory').first()) != null ? _ref2[0] : void 0);
        }
      } else {
        this.selectEntry((_ref3 = this.list.find('.entry').last()) != null ? _ref3[0] : void 0);
      }
      return this.scrollToEntry(this.selectedEntry());
    };

    TreeView.prototype.expandDirectory = function(isRecursive) {
      var _ref2;
      if (isRecursive == null) {
        isRecursive = false;
      }
      return (_ref2 = this.selectedEntry()) != null ? typeof _ref2.expand === "function" ? _ref2.expand(isRecursive) : void 0 : void 0;
    };

    TreeView.prototype.collapseDirectory = function(isRecursive) {
      var directory, selectedEntry;
      if (isRecursive == null) {
        isRecursive = false;
      }
      selectedEntry = this.selectedEntry();
      if (selectedEntry == null) {
        return;
      }
      if (directory = $(selectedEntry).closest('.expanded.directory')[0]) {
        directory.collapse(isRecursive);
        return this.selectEntry(directory);
      }
    };

    TreeView.prototype.openSelectedEntry = function(activatePane) {
      var selectedEntry;
      selectedEntry = this.selectedEntry();
      if (selectedEntry instanceof DirectoryView) {
        return selectedEntry.toggleExpansion();
      } else if (selectedEntry instanceof FileView) {
        return atom.workspace.open(selectedEntry.getPath(), {
          activatePane: activatePane
        });
      }
    };

    TreeView.prototype.openSelectedEntrySplit = function(orientation, side) {
      var pane, selectedEntry, split;
      selectedEntry = this.selectedEntry();
      pane = atom.workspace.getActivePane();
      if (pane && selectedEntry instanceof FileView) {
        if (atom.workspace.getActivePaneItem()) {
          split = pane.split(orientation, side);
          return atom.workspace.openURIInPane(selectedEntry.getPath(), split);
        } else {
          return this.openSelectedEntry(true);
        }
      }
    };

    TreeView.prototype.openSelectedEntryRight = function() {
      return this.openSelectedEntrySplit('horizontal', 'after');
    };

    TreeView.prototype.openSelectedEntryLeft = function() {
      return this.openSelectedEntrySplit('horizontal', 'before');
    };

    TreeView.prototype.openSelectedEntryUp = function() {
      return this.openSelectedEntrySplit('vertical', 'before');
    };

    TreeView.prototype.openSelectedEntryDown = function() {
      return this.openSelectedEntrySplit('vertical', 'after');
    };

    TreeView.prototype.openSelectedEntryInPane = function(index) {
      var pane, selectedEntry;
      selectedEntry = this.selectedEntry();
      pane = atom.workspace.getPanes()[index];
      if (pane && selectedEntry instanceof FileView) {
        return atom.workspace.openURIInPane(selectedEntry.getPath(), pane);
      }
    };

    TreeView.prototype.moveSelectedEntry = function() {
      var dialog, entry, oldPath;
      if (this.hasFocus()) {
        entry = this.selectedEntry();
        if ((entry == null) || __indexOf.call(this.roots, entry) >= 0) {
          return;
        }
        oldPath = entry.getPath();
      } else {
        oldPath = this.getActivePath();
      }
      if (oldPath) {
        if (MoveDialog == null) {
          MoveDialog = require('./move-dialog');
        }
        dialog = new MoveDialog(oldPath);
        return dialog.attach();
      }
    };

    TreeView.prototype.fileManagerCommandForPath = function(pathToOpen, isFile) {
      var args, command;
      switch (process.platform) {
        case 'darwin':
          return {
            command: 'open',
            label: 'Finder',
            args: ['-R', pathToOpen]
          };
        case 'win32':
          args = ["/select," + pathToOpen];
          if (process.env.SystemRoot) {
            command = path.join(process.env.SystemRoot, 'explorer.exe');
          } else {
            command = 'explorer.exe';
          }
          return {
            command: command,
            label: 'Explorer',
            args: args
          };
        default:
          if (isFile) {
            pathToOpen = path.dirname(pathToOpen);
          }
          return {
            command: 'xdg-open',
            label: 'File Manager',
            args: [pathToOpen]
          };
      }
    };

    TreeView.prototype.showSelectedEntryInFileManager = function() {
      var args, command, entry, errorLines, exit, isFile, label, stderr, _ref2;
      entry = this.selectedEntry();
      if (!entry) {
        return;
      }
      isFile = entry instanceof FileView;
      _ref2 = this.fileManagerCommandForPath(entry.getPath(), isFile), command = _ref2.command, args = _ref2.args, label = _ref2.label;
      errorLines = [];
      stderr = function(lines) {
        return errorLines.push(lines);
      };
      exit = function(code) {
        var error, failed;
        failed = code !== 0;
        error = errorLines.join('\n');
        if (process.platform === 'win32' && code === 1 && !error) {
          failed = false;
        }
        if (failed) {
          return atom.confirm({
            message: "Opening " + (isFile ? 'file' : 'folder') + " in " + label + " failed",
            detailedMessage: error,
            buttons: ['OK']
          });
        }
      };
      return new BufferedProcess({
        command: command,
        args: args,
        stderr: stderr,
        exit: exit
      });
    };

    TreeView.prototype.openSelectedEntryInNewWindow = function() {
      var pathToOpen, _ref2;
      if (pathToOpen = (_ref2 = this.selectedEntry()) != null ? _ref2.getPath() : void 0) {
        return atom.open({
          pathsToOpen: [pathToOpen],
          newWindow: true
        });
      }
    };

    TreeView.prototype.copySelectedEntry = function() {
      var dialog, entry, oldPath;
      if (this.hasFocus()) {
        entry = this.selectedEntry();
        if (__indexOf.call(this.roots, entry) >= 0) {
          return;
        }
        oldPath = entry != null ? entry.getPath() : void 0;
      } else {
        oldPath = this.getActivePath();
      }
      if (!oldPath) {
        return;
      }
      if (CopyDialog == null) {
        CopyDialog = require('./copy-dialog');
      }
      dialog = new CopyDialog(oldPath);
      return dialog.attach();
    };

    TreeView.prototype.removeSelectedEntries = function() {
      var activePath, root, selectedPaths, _i, _len, _ref2, _ref3;
      if (this.hasFocus()) {
        selectedPaths = this.selectedPaths();
      } else if (activePath = this.getActivePath()) {
        selectedPaths = [activePath];
      }
      if (!selectedPaths) {
        return;
      }
      _ref2 = this.roots;
      for (_i = 0, _len = _ref2.length; _i < _len; _i++) {
        root = _ref2[_i];
        if (_ref3 = root.getPath(), __indexOf.call(selectedPaths, _ref3) >= 0) {
          atom.confirm({
            message: "The root directory '" + root.directory.name + "' can't be removed.",
            buttons: ['OK']
          });
          return;
        }
      }
      return atom.confirm({
        message: "Are you sure you want to delete the selected " + (selectedPaths.length > 1 ? 'items' : 'item') + "?",
        detailedMessage: "You are deleting:\n" + (selectedPaths.join('\n')),
        buttons: {
          "Move to Trash": function() {
            var selectedPath, _j, _len1, _results;
            _results = [];
            for (_j = 0, _len1 = selectedPaths.length; _j < _len1; _j++) {
              selectedPath = selectedPaths[_j];
              _results.push(shell.moveItemToTrash(selectedPath));
            }
            return _results;
          },
          "Cancel": null
        }
      });
    };

    TreeView.prototype.copySelectedEntries = function() {
      var selectedPaths;
      selectedPaths = this.selectedPaths();
      if (!(selectedPaths && selectedPaths.length > 0)) {
        return;
      }
      LocalStorage.removeItem('tree-view:cutPath');
      return LocalStorage['tree-view:copyPath'] = JSON.stringify(selectedPaths);
    };

    TreeView.prototype.cutSelectedEntries = function() {
      var selectedPaths;
      selectedPaths = this.selectedPaths();
      if (!(selectedPaths && selectedPaths.length > 0)) {
        return;
      }
      LocalStorage.removeItem('tree-view:copyPath');
      return LocalStorage['tree-view:cutPath'] = JSON.stringify(selectedPaths);
    };

    TreeView.prototype.pasteEntries = function() {
      var basePath, copiedPaths, cutPaths, fileArr, fileCounter, initialPath, initialPathIsDirectory, initialPaths, newPath, originalNewPath, selectedEntry, _i, _len, _ref2, _results;
      selectedEntry = this.selectedEntry();
      cutPaths = LocalStorage['tree-view:cutPath'] ? JSON.parse(LocalStorage['tree-view:cutPath']) : null;
      copiedPaths = LocalStorage['tree-view:copyPath'] ? JSON.parse(LocalStorage['tree-view:copyPath']) : null;
      initialPaths = copiedPaths || cutPaths;
      _ref2 = initialPaths != null ? initialPaths : [];
      _results = [];
      for (_i = 0, _len = _ref2.length; _i < _len; _i++) {
        initialPath = _ref2[_i];
        initialPathIsDirectory = fs.isDirectorySync(initialPath);
        if (selectedEntry && initialPath && fs.existsSync(initialPath)) {
          basePath = selectedEntry.getPath();
          if (selectedEntry instanceof FileView) {
            basePath = path.dirname(basePath);
          }
          newPath = path.join(basePath, path.basename(initialPath));
          if (copiedPaths) {
            fileCounter = 0;
            originalNewPath = newPath;
            while (fs.existsSync(newPath)) {
              if (initialPathIsDirectory) {
                newPath = "" + originalNewPath + (fileCounter.toString());
              } else {
                fileArr = originalNewPath.split('.');
                newPath = "" + fileArr[0] + (fileCounter.toString()) + "." + fileArr[1];
              }
              fileCounter += 1;
            }
            if (fs.isDirectorySync(initialPath)) {
              _results.push(fs.copySync(initialPath, newPath));
            } else {
              _results.push(fs.writeFileSync(newPath, fs.readFileSync(initialPath)));
            }
          } else if (cutPaths) {
            if (!(fs.existsSync(newPath) || !!newPath.match(new RegExp("^" + initialPath)))) {
              _results.push(fs.moveSync(initialPath, newPath));
            } else {
              _results.push(void 0);
            }
          } else {
            _results.push(void 0);
          }
        } else {
          _results.push(void 0);
        }
      }
      return _results;
    };

    TreeView.prototype.add = function(isCreatingFile) {
      var dialog, selectedEntry, selectedPath, _ref2, _ref3;
      selectedEntry = (_ref2 = this.selectedEntry()) != null ? _ref2 : this.roots[0];
      selectedPath = (_ref3 = selectedEntry != null ? selectedEntry.getPath() : void 0) != null ? _ref3 : '';
      if (AddDialog == null) {
        AddDialog = require('./add-dialog');
      }
      dialog = new AddDialog(selectedPath, isCreatingFile);
      dialog.on('directory-created', (function(_this) {
        return function(event, createdPath) {
          var _ref4;
          if ((_ref4 = _this.entryForPath(createdPath)) != null) {
            _ref4.reload();
          }
          _this.selectEntryForPath(createdPath);
          return false;
        };
      })(this));
      dialog.on('file-created', function(event, createdPath) {
        atom.workspace.open(createdPath);
        return false;
      });
      return dialog.attach();
    };

    TreeView.prototype.removeProjectFolder = function(e) {
      var pathToRemove;
      pathToRemove = $(e.target).closest(".project-root > .header").find(".name").data("path");
      if (atom.project.removePath != null) {
        if (pathToRemove != null) {
          return atom.project.removePath(pathToRemove);
        }
      }
    };

    TreeView.prototype.selectedEntry = function() {
      return this.list[0].querySelector('.selected');
    };

    TreeView.prototype.selectEntry = function(entry) {
      var selectedEntries;
      if (entry == null) {
        return;
      }
      this.selectedPath = entry.getPath();
      selectedEntries = this.getSelectedEntries();
      if (selectedEntries.length > 1 || selectedEntries[0] !== entry) {
        this.deselect(selectedEntries);
        entry.classList.add('selected');
      }
      return entry;
    };

    TreeView.prototype.getSelectedEntries = function() {
      return this.list[0].querySelectorAll('.selected');
    };

    TreeView.prototype.deselect = function(elementsToDeselect) {
      var selected, _i, _len;
      if (elementsToDeselect == null) {
        elementsToDeselect = this.getSelectedEntries();
      }
      for (_i = 0, _len = elementsToDeselect.length; _i < _len; _i++) {
        selected = elementsToDeselect[_i];
        selected.classList.remove('selected');
      }
      return void 0;
    };

    TreeView.prototype.scrollTop = function(top) {
      if (top != null) {
        return this.scroller.scrollTop(top);
      } else {
        return this.scroller.scrollTop();
      }
    };

    TreeView.prototype.scrollBottom = function(bottom) {
      if (bottom != null) {
        return this.scroller.scrollBottom(bottom);
      } else {
        return this.scroller.scrollBottom();
      }
    };

    TreeView.prototype.scrollToEntry = function(entry, offset) {
      var bottom, displayElement, top;
      if (offset == null) {
        offset = 0;
      }
      if (entry instanceof DirectoryView) {
        displayElement = $(entry.header);
      } else {
        displayElement = $(entry);
      }
      top = displayElement.position().top;
      bottom = top + displayElement.outerHeight();
      if (bottom > this.scrollBottom()) {
        this.scrollBottom(bottom + offset);
      }
      if (top < this.scrollTop()) {
        return this.scrollTop(top + offset);
      }
    };

    TreeView.prototype.scrollToBottom = function() {
      var lastEntry;
      if (lastEntry = _.last(this.list[0].querySelectorAll('.entry'))) {
        this.selectEntry(lastEntry);
        return this.scrollToEntry(lastEntry);
      }
    };

    TreeView.prototype.scrollToTop = function() {
      if (this.roots[0] != null) {
        this.selectEntry(this.roots[0]);
      }
      return this.scrollTop(0);
    };

    TreeView.prototype.toggleSide = function() {
      return toggleConfig('tree-view.showOnRightSide');
    };

    TreeView.prototype.onStylesheetsChanged = function() {
      if (!this.isVisible()) {
        return;
      }
      this.element.style.display = 'none';
      this.element.offsetWidth;
      return this.element.style.display = 'block';
    };

    TreeView.prototype.onMouseDown = function(e) {
      var entryToSelect;
      e.stopPropagation();
      if (this.multiSelectEnabled() && e.currentTarget.classList.contains('selected') && (e.button === 2 || e.ctrlKey && process.platform === 'darwin')) {
        return;
      }
      entryToSelect = e.currentTarget;
      if (e.shiftKey) {
        this.selectContinuousEntries(entryToSelect);
        return this.showMultiSelectMenu();
      } else if (e.metaKey || (e.ctrlKey && process.platform !== 'darwin')) {
        this.selectMultipleEntries(entryToSelect);
        if (this.selectedPaths().length > 1) {
          return this.showMultiSelectMenu();
        }
      } else {
        this.selectEntry(entryToSelect);
        return this.showFullMenu();
      }
    };

    TreeView.prototype.onSideToggled = function(newValue) {
      this.element.dataset.showOnRightSide = newValue;
      if (this.isVisible()) {
        this.detach();
        return this.attach();
      }
    };

    TreeView.prototype.selectedPaths = function() {
      var entry, _i, _len, _ref2, _results;
      _ref2 = this.getSelectedEntries();
      _results = [];
      for (_i = 0, _len = _ref2.length; _i < _len; _i++) {
        entry = _ref2[_i];
        _results.push(entry.getPath());
      }
      return _results;
    };

    TreeView.prototype.selectContinuousEntries = function(entry) {
      var currentSelectedEntry, element, elements, entries, entryIndex, i, parentContainer, selectedIndex, _i, _len;
      currentSelectedEntry = this.selectedEntry();
      parentContainer = $(entry).parent();
      if ($.contains(parentContainer[0], currentSelectedEntry)) {
        entries = parentContainer.find('.entry').toArray();
        entryIndex = entries.indexOf(entry);
        selectedIndex = entries.indexOf(currentSelectedEntry);
        elements = (function() {
          var _i, _results;
          _results = [];
          for (i = _i = entryIndex; entryIndex <= selectedIndex ? _i <= selectedIndex : _i >= selectedIndex; i = entryIndex <= selectedIndex ? ++_i : --_i) {
            _results.push(entries[i]);
          }
          return _results;
        })();
        this.deselect();
        for (_i = 0, _len = elements.length; _i < _len; _i++) {
          element = elements[_i];
          element.classList.add('selected');
        }
      }
      return elements;
    };

    TreeView.prototype.selectMultipleEntries = function(entry) {
      if (entry != null) {
        entry.classList.toggle('selected');
      }
      return entry;
    };

    TreeView.prototype.showFullMenu = function() {
      this.list[0].classList.remove('multi-select');
      return this.list[0].classList.add('full-menu');
    };

    TreeView.prototype.showMultiSelectMenu = function() {
      this.list[0].classList.remove('full-menu');
      return this.list[0].classList.add('multi-select');
    };

    TreeView.prototype.multiSelectEnabled = function() {
      return this.list[0].classList.contains('multi-select');
    };

    return TreeView;

  })(View);

}).call(this);
