mirror of https://github.com/procxx/kepka.git
Added ability to filter languages in dictionaries manager.
This commit is contained in:
parent
a0f995b134
commit
311678af80
|
@ -16,12 +16,14 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
#include "mtproto/dedicated_file_loader.h"
|
#include "mtproto/dedicated_file_loader.h"
|
||||||
|
#include "spellcheck/spellcheck_utils.h"
|
||||||
#include "styles/style_layers.h"
|
#include "styles/style_layers.h"
|
||||||
#include "styles/style_settings.h"
|
#include "styles/style_settings.h"
|
||||||
#include "styles/style_boxes.h"
|
#include "styles/style_boxes.h"
|
||||||
#include "ui/wrap/vertical_layout.h"
|
#include "ui/wrap/vertical_layout.h"
|
||||||
#include "ui/widgets/buttons.h"
|
#include "ui/widgets/buttons.h"
|
||||||
#include "ui/widgets/labels.h"
|
#include "ui/widgets/labels.h"
|
||||||
|
#include "ui/widgets/multi_select.h"
|
||||||
#include "ui/widgets/popup_menu.h"
|
#include "ui/widgets/popup_menu.h"
|
||||||
#include "ui/wrap/slide_wrap.h"
|
#include "ui/wrap/slide_wrap.h"
|
||||||
#include "ui/effects/animations.h"
|
#include "ui/effects/animations.h"
|
||||||
|
@ -34,6 +36,13 @@ using namespace Storage::CloudBlob;
|
||||||
|
|
||||||
using Loading = MTP::DedicatedLoader::Progress;
|
using Loading = MTP::DedicatedLoader::Progress;
|
||||||
using DictState = BlobState;
|
using DictState = BlobState;
|
||||||
|
using QueryCallback = Fn<void(const QString &)>;
|
||||||
|
constexpr auto kMaxQueryLength = 15;
|
||||||
|
|
||||||
|
#if QT_VERSION < QT_VERSION_CHECK(5, 10, 0)
|
||||||
|
#define OLD_QT
|
||||||
|
using QStringView = QString;
|
||||||
|
#endif
|
||||||
|
|
||||||
class Loader : public BlobLoader {
|
class Loader : public BlobLoader {
|
||||||
public:
|
public:
|
||||||
|
@ -58,11 +67,13 @@ public:
|
||||||
Inner(QWidget *parent, Dictionaries enabledDictionaries);
|
Inner(QWidget *parent, Dictionaries enabledDictionaries);
|
||||||
|
|
||||||
Dictionaries enabledRows() const;
|
Dictionaries enabledRows() const;
|
||||||
|
QueryCallback queryCallback() const;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void setupContent(Dictionaries enabledDictionaries);
|
void setupContent(Dictionaries enabledDictionaries);
|
||||||
|
|
||||||
Dictionaries _enabledRows;
|
Dictionaries _enabledRows;
|
||||||
|
QueryCallback _queryCallback;
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -115,12 +126,27 @@ void Loader::unpack(const QString &path) {
|
||||||
void Loader::destroy() {
|
void Loader::destroy() {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
auto CreateMultiSelect(QWidget *parent) {
|
||||||
|
const auto result = Ui::CreateChild<Ui::MultiSelect>(
|
||||||
|
parent,
|
||||||
|
st::contactsMultiSelect,
|
||||||
|
tr::lng_participant_filter());
|
||||||
|
|
||||||
|
result->resizeToWidth(st::boxWidth);
|
||||||
|
result->moveToLeft(0, 0);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
Inner::Inner(
|
Inner::Inner(
|
||||||
QWidget *parent,
|
QWidget *parent,
|
||||||
Dictionaries enabledDictionaries) : RpWidget(parent) {
|
Dictionaries enabledDictionaries) : RpWidget(parent) {
|
||||||
setupContent(std::move(enabledDictionaries));
|
setupContent(std::move(enabledDictionaries));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QueryCallback Inner::queryCallback() const {
|
||||||
|
return _queryCallback;
|
||||||
|
}
|
||||||
|
|
||||||
Dictionaries Inner::enabledRows() const {
|
Dictionaries Inner::enabledRows() const {
|
||||||
return _enabledRows;
|
return _enabledRows;
|
||||||
}
|
}
|
||||||
|
@ -128,11 +154,19 @@ Dictionaries Inner::enabledRows() const {
|
||||||
auto AddButtonWithLoader(
|
auto AddButtonWithLoader(
|
||||||
not_null<Ui::VerticalLayout*> content,
|
not_null<Ui::VerticalLayout*> content,
|
||||||
const Spellchecker::Dict &dict,
|
const Spellchecker::Dict &dict,
|
||||||
bool buttonEnabled) {
|
bool buttonEnabled,
|
||||||
|
rpl::producer<QStringView> query) {
|
||||||
const auto id = dict.id;
|
const auto id = dict.id;
|
||||||
buttonEnabled &= DictExists(id);
|
buttonEnabled &= DictExists(id);
|
||||||
|
|
||||||
const auto button = content->add(
|
const auto locale = Spellchecker::LocaleFromLangId(id);
|
||||||
|
const std::vector<QString> indexList = {
|
||||||
|
dict.name,
|
||||||
|
QLocale::languageToString(locale.language()),
|
||||||
|
QLocale::countryToString(locale.country())
|
||||||
|
};
|
||||||
|
|
||||||
|
const auto wrap = content->add(
|
||||||
object_ptr<Ui::SlideWrap<Ui::SettingsButton>>(
|
object_ptr<Ui::SlideWrap<Ui::SettingsButton>>(
|
||||||
content,
|
content,
|
||||||
object_ptr<Ui::SettingsButton>(
|
object_ptr<Ui::SettingsButton>(
|
||||||
|
@ -141,8 +175,18 @@ auto AddButtonWithLoader(
|
||||||
st::dictionariesSectionButton
|
st::dictionariesSectionButton
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
)->entity();
|
);
|
||||||
|
const auto button = wrap->entity();
|
||||||
|
|
||||||
|
std::move(
|
||||||
|
query
|
||||||
|
) | rpl::start_with_next([=](auto string) {
|
||||||
|
wrap->toggle(
|
||||||
|
ranges::any_of(indexList, [&](const QString &s) {
|
||||||
|
return s.startsWith(string, Qt::CaseInsensitive);
|
||||||
|
}),
|
||||||
|
anim::type::instant);
|
||||||
|
}, button->lifetime());
|
||||||
|
|
||||||
const auto localLoader = button->lifetime()
|
const auto localLoader = button->lifetime()
|
||||||
.make_state<base::unique_qptr<Loader>>();
|
.make_state<base::unique_qptr<Loader>>();
|
||||||
|
@ -283,12 +327,16 @@ auto AddButtonWithLoader(
|
||||||
void Inner::setupContent(Dictionaries enabledDictionaries) {
|
void Inner::setupContent(Dictionaries enabledDictionaries) {
|
||||||
const auto content = Ui::CreateChild<Ui::VerticalLayout>(this);
|
const auto content = Ui::CreateChild<Ui::VerticalLayout>(this);
|
||||||
|
|
||||||
|
const auto queryStream = content->lifetime()
|
||||||
|
.make_state<rpl::event_stream<QStringView>>();
|
||||||
|
|
||||||
for (const auto &dict : Spellchecker::Dictionaries()) {
|
for (const auto &dict : Spellchecker::Dictionaries()) {
|
||||||
const auto id = dict.id;
|
const auto id = dict.id;
|
||||||
const auto row = AddButtonWithLoader(
|
const auto row = AddButtonWithLoader(
|
||||||
content,
|
content,
|
||||||
dict,
|
dict,
|
||||||
ranges::contains(enabledDictionaries, id));
|
ranges::contains(enabledDictionaries, id),
|
||||||
|
queryStream->events());
|
||||||
row->toggledValue(
|
row->toggledValue(
|
||||||
) | rpl::start_with_next([=](auto enabled) {
|
) | rpl::start_with_next([=](auto enabled) {
|
||||||
if (enabled) {
|
if (enabled) {
|
||||||
|
@ -300,6 +348,13 @@ void Inner::setupContent(Dictionaries enabledDictionaries) {
|
||||||
}, row->lifetime());
|
}, row->lifetime());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_queryCallback = [=](const QString &query) {
|
||||||
|
if (query.size() >= kMaxQueryLength) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
queryStream->fire_copy(query);
|
||||||
|
};
|
||||||
|
|
||||||
content->resizeToWidth(st::boxWidth);
|
content->resizeToWidth(st::boxWidth);
|
||||||
Ui::ResizeFitChild(this, content);
|
Ui::ResizeFitChild(this, content);
|
||||||
}
|
}
|
||||||
|
@ -312,10 +367,25 @@ ManageDictionariesBox::ManageDictionariesBox(
|
||||||
: _session(session) {
|
: _session(session) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ManageDictionariesBox::setInnerFocus() {
|
||||||
|
_setInnerFocus();
|
||||||
|
}
|
||||||
|
|
||||||
void ManageDictionariesBox::prepare() {
|
void ManageDictionariesBox::prepare() {
|
||||||
const auto inner = setInnerWidget(object_ptr<Inner>(
|
const auto multiSelect = CreateMultiSelect(this);
|
||||||
|
|
||||||
|
const auto inner = setInnerWidget(
|
||||||
|
object_ptr<Inner>(
|
||||||
this,
|
this,
|
||||||
_session->settings().dictionariesEnabled()));
|
_session->settings().dictionariesEnabled()),
|
||||||
|
st::boxScroll,
|
||||||
|
multiSelect->height()
|
||||||
|
);
|
||||||
|
|
||||||
|
multiSelect->setQueryChangedCallback(inner->queryCallback());
|
||||||
|
_setInnerFocus = [=] {
|
||||||
|
multiSelect->setInnerFocus();
|
||||||
|
};
|
||||||
|
|
||||||
// The initial list of enabled rows may differ from the list of languages
|
// The initial list of enabled rows may differ from the list of languages
|
||||||
// in settings, so we should store it when box opens
|
// in settings, so we should store it when box opens
|
||||||
|
@ -342,10 +412,16 @@ void ManageDictionariesBox::prepare() {
|
||||||
|
|
||||||
setDimensionsToContent(st::boxWidth, inner);
|
setDimensionsToContent(st::boxWidth, inner);
|
||||||
|
|
||||||
inner->heightValue(
|
using namespace rpl::mappers;
|
||||||
|
const auto max = lifetime().make_state<int>(0);
|
||||||
|
rpl::combine(
|
||||||
|
inner->heightValue(),
|
||||||
|
multiSelect->heightValue(),
|
||||||
|
_1 + _2
|
||||||
) | rpl::start_with_next([=](int height) {
|
) | rpl::start_with_next([=](int height) {
|
||||||
using std::min;
|
using std::min;
|
||||||
setDimensions(st::boxWidth, min(height, st::boxMaxListHeight));
|
accumulate_max(*max, height);
|
||||||
|
setDimensions(st::boxWidth, min(*max, st::boxMaxListHeight), true);
|
||||||
}, inner->lifetime());
|
}, inner->lifetime());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -25,9 +25,11 @@ public:
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void prepare() override;
|
void prepare() override;
|
||||||
|
void setInnerFocus() override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
const not_null<Main::Session*> _session;
|
const not_null<Main::Session*> _session;
|
||||||
|
Fn<void()> _setInnerFocus;
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue