diff --git a/src/commands.cc b/src/commands.cc index d51846bf..a67fb032 100644 --- a/src/commands.cc +++ b/src/commands.cc @@ -831,7 +831,8 @@ const CommandDesc declare_option_cmd = { " str-list: list of character strings\n" " line-flag-list: list of line flags\n", ParameterDesc{ - SwitchMap{ { "hidden", { false, "do not display option name when completing" } } }, + SwitchMap{ { "hidden", { false, "do not display option name when completing" } }, + { "docstring", { true, "specify option description" } } }, ParameterDesc::Flags::SwitchesOnlyAtStart, 2, 3 }, @@ -845,22 +846,26 @@ const CommandDesc declare_option_cmd = { if (parser.has_option("hidden")) flags = Option::Flags::Hidden; + String docstring; + if (parser.has_option("docstring")) + docstring = parser.option_value("docstring"); + GlobalOptions& opts = GlobalOptions::instance(); if (parser[0] == "int") - opt = &opts.declare_option(parser[1], 0, flags); + opt = &opts.declare_option(parser[1], docstring, 0, flags); if (parser[0] == "bool") - opt = &opts.declare_option(parser[1], 0, flags); + opt = &opts.declare_option(parser[1], docstring, 0, flags); else if (parser[0] == "str") - opt = &opts.declare_option(parser[1], "", flags); + opt = &opts.declare_option(parser[1], docstring, "", flags); else if (parser[0] == "regex") - opt = &opts.declare_option(parser[1], Regex{}, flags); + opt = &opts.declare_option(parser[1], docstring, {}, flags); else if (parser[0] == "int-list") - opt = &opts.declare_option>(parser[1], {}, flags); + opt = &opts.declare_option>(parser[1], docstring, {}, flags); else if (parser[0] == "str-list") - opt = &opts.declare_option>(parser[1], {}, flags); + opt = &opts.declare_option>(parser[1], docstring, {}, flags); else if (parser[0] == "line-flag-list") - opt = &opts.declare_option>(parser[1], {}, flags); + opt = &opts.declare_option>(parser[1], docstring, {}, flags); else throw runtime_error("unknown type " + parser[0]); diff --git a/src/option_manager.cc b/src/option_manager.cc index c917d8e8..414e7f15 100644 --- a/src/option_manager.cc +++ b/src/option_manager.cc @@ -7,8 +7,10 @@ namespace Kakoune { -Option::Option(OptionManager& manager, String name, Flags flags) - : m_manager(manager), m_name(std::move(name)), m_flags(flags) {} +Option::Option(OptionManager& manager, String name, String docstring, + Flags flags) + : m_manager(manager), m_name(std::move(name)), + m_docstring(std::move(docstring)), m_flags(flags) {} OptionManager::OptionManager(OptionManager& parent) : m_parent(&parent) @@ -120,32 +122,51 @@ void OptionManager::on_option_changed(const Option& option) GlobalOptions::GlobalOptions() : OptionManager() { - declare_option("tabstop", 8); - declare_option("indentwidth", 4); - declare_option("scrolloff", 0); - declare_option("eolformat", "lf"); - declare_option("BOM", "no"); - declare_option("complete_prefix", true); - declare_option("incsearch", true); - declare_option("autoinfo", true); - declare_option("autoshowcompl", true); - declare_option("aligntab", false); - declare_option("ignored_files", Regex{R"(^(\..*|.*\.(o|so|a))$)"}); - declare_option("filetype", ""); - declare_option>("path", { "./", "/usr/include" }); - declare_option>("completers", {"filename", "word=buffer"}, - Option::Flags::None, - [](const std::vector& s) { - static const auto values = {"word=buffer", "word=all", "filename" }; - for (auto& v : s) - { - if (v.substr(0_byte, 7_byte) == "option=") - continue; - if (not contains(values, v)) - throw runtime_error(v + " is not a recognised value for completers"); - } - }); - declare_option("autoreload", Ask); + declare_option("tabstop", "size of a tab character", 8); + declare_option("indentwidth", "indentation width", 4); + declare_option("scrolloff", + "number of lines to keep visible main cursor when scrolling", + 0); + declare_option("eolformat", "end of line format: 'crlf' or 'lf'", "lf"_str); + declare_option("BOM", "insert a byte order mark when writing buffer", + "no"_str); + declare_option("complete_prefix", + "complete up to common prefix in tab completion", + true); + declare_option("incsearch", + "incrementaly apply search/select/split regex", + true); + declare_option("autoinfo", + "automatically display contextual help", + true); + declare_option("autoshowcompl", + "automatically display possible completions for prompts", + true); + declare_option("aligntab", + "use tab characters when possible for alignement", + false); + declare_option("ignored_files", + "patterns to ignore when completing filenames", + Regex{R"(^(\..*|.*\.(o|so|a))$)"}); + declare_option("filetype", "buffer filetype", ""_str); + declare_option("path", "path to consider when trying to find a file", + std::vector({ "./", "/usr/include" })); + declare_option("completers", "insert mode completers to execute.", + std::vector({"filename", "word=buffer"}), + Option::Flags::None, + OptionChecker>([](const std::vector& s) { + static const auto values = {"word=buffer", "word=all", "filename"}; + for (auto& v : s) + { + if (v.substr(0_byte, 7_byte) == "option=") + continue; + if (not contains(values, v)) + throw runtime_error(v + " is not a recognised value for completers"); + } + })); + declare_option("autoreload", + "autoreload buffer when a filesystem modification is detected", + Ask); } } diff --git a/src/option_manager.hh b/src/option_manager.hh index 123d1d7d..d173c747 100644 --- a/src/option_manager.hh +++ b/src/option_manager.hh @@ -28,7 +28,7 @@ public: Hidden = 1, }; - Option(OptionManager& manager, String name, Flags flags); + Option(OptionManager& manager, String name, String docstring, Flags flags); virtual ~Option() {} template const T& get() const; @@ -40,6 +40,7 @@ public: virtual void add_from_string(const String& str) = 0; const String& name() const { return m_name; } + const String& docstring() const { return m_docstring; } OptionManager& manager() const { return m_manager; } virtual Option* clone(OptionManager& manager) const = 0; @@ -55,6 +56,7 @@ public: protected: OptionManager& m_manager; String m_name; + String m_docstring; Flags m_flags; }; @@ -106,10 +108,10 @@ template class TypedOption : public Option { public: - TypedOption(OptionManager& manager, String name, Option::Flags flags, - const T& value, OptionChecker checker) - : Option(manager, std::move(name), flags), m_value(value), - m_checker(std::move(checker)) {} + TypedOption(OptionManager& manager, String name, String docstring, + Option::Flags flags, const T& value, OptionChecker checker) + : Option(manager, std::move(name), std::move(docstring), flags), + m_value(value), m_checker(std::move(checker)) {} void set(T value) { @@ -145,7 +147,8 @@ public: Option* clone(OptionManager& manager) const override { - return new TypedOption{manager, name(), flags(), m_value, m_checker}; + return new TypedOption{manager, name(), docstring(), flags(), + m_value, m_checker}; } private: T m_value; @@ -187,7 +190,8 @@ public: GlobalOptions(); template - Option& declare_option(const String& name, const T& value, + Option& declare_option(const String& name, const String& docstring, + const T& value, Option::Flags flags = Option::Flags::None, OptionChecker checker = OptionChecker{}) { @@ -198,7 +202,8 @@ public: return **it; throw runtime_error("option " + name + " already declared with different type or flags"); } - m_options.emplace_back(new TypedOption{*this, name, flags, value, + m_options.emplace_back(new TypedOption{*this, name, docstring, + flags, value, std::move(checker)}); return *m_options.back(); }