mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-19 07:37:11 +02:00
Added check views to selection mode of messages.
This commit is contained in:
parent
9064f3ba4b
commit
7b4bd5696b
12 changed files with 242 additions and 39 deletions
|
@ -662,8 +662,8 @@ bool InnerWidget::elementUnderCursor(
|
|||
return (Element::Hovered() == view);
|
||||
}
|
||||
|
||||
bool InnerWidget::elementInSelectionMode() {
|
||||
return false;
|
||||
HistoryView::SelectionModeResult InnerWidget::elementInSelectionMode() {
|
||||
return {};
|
||||
}
|
||||
|
||||
bool InnerWidget::elementIntersectsRange(
|
||||
|
|
|
@ -94,7 +94,7 @@ public:
|
|||
HistoryView::Context elementContext() override;
|
||||
bool elementUnderCursor(
|
||||
not_null<const HistoryView::Element*> view) override;
|
||||
bool elementInSelectionMode() override;
|
||||
HistoryView::SelectionModeResult elementInSelectionMode() override;
|
||||
bool elementIntersectsRange(
|
||||
not_null<const HistoryView::Element*> view,
|
||||
int from,
|
||||
|
|
|
@ -43,8 +43,9 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "ui/boxes/report_box_graphics.h"
|
||||
#include "ui/layers/generic_box.h"
|
||||
#include "ui/controls/delete_message_context_action.h"
|
||||
#include "ui/painter.h"
|
||||
#include "ui/inactive_press.h"
|
||||
#include "ui/painter.h"
|
||||
#include "ui/rect.h"
|
||||
#include "ui/ui_utility.h"
|
||||
#include "window/window_session_controller.h"
|
||||
#include "window/window_controller.h"
|
||||
|
@ -210,8 +211,10 @@ public:
|
|||
not_null<const Element*> view) override {
|
||||
return (Element::Moused() == view);
|
||||
}
|
||||
bool elementInSelectionMode() override {
|
||||
return _widget ? _widget->inSelectionMode() : false;
|
||||
HistoryView::SelectionModeResult elementInSelectionMode() override {
|
||||
return _widget
|
||||
? _widget->inSelectionMode()
|
||||
: HistoryView::SelectionModeResult();
|
||||
}
|
||||
bool elementIntersectsRange(
|
||||
not_null<const Element*> view,
|
||||
|
@ -599,7 +602,7 @@ void HistoryInner::setupSwipeReply() {
|
|||
}
|
||||
}, [=, show = _controller->uiShow()](int cursorTop) {
|
||||
auto result = HistoryView::SwipeHandlerFinishData();
|
||||
if (inSelectionMode()) {
|
||||
if (inSelectionMode().inSelectionMode) {
|
||||
return result;
|
||||
}
|
||||
enumerateItems<EnumItemsDirection::BottomToTop>([&](
|
||||
|
@ -1369,6 +1372,18 @@ bool HistoryInner::eventHook(QEvent *e) {
|
|||
return RpWidget::eventHook(e);
|
||||
}
|
||||
|
||||
int HistoryInner::SelectionViewOffset(
|
||||
not_null<const HistoryInner*> inner,
|
||||
not_null<const Element*> view) {
|
||||
if (inner->_lastInSelectionMode) {
|
||||
const auto translation
|
||||
= Element::AdditionalSpaceForSelectionCheckbox(view);
|
||||
const auto progress = inner->_inSelectionModeAnimation.value(1.);
|
||||
return translation * progress;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
HistoryInner::VideoUserpic *HistoryInner::validateVideoUserpic(
|
||||
not_null<PeerData*> peer) {
|
||||
if (!peer->isPremium()
|
||||
|
@ -1705,7 +1720,7 @@ void HistoryInner::mouseActionStart(const QPoint &screenPos, Qt::MouseButton but
|
|||
&& (!Element::Hovered()
|
||||
|| !Element::Hovered()->allowTextSelectionByHandler(pressed))) {
|
||||
_mouseAction = MouseAction::PrepareDrag;
|
||||
} else if (inSelectionMode()) {
|
||||
} else if (inSelectionMode().inSelectionMode) {
|
||||
if (_dragStateItem
|
||||
&& _selected.find(_dragStateItem) != _selected.cend()
|
||||
&& Element::Hovered()) {
|
||||
|
@ -1993,7 +2008,7 @@ void HistoryInner::mouseActionFinish(
|
|||
// toggle selection instead of activating the pressed link
|
||||
if (_mouseAction == MouseAction::PrepareDrag
|
||||
&& !_pressWasInactive
|
||||
&& inSelectionMode()
|
||||
&& inSelectionMode().inSelectionMode
|
||||
&& button != Qt::RightButton) {
|
||||
if (const auto view = viewByItem(_mouseActionItem)) {
|
||||
if (view->toggleSelectionByHandlerClick(activated)) {
|
||||
|
@ -2026,7 +2041,7 @@ void HistoryInner::mouseActionFinish(
|
|||
}
|
||||
if ((_mouseAction == MouseAction::PrepareSelect)
|
||||
&& !_pressWasInactive
|
||||
&& inSelectionMode()) {
|
||||
&& inSelectionMode().inSelectionMode) {
|
||||
changeSelectionAsGroup(
|
||||
&_selected,
|
||||
_mouseActionItem,
|
||||
|
@ -2043,7 +2058,7 @@ void HistoryInner::mouseActionFinish(
|
|||
} else if ((i == _selected.cend())
|
||||
&& !_dragStateItem->isService()
|
||||
&& _dragStateItem->isRegular()
|
||||
&& inSelectionMode()) {
|
||||
&& inSelectionMode().inSelectionMode) {
|
||||
if (_selected.size() < MaxSelectedItems) {
|
||||
_selected.emplace(_dragStateItem, FullSelection);
|
||||
repaintItem(_mouseActionItem);
|
||||
|
@ -2127,7 +2142,7 @@ void HistoryInner::mouseDoubleClickEvent(QMouseEvent *e) {
|
|||
&& !ClickHandler::getPressed()
|
||||
&& (_mouseCursorState == CursorState::None
|
||||
|| _mouseCursorState == CursorState::Date)
|
||||
&& !inSelectionMode()
|
||||
&& !inSelectionMode().inSelectionMode
|
||||
&& !_emptyPainter
|
||||
&& e->button() == Qt::LeftButton) {
|
||||
if (const auto view = Element::Moused()) {
|
||||
|
@ -3638,17 +3653,46 @@ bool HistoryInner::canDeleteSelected() const {
|
|||
&& (selectedState.count == selectedState.canDeleteCount);
|
||||
}
|
||||
|
||||
bool HistoryInner::inSelectionMode() const {
|
||||
if (hasSelectedItems()) {
|
||||
return true;
|
||||
} else if (_mouseAction == MouseAction::Selecting
|
||||
&& _dragSelFrom
|
||||
&& _dragSelTo) {
|
||||
return true;
|
||||
} else if (_chooseForReportReason.has_value()) {
|
||||
return true;
|
||||
HistoryView::SelectionModeResult HistoryInner::inSelectionMode() const {
|
||||
const auto inSelectionMode = [&] {
|
||||
if (hasSelectedItems()) {
|
||||
return true;
|
||||
} else if (_mouseAction == MouseAction::Selecting
|
||||
&& _dragSelFrom
|
||||
&& _dragSelTo) {
|
||||
return true;
|
||||
} else if (_chooseForReportReason.has_value()) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}();
|
||||
const auto now = inSelectionMode;
|
||||
if (_lastInSelectionMode != now) {
|
||||
_lastInSelectionMode = now;
|
||||
if (_inSelectionModeAnimation.animating()) {
|
||||
const auto progress = !now
|
||||
? _inSelectionModeAnimation.value(0.)
|
||||
: 1. - _inSelectionModeAnimation.value(0.);
|
||||
_inSelectionModeAnimation.change(
|
||||
now ? 1. : 0.,
|
||||
st::universalDuration * (1. - progress));
|
||||
} else {
|
||||
_inSelectionModeAnimation.stop();
|
||||
_inSelectionModeAnimation.start(
|
||||
[this] {
|
||||
const_cast<HistoryInner*>(this)->update(
|
||||
QRect(
|
||||
0,
|
||||
_visibleAreaTop,
|
||||
width(),
|
||||
_visibleAreaBottom - _visibleAreaTop));
|
||||
},
|
||||
now ? 0. : 1.,
|
||||
now ? 1. : 0.,
|
||||
st::universalDuration);
|
||||
}
|
||||
}
|
||||
return false;
|
||||
return { now, _inSelectionModeAnimation.value(now ? 1. : 0.) };
|
||||
}
|
||||
|
||||
bool HistoryInner::elementIntersectsRange(
|
||||
|
@ -3835,7 +3879,7 @@ auto HistoryInner::reactionButtonParameters(
|
|||
|| !view->data()->canReact()
|
||||
|| _mouseAction == MouseAction::Dragging
|
||||
|| _mouseAction == MouseAction::Selecting
|
||||
|| inSelectionMode()) {
|
||||
|| inSelectionMode().inSelectionMode) {
|
||||
return {};
|
||||
}
|
||||
auto result = view->reactionButtonParameters(
|
||||
|
@ -3856,7 +3900,7 @@ void HistoryInner::mouseActionUpdate() {
|
|||
auto mousePos = mapFromGlobal(_mousePosition);
|
||||
auto point = _widget->clampMousePosition(mousePos);
|
||||
|
||||
QPoint m;
|
||||
auto m = QPoint();
|
||||
|
||||
adjustCurrent(point.y());
|
||||
const auto reactionState = _reactionsManager->buttonTextState(point);
|
||||
|
@ -3873,6 +3917,10 @@ void HistoryInner::mouseActionUpdate() {
|
|||
? _curHistory->blocks[_curBlock]->messages[_curItem].get()
|
||||
: nullptr;
|
||||
const auto item = view ? view->data().get() : nullptr;
|
||||
const auto selectionViewOffset = view
|
||||
? QPoint(SelectionViewOffset(this, view), 0)
|
||||
: QPoint(0, 0);
|
||||
point -= selectionViewOffset;
|
||||
if (view) {
|
||||
const auto changed = (Element::Moused() != view);
|
||||
if (changed) {
|
||||
|
@ -3920,7 +3968,7 @@ void HistoryInner::mouseActionUpdate() {
|
|||
dragState = reactionState;
|
||||
lnkhost = reactionView;
|
||||
} else if (item) {
|
||||
if (item != _mouseActionItem || (m - _dragStartPosition).manhattanLength() >= QApplication::startDragDistance()) {
|
||||
if (item != _mouseActionItem || ((m + selectionViewOffset) - _dragStartPosition).manhattanLength() >= QApplication::startDragDistance()) {
|
||||
if (_mouseAction == MouseAction::PrepareDrag) {
|
||||
_mouseAction = MouseAction::Dragging;
|
||||
InvokeQueued(this, [=] { performDrag(); });
|
||||
|
|
|
@ -30,6 +30,7 @@ namespace HistoryView {
|
|||
class ElementDelegate;
|
||||
class EmojiInteractions;
|
||||
struct TextState;
|
||||
struct SelectionModeResult;
|
||||
struct StateRequest;
|
||||
enum class CursorState : char;
|
||||
enum class PointState : char;
|
||||
|
@ -135,7 +136,7 @@ public:
|
|||
void clearSelected(bool onlyTextSelection = false);
|
||||
[[nodiscard]] MessageIdsList getSelectedItems() const;
|
||||
[[nodiscard]] bool hasSelectedItems() const;
|
||||
[[nodiscard]] bool inSelectionMode() const;
|
||||
[[nodiscard]] HistoryView::SelectionModeResult inSelectionMode() const;
|
||||
[[nodiscard]] bool elementIntersectsRange(
|
||||
not_null<const Element*> view,
|
||||
int from,
|
||||
|
@ -243,6 +244,10 @@ private:
|
|||
void onTouchSelect();
|
||||
void onTouchScrollTimer();
|
||||
|
||||
[[nodiscard]] static int SelectionViewOffset(
|
||||
not_null<const HistoryInner*> inner,
|
||||
not_null<const Element*> view);
|
||||
|
||||
using ChosenReaction = HistoryView::Reactions::ChosenReaction;
|
||||
using VideoUserpic = Dialogs::Ui::VideoUserpic;
|
||||
using SelectedItems = std::map<HistoryItem*, TextSelection, std::less<>>;
|
||||
|
@ -508,6 +513,9 @@ private:
|
|||
bool _dragSelecting = false;
|
||||
bool _wasSelectedText = false; // was some text selected in current drag action
|
||||
|
||||
mutable bool _lastInSelectionMode = false;
|
||||
mutable Ui::Animations::Simple _inSelectionModeAnimation;
|
||||
|
||||
// scroll by touch support (at least Windows Surface tablets)
|
||||
bool _touchScroll = false;
|
||||
bool _touchSelect = false;
|
||||
|
|
|
@ -37,6 +37,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "ui/text/text_utilities.h"
|
||||
#include "ui/item_text_options.h"
|
||||
#include "ui/painter.h"
|
||||
#include "ui/rect.h"
|
||||
#include "data/components/sponsored_messages.h"
|
||||
#include "data/data_session.h"
|
||||
#include "data/data_forum.h"
|
||||
|
@ -110,8 +111,8 @@ bool DefaultElementDelegate::elementUnderCursor(
|
|||
return false;
|
||||
}
|
||||
|
||||
bool DefaultElementDelegate::elementInSelectionMode() {
|
||||
return false;
|
||||
SelectionModeResult DefaultElementDelegate::elementInSelectionMode() {
|
||||
return {};
|
||||
}
|
||||
|
||||
bool DefaultElementDelegate::elementIntersectsRange(
|
||||
|
@ -740,6 +741,25 @@ not_null<PurchasedTag*> Element::enforcePurchasedTag() {
|
|||
return Get<PurchasedTag>();
|
||||
}
|
||||
|
||||
int Element::AdditionalSpaceForSelectionCheckbox(
|
||||
not_null<const Element*> view,
|
||||
QRect countedGeometry) {
|
||||
if (!view->hasOutLayout() || view->delegate()->elementIsChatWide()) {
|
||||
return 0;
|
||||
}
|
||||
if (countedGeometry.isEmpty()) {
|
||||
countedGeometry = view->innerGeometry();
|
||||
}
|
||||
const auto diff = view->width()
|
||||
- (countedGeometry.x() + countedGeometry.width())
|
||||
- st::msgPadding.right()
|
||||
- st::msgSelectionOffset
|
||||
- view->rightActionSize().value_or(QSize()).width();
|
||||
return (diff < 0)
|
||||
? -(std::min(st::msgSelectionOffset, -diff))
|
||||
: 0;
|
||||
}
|
||||
|
||||
void Element::refreshMedia(Element *replacing) {
|
||||
if (_flags & Flag::MediaOverriden) {
|
||||
return;
|
||||
|
|
|
@ -70,12 +70,17 @@ enum class OnlyEmojiAndSpaces : char {
|
|||
No,
|
||||
};
|
||||
|
||||
struct SelectionModeResult {
|
||||
bool inSelectionMode = false;
|
||||
float64 progress = 0.0;
|
||||
};
|
||||
|
||||
class Element;
|
||||
class ElementDelegate {
|
||||
public:
|
||||
virtual Context elementContext() = 0;
|
||||
virtual bool elementUnderCursor(not_null<const Element*> view) = 0;
|
||||
virtual bool elementInSelectionMode() = 0;
|
||||
virtual SelectionModeResult elementInSelectionMode() = 0;
|
||||
virtual bool elementIntersectsRange(
|
||||
not_null<const Element*> view,
|
||||
int from,
|
||||
|
@ -131,7 +136,7 @@ public:
|
|||
class DefaultElementDelegate : public ElementDelegate {
|
||||
public:
|
||||
bool elementUnderCursor(not_null<const Element*> view) override;
|
||||
bool elementInSelectionMode() override;
|
||||
SelectionModeResult elementInSelectionMode() override;
|
||||
bool elementIntersectsRange(
|
||||
not_null<const Element*> view,
|
||||
int from,
|
||||
|
@ -571,6 +576,10 @@ public:
|
|||
|
||||
[[nodiscard]] not_null<PurchasedTag*> enforcePurchasedTag();
|
||||
|
||||
[[nodiscard]] static int AdditionalSpaceForSelectionCheckbox(
|
||||
not_null<const Element*> view,
|
||||
QRect countedGeometry = QRect());
|
||||
|
||||
virtual bool consumeHorizontalScroll(QPoint position, int delta) {
|
||||
return false;
|
||||
}
|
||||
|
|
|
@ -1229,8 +1229,34 @@ bool ListWidget::hasSelectedItems() const {
|
|||
return !_selected.empty();
|
||||
}
|
||||
|
||||
bool ListWidget::inSelectionMode() const {
|
||||
return hasSelectedItems() || !_dragSelected.empty();
|
||||
SelectionModeResult ListWidget::inSelectionMode() const {
|
||||
const auto now = hasSelectedItems() || !_dragSelected.empty();
|
||||
if (_lastInSelectionMode != now) {
|
||||
_lastInSelectionMode = now;
|
||||
if (_inSelectionModeAnimation.animating()) {
|
||||
const auto progress = !now
|
||||
? _inSelectionModeAnimation.value(0.)
|
||||
: 1. - _inSelectionModeAnimation.value(0.);
|
||||
_inSelectionModeAnimation.change(
|
||||
now ? 1. : 0.,
|
||||
st::universalDuration * (1. - progress));
|
||||
} else {
|
||||
_inSelectionModeAnimation.stop();
|
||||
_inSelectionModeAnimation.start(
|
||||
[this] {
|
||||
const_cast<ListWidget*>(this)->update(
|
||||
QRect(
|
||||
0,
|
||||
_visibleTop,
|
||||
width(),
|
||||
_visibleBottom - _visibleTop));
|
||||
},
|
||||
now ? 0. : 1.,
|
||||
now ? 1. : 0.,
|
||||
st::universalDuration);
|
||||
}
|
||||
}
|
||||
return { now, _inSelectionModeAnimation.value(now ? 1. : 0.) };
|
||||
}
|
||||
|
||||
bool ListWidget::overSelectedItems() const {
|
||||
|
@ -1751,7 +1777,7 @@ bool ListWidget::elementUnderCursor(
|
|||
return (_overElement == view);
|
||||
}
|
||||
|
||||
bool ListWidget::elementInSelectionMode() {
|
||||
SelectionModeResult ListWidget::elementInSelectionMode() {
|
||||
return inSelectionMode();
|
||||
}
|
||||
|
||||
|
@ -3410,7 +3436,7 @@ Reactions::ButtonParameters ListWidget::reactionButtonParameters(
|
|||
if (top < 0
|
||||
|| !view->data()->canReact()
|
||||
|| _mouseAction == MouseAction::Dragging
|
||||
|| inSelectionMode()) {
|
||||
|| inSelectionMode().inSelectionMode) {
|
||||
return {};
|
||||
}
|
||||
auto result = view->reactionButtonParameters(
|
||||
|
@ -3536,6 +3562,19 @@ ClickHandlerContext ListWidget::prepareClickHandlerContext(FullMsgId id) {
|
|||
};
|
||||
}
|
||||
|
||||
int ListWidget::SelectionViewOffset(
|
||||
not_null<const ListWidget*> inner,
|
||||
not_null<const Element*> view) {
|
||||
if (inner->_lastInSelectionMode) {
|
||||
const auto translation
|
||||
= Element::AdditionalSpaceForSelectionCheckbox(view);
|
||||
const auto progress = inner->_inSelectionModeAnimation.value(1.);
|
||||
return translation * progress;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
void ListWidget::mouseActionUpdate() {
|
||||
auto mousePosition = mapFromGlobal(_mousePosition);
|
||||
auto point = QPoint(
|
||||
|
@ -3551,6 +3590,9 @@ void ListWidget::mouseActionUpdate() {
|
|||
? reactionView
|
||||
: strictFindItemByY(point.y());
|
||||
const auto item = view ? view->data().get() : nullptr;
|
||||
if (view) {
|
||||
point -= QPoint(SelectionViewOffset(this, view), 0);
|
||||
}
|
||||
const auto itemPoint = mapPointToItem(point, view);
|
||||
_overState = MouseState(
|
||||
item ? item->fullId() : FullMsgId(),
|
||||
|
|
|
@ -389,7 +389,7 @@ public:
|
|||
// ElementDelegate interface.
|
||||
Context elementContext() override;
|
||||
bool elementUnderCursor(not_null<const Element*> view) override;
|
||||
bool elementInSelectionMode() override;
|
||||
SelectionModeResult elementInSelectionMode() override;
|
||||
bool elementIntersectsRange(
|
||||
not_null<const Element*> view,
|
||||
int from,
|
||||
|
@ -459,6 +459,10 @@ protected:
|
|||
int resizeGetHeight(int newWidth) override;
|
||||
|
||||
private:
|
||||
[[nodiscard]] static int SelectionViewOffset(
|
||||
not_null<const ListWidget*> inner,
|
||||
not_null<const Element*> view);
|
||||
|
||||
using ScrollTopState = ListMemento::ScrollTopState;
|
||||
using PointState = HistoryView::PointState;
|
||||
using CursorState = HistoryView::CursorState;
|
||||
|
@ -618,7 +622,7 @@ private:
|
|||
const SelectedMap::const_iterator &i);
|
||||
bool hasSelectedText() const;
|
||||
bool hasSelectedItems() const;
|
||||
bool inSelectionMode() const;
|
||||
SelectionModeResult inSelectionMode() const;
|
||||
bool overSelectedItems() const;
|
||||
void clearTextSelection();
|
||||
void clearSelected();
|
||||
|
@ -830,6 +834,9 @@ private:
|
|||
|
||||
ElementHighlighter _highlighter;
|
||||
|
||||
mutable bool _lastInSelectionMode = false;
|
||||
mutable Ui::Animations::Simple _inSelectionModeAnimation;
|
||||
|
||||
// scroll by touch support (at least Windows Surface tablets)
|
||||
bool _touchScroll = false;
|
||||
bool _touchSelect = false;
|
||||
|
|
|
@ -1100,6 +1100,14 @@ void Message::draw(Painter &p, const PaintContext &context) const {
|
|||
if (hasGesture) {
|
||||
p.translate(context.gestureHorizontal.translation, 0);
|
||||
}
|
||||
const auto selectionModeResult = delegate()->elementInSelectionMode();
|
||||
const auto selectionTranslation = (selectionModeResult.progress > 0)
|
||||
? (selectionModeResult.progress
|
||||
* AdditionalSpaceForSelectionCheckbox(this, g))
|
||||
: 0;
|
||||
if (selectionTranslation) {
|
||||
p.translate(selectionTranslation, 0);
|
||||
}
|
||||
|
||||
if (item->hasUnrequestedFactcheck()) {
|
||||
item->history()->session().factchecks().requestFor(item);
|
||||
|
@ -1449,7 +1457,14 @@ void Message::draw(Painter &p, const PaintContext &context) const {
|
|||
const auto fastShareTop = data()->isSponsored()
|
||||
? g.top() + fastShareSkip
|
||||
: g.top() + g.height() - fastShareSkip - size->height();
|
||||
const auto o = p.opacity();
|
||||
if (selectionModeResult.progress > 0) {
|
||||
p.setOpacity(1. - selectionModeResult.progress);
|
||||
}
|
||||
drawRightAction(p, context, fastShareLeft, fastShareTop, width());
|
||||
if (selectionModeResult.progress > 0) {
|
||||
p.setOpacity(o);
|
||||
}
|
||||
}
|
||||
|
||||
if (media) {
|
||||
|
@ -1570,6 +1585,48 @@ void Message::draw(Painter &p, const PaintContext &context) const {
|
|||
}
|
||||
p.restore();
|
||||
}
|
||||
if (selectionTranslation) {
|
||||
p.translate(-selectionTranslation, 0);
|
||||
}
|
||||
if (selectionModeResult.progress) {
|
||||
const auto progress = selectionModeResult.progress;
|
||||
if (progress <= 1.) {
|
||||
if (context.selected()) {
|
||||
if (!_selectionRoundCheckbox) {
|
||||
_selectionRoundCheckbox
|
||||
= std::make_unique<Ui::RoundCheckbox>(
|
||||
st::msgSelectionCheck,
|
||||
[this] { repaint(); });
|
||||
}
|
||||
}
|
||||
if (_selectionRoundCheckbox) {
|
||||
_selectionRoundCheckbox->setChecked(
|
||||
context.selected(),
|
||||
anim::type::normal);
|
||||
}
|
||||
const auto o = ScopedPainterOpacity(p, progress);
|
||||
const auto &st = st::msgSelectionCheck;
|
||||
const auto pos = QPoint(
|
||||
(width()
|
||||
- (st::msgSelectionOffset * progress - st.size) / 2
|
||||
- st::msgPadding.right() / 2
|
||||
- st.size),
|
||||
g.y() + (g.height() - st.size) / 2);
|
||||
{
|
||||
p.setPen(QPen(st.border, st.width));
|
||||
p.setBrush(context.st->msgServiceBg());
|
||||
auto hq = PainterHighQualityEnabler(p);
|
||||
p.drawEllipse(QRect(pos, Size(st.size)));
|
||||
}
|
||||
if (_selectionRoundCheckbox) {
|
||||
_selectionRoundCheckbox->paint(p, pos.x(), pos.y(), width());
|
||||
}
|
||||
} else {
|
||||
_selectionRoundCheckbox = nullptr;
|
||||
}
|
||||
} else {
|
||||
_selectionRoundCheckbox = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
void Message::paintCommentsButton(
|
||||
|
@ -2959,7 +3016,9 @@ bool Message::getStateText(
|
|||
void Message::updatePressed(QPoint point) {
|
||||
const auto item = data();
|
||||
const auto media = this->media();
|
||||
if (!media) return;
|
||||
if (!media) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto g = countGeometry();
|
||||
auto keyboard = item->inlineReplyKeyboard();
|
||||
|
@ -3792,7 +3851,7 @@ bool Message::displayFastReply() const {
|
|||
return hasFastReply()
|
||||
&& data()->isRegular()
|
||||
&& canSendAnything()
|
||||
&& !delegate()->elementInSelectionMode();
|
||||
&& !delegate()->elementInSelectionMode().inSelectionMode;
|
||||
}
|
||||
|
||||
bool Message::displayRightActionComments() const {
|
||||
|
@ -3956,6 +4015,9 @@ void Message::drawRightAction(
|
|||
|
||||
ClickHandlerPtr Message::rightActionLink(
|
||||
std::optional<QPoint> pressPoint) const {
|
||||
if (delegate()->elementInSelectionMode().progress > 0) {
|
||||
return nullptr;
|
||||
}
|
||||
ensureRightAction();
|
||||
if (!_rightAction->link) {
|
||||
_rightAction->link = prepareRightActionLink();
|
||||
|
|
|
@ -22,6 +22,7 @@ struct ReactionId;
|
|||
|
||||
namespace Ui {
|
||||
struct BubbleRounding;
|
||||
class RoundCheckbox;
|
||||
} // namespace Ui
|
||||
|
||||
namespace HistoryView {
|
||||
|
@ -313,6 +314,7 @@ private:
|
|||
|
||||
mutable Ui::Text::String _fromName;
|
||||
mutable std::unique_ptr<FromNameStatus> _fromNameStatus;
|
||||
mutable std::unique_ptr<Ui::RoundCheckbox> _selectionRoundCheckbox;
|
||||
Ui::Text::String _rightBadge;
|
||||
mutable int _fromNameVersion = 0;
|
||||
uint32 _bubbleWidthLimit : 28 = 0;
|
||||
|
|
|
@ -898,7 +898,7 @@ void RepliesWidget::setupSwipeReply() {
|
|||
}
|
||||
}, [=, show = controller()->uiShow()](int cursorTop) {
|
||||
auto result = HistoryView::SwipeHandlerFinishData();
|
||||
if (_inner->elementInSelectionMode()) {
|
||||
if (_inner->elementInSelectionMode().inSelectionMode) {
|
||||
return result;
|
||||
}
|
||||
const auto view = _inner->lookupItemByY(cursorTop);
|
||||
|
|
|
@ -26,6 +26,7 @@ msgPadding: margins(11px, 8px, 11px, 8px);
|
|||
msgMargin: margins(16px, 6px, 56px, 2px);
|
||||
msgMarginTopAttached: 0px;
|
||||
msgShadow: 2px;
|
||||
msgSelectionOffset: 30px;
|
||||
|
||||
historyReplyTop: 2px;
|
||||
historyReplyBottom: 2px;
|
||||
|
@ -1149,3 +1150,7 @@ factcheckField: InputField(defaultInputField) {
|
|||
style: defaultTextStyle;
|
||||
}
|
||||
purchasedTagPadding: margins(3px, 2px, 6px, 2px);
|
||||
|
||||
msgSelectionCheck: RoundCheckbox(defaultPeerListCheck) {
|
||||
bgActive: boxTextFgGood;
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue