Added ability to provide back button to pinned to top content.

This commit is contained in:
23rd 2022-05-23 02:06:35 +03:00
parent 00632dff46
commit c310b263a6
8 changed files with 83 additions and 3 deletions

View file

@ -23,7 +23,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "main/main_session.h"
#include "main/main_domain.h"
#include "info/info_memento.h"
#include "info/settings/info_settings_widget.h"
#include "info/info_controller.h"
#include "window/window_session_controller.h"
#include "settings/settings_advanced.h"
#include "settings/settings_intro.h"

View file

@ -56,6 +56,8 @@ public:
virtual void setInnerFocus();
virtual void showFinished() {
}
virtual void enableBackButton() {
}
// When resizing the widget with top edge moved up or down and we
// want to add this top movement to the scroll position, so inner

View file

@ -376,7 +376,7 @@ void WrapWidget::createTopBar() {
_content->selectionAction(action);
}, _topBar->lifetime());
if (wrapValue == Wrap::Narrow || hasStackHistory()) {
if (hasBackButton()) {
_topBar->enableBackButton();
_topBar->backRequest(
) | rpl::start_with_next([=] {
@ -995,6 +995,11 @@ void WrapWidget::showNewContent(
_historyStack.clear();
}
{
if (hasBackButton()) {
newContent->enableBackButton();
}
}
{
// Let old controller outlive old content widget.
const auto oldController = std::exchange(
@ -1091,7 +1096,7 @@ QRect WrapWidget::floatPlayerAvailableRect() {
object_ptr<Ui::RpWidget> WrapWidget::createTopBarSurrogate(
QWidget *parent) {
if (_topBar && (hasStackHistory() || wrap() == Wrap::Narrow)) {
if (_topBar && hasBackButton()) {
Assert(_topBar != nullptr);
auto result = object_ptr<Ui::AbstractButton>(parent);
@ -1151,6 +1156,10 @@ rpl::producer<bool> WrapWidget::grabbingForExpanding() const {
return _grabbingForExpanding.value();
}
bool WrapWidget::hasBackButton() const {
return (wrap() == Wrap::Narrow || hasStackHistory());
}
WrapWidget::~WrapWidget() = default;
} // namespace Info

View file

@ -180,6 +180,8 @@ private:
void highlightTopBar();
void setupShortcuts();
[[nodiscard]] bool hasBackButton() const;
not_null<RpWidget*> topWidget() const;
QRect contentGeometry() const;

View file

@ -60,6 +60,10 @@ Widget::Widget(
_flexibleScroll.fillerWidthValue,
lifetime());
controller->stepDataReference() = SectionCustomTopBarData{
.backButtonEnables = _flexibleScroll.backButtonEnables.events(),
};
// ScrollArea -> PaddingWrap -> RpWidget.
inner->setParent(filler->parentWidget()->parentWidget());
inner->raise();
@ -220,6 +224,10 @@ std::shared_ptr<ContentMemento> Widget::doCreateMemento() {
return result;
}
void Widget::enableBackButton() {
_flexibleScroll.backButtonEnables.fire({});
}
void Widget::saveState(not_null<Memento*> memento) {
memento->setScrollTop(scrollTopSave());
}

View file

@ -21,6 +21,10 @@ using Type = Section::SettingsType;
struct Tag;
struct SectionCustomTopBarData {
rpl::producer<> backButtonEnables;
};
class Memento final : public ContentMemento {
public:
Memento(not_null<UserData*> self, Type type);
@ -72,6 +76,8 @@ public:
rpl::producer<QString> title() override;
void enableBackButton() override;
private:
void saveState(not_null<Memento*> memento);
void restoreState(not_null<Memento*> memento);
@ -84,6 +90,7 @@ private:
struct {
rpl::event_stream<int> contentHeightValue;
rpl::event_stream<int> fillerWidthValue;
rpl::event_stream<> backButtonEnables;
} _flexibleScroll;
not_null<::Settings::AbstractSection*> _inner;
QPointer<Ui::RpWidget> _pinnedToTop;

View file

@ -423,4 +423,20 @@ notifyPreviewBottomSkip: 9px;
settingsPremiumDescriptionSkip: 3px;
settingsPremiumButtonPadding: margins(11px, 11px, 11px, 3px);
settingsPremiumTopBarBackIcon: icon {{ "info/info_back", premiumButtonFg }};
settingsPremiumTopBarBackIconOver: icon {{ "info/info_back", premiumButtonFg }};
settingsPremiumTopBarBack: IconButton(infoTopBarBack) {
icon: settingsPremiumTopBarBackIcon;
iconOver: settingsPremiumTopBarBackIconOver;
ripple: RippleAnimation(defaultRippleAnimation) {
color: shadowFg;
}
}
settingsPremiumLayerTopBarBack: IconButton(infoLayerTopBarBack) {
icon: settingsPremiumTopBarBackIcon;
iconOver: settingsPremiumTopBarBackIcon;
ripple: RippleAnimation(defaultRippleAnimation) {
color: shadowFg;
}
}

View file

@ -7,6 +7,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
*/
#include "settings/settings_premium.h"
#include "core/application.h"
#include "info/settings/info_settings_widget.h" // SectionCustomTopBarData.
#include "lang/lang_keys.h"
#include "settings/settings_common.h"
#include "settings/settings_premium.h"
@ -18,6 +20,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "ui/text/text_utilities.h"
#include "ui/widgets/gradient_round_button.h"
#include "ui/widgets/labels.h"
#include "ui/wrap/fade_wrap.h"
#include "ui/wrap/padding_wrap.h"
#include "ui/wrap/vertical_layout.h"
#include "window/window_session_controller.h"
@ -35,6 +38,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
namespace Settings {
namespace {
using SectionCustomTopBarData = Info::Settings::SectionCustomTopBarData;
class Premium : public Section<Premium> {
public:
Premium(
@ -50,11 +55,19 @@ public:
[[nodiscard]] bool hasFlexibleTopBar() const override;
void setStepDataReference(std::any &data) override;
[[nodiscard]] rpl::producer<> sectionShowBack() override final;
private:
void setupContent();
const not_null<Window::SessionController*> _controller;
rpl::variable<bool> _backToggles;
rpl::event_stream<> _showBack;
};
Premium::Premium(
@ -73,6 +86,19 @@ bool Premium::hasFlexibleTopBar() const {
return true;
}
rpl::producer<> Premium::sectionShowBack() {
return _showBack.events();
}
void Premium::setStepDataReference(std::any &data) {
const auto my = std::any_cast<SectionCustomTopBarData>(&data);
if (my) {
_backToggles = std::move(
my->backButtonEnables
) | rpl::map_to(true);
}
}
void Premium::setupContent() {
const auto content = Ui::CreateChild<Ui::VerticalLayout>(this);
@ -271,6 +297,16 @@ QPointer<Ui::RpWidget> Premium::createPinnedToTop(
container->setMaximumHeight(st::introQrStepsTop);
container->setMinimumHeight(st::infoLayerTopBarHeight);
const auto back = Ui::CreateChild<Ui::FadeWrap<Ui::IconButton>>(
content,
object_ptr<Ui::IconButton>(content, st::settingsPremiumTopBarBack),
st::infoTopBarScale);
back->setDuration(0);
back->toggleOn(_backToggles.value());
back->entity()->addClickHandler([=] {
_showBack.fire({});
});
return Ui::MakeWeak(not_null<Ui::RpWidget*>{ container });
}