1
0
mirror of https://github.com/SpaceVim/SpaceVim.git synced 2025-02-04 01:10:06 +08:00
SpaceVim/bundle/defx.nvim/rplugin/python3/defx/defx.py

160 lines
5.4 KiB
Python
Raw Normal View History

2020-06-13 14:06:35 +08:00
# ============================================================================
# FILE: defx.py
# AUTHOR: Shougo Matsushita <Shougo.Matsu at gmail.com>
# License: MIT license
# ============================================================================
import typing
2020-10-31 15:58:52 +08:00
from defx.base.source import Base as Source
from defx.source.file.list import Source as SourceList
from defx.source.file import Source as SourceFile
2020-06-13 14:06:35 +08:00
from defx.context import Context
from defx.sort import sort
from defx.util import Nvim
from defx.util import cd, error
from pathlib import Path
Candidate = typing.Dict[str, typing.Any]
class Defx(object):
def __init__(self, vim: Nvim, context: Context,
2020-10-31 15:58:52 +08:00
source_name: str, cwd: str, index: int) -> None:
2020-06-13 14:06:35 +08:00
self._vim = vim
self._context = context
self._cwd = self._vim.call('getcwd')
self.cd(cwd)
2020-10-31 15:58:52 +08:00
self._source: Source = (SourceList(self._vim)
if source_name == 'file/list'
else SourceFile(self._vim))
2020-06-13 14:06:35 +08:00
self._index = index
self._enabled_ignored_files = not context.show_ignored_files
2020-10-31 15:58:52 +08:00
self._filtered_files = context.filtered_files.split(',')
2020-06-13 14:06:35 +08:00
self._ignored_files = context.ignored_files.split(',')
self._cursor_history: typing.Dict[str, Path] = {}
self._sort_method: str = self._context.sort
self._mtime: int = -1
self._opened_candidates: typing.Set[str] = set()
self._selected_candidates: typing.Set[str] = set()
2020-10-31 15:58:52 +08:00
self._nested_candidates: typing.Set[str] = set()
2020-06-13 14:06:35 +08:00
self._init_source()
def _init_source(self) -> None:
custom = self._vim.call('defx#custom#_get')['source']
name = self._source.name
if name in custom:
self._source.vars.update(custom[name])
def debug(self, expr: typing.Any) -> None:
error(self._vim, expr)
def cd(self, path: str) -> None:
self._cwd = str(Path(self._cwd).joinpath(path))
2020-10-31 15:58:52 +08:00
if self._context.auto_cd and Path(path).is_dir():
2020-06-13 14:06:35 +08:00
cd(self._vim, path)
def get_root_candidate(self) -> Candidate:
"""
Returns root candidate
"""
2020-10-31 15:58:52 +08:00
if not self._source:
return {}
2020-06-13 14:06:35 +08:00
root = self._source.get_root_candidate(self._context, Path(self._cwd))
root['is_root'] = True
root['is_opened_tree'] = False
root['is_selected'] = False
root['level'] = 0
2020-10-31 15:58:52 +08:00
root['root_marker'] = self._context.root_marker + (
self._source.name + ':' if self._source.name != 'file' else '')
root['word'] = root['root_marker'] + root['word']
2020-06-13 14:06:35 +08:00
return root
def tree_candidates(
self, path: str, base_level: int, max_level: int
) -> typing.List[Candidate]:
gathered_candidates = self.gather_candidates_recursive(
path, base_level, max_level)
2020-10-31 15:58:52 +08:00
if not self._opened_candidates and not self._nested_candidates:
return gathered_candidates
candidates = []
for candidate in gathered_candidates:
candidates.append(candidate)
candidate['level'] = base_level
candidate_path = str(candidate['action__path'])
if not candidate['is_directory']:
continue
if (candidate_path not in self._opened_candidates and
candidate_path not in self._nested_candidates):
continue
children = self.tree_candidates(
candidate_path, base_level + 1, max_level)
2020-06-13 14:06:35 +08:00
2020-10-31 15:58:52 +08:00
candidate['is_opened_tree'] = True
candidates += children
2020-06-13 14:06:35 +08:00
return candidates
def gather_candidates_recursive(
self, path: str, base_level: int, max_level: int
) -> typing.List[Candidate]:
candidates = self._gather_candidates(path, base_level)
if base_level >= max_level:
return candidates
ret = []
for candidate in candidates:
ret.append(candidate)
if candidate['is_directory']:
candidate['is_opened_tree'] = True
ret += self.gather_candidates_recursive(
str(candidate['action__path']), base_level + 1, max_level)
return ret
def _gather_candidates(
self, path: str, base_level: int = 0) -> typing.List[Candidate]:
"""
Returns file candidates
"""
2020-10-31 15:58:52 +08:00
if not self._source:
return []
2020-06-13 14:06:35 +08:00
candidates = self._source.gather_candidates(
self._context, Path(path))
2020-10-31 15:58:52 +08:00
if self._filtered_files != ['']:
new_candidates = []
for candidate in candidates:
matched = False
for glob in self._filtered_files:
if candidate['action__path'].match(glob):
matched = True
break
if matched or candidate['is_directory']:
new_candidates.append(candidate)
candidates = new_candidates
2020-06-13 14:06:35 +08:00
if self._enabled_ignored_files:
for glob in self._ignored_files:
candidates = [x for x in candidates
if not x['action__path'].match(glob)]
for candidate in candidates:
candidate['is_opened_tree'] = False
candidate['is_root'] = False
candidate['is_selected'] = False
candidate['level'] = base_level
return sort(self._sort_method, candidates)