mirror of https://github.com/procxx/kepka.git
Cloud draft handling improved. Fixed Edit while already editing a msg.
This commit is contained in:
parent
19cacd0efb
commit
a428534345
|
@ -21,6 +21,7 @@ Copyright (c) 2014-2016 John Preston, https://desktop.telegram.org
|
|||
#include "stdafx.h"
|
||||
#include "apiwrap.h"
|
||||
|
||||
#include "data/data_drafts.h"
|
||||
#include "observer_peer.h"
|
||||
#include "lang.h"
|
||||
#include "application.h"
|
||||
|
@ -851,7 +852,7 @@ void ApiWrap::saveCloudDraftDone(History *history, const MTPBool &result, mtpReq
|
|||
if (auto cloudDraft = history->cloudDraft()) {
|
||||
if (cloudDraft->saveRequestId == requestId) {
|
||||
cloudDraft->saveRequestId = 0;
|
||||
history->updateChatListEntry();
|
||||
history->draftSavedToCloud();
|
||||
}
|
||||
}
|
||||
auto i = _draftsSaveRequestIds.find(history);
|
||||
|
|
|
@ -286,10 +286,10 @@ namespace {
|
|||
QString onlineText(UserData *user, TimeId now, bool precise) {
|
||||
if (isNotificationsUser(user->id)) {
|
||||
return lang(lng_status_service_notifications);
|
||||
} else if (isServiceUser(user->id)) {
|
||||
return lang(lng_status_support);
|
||||
} else if (user->botInfo) {
|
||||
return lang(lng_status_bot);
|
||||
} else if (isServiceUser(user->id)) {
|
||||
return lang(lng_status_support);
|
||||
}
|
||||
return onlineText(user->onlineTill, now, precise);
|
||||
}
|
||||
|
|
|
@ -23,6 +23,7 @@ Copyright (c) 2014-2016 John Preston, https://desktop.telegram.org
|
|||
|
||||
#include "historywidget.h"
|
||||
#include "mainwidget.h"
|
||||
#include "localstorage.h"
|
||||
|
||||
namespace Data {
|
||||
namespace {
|
||||
|
@ -35,7 +36,7 @@ void applyPeerCloudDraft(PeerId peerId, const MTPDdraftMessage &draft) {
|
|||
auto entities = draft.has_entities() ? entitiesFromMTP(draft.ventities.c_vector().v) : EntitiesInText();
|
||||
TextWithTags textWithTags = { textApplyEntities(text, entities), textTagsFromEntities(entities) };
|
||||
MsgId replyTo = draft.has_reply_to_msg_id() ? draft.vreply_to_msg_id.v : 0;
|
||||
auto cloudDraft = std_::make_unique<HistoryDraft>(textWithTags, replyTo, MessageCursor(QFIXED_MAX, QFIXED_MAX, QFIXED_MAX), draft.is_no_webpage());
|
||||
auto cloudDraft = std_::make_unique<Draft>(textWithTags, replyTo, MessageCursor(QFIXED_MAX, QFIXED_MAX, QFIXED_MAX), draft.is_no_webpage());
|
||||
cloudDraft->date = ::date(draft.vdate);
|
||||
|
||||
history->setCloudDraft(std_::move(cloudDraft));
|
||||
|
@ -48,4 +49,18 @@ void applyPeerCloudDraft(PeerId peerId, const MTPDdraftMessage &draft) {
|
|||
}
|
||||
}
|
||||
|
||||
void clearPeerCloudDraft(PeerId peerId) {
|
||||
auto history = App::history(peerId);
|
||||
|
||||
history->clearCloudDraft();
|
||||
history->clearLocalDraft();
|
||||
|
||||
history->updateChatListSortPosition();
|
||||
history->updateChatListEntry();
|
||||
|
||||
if (auto main = App::main()) {
|
||||
main->applyCloudDraft(history);
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace Data
|
||||
|
|
|
@ -23,5 +23,55 @@ Copyright (c) 2014-2016 John Preston, https://desktop.telegram.org
|
|||
namespace Data {
|
||||
|
||||
void applyPeerCloudDraft(PeerId peerId, const MTPDdraftMessage &draft);
|
||||
void clearPeerCloudDraft(PeerId peerId);
|
||||
|
||||
struct Draft {
|
||||
Draft() {
|
||||
}
|
||||
Draft(const TextWithTags &textWithTags, MsgId msgId, const MessageCursor &cursor, bool previewCancelled, mtpRequestId saveRequestId = 0)
|
||||
: textWithTags(textWithTags)
|
||||
, msgId(msgId)
|
||||
, cursor(cursor)
|
||||
, previewCancelled(previewCancelled)
|
||||
, saveRequestId(saveRequestId) {
|
||||
}
|
||||
Draft(const FlatTextarea &field, MsgId msgId, bool previewCancelled, mtpRequestId saveRequestId = 0)
|
||||
: textWithTags(field.getTextWithTags())
|
||||
, msgId(msgId)
|
||||
, cursor(field)
|
||||
, previewCancelled(previewCancelled) {
|
||||
}
|
||||
QDateTime date;
|
||||
TextWithTags textWithTags;
|
||||
MsgId msgId = 0; // replyToId for message draft, editMsgId for edit draft
|
||||
MessageCursor cursor;
|
||||
bool previewCancelled = false;
|
||||
mtpRequestId saveRequestId = 0;
|
||||
};
|
||||
|
||||
inline bool draftStringIsEmpty(const QString &text) {
|
||||
for_const (auto ch, text) {
|
||||
if (!ch.isSpace()) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
inline bool draftIsNull(Draft *draft) {
|
||||
return !draft || draftStringIsEmpty(draft->textWithTags.text);
|
||||
}
|
||||
|
||||
inline bool draftsAreEqual(Draft *a, Draft *b) {
|
||||
bool aIsNull = draftIsNull(a);
|
||||
bool bIsNull = draftIsNull(b);
|
||||
if (aIsNull) {
|
||||
return bIsNull;
|
||||
} else if (bIsNull) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return (a->textWithTags == b->textWithTags) && (a->msgId == b->msgId) && (a->previewCancelled == b->previewCancelled);
|
||||
}
|
||||
|
||||
} // namespace Data
|
||||
|
|
|
@ -22,6 +22,7 @@ Copyright (c) 2014-2016 John Preston, https://desktop.telegram.org
|
|||
#include "dialogs/dialogs_layout.h"
|
||||
|
||||
#include "data/data_abstract_structure.h"
|
||||
#include "data/data_drafts.h"
|
||||
#include "dialogs/dialogs_list.h"
|
||||
#include "styles/style_dialogs.h"
|
||||
#include "localstorage.h"
|
||||
|
@ -51,7 +52,7 @@ void paintRowDate(Painter &p, const QDateTime &date, QRect &rectForName, bool ac
|
|||
}
|
||||
|
||||
template <typename PaintItemCallback>
|
||||
void paintRow(Painter &p, History *history, HistoryItem *item, HistoryDraft *draft, int w, bool active, bool selected, bool onlyBackground, PaintItemCallback paintItemCallback) {
|
||||
void paintRow(Painter &p, History *history, HistoryItem *item, Data::Draft *draft, int w, bool active, bool selected, bool onlyBackground, PaintItemCallback paintItemCallback) {
|
||||
QRect fullRect(0, 0, w, st::dialogsRowHeight);
|
||||
p.fillRect(fullRect, active ? st::dialogsBgActive : (selected ? st::dialogsBgOver : st::dialogsBg));
|
||||
if (onlyBackground) return;
|
||||
|
|
|
@ -25,6 +25,7 @@ Copyright (c) 2014-2016 John Preston, https://desktop.telegram.org
|
|||
#include "dialogs/dialogs_indexed_list.h"
|
||||
#include "styles/style_dialogs.h"
|
||||
#include "history/history_service_layout.h"
|
||||
#include "data/data_drafts.h"
|
||||
#include "lang.h"
|
||||
#include "mainwidget.h"
|
||||
#include "application.h"
|
||||
|
@ -168,14 +169,31 @@ void History::setHasPendingResizedItems() {
|
|||
Global::RefHandleHistoryUpdate().call();
|
||||
}
|
||||
|
||||
void History::setLocalDraft(std_::unique_ptr<Data::Draft> &&draft) {
|
||||
_localDraft = std_::move(draft);
|
||||
}
|
||||
|
||||
void History::takeLocalDraft(History *from) {
|
||||
if (auto &draft = from->_localDraft) {
|
||||
if (!draft->textWithTags.text.isEmpty() && !_localDraft) {
|
||||
_localDraft = std_::move(draft);
|
||||
|
||||
// Edit and reply to drafts can't migrate.
|
||||
// Cloud drafts do not migrate automatically.
|
||||
_localDraft->msgId = 0;
|
||||
}
|
||||
from->clearLocalDraft();
|
||||
}
|
||||
}
|
||||
|
||||
void History::createLocalDraftFromCloud() {
|
||||
auto draft = cloudDraft();
|
||||
if (historyDraftIsNull(draft) || !draft->date.isValid()) return;
|
||||
if (Data::draftIsNull(draft) || !draft->date.isValid()) return;
|
||||
|
||||
auto existing = localDraft();
|
||||
if (historyDraftIsNull(existing) || !existing->date.isValid() || draft->date > existing->date) {
|
||||
if (Data::draftIsNull(existing) || !existing->date.isValid() || draft->date >= existing->date) {
|
||||
if (!existing) {
|
||||
setLocalDraft(std_::make_unique<HistoryDraft>(draft->textWithTags, draft->msgId, draft->cursor, draft->previewCancelled));
|
||||
setLocalDraft(std_::make_unique<Data::Draft>(draft->textWithTags, draft->msgId, draft->cursor, draft->previewCancelled));
|
||||
existing = localDraft();
|
||||
} else if (existing != draft) {
|
||||
existing->textWithTags = draft->textWithTags;
|
||||
|
@ -187,14 +205,19 @@ void History::createLocalDraftFromCloud() {
|
|||
}
|
||||
}
|
||||
|
||||
HistoryDraft *History::createCloudDraft(HistoryDraft *fromDraft) {
|
||||
if (historyDraftIsNull(fromDraft)) {
|
||||
setCloudDraft(std_::make_unique<HistoryDraft>(TextWithTags(), 0, MessageCursor(), false));
|
||||
void History::setCloudDraft(std_::unique_ptr<Data::Draft> &&draft) {
|
||||
_cloudDraft = std_::move(draft);
|
||||
cloudDraftTextCache.clear();
|
||||
}
|
||||
|
||||
Data::Draft *History::createCloudDraft(Data::Draft *fromDraft) {
|
||||
if (Data::draftIsNull(fromDraft)) {
|
||||
setCloudDraft(std_::make_unique<Data::Draft>(TextWithTags(), 0, MessageCursor(), false));
|
||||
cloudDraft()->date = QDateTime();
|
||||
} else {
|
||||
auto existing = cloudDraft();
|
||||
if (!existing) {
|
||||
setCloudDraft(std_::make_unique<HistoryDraft>(fromDraft->textWithTags, fromDraft->msgId, fromDraft->cursor, fromDraft->previewCancelled));
|
||||
setCloudDraft(std_::make_unique<Data::Draft>(fromDraft->textWithTags, fromDraft->msgId, fromDraft->cursor, fromDraft->previewCancelled));
|
||||
existing = cloudDraft();
|
||||
} else if (existing != fromDraft) {
|
||||
existing->textWithTags = fromDraft->textWithTags;
|
||||
|
@ -212,6 +235,14 @@ HistoryDraft *History::createCloudDraft(HistoryDraft *fromDraft) {
|
|||
return cloudDraft();
|
||||
}
|
||||
|
||||
void History::setEditDraft(std_::unique_ptr<Data::Draft> &&draft) {
|
||||
_editDraft = std_::move(draft);
|
||||
}
|
||||
|
||||
void History::clearLocalDraft() {
|
||||
_localDraft = nullptr;
|
||||
}
|
||||
|
||||
void History::clearCloudDraft() {
|
||||
if (_cloudDraft) {
|
||||
_cloudDraft = nullptr;
|
||||
|
@ -221,6 +252,15 @@ void History::clearCloudDraft() {
|
|||
}
|
||||
}
|
||||
|
||||
void History::clearEditDraft() {
|
||||
_editDraft = nullptr;
|
||||
}
|
||||
|
||||
void History::draftSavedToCloud() {
|
||||
updateChatListEntry();
|
||||
if (App::main()) App::main()->writeDrafts(this);
|
||||
}
|
||||
|
||||
bool History::updateTyping(uint64 ms, bool force) {
|
||||
bool changed = force;
|
||||
for (TypingUsers::iterator i = typing.begin(), e = typing.end(); i != e;) {
|
||||
|
|
|
@ -154,45 +154,10 @@ struct SendAction {
|
|||
};
|
||||
|
||||
using TextWithTags = FlatTextarea::TextWithTags;
|
||||
struct HistoryDraft {
|
||||
HistoryDraft() {
|
||||
}
|
||||
HistoryDraft(const TextWithTags &textWithTags, MsgId msgId, const MessageCursor &cursor, bool previewCancelled, mtpRequestId saveRequestId = 0)
|
||||
: textWithTags(textWithTags)
|
||||
, msgId(msgId)
|
||||
, cursor(cursor)
|
||||
, previewCancelled(previewCancelled)
|
||||
, saveRequestId(saveRequestId) {
|
||||
}
|
||||
HistoryDraft(const FlatTextarea &field, MsgId msgId, bool previewCancelled, mtpRequestId saveRequestId = 0)
|
||||
: textWithTags(field.getTextWithTags())
|
||||
, msgId(msgId)
|
||||
, cursor(field)
|
||||
, previewCancelled(previewCancelled) {
|
||||
}
|
||||
QDateTime date;
|
||||
TextWithTags textWithTags;
|
||||
MsgId msgId = 0; // replyToId for message draft, editMsgId for edit draft
|
||||
MessageCursor cursor;
|
||||
bool previewCancelled = false;
|
||||
mtpRequestId saveRequestId = 0;
|
||||
};
|
||||
|
||||
inline bool historyDraftIsNull(HistoryDraft *draft) {
|
||||
return (!draft || (!draft->msgId && draft->textWithTags.text.isEmpty()));
|
||||
}
|
||||
|
||||
inline bool historyDraftsAreEqual(HistoryDraft *a, HistoryDraft *b) {
|
||||
bool aIsNull = historyDraftIsNull(a);
|
||||
bool bIsNull = historyDraftIsNull(b);
|
||||
if (aIsNull) {
|
||||
return bIsNull;
|
||||
} else if (bIsNull) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return (a->textWithTags == b->textWithTags) && (a->msgId == b->msgId) && (a->previewCancelled == b->previewCancelled);
|
||||
}
|
||||
namespace Data {
|
||||
struct Draft;
|
||||
} // namespace Data
|
||||
|
||||
class HistoryMedia;
|
||||
class HistoryMessage;
|
||||
|
@ -373,47 +338,26 @@ public:
|
|||
typedef QList<HistoryItem*> NotifyQueue;
|
||||
NotifyQueue notifies;
|
||||
|
||||
HistoryDraft *localDraft() {
|
||||
Data::Draft *localDraft() {
|
||||
return _localDraft.get();
|
||||
}
|
||||
HistoryDraft *cloudDraft() {
|
||||
Data::Draft *cloudDraft() {
|
||||
return _cloudDraft.get();
|
||||
}
|
||||
HistoryDraft *editDraft() {
|
||||
Data::Draft *editDraft() {
|
||||
return _editDraft.get();
|
||||
}
|
||||
void setLocalDraft(std_::unique_ptr<HistoryDraft> &&draft) {
|
||||
_localDraft = std_::move(draft);
|
||||
}
|
||||
void takeLocalDraft(History *from) {
|
||||
if (auto &draft = from->_localDraft) {
|
||||
if (!draft->textWithTags.text.isEmpty() && !_localDraft) {
|
||||
_localDraft = std_::move(draft);
|
||||
|
||||
// Edit and reply to drafts can't migrate.
|
||||
// Cloud drafts do not migrate automatically.
|
||||
_localDraft->msgId = 0;
|
||||
}
|
||||
from->clearLocalDraft();
|
||||
}
|
||||
}
|
||||
void setLocalDraft(std_::unique_ptr<Data::Draft> &&draft);
|
||||
void takeLocalDraft(History *from);
|
||||
void createLocalDraftFromCloud();
|
||||
void setCloudDraft(std_::unique_ptr<HistoryDraft> &&draft) {
|
||||
_cloudDraft = std_::move(draft);
|
||||
cloudDraftTextCache.clear();
|
||||
}
|
||||
HistoryDraft *createCloudDraft(HistoryDraft *fromDraft);
|
||||
void setEditDraft(std_::unique_ptr<HistoryDraft> &&draft) {
|
||||
_editDraft = std_::move(draft);
|
||||
}
|
||||
void clearLocalDraft() {
|
||||
_localDraft = nullptr;
|
||||
}
|
||||
void setCloudDraft(std_::unique_ptr<Data::Draft> &&draft);
|
||||
Data::Draft *createCloudDraft(Data::Draft *fromDraft);
|
||||
void setEditDraft(std_::unique_ptr<Data::Draft> &&draft);
|
||||
void clearLocalDraft();
|
||||
void clearCloudDraft();
|
||||
void clearEditDraft() {
|
||||
_editDraft = nullptr;
|
||||
}
|
||||
HistoryDraft *draft() {
|
||||
void clearEditDraft();
|
||||
void draftSavedToCloud();
|
||||
Data::Draft *draft() {
|
||||
return _editDraft ? editDraft() : localDraft();
|
||||
}
|
||||
|
||||
|
@ -599,8 +543,8 @@ private:
|
|||
// Depending on isBuildingFrontBlock() gets front or back block.
|
||||
HistoryBlock *prepareBlockForAddingItem();
|
||||
|
||||
std_::unique_ptr<HistoryDraft> _localDraft, _cloudDraft;
|
||||
std_::unique_ptr<HistoryDraft> _editDraft;
|
||||
std_::unique_ptr<Data::Draft> _localDraft, _cloudDraft;
|
||||
std_::unique_ptr<Data::Draft> _editDraft;
|
||||
|
||||
};
|
||||
|
||||
|
|
|
@ -29,6 +29,7 @@ Copyright (c) 2014-2016 John Preston, https://desktop.telegram.org
|
|||
#include "ui/toast/toast.h"
|
||||
#include "ui/buttons/history_down_button.h"
|
||||
#include "inline_bots/inline_bot_result.h"
|
||||
#include "data/data_drafts.h"
|
||||
#include "lang.h"
|
||||
#include "application.h"
|
||||
#include "mainwidget.h"
|
||||
|
@ -99,8 +100,6 @@ HistoryInner::HistoryInner(HistoryWidget *historyWidget, ScrollArea *scroll, His
|
|||
, _history(history)
|
||||
, _widget(historyWidget)
|
||||
, _scroll(scroll) {
|
||||
connect(App::wnd(), SIGNAL(imageLoaded()), this, SLOT(update()));
|
||||
|
||||
_touchSelectTimer.setSingleShot(true);
|
||||
connect(&_touchSelectTimer, SIGNAL(timeout()), this, SLOT(onTouchSelect()));
|
||||
|
||||
|
@ -2838,7 +2837,7 @@ HistoryWidget::HistoryWidget(QWidget *parent) : TWidget(parent)
|
|||
|
||||
setAcceptDrops(true);
|
||||
|
||||
connect(App::wnd(), SIGNAL(imageLoaded()), this, SLOT(updateField()));
|
||||
connect(App::wnd(), SIGNAL(imageLoaded()), this, SLOT(update()));
|
||||
connect(&_scroll, SIGNAL(scrolled()), this, SLOT(onScroll()));
|
||||
connect(&_reportSpamPanel, SIGNAL(reportClicked()), this, SLOT(onReportSpamClicked()));
|
||||
connect(&_reportSpamPanel, SIGNAL(hideClicked()), this, SLOT(onReportSpamHide()));
|
||||
|
@ -3128,10 +3127,10 @@ void HistoryWidget::saveFieldToHistoryLocalDraft() {
|
|||
if (!_history) return;
|
||||
|
||||
if (_editMsgId) {
|
||||
_history->setEditDraft(std_::make_unique<HistoryDraft>(_field, _editMsgId, _previewCancelled, _saveEditMsgRequestId));
|
||||
_history->setEditDraft(std_::make_unique<Data::Draft>(_field, _editMsgId, _previewCancelled, _saveEditMsgRequestId));
|
||||
} else {
|
||||
if (_replyToId || !_field.isEmpty()) {
|
||||
_history->setLocalDraft(std_::make_unique<HistoryDraft>(_field, _replyToId, _previewCancelled));
|
||||
_history->setLocalDraft(std_::make_unique<Data::Draft>(_field, _replyToId, _previewCancelled));
|
||||
} else {
|
||||
_history->clearLocalDraft();
|
||||
}
|
||||
|
@ -3145,8 +3144,8 @@ void HistoryWidget::onCloudDraftSave() {
|
|||
}
|
||||
}
|
||||
|
||||
void HistoryWidget::writeDrafts(HistoryDraft **localDraft, HistoryDraft **editDraft) {
|
||||
HistoryDraft *historyLocalDraft = _history ? _history->localDraft() : nullptr;
|
||||
void HistoryWidget::writeDrafts(Data::Draft **localDraft, Data::Draft **editDraft) {
|
||||
Data::Draft *historyLocalDraft = _history ? _history->localDraft() : nullptr;
|
||||
if (!localDraft && _editMsgId) localDraft = &historyLocalDraft;
|
||||
|
||||
bool save = _peer && (_saveDraftStart > 0);
|
||||
|
@ -3203,21 +3202,6 @@ void HistoryWidget::writeDrafts(HistoryDraft **localDraft, HistoryDraft **editDr
|
|||
}
|
||||
}
|
||||
|
||||
void HistoryWidget::writeDrafts(History *history) {
|
||||
Local::MessageDraft storedLocalDraft, storedEditDraft;
|
||||
MessageCursor localCursor, editCursor;
|
||||
if (auto localDraft = history->localDraft()) {
|
||||
storedLocalDraft = Local::MessageDraft(localDraft->msgId, localDraft->textWithTags, localDraft->previewCancelled);
|
||||
localCursor = localDraft->cursor;
|
||||
}
|
||||
if (auto editDraft = history->editDraft()) {
|
||||
storedEditDraft = Local::MessageDraft(editDraft->msgId, editDraft->textWithTags, editDraft->previewCancelled);
|
||||
editCursor = editDraft->cursor;
|
||||
}
|
||||
Local::writeDrafts(history->peer->id, storedLocalDraft, storedEditDraft);
|
||||
Local::writeDraftCursors(history->peer->id, localCursor, editCursor);
|
||||
}
|
||||
|
||||
void HistoryWidget::cancelSendAction(History *history, SendActionType type) {
|
||||
QMap<QPair<History*, SendActionType>, mtpRequestId>::iterator i = _sendActionRequests.find(qMakePair(history, type));
|
||||
if (i != _sendActionRequests.cend()) {
|
||||
|
@ -3388,7 +3372,7 @@ bool HistoryWidget::notify_switchInlineBotButtonReceived(const QString &query) {
|
|||
History *h = App::history(toPeerId);
|
||||
TextWithTags textWithTags = { '@' + bot->username + ' ' + query, TextWithTags::Tags() };
|
||||
MessageCursor cursor = { textWithTags.text.size(), textWithTags.text.size(), QFIXED_MAX };
|
||||
h->setLocalDraft(std_::make_unique<HistoryDraft>(textWithTags, 0, cursor, false));
|
||||
h->setLocalDraft(std_::make_unique<Data::Draft>(textWithTags, 0, cursor, false));
|
||||
if (h == _history) {
|
||||
applyDraft();
|
||||
} else {
|
||||
|
@ -3679,10 +3663,11 @@ void HistoryWidget::fastShowAtEnd(History *h) {
|
|||
}
|
||||
|
||||
void HistoryWidget::applyDraft(bool parseLinks) {
|
||||
HistoryDraft *draft = _history ? _history->draft() : nullptr;
|
||||
auto draft = _history ? _history->draft() : nullptr;
|
||||
if (!draft) {
|
||||
clearFieldText();
|
||||
_field.setFocus();
|
||||
_replyEditMsg = nullptr;
|
||||
_editMsgId = _replyToId = 0;
|
||||
return;
|
||||
}
|
||||
|
@ -3693,6 +3678,7 @@ void HistoryWidget::applyDraft(bool parseLinks) {
|
|||
draft->cursor.applyTo(_field);
|
||||
_textUpdateEvents = TextUpdateEvent::SaveDraft | TextUpdateEvent::SendTyping;
|
||||
_previewCancelled = draft->previewCancelled;
|
||||
_replyEditMsg = nullptr;
|
||||
if (auto editDraft = _history->editDraft()) {
|
||||
_editMsgId = editDraft->msgId;
|
||||
_replyToId = 0;
|
||||
|
@ -3700,6 +3686,7 @@ void HistoryWidget::applyDraft(bool parseLinks) {
|
|||
_editMsgId = 0;
|
||||
_replyToId = readyToForward() ? 0 : _history->localDraft()->msgId;
|
||||
}
|
||||
|
||||
if (parseLinks) {
|
||||
onPreviewParse();
|
||||
}
|
||||
|
@ -3784,10 +3771,6 @@ void HistoryWidget::showHistory(const PeerId &peerId, MsgId showAtMsgId, bool re
|
|||
_migrated->clearEditDraft();
|
||||
}
|
||||
|
||||
auto localDraft = _history->localDraft();
|
||||
auto editDraft = _history->editDraft();
|
||||
writeDrafts(&localDraft, &editDraft);
|
||||
|
||||
_history->showAtMsgId = _showAtMsgId;
|
||||
|
||||
destroyUnreadBar();
|
||||
|
@ -3797,10 +3780,9 @@ void HistoryWidget::showHistory(const PeerId &peerId, MsgId showAtMsgId, bool re
|
|||
}
|
||||
|
||||
_addToScroll = 0;
|
||||
_editMsgId = 0;
|
||||
_saveEditMsgRequestId = 0;
|
||||
_replyToId = 0;
|
||||
_replyEditMsg = 0;
|
||||
_replyEditMsg = nullptr;
|
||||
_editMsgId = _replyToId = 0;
|
||||
_previewData = 0;
|
||||
_previewCache.clear();
|
||||
_fieldBarCancel.hide();
|
||||
|
@ -4173,14 +4155,12 @@ void HistoryWidget::updateControlsVisibility() {
|
|||
} else if (_canSendMessages) {
|
||||
onCheckFieldAutocomplete();
|
||||
if (isBotStart()) {
|
||||
if (isBotStart()) {
|
||||
_unblock.hide();
|
||||
_joinChannel.hide();
|
||||
_muteUnmute.hide();
|
||||
if (_botStart.isHidden()) {
|
||||
_botStart.clearState();
|
||||
_botStart.show();
|
||||
}
|
||||
_unblock.hide();
|
||||
_joinChannel.hide();
|
||||
_muteUnmute.hide();
|
||||
if (_botStart.isHidden()) {
|
||||
_botStart.clearState();
|
||||
_botStart.show();
|
||||
}
|
||||
_kbShown = false;
|
||||
_send.hide();
|
||||
|
@ -4773,7 +4753,7 @@ void HistoryWidget::saveEditMsgDone(History *history, const MTPUpdates &updates,
|
|||
if (auto editDraft = history->editDraft()) {
|
||||
if (editDraft->saveRequestId == req) {
|
||||
history->clearEditDraft();
|
||||
writeDrafts(history);
|
||||
if (App::main()) App::main()->writeDrafts(history);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -5407,7 +5387,7 @@ bool HistoryWidget::botCallbackFail(BotCallbackInfo info, const RPCError &error,
|
|||
}
|
||||
|
||||
bool HistoryWidget::insertBotCommand(const QString &cmd, bool specialGif) {
|
||||
if (!_history) return false;
|
||||
if (!_history || !_canSendMessages) return false;
|
||||
|
||||
bool insertingInlineBot = !cmd.isEmpty() && (cmd.at(0) == '@');
|
||||
QString toInsert = cmd;
|
||||
|
@ -7266,7 +7246,7 @@ void HistoryWidget::onReplyToMessage() {
|
|||
if (auto localDraft = _history->localDraft()) {
|
||||
localDraft->msgId = to->id;
|
||||
} else {
|
||||
_history->setLocalDraft(std_::make_unique<HistoryDraft>(TextWithTags(), to->id, MessageCursor(), false));
|
||||
_history->setLocalDraft(std_::make_unique<Data::Draft>(TextWithTags(), to->id, MessageCursor(), false));
|
||||
}
|
||||
} else {
|
||||
_replyEditMsg = to;
|
||||
|
@ -7299,10 +7279,12 @@ void HistoryWidget::onEditMessage() {
|
|||
} else {
|
||||
delete box;
|
||||
|
||||
if (_replyToId || !_field.isEmpty()) {
|
||||
_history->setLocalDraft(std_::make_unique<HistoryDraft>(_field, _replyToId, _previewCancelled));
|
||||
} else {
|
||||
_history->clearLocalDraft();
|
||||
if (!_editMsgId) {
|
||||
if (_replyToId || !_field.isEmpty()) {
|
||||
_history->setLocalDraft(std_::make_unique<Data::Draft>(_field, _replyToId, _previewCancelled));
|
||||
} else {
|
||||
_history->clearLocalDraft();
|
||||
}
|
||||
}
|
||||
|
||||
auto original = to->originalText();
|
||||
|
@ -7310,7 +7292,7 @@ void HistoryWidget::onEditMessage() {
|
|||
auto editTags = textTagsFromEntities(original.entities);
|
||||
TextWithTags editData = { editText, editTags };
|
||||
MessageCursor cursor = { editText.size(), editText.size(), QFIXED_MAX };
|
||||
_history->setEditDraft(std_::make_unique<HistoryDraft>(editData, to->id, cursor, false));
|
||||
_history->setEditDraft(std_::make_unique<Data::Draft>(editData, to->id, cursor, false));
|
||||
applyDraft(false);
|
||||
|
||||
_previewData = nullptr;
|
||||
|
@ -7411,11 +7393,11 @@ bool HistoryWidget::lastForceReplyReplied(const FullMsgId &replyTo) const {
|
|||
}
|
||||
|
||||
void HistoryWidget::cancelReply(bool lastKeyboardUsed) {
|
||||
bool wasReply = false; ;
|
||||
bool wasReply = false;
|
||||
if (_replyToId) {
|
||||
wasReply = true;
|
||||
|
||||
_replyEditMsg = 0;
|
||||
_replyEditMsg = nullptr;
|
||||
_replyToId = 0;
|
||||
mouseMoveEvent(0);
|
||||
if (!readyToForward() && (!_previewData || _previewData->pendingTill < 0) && !_kbReplyTo) {
|
||||
|
@ -7451,8 +7433,8 @@ void HistoryWidget::cancelReply(bool lastKeyboardUsed) {
|
|||
void HistoryWidget::cancelEdit() {
|
||||
if (!_editMsgId) return;
|
||||
|
||||
_editMsgId = 0;
|
||||
_replyEditMsg = nullptr;
|
||||
_editMsgId = 0;
|
||||
_history->clearEditDraft();
|
||||
applyDraft();
|
||||
|
||||
|
|
|
@ -973,7 +973,7 @@ private:
|
|||
Q_DECLARE_FLAGS(TextUpdateEvents, TextUpdateEvent);
|
||||
Q_DECLARE_FRIEND_OPERATORS_FOR_FLAGS(TextUpdateEvents);
|
||||
|
||||
void writeDrafts(HistoryDraft **localDraft, HistoryDraft **editDraft);
|
||||
void writeDrafts(Data::Draft **localDraft, Data::Draft **editDraft);
|
||||
void writeDrafts(History *history);
|
||||
void setFieldText(const TextWithTags &textWithTags, TextUpdateEvents events = 0, FlatTextarea::UndoHistoryAction undoHistoryAction = FlatTextarea::ClearUndoHistory);
|
||||
void clearFieldText(TextUpdateEvents events = 0, FlatTextarea::UndoHistoryAction undoHistoryAction = FlatTextarea::ClearUndoHistory) {
|
||||
|
|
|
@ -25,6 +25,7 @@ Copyright (c) 2014-2016 John Preston, https://desktop.telegram.org
|
|||
|
||||
#include "serialize/serialize_document.h"
|
||||
#include "serialize/serialize_common.h"
|
||||
#include "data/data_drafts.h"
|
||||
#include "observer_peer.h"
|
||||
#include "mainwidget.h"
|
||||
#include "mainwindow.h"
|
||||
|
@ -2409,13 +2410,13 @@ namespace Local {
|
|||
if (msgData.text.isEmpty() && !msgReplyTo) {
|
||||
h->clearLocalDraft();
|
||||
} else {
|
||||
h->setLocalDraft(std_::make_unique<HistoryDraft>(msgData, msgReplyTo, msgCursor, msgPreviewCancelled));
|
||||
h->setLocalDraft(std_::make_unique<Data::Draft>(msgData, msgReplyTo, msgCursor, msgPreviewCancelled));
|
||||
}
|
||||
}
|
||||
if (!editMsgId) {
|
||||
h->clearEditDraft();
|
||||
} else {
|
||||
h->setEditDraft(std_::make_unique<HistoryDraft>(editData, editMsgId, editCursor, editPreviewCancelled));
|
||||
h->setEditDraft(std_::make_unique<Data::Draft>(editData, editMsgId, editCursor, editPreviewCancelled));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -174,7 +174,7 @@ bool MainWidget::onShareUrl(const PeerId &peer, const QString &url, const QStrin
|
|||
History *h = App::history(peer);
|
||||
TextWithTags textWithTags = { url + '\n' + text, TextWithTags::Tags() };
|
||||
MessageCursor cursor = { url.size() + 1, url.size() + 1 + text.size(), QFIXED_MAX };
|
||||
h->setLocalDraft(std_::make_unique<HistoryDraft>(textWithTags, 0, cursor, false));
|
||||
h->setLocalDraft(std_::make_unique<Data::Draft>(textWithTags, 0, cursor, false));
|
||||
h->clearEditDraft();
|
||||
bool opened = _history->peer() && (_history->peer()->id == peer);
|
||||
if (opened) {
|
||||
|
@ -194,7 +194,7 @@ bool MainWidget::onInlineSwitchChosen(const PeerId &peer, const QString &botAndQ
|
|||
History *h = App::history(peer);
|
||||
TextWithTags textWithTags = { botAndQuery, TextWithTags::Tags() };
|
||||
MessageCursor cursor = { botAndQuery.size(), botAndQuery.size(), QFIXED_MAX };
|
||||
h->setLocalDraft(std_::make_unique<HistoryDraft>(textWithTags, 0, cursor, false));
|
||||
h->setLocalDraft(std_::make_unique<Data::Draft>(textWithTags, 0, cursor, false));
|
||||
h->clearEditDraft();
|
||||
bool opened = _history->peer() && (_history->peer()->id == peer);
|
||||
if (opened) {
|
||||
|
@ -3772,9 +3772,11 @@ void MainWidget::saveDraftToCloud() {
|
|||
|
||||
auto peer = _history->peer();
|
||||
if (auto history = App::historyLoaded(peer)) {
|
||||
writeDrafts(history);
|
||||
|
||||
auto localDraft = history->localDraft();
|
||||
auto cloudDraft = history->cloudDraft();
|
||||
if (!historyDraftsAreEqual(localDraft, cloudDraft)) {
|
||||
if (!Data::draftsAreEqual(localDraft, cloudDraft)) {
|
||||
App::api()->saveDraftToCloudDelayed(history);
|
||||
}
|
||||
}
|
||||
|
@ -3784,6 +3786,23 @@ void MainWidget::applyCloudDraft(History *history) {
|
|||
_history->applyCloudDraft(history);
|
||||
}
|
||||
|
||||
void MainWidget::writeDrafts(History *history) {
|
||||
Local::MessageDraft storedLocalDraft, storedEditDraft;
|
||||
MessageCursor localCursor, editCursor;
|
||||
if (auto localDraft = history->localDraft()) {
|
||||
if (!Data::draftsAreEqual(localDraft, history->cloudDraft())) {
|
||||
storedLocalDraft = Local::MessageDraft(localDraft->msgId, localDraft->textWithTags, localDraft->previewCancelled);
|
||||
localCursor = localDraft->cursor;
|
||||
}
|
||||
}
|
||||
if (auto editDraft = history->editDraft()) {
|
||||
storedEditDraft = Local::MessageDraft(editDraft->msgId, editDraft->textWithTags, editDraft->previewCancelled);
|
||||
editCursor = editDraft->cursor;
|
||||
}
|
||||
Local::writeDrafts(history->peer->id, storedLocalDraft, storedEditDraft);
|
||||
Local::writeDraftCursors(history->peer->id, localCursor, editCursor);
|
||||
}
|
||||
|
||||
void MainWidget::checkIdleFinish() {
|
||||
if (this != App::main()) return;
|
||||
if (psIdleTime() < uint64(Global::OfflineIdleTimeout())) {
|
||||
|
@ -4668,6 +4687,8 @@ void MainWidget::feedUpdate(const MTPUpdate &update) {
|
|||
if (draftMessage.type() == mtpc_draftMessage) {
|
||||
auto &draft = draftMessage.c_draftMessage();
|
||||
Data::applyPeerCloudDraft(peerId, draft);
|
||||
} else {
|
||||
Data::clearPeerCloudDraft(peerId);
|
||||
}
|
||||
} break;
|
||||
|
||||
|
|
|
@ -241,6 +241,7 @@ public:
|
|||
|
||||
void saveDraftToCloud();
|
||||
void applyCloudDraft(History *history);
|
||||
void writeDrafts(History *history);
|
||||
|
||||
int32 dlgsWidth() const;
|
||||
|
||||
|
|
|
@ -1869,7 +1869,6 @@
|
|||
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
|
||||
<Command Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\GeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" -DAL_LIBTYPE_STATIC -DUNICODE -DWIN32 -DWIN64 -DHAVE_STDINT_H -DZLIB_WINAPI -DQT_NO_DEBUG -DNDEBUG -D_SCL_SECURE_NO_WARNINGS "-I.\SourceFiles" "-I.\GeneratedFiles" "-I.\GeneratedFiles\$(ConfigurationName)\." "-I$(QTDIR)\include" "-I$(QTDIR)\include\QtCore\5.6.0\QtCore" "-I$(QTDIR)\include\QtGui\5.6.0\QtGui" "-I.\..\..\Libraries\breakpad\src" "-I.\..\..\Libraries\lzma\C" "-I.\..\..\Libraries\libexif-0.6.20" "-I.\..\..\Libraries\zlib-1.2.8" "-I.\..\..\Libraries\ffmpeg" "-I.\..\..\Libraries\openal-soft\include" "-I.\ThirdParty\minizip" "-I.\..\..\Libraries\openssl\Release\include" "-fstdafx.h" "-f../../SourceFiles/ui/twidget.h"</Command>
|
||||
</CustomBuild>
|
||||
<ClInclude Include="SourceFiles\ui\style\style_abstract_data.h" />
|
||||
<ClInclude Include="SourceFiles\ui\style\style_core.h" />
|
||||
<ClInclude Include="SourceFiles\ui\style\style_core_color.h" />
|
||||
<ClInclude Include="SourceFiles\ui\style\style_core_font.h" />
|
||||
|
|
|
@ -1520,9 +1520,6 @@
|
|||
<ClInclude Include="SourceFiles\history\history_service_layout.h">
|
||||
<Filter>SourceFiles\history</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="SourceFiles\ui\style\style_abstract_data.h">
|
||||
<Filter>SourceFiles\ui\style</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="SourceFiles\data\data_abstract_structure.h">
|
||||
<Filter>SourceFiles\data</Filter>
|
||||
</ClInclude>
|
||||
|
|
Loading…
Reference in New Issue