mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-15 21:57:10 +02:00
Implement keyboard navigation for recent peers.
This commit is contained in:
parent
051ca51d3b
commit
19f5d95a3c
5 changed files with 110 additions and 72 deletions
|
@ -3165,32 +3165,25 @@ void Widget::keyPressEvent(QKeyEvent *e) {
|
|||
//}
|
||||
} else if (e->key() == Qt::Key_Return || e->key() == Qt::Key_Enter) {
|
||||
submit();
|
||||
} else if (_suggestions
|
||||
&& (e->key() == Qt::Key_Down
|
||||
|| e->key() == Qt::Key_Up
|
||||
|| e->key() == Qt::Key_Left
|
||||
|| e->key() == Qt::Key_Right)) {
|
||||
_suggestions->selectJump(Qt::Key(e->key()));
|
||||
} else if (e->key() == Qt::Key_Down) {
|
||||
if (_suggestions) {
|
||||
_suggestions->selectSkip(1);
|
||||
} else {
|
||||
_inner->selectSkip(1);
|
||||
}
|
||||
_inner->selectSkip(1);
|
||||
} else if (e->key() == Qt::Key_Up) {
|
||||
if (_suggestions) {
|
||||
_suggestions->selectSkip(-1);
|
||||
} else {
|
||||
_inner->selectSkip(-1);
|
||||
}
|
||||
_inner->selectSkip(-1);
|
||||
} else if (e->key() == Qt::Key_Left && _suggestions) {
|
||||
_suggestions->selectLeft();
|
||||
} else if (e->key() == Qt::Key_Right && _suggestions) {
|
||||
_suggestions->selectRight();
|
||||
} else if (e->key() == Qt::Key_PageDown) {
|
||||
if (_suggestions) {
|
||||
_suggestions->selectSkipPage(_scroll->height(), 1);
|
||||
_suggestions->selectJump(Qt::Key_Down, _scroll->height());
|
||||
} else {
|
||||
_inner->selectSkipPage(_scroll->height(), 1);
|
||||
}
|
||||
} else if (e->key() == Qt::Key_PageUp) {
|
||||
if (_suggestions) {
|
||||
_suggestions->selectSkipPage(_scroll->height(), -1);
|
||||
_suggestions->selectJump(Qt::Key_Up, _scroll->height());
|
||||
} else {
|
||||
_inner->selectSkipPage(_scroll->height(), -1);
|
||||
}
|
||||
|
|
|
@ -491,43 +491,60 @@ Suggestions::Suggestions(
|
|||
|
||||
Suggestions::~Suggestions() = default;
|
||||
|
||||
void Suggestions::selectSkip(int delta) {
|
||||
if (!delta) {
|
||||
return;
|
||||
} else if (delta > 0) {
|
||||
const auto hasRecent = false;
|
||||
if (hasRecent && (_topPeers->selectedByKeyboard() || delta > 1)) {
|
||||
void Suggestions::selectJump(Qt::Key direction, int pageSize) {
|
||||
const auto recentHasSelection = [=] {
|
||||
return _recentSelectJump(Qt::Key(), 0) == JumpResult::Applied;
|
||||
};
|
||||
if (pageSize) {
|
||||
if (direction == Qt::Key_Down || direction == Qt::Key_Up) {
|
||||
_topPeers->deselectByKeyboard();
|
||||
if (!recentHasSelection()) {
|
||||
if (direction == Qt::Key_Down) {
|
||||
_recentSelectJump(direction, 0);
|
||||
} else {
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (_recentSelectJump(direction, pageSize) == JumpResult::AppliedAndOut) {
|
||||
if (direction == Qt::Key_Up) {
|
||||
_scroll->scrollTo(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
} else if (direction == Qt::Key_Up) {
|
||||
if (_recentSelectJump(direction, pageSize)
|
||||
== JumpResult::AppliedAndOut) {
|
||||
_topPeers->selectByKeyboard(Qt::Key());
|
||||
_scroll->scrollTo(0);
|
||||
} else {
|
||||
_topPeers->selectByKeyboard(0);
|
||||
}
|
||||
} else {
|
||||
if (_topPeers->selectedByKeyboard()) {
|
||||
_topPeers->deselectByKeyboard();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Suggestions::selectSkipPage(int height, int direction) {
|
||||
if (_topPeers->selectedByKeyboard()) {
|
||||
_topPeers->deselectByKeyboard();
|
||||
} else if (direction == Qt::Key_Down) {
|
||||
if (_topPeers->selectedByKeyboard()) {
|
||||
if (_recentCount.current() > 0) {
|
||||
_topPeers->deselectByKeyboard();
|
||||
_recentSelectJump(direction, pageSize);
|
||||
}
|
||||
} else if (!_topPeersWrap->toggled() || recentHasSelection()) {
|
||||
_recentSelectJump(direction, pageSize);
|
||||
} else {
|
||||
_topPeers->selectByKeyboard(Qt::Key());
|
||||
_scroll->scrollTo(0);
|
||||
}
|
||||
} else if (direction == Qt::Key_Left || direction == Qt::Key_Right) {
|
||||
if (!recentHasSelection()) {
|
||||
_topPeers->selectByKeyboard(direction);
|
||||
_scroll->scrollTo(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Suggestions::chooseRow() {
|
||||
if (_topPeers->chooseRow()) {
|
||||
return;
|
||||
if (!_topPeers->chooseRow()) {
|
||||
_recentPeersChoose();
|
||||
}
|
||||
}
|
||||
|
||||
void Suggestions::selectLeft() {
|
||||
_topPeers->selectLeft();
|
||||
}
|
||||
|
||||
void Suggestions::selectRight() {
|
||||
_topPeers->selectRight();
|
||||
}
|
||||
|
||||
void Suggestions::paintEvent(QPaintEvent *e) {
|
||||
QPainter(this).fillRect(e->rect(), st::windowBg);
|
||||
}
|
||||
|
@ -559,7 +576,39 @@ object_ptr<Ui::SlideWrap<>> Suggestions::setupRecentPeers(
|
|||
}, lifetime);
|
||||
|
||||
auto content = object_ptr<PeerListContent>(_content, controller);
|
||||
delegate->setContent(content);
|
||||
|
||||
const auto raw = content.data();
|
||||
_recentPeersChoose = [=] {
|
||||
return raw->submitted();
|
||||
};
|
||||
_recentSelectJump = [raw](Qt::Key direction, int pageSize) {
|
||||
const auto had = raw->hasSelection();
|
||||
if (direction == Qt::Key()) {
|
||||
return had ? JumpResult::Applied : JumpResult::NotApplied;
|
||||
} else if (direction == Qt::Key_Up && !had) {
|
||||
return JumpResult::NotApplied;
|
||||
} else if (direction == Qt::Key_Down || direction == Qt::Key_Up) {
|
||||
const auto delta = (direction == Qt::Key_Down) ? 1 : -1;
|
||||
if (pageSize > 0) {
|
||||
raw->selectSkipPage(pageSize, delta);
|
||||
} else {
|
||||
raw->selectSkip(delta);
|
||||
}
|
||||
return raw->hasSelection()
|
||||
? JumpResult::Applied
|
||||
: had
|
||||
? JumpResult::AppliedAndOut
|
||||
: JumpResult::NotApplied;
|
||||
}
|
||||
return JumpResult::NotApplied;
|
||||
};
|
||||
raw->scrollToRequests(
|
||||
) | rpl::start_with_next([this](Ui::ScrollToRequest request) {
|
||||
const auto add = _topPeersWrap->toggled() ? _topPeers->height() : 0;
|
||||
_scroll->scrollToY(request.ymin + add, request.ymax + add);
|
||||
}, lifetime);
|
||||
|
||||
delegate->setContent(raw);
|
||||
controller->setDelegate(delegate);
|
||||
|
||||
return object_ptr<Ui::SlideWrap<>>(this, std::move(content));
|
||||
|
|
|
@ -41,10 +41,7 @@ public:
|
|||
RecentPeersList recentPeers);
|
||||
~Suggestions();
|
||||
|
||||
void selectSkip(int delta);
|
||||
void selectSkipPage(int height, int direction);
|
||||
void selectLeft();
|
||||
void selectRight();
|
||||
void selectJump(Qt::Key direction, int pageSize = 0);
|
||||
void chooseRow();
|
||||
|
||||
[[nodiscard]] rpl::producer<not_null<PeerData*>> topPeerChosen() const {
|
||||
|
@ -55,6 +52,12 @@ public:
|
|||
}
|
||||
|
||||
private:
|
||||
enum class JumpResult {
|
||||
NotApplied,
|
||||
Applied,
|
||||
AppliedAndOut,
|
||||
};
|
||||
|
||||
void paintEvent(QPaintEvent *e) override;
|
||||
void resizeEvent(QResizeEvent *e) override;
|
||||
|
||||
|
@ -70,6 +73,8 @@ private:
|
|||
const not_null<TopPeersStrip*> _topPeers;
|
||||
|
||||
rpl::variable<int> _recentCount;
|
||||
Fn<bool()> _recentPeersChoose;
|
||||
Fn<JumpResult(Qt::Key, int)> _recentSelectJump;
|
||||
const not_null<Ui::SlideWrap<Ui::RpWidget>*> _recentPeers;
|
||||
const not_null<Ui::SlideWrap<Ui::RpWidget>*> _emptyRecent;
|
||||
|
||||
|
|
|
@ -282,20 +282,29 @@ bool TopPeersStrip::selectedByKeyboard() const {
|
|||
return _selectionByKeyboard && _selected >= 0;
|
||||
}
|
||||
|
||||
void TopPeersStrip::selectByKeyboard(int delta) {
|
||||
void TopPeersStrip::selectByKeyboard(Qt::Key direction) {
|
||||
if (_entries.empty()) {
|
||||
return;
|
||||
}
|
||||
_selectionByKeyboard = true;
|
||||
if (!delta) {
|
||||
if (direction == Qt::Key()) {
|
||||
_selectionByKeyboard = true;
|
||||
if (_selected < 0) {
|
||||
setSelected(0);
|
||||
scrollToSelected();
|
||||
}
|
||||
return;
|
||||
} else if (direction == Qt::Key_Left) {
|
||||
if (_selected > 0) {
|
||||
_selectionByKeyboard = true;
|
||||
setSelected(_selected - 1);
|
||||
scrollToSelected();
|
||||
}
|
||||
} else if (direction == Qt::Key_Right) {
|
||||
if (_selected + 1 < _entries.size()) {
|
||||
_selectionByKeyboard = true;
|
||||
setSelected(_selected + 1);
|
||||
scrollToSelected();
|
||||
}
|
||||
}
|
||||
setSelected(std::clamp(_selected + delta, 0, int(_entries.size()) - 1));
|
||||
scrollToSelected();
|
||||
}
|
||||
|
||||
void TopPeersStrip::deselectByKeyboard() {
|
||||
|
@ -305,22 +314,6 @@ void TopPeersStrip::deselectByKeyboard() {
|
|||
}
|
||||
}
|
||||
|
||||
void TopPeersStrip::selectLeft() {
|
||||
if (_selected > 0) {
|
||||
_selectionByKeyboard = true;
|
||||
setSelected(_selected - 1);
|
||||
scrollToSelected();
|
||||
}
|
||||
}
|
||||
|
||||
void TopPeersStrip::selectRight() {
|
||||
if (_selected + 1 < _entries.size()) {
|
||||
_selectionByKeyboard = true;
|
||||
setSelected(_selected + 1);
|
||||
scrollToSelected();
|
||||
}
|
||||
}
|
||||
|
||||
bool TopPeersStrip::chooseRow() {
|
||||
if (_selected >= 0) {
|
||||
Assert(_selected < _entries.size());
|
||||
|
|
|
@ -53,9 +53,7 @@ public:
|
|||
void removeLocally(uint64 id = 0);
|
||||
|
||||
[[nodiscard]] bool selectedByKeyboard() const;
|
||||
void selectByKeyboard(int delta);
|
||||
void selectLeft();
|
||||
void selectRight();
|
||||
void selectByKeyboard(Qt::Key direction);
|
||||
void deselectByKeyboard();
|
||||
bool chooseRow();
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue