wip redesign info top bar
Before Width: | Height: | Size: 224 B After Width: | Height: | Size: 189 B |
Before Width: | Height: | Size: 398 B After Width: | Height: | Size: 351 B |
Before Width: | Height: | Size: 204 B After Width: | Height: | Size: 213 B |
Before Width: | Height: | Size: 377 B After Width: | Height: | Size: 390 B |
|
@ -21,12 +21,16 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
|
|||
#include "info/info_top_bar.h"
|
||||
|
||||
#include <rpl/never.h>
|
||||
#include <rpl/merge.h>
|
||||
#include "styles/style_info.h"
|
||||
#include "lang/lang_keys.h"
|
||||
#include "info/info_wrap_widget.h"
|
||||
#include "info/info_controller.h"
|
||||
#include "info/profile/info_profile_values.h"
|
||||
#include "storage/storage_shared_media.h"
|
||||
#include "boxes/confirm_box.h"
|
||||
#include "boxes/peer_list_controllers.h"
|
||||
#include "mainwidget.h"
|
||||
#include "ui/widgets/buttons.h"
|
||||
#include "ui/widgets/labels.h"
|
||||
#include "ui/widgets/input_fields.h"
|
||||
|
@ -37,30 +41,48 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
|
|||
|
||||
namespace Info {
|
||||
|
||||
TopBar::TopBar(QWidget *parent, const style::InfoTopBar &st)
|
||||
TopBar::TopBar(
|
||||
QWidget *parent,
|
||||
const style::InfoTopBar &st,
|
||||
SelectedItems &&selectedItems)
|
||||
: RpWidget(parent)
|
||||
, _st(st) {
|
||||
, _st(st)
|
||||
, _selectedItems(Section::MediaType::kCount) {
|
||||
setAttribute(Qt::WA_OpaquePaintEvent);
|
||||
setSelectedItems(std::move(selectedItems));
|
||||
finishSelectionAnimations();
|
||||
}
|
||||
|
||||
void TopBar::setTitle(rpl::producer<QString> &&title) {
|
||||
_title.create(this, std::move(title), _st.title);
|
||||
if (_title) {
|
||||
delete _title;
|
||||
}
|
||||
_title = Ui::CreateChild<Ui::FadeWrapScaled<Ui::FlatLabel>>(
|
||||
this,
|
||||
object_ptr<Ui::FlatLabel>(this, std::move(title), _st.title));
|
||||
_title->toggle(!selectionMode(), anim::type::instant);
|
||||
_defaultControls.push_back(_title.data());
|
||||
|
||||
if (_back) {
|
||||
_title->setAttribute(Qt::WA_TransparentForMouseEvents);
|
||||
}
|
||||
updateControlsGeometry(width());
|
||||
}
|
||||
|
||||
void TopBar::enableBackButton(bool enable) {
|
||||
if (enable) {
|
||||
_back.create(this, _st.back);
|
||||
_back->clicks()
|
||||
| rpl::start_to_stream(_backClicks, _back->lifetime());
|
||||
} else {
|
||||
_back.destroy();
|
||||
void TopBar::enableBackButton() {
|
||||
if (_back) {
|
||||
return;
|
||||
}
|
||||
_back = Ui::CreateChild<Ui::FadeWrapScaled<Ui::IconButton>>(
|
||||
this,
|
||||
object_ptr<Ui::IconButton>(this, _st.back));
|
||||
_back->toggle(!selectionMode(), anim::type::instant);
|
||||
_back->entity()->clicks()
|
||||
| rpl::start_to_stream(_backClicks, _back->lifetime());
|
||||
_defaultControls.push_back(_back.data());
|
||||
|
||||
if (_title) {
|
||||
_title->setAttribute(Qt::WA_TransparentForMouseEvents, enable);
|
||||
_title->setAttribute(Qt::WA_TransparentForMouseEvents);
|
||||
}
|
||||
updateControlsGeometry(width());
|
||||
}
|
||||
|
@ -104,26 +126,30 @@ void TopBar::createSearchView(
|
|||
field->setParent(wrap);
|
||||
|
||||
auto search = addButton(
|
||||
base::make_unique_q<Ui::FadeWrapScaled<Ui::IconButton>>(
|
||||
base::make_unique_q<Ui::FadeWrapScaled<Ui::FadeWrapScaled<Ui::IconButton>>>(
|
||||
this,
|
||||
object_ptr<Ui::IconButton>(this, _st.search)));
|
||||
auto cancel = Ui::CreateChild<Ui::CrossButton>(
|
||||
object_ptr<Ui::FadeWrapScaled<Ui::IconButton>>(
|
||||
this,
|
||||
object_ptr<Ui::IconButton>(this, _st.search))));
|
||||
_defaultControls.push_back(search);
|
||||
auto cancel = Ui::CreateChild<Ui::FadeWrapScaled<Ui::CrossButton>>(
|
||||
wrap,
|
||||
_st.searchRow.fieldCancel);
|
||||
object_ptr<Ui::CrossButton>(wrap, _st.searchRow.fieldCancel));
|
||||
_defaultControls.push_back(cancel);
|
||||
|
||||
auto toggleSearchMode = [=](bool enabled, anim::type animated) {
|
||||
if (!enabled) {
|
||||
setFocus();
|
||||
}
|
||||
if (_title) {
|
||||
_title->setVisible(!enabled);
|
||||
_title->entity()->setVisible(!enabled);
|
||||
}
|
||||
field->setVisible(enabled);
|
||||
cancel->toggleAnimated(enabled);
|
||||
cancel->entity()->toggleAnimated(enabled);
|
||||
if (animated == anim::type::instant) {
|
||||
cancel->finishAnimations();
|
||||
cancel->entity()->finishAnimations();
|
||||
}
|
||||
search->toggle(!enabled, animated);
|
||||
search->wrapped()->toggle(!enabled, animated);
|
||||
if (enabled) {
|
||||
field->setFocus();
|
||||
}
|
||||
|
@ -137,7 +163,7 @@ void TopBar::createSearchView(
|
|||
}
|
||||
};
|
||||
|
||||
cancel->addClickHandler(cancelSearch);
|
||||
cancel->entity()->addClickHandler(cancelSearch);
|
||||
field->connect(field, &Ui::InputField::cancelled, cancelSearch);
|
||||
|
||||
wrap->widthValue()
|
||||
|
@ -187,7 +213,7 @@ void TopBar::createSearchView(
|
|||
}
|
||||
toggleSearchMode(false, anim::type::instant);
|
||||
wrap->setVisible(visible);
|
||||
search->toggle(visible, anim::type::instant);
|
||||
search->wrapped()->toggle(visible, anim::type::instant);
|
||||
}, wrap->lifetime());
|
||||
}
|
||||
|
||||
|
@ -202,7 +228,23 @@ int TopBar::resizeGetHeight(int newWidth) {
|
|||
return _st.height;
|
||||
}
|
||||
|
||||
void TopBar::finishSelectionAnimations() {
|
||||
ranges::for_each(ranges::view::concat(
|
||||
_defaultControls,
|
||||
_selectionControls
|
||||
), [](auto &&control) {
|
||||
if (auto pointer = control.data()) {
|
||||
pointer->finishAnimating();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
void TopBar::updateControlsGeometry(int newWidth) {
|
||||
updateDefaultControlsGeometry(newWidth);
|
||||
updateSelectionControlsGeometry(newWidth);
|
||||
}
|
||||
|
||||
void TopBar::updateDefaultControlsGeometry(int newWidth) {
|
||||
auto right = 0;
|
||||
for (auto &button : _buttons) {
|
||||
if (!button) continue;
|
||||
|
@ -225,6 +267,32 @@ void TopBar::updateControlsGeometry(int newWidth) {
|
|||
}
|
||||
}
|
||||
|
||||
void TopBar::updateSelectionControlsGeometry(int newWidth) {
|
||||
if (!_selectionText) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto right = _st.mediaActionsSkip;
|
||||
if (_canDelete) {
|
||||
_delete->moveToRight(right, 0, newWidth);
|
||||
right += _delete->width();
|
||||
}
|
||||
_forward->moveToRight(right, 0, newWidth);
|
||||
right += _forward->width();
|
||||
|
||||
auto left = 0;
|
||||
_cancelSelection->moveToLeft(left, 0);
|
||||
left += _cancelSelection->width();
|
||||
|
||||
const auto top = 0;
|
||||
const auto availableWidth = newWidth - left - right;
|
||||
_selectionText->resizeToWidth(availableWidth);
|
||||
_selectionText->moveToLeft(
|
||||
left,
|
||||
top,
|
||||
newWidth);
|
||||
}
|
||||
|
||||
void TopBar::paintEvent(QPaintEvent *e) {
|
||||
Painter p(this);
|
||||
|
||||
|
@ -251,6 +319,182 @@ void TopBar::startHighlightAnimation() {
|
|||
_st.highlightDuration);
|
||||
}
|
||||
|
||||
void TopBar::setSelectedItems(SelectedItems &&items) {
|
||||
_selectedItems = std::move(items);
|
||||
if (selectionMode()) {
|
||||
if (_selectionText) {
|
||||
updateSelectionState();
|
||||
} else {
|
||||
createSelectionControls();
|
||||
}
|
||||
}
|
||||
toggleSelectionControls();
|
||||
}
|
||||
|
||||
SelectedItems TopBar::takeSelectedItems() {
|
||||
_canDelete = false;
|
||||
return std::move(_selectedItems);
|
||||
}
|
||||
|
||||
rpl::producer<> TopBar::cancelSelectionRequests() const {
|
||||
return _cancelSelectionClicks.events();
|
||||
}
|
||||
|
||||
void TopBar::updateSelectionState() {
|
||||
Expects(_selectionText && _delete);
|
||||
|
||||
_canDelete = computeCanDelete();
|
||||
_selectionText->entity()->setValue(generateSelectedText());
|
||||
_delete->entity()->setVisible(_canDelete);
|
||||
|
||||
updateSelectionControlsGeometry(width());
|
||||
}
|
||||
|
||||
void TopBar::createSelectionControls() {
|
||||
auto wrap = [&](auto created) {
|
||||
_selectionControls.push_back(created);
|
||||
created->toggle(false, anim::type::instant);
|
||||
return created;
|
||||
};
|
||||
_canDelete = computeCanDelete();
|
||||
_cancelSelection = wrap(Ui::CreateChild<Ui::FadeWrapScaled<Ui::IconButton>>(
|
||||
this,
|
||||
object_ptr<Ui::IconButton>(this, _st.mediaCancel)));
|
||||
_cancelSelection->entity()->clicks()
|
||||
| rpl::start_to_stream(
|
||||
_cancelSelectionClicks,
|
||||
_cancelSelection->lifetime());
|
||||
_selectionText = wrap(Ui::CreateChild<Ui::FadeWrapScaled<Ui::LabelWithNumbers>>(
|
||||
this,
|
||||
object_ptr<Ui::LabelWithNumbers>(
|
||||
this,
|
||||
_st.title,
|
||||
_st.titlePosition.y(),
|
||||
generateSelectedText())));
|
||||
_selectionText->entity()->resize(0, _st.height);
|
||||
_forward = wrap(Ui::CreateChild<Ui::FadeWrapScaled<Ui::IconButton>>(
|
||||
this,
|
||||
object_ptr<Ui::IconButton>(this, _st.mediaForward)));
|
||||
_forward->entity()->addClickHandler([this] { performForward(); });
|
||||
_delete = wrap(Ui::CreateChild<Ui::FadeWrapScaled<Ui::IconButton>>(
|
||||
this,
|
||||
object_ptr<Ui::IconButton>(this, _st.mediaDelete)));
|
||||
_delete->entity()->addClickHandler([this] { performDelete(); });
|
||||
_delete->entity()->setVisible(_canDelete);
|
||||
|
||||
updateControlsGeometry(width());
|
||||
}
|
||||
|
||||
bool TopBar::computeCanDelete() const {
|
||||
return ranges::find_if(
|
||||
_selectedItems.list,
|
||||
[](const SelectedItem &item) { return !item.canDelete; }
|
||||
) == _selectedItems.list.end();
|
||||
}
|
||||
|
||||
void TopBar::toggleSelectionControls() {
|
||||
auto toggle = [](bool shown) {
|
||||
return [=](auto &&control) {
|
||||
if (auto pointer = control.data()) {
|
||||
pointer->toggle(shown, anim::type::normal);
|
||||
}
|
||||
};
|
||||
};
|
||||
auto shown = selectionMode();
|
||||
ranges::for_each(_defaultControls, toggle(!shown));
|
||||
ranges::for_each(_selectionControls, toggle(shown));
|
||||
|
||||
if (!shown) {
|
||||
clearSelectionControls();
|
||||
}
|
||||
}
|
||||
|
||||
Ui::StringWithNumbers TopBar::generateSelectedText() const {
|
||||
using Data = Ui::StringWithNumbers;
|
||||
using Type = Storage::SharedMediaType;
|
||||
auto phrase = [&] {
|
||||
switch (_selectedItems.type) {
|
||||
case Type::Photo: return lng_media_selected_photo__generic<Data>;
|
||||
case Type::Video: return lng_media_selected_video__generic<Data>;
|
||||
case Type::File: return lng_media_selected_file__generic<Data>;
|
||||
case Type::MusicFile: return lng_media_selected_song__generic<Data>;
|
||||
case Type::Link: return lng_media_selected_link__generic<Data>;
|
||||
case Type::VoiceFile: return lng_media_selected_audio__generic<Data>;
|
||||
// case Type::RoundFile: return lng_media_selected_round__generic<Data>;
|
||||
}
|
||||
Unexpected("Type in TopBarOverride::generateText()");
|
||||
}();
|
||||
return phrase(lt_count, _selectedItems.list.size());
|
||||
}
|
||||
|
||||
bool TopBar::selectionMode() const {
|
||||
return !_selectedItems.list.empty();
|
||||
}
|
||||
|
||||
void TopBar::clearSelectionControls() {
|
||||
for (auto &&control : _selectionControls) {
|
||||
if (auto pointer = control.data()) {
|
||||
pointer->shownValue()
|
||||
| rpl::filter([](bool shown) { return !shown; })
|
||||
| rpl::start_with_next([control] {
|
||||
if (auto pointer = control.data()) {
|
||||
InvokeQueued(pointer, [pointer] { delete pointer; });
|
||||
}
|
||||
}, pointer->lifetime());
|
||||
}
|
||||
}
|
||||
|
||||
auto isStale = [](auto &&control) { return !control; };
|
||||
_defaultControls |= ranges::action::remove_if(isStale);
|
||||
_selectionControls |= ranges::action::remove_if(isStale);
|
||||
|
||||
_cancelSelection = nullptr;
|
||||
_selectionText = nullptr;
|
||||
_forward = nullptr;
|
||||
_delete = nullptr;
|
||||
}
|
||||
|
||||
SelectedItemSet TopBar::collectItems() const {
|
||||
auto result = SelectedItemSet();
|
||||
for (auto value : _selectedItems.list) {
|
||||
if (auto item = App::histItemById(value.msgId)) {
|
||||
result.insert(result.size(), item);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
void TopBar::performForward() {
|
||||
auto items = collectItems();
|
||||
if (items.empty()) {
|
||||
_cancelSelectionClicks.fire({});
|
||||
return;
|
||||
}
|
||||
auto callback = [items = std::move(items), that = weak(this)](
|
||||
not_null<PeerData*> peer) {
|
||||
App::main()->setForwardDraft(peer->id, items);
|
||||
if (that) {
|
||||
that->_cancelSelectionClicks.fire({});
|
||||
}
|
||||
};
|
||||
Ui::show(Box<PeerListBox>(
|
||||
std::make_unique<ChooseRecipientBoxController>(std::move(callback)),
|
||||
[](not_null<PeerListBox*> box) {
|
||||
box->addButton(langFactory(lng_cancel), [box] {
|
||||
box->closeBox();
|
||||
});
|
||||
}));
|
||||
}
|
||||
|
||||
void TopBar::performDelete() {
|
||||
auto items = collectItems();
|
||||
if (items.empty()) {
|
||||
_cancelSelectionClicks.fire({});
|
||||
} else {
|
||||
Ui::show(Box<DeleteMessagesBox>(items));
|
||||
}
|
||||
}
|
||||
|
||||
rpl::producer<QString> TitleValue(
|
||||
const Section §ion,
|
||||
not_null<PeerData*> peer) {
|
||||
|
|
|
@ -21,6 +21,9 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
|
|||
#pragma once
|
||||
|
||||
#include "ui/rp_widget.h"
|
||||
#include "ui/wrap/fade_wrap.h"
|
||||
#include "ui/effects/numbers_animation.h"
|
||||
#include "info/info_wrap_widget.h"
|
||||
|
||||
namespace style {
|
||||
struct InfoTopBar;
|
||||
|
@ -31,6 +34,7 @@ class IconButton;
|
|||
class FlatLabel;
|
||||
class InputField;
|
||||
class SearchFieldController;
|
||||
class LabelWithNumbers;
|
||||
} // namespace Ui
|
||||
|
||||
namespace Info {
|
||||
|
@ -43,14 +47,17 @@ rpl::producer<QString> TitleValue(
|
|||
|
||||
class TopBar : public Ui::RpWidget {
|
||||
public:
|
||||
TopBar(QWidget *parent, const style::InfoTopBar &st);
|
||||
TopBar(
|
||||
QWidget *parent,
|
||||
const style::InfoTopBar &st,
|
||||
SelectedItems &&items);
|
||||
|
||||
auto backRequest() const {
|
||||
return _backClicks.events();
|
||||
}
|
||||
|
||||
void setTitle(rpl::producer<QString> &&title);
|
||||
void enableBackButton(bool enable);
|
||||
void enableBackButton();
|
||||
void highlight();
|
||||
|
||||
template <typename ButtonWidget>
|
||||
|
@ -64,16 +71,37 @@ public:
|
|||
not_null<Ui::SearchFieldController*> controller,
|
||||
rpl::producer<bool> &&shown);
|
||||
|
||||
void setSelectedItems(SelectedItems &&items);
|
||||
SelectedItems takeSelectedItems();
|
||||
|
||||
rpl::producer<> cancelSelectionRequests() const;
|
||||
void finishSelectionAnimations();
|
||||
|
||||
protected:
|
||||
int resizeGetHeight(int newWidth) override;
|
||||
void paintEvent(QPaintEvent *e) override;
|
||||
|
||||
private:
|
||||
void updateControlsGeometry(int newWidth);
|
||||
void updateDefaultControlsGeometry(int newWidth);
|
||||
void updateSelectionControlsGeometry(int newWidth);
|
||||
void pushButton(base::unique_qptr<Ui::RpWidget> button);
|
||||
void removeButton(not_null<Ui::RpWidget*> button);
|
||||
void startHighlightAnimation();
|
||||
|
||||
bool selectionMode() const;
|
||||
Ui::StringWithNumbers generateSelectedText() const;
|
||||
[[nodiscard]] bool computeCanDelete() const;
|
||||
[[nodiscard]] SelectedItemSet collectSelectedItems() const;
|
||||
void updateSelectionState();
|
||||
void createSelectionControls();
|
||||
void toggleSelectionControls();
|
||||
void clearSelectionControls();
|
||||
|
||||
SelectedItemSet collectItems() const;
|
||||
void performForward();
|
||||
void performDelete();
|
||||
|
||||
void setSearchField(
|
||||
base::unique_qptr<Ui::InputField> field,
|
||||
rpl::producer<bool> &&shown);
|
||||
|
@ -84,14 +112,26 @@ private:
|
|||
const style::InfoTopBar &_st;
|
||||
Animation _a_highlight;
|
||||
bool _highlight = false;
|
||||
object_ptr<Ui::IconButton> _back = { nullptr };
|
||||
QPointer<Ui::FadeWrap<Ui::IconButton>> _back;
|
||||
std::vector<base::unique_qptr<Ui::RpWidget>> _buttons;
|
||||
object_ptr<Ui::FlatLabel> _title = { nullptr };
|
||||
QPointer<Ui::FadeWrap<Ui::FlatLabel>> _title;
|
||||
|
||||
base::unique_qptr<Ui::RpWidget> _searchView;
|
||||
|
||||
rpl::event_stream<> _backClicks;
|
||||
|
||||
SelectedItems _selectedItems;
|
||||
bool _canDelete = false;
|
||||
QPointer<Ui::FadeWrap<Ui::IconButton>> _cancelSelection;
|
||||
QPointer<Ui::FadeWrap<Ui::LabelWithNumbers>> _selectionText;
|
||||
QPointer<Ui::FadeWrap<Ui::IconButton>> _forward;
|
||||
QPointer<Ui::FadeWrap<Ui::IconButton>> _delete;
|
||||
rpl::event_stream<> _cancelSelectionClicks;
|
||||
|
||||
using FadingControl = QPointer<Ui::FadeWrap<RpWidget>>;
|
||||
std::vector<FadingControl> _defaultControls;
|
||||
std::vector<FadingControl> _selectionControls;
|
||||
|
||||
};
|
||||
|
||||
} // namespace Info
|
||||
|
|
|
@ -30,7 +30,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org
|
|||
#include "info/info_controller.h"
|
||||
#include "info/info_memento.h"
|
||||
#include "info/info_top_bar.h"
|
||||
#include "info/info_top_bar_override.h"
|
||||
#include "ui/widgets/discrete_sliders.h"
|
||||
#include "ui/widgets/buttons.h"
|
||||
#include "ui/widgets/shadow.h"
|
||||
|
@ -84,7 +83,7 @@ WrapWidget::WrapWidget(
|
|||
selectedListValue()
|
||||
| rpl::start_with_next([this](SelectedItems &&items) {
|
||||
InvokeQueued(this, [this, items = std::move(items)]() mutable {
|
||||
refreshTopBarOverride(std::move(items));
|
||||
if (_topBar) _topBar->setSelectedItems(std::move(items));
|
||||
});
|
||||
}, lifetime());
|
||||
restoreHistoryStack(memento->takeStack());
|
||||
|
@ -283,18 +282,24 @@ void WrapWidget::setupTop() {
|
|||
// createTopBar();
|
||||
//}
|
||||
createTopBar();
|
||||
refreshTopBarOverride();
|
||||
}
|
||||
|
||||
void WrapWidget::createTopBar() {
|
||||
auto wrapValue = wrap();
|
||||
_topBar.create(this, TopBarStyle(wrapValue));
|
||||
auto selectedItems = _topBar
|
||||
? _topBar->takeSelectedItems()
|
||||
: SelectedItems(Section::MediaType::kCount);
|
||||
_topBar.create(this, TopBarStyle(wrapValue), std::move(selectedItems));
|
||||
_topBar->cancelSelectionRequests()
|
||||
| rpl::start_with_next([this](auto) {
|
||||
_content->cancelSelection();
|
||||
}, _topBar->lifetime());
|
||||
|
||||
_topBar->setTitle(TitleValue(
|
||||
_controller->section(),
|
||||
_controller->peer()));
|
||||
if (wrapValue == Wrap::Narrow || hasStackHistory()) {
|
||||
_topBar->enableBackButton(true);
|
||||
_topBar->enableBackButton();
|
||||
_topBar->backRequest()
|
||||
| rpl::start_with_next([this] {
|
||||
showBackFromStack();
|
||||
|
@ -418,81 +423,6 @@ void WrapWidget::showProfileMenu() {
|
|||
_topBarMenu->showAnimated(Ui::PanelAnimation::Origin::TopRight);
|
||||
}
|
||||
|
||||
void WrapWidget::refreshTopBarOverride(SelectedItems &&items) {
|
||||
auto empty = items.list.empty();
|
||||
if (!empty) {
|
||||
if (_topBarOverride) {
|
||||
_topBarOverride->setItems(std::move(items));
|
||||
} else {
|
||||
createTopBarOverride(std::move(items));
|
||||
}
|
||||
}
|
||||
toggleTopBarOverride(!empty);
|
||||
}
|
||||
|
||||
void WrapWidget::refreshTopBarOverride() {
|
||||
if (_topBarOverride) {
|
||||
auto items = _topBarOverride->takeItems();
|
||||
createTopBarOverride(std::move(items));
|
||||
topBarOverrideStep();
|
||||
}
|
||||
}
|
||||
|
||||
void WrapWidget::toggleTopBarOverride(bool shown) {
|
||||
if (_topBarOverrideShown == shown) {
|
||||
return;
|
||||
}
|
||||
_topBarOverrideShown = shown;
|
||||
_topBar->show();
|
||||
_topBarOverrideAnimation.start(
|
||||
[this] { topBarOverrideStep(); },
|
||||
_topBarOverrideShown ? 0. : 1.,
|
||||
_topBarOverrideShown ? 1. : 0.,
|
||||
st::slideWrapDuration,
|
||||
anim::easeOutCirc);
|
||||
}
|
||||
|
||||
void WrapWidget::topBarOverrideStep() {
|
||||
auto shown = _topBarOverrideAnimation.current(
|
||||
_topBarOverrideShown ? 1. : 0.);
|
||||
auto topBarTop = anim::interpolate(0, _topBar->height(), shown);
|
||||
auto overrideTop = anim::interpolate(-_topBar->height(), 0, shown);
|
||||
_topBar->moveToLeft(0, topBarTop);
|
||||
if (_topBarOverride) {
|
||||
_topBarOverride->moveToLeft(0, overrideTop);
|
||||
}
|
||||
if (!_topBarOverrideAnimation.animating()) {
|
||||
if (_topBarOverrideShown) {
|
||||
_topBar->hide();
|
||||
} else {
|
||||
_topBarOverride = nullptr;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void WrapWidget::createTopBarOverride(SelectedItems &&items) {
|
||||
_topBarOverride.create(
|
||||
this,
|
||||
TopBarStyle(wrap()),
|
||||
std::move(items));
|
||||
|
||||
// This was done for tabs support.
|
||||
//
|
||||
//if (_topTabs) {
|
||||
// _topTabs->hide();
|
||||
//}
|
||||
|
||||
if (_topBar) {
|
||||
_topBar->hide();
|
||||
}
|
||||
_topBarOverride->cancelRequests()
|
||||
| rpl::start_with_next([this](auto) {
|
||||
_content->cancelSelection();
|
||||
}, _topBarOverride->lifetime());
|
||||
_topBarOverride->resizeToWidth(width());
|
||||
_topBarOverride->show();
|
||||
}
|
||||
|
||||
bool WrapWidget::requireTopBarSearch() const {
|
||||
if (!_controller->searchFieldController()) {
|
||||
return false;
|
||||
|
@ -832,10 +762,6 @@ void WrapWidget::showNewContent(
|
|||
showNewContent(memento);
|
||||
}
|
||||
if (animationParams) {
|
||||
refreshTopBarOverride(SelectedItems(Section::MediaType::kCount));
|
||||
_topBarOverrideAnimation.finish();
|
||||
topBarOverrideStep();
|
||||
|
||||
showAnimated(
|
||||
saveToStack
|
||||
? SlideDirection::FromRight
|
||||
|
@ -876,9 +802,6 @@ void WrapWidget::resizeEvent(QResizeEvent *e) {
|
|||
if (_topBar) {
|
||||
_topBar->resizeToWidth(width());
|
||||
}
|
||||
if (_topBarOverride) {
|
||||
_topBarOverride->resizeToWidth(width());
|
||||
}
|
||||
updateContentGeometry();
|
||||
}
|
||||
|
||||
|
|
|
@ -52,7 +52,6 @@ class MoveMemento;
|
|||
class ContentMemento;
|
||||
class ContentWidget;
|
||||
class TopBar;
|
||||
class TopBarOverride;
|
||||
|
||||
enum class Wrap {
|
||||
Layer,
|
||||
|
@ -190,11 +189,6 @@ private:
|
|||
//void convertProfileFromStackToTab();
|
||||
|
||||
rpl::producer<SelectedItems> selectedListValue() const;
|
||||
void refreshTopBarOverride();
|
||||
void refreshTopBarOverride(SelectedItems &&items);
|
||||
void createTopBarOverride(SelectedItems &&items);
|
||||
void toggleTopBarOverride(bool shown);
|
||||
void topBarOverrideStep();
|
||||
bool requireTopBarSearch() const;
|
||||
|
||||
void addProfileMenuButton();
|
||||
|
@ -209,7 +203,6 @@ private:
|
|||
//object_ptr<Ui::SettingsSlider> _topTabs = { nullptr };
|
||||
object_ptr<TopBar> _topBar = { nullptr };
|
||||
object_ptr<Ui::RpWidget> _topBarSurrogate = { nullptr };
|
||||
object_ptr<TopBarOverride> _topBarOverride = { nullptr };
|
||||
Animation _topBarOverrideAnimation;
|
||||
bool _topBarOverrideShown = false;
|
||||
object_ptr<Ui::FadeShadow> _topShadow;
|
||||
|
|
|
@ -794,6 +794,10 @@ void ListWidget::refreshViewer() {
|
|||
_idsLimit)
|
||||
| rpl::start_with_next([=](
|
||||
SparseIdsMergedSlice &&slice) {
|
||||
if (!slice.fullCount()) {
|
||||
// Don't display anything while full count is unknown.
|
||||
return;
|
||||
}
|
||||
_slice = std::move(slice);
|
||||
if (auto nearest = _slice.nearest(idForViewer)) {
|
||||
_universalAroundId = GetUniversalId(*nearest);
|
||||
|
@ -906,9 +910,11 @@ void ListWidget::refreshRows() {
|
|||
_sections.push_back(std::move(section));
|
||||
}
|
||||
|
||||
if (_layouts.size() > kMediaCountForSearch) {
|
||||
if (auto count = _slice.fullCount()) {
|
||||
if (*count > kMediaCountForSearch) {
|
||||
_controller->setSearchEnabledByContent(true);
|
||||
}
|
||||
}
|
||||
|
||||
clearStaleLayouts();
|
||||
|
||||
|
|