mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-16 06:07:06 +02:00
Set / suggest / reset a contact personal photo.
This commit is contained in:
parent
cb99d611f3
commit
5fe9c93cb6
12 changed files with 190 additions and 72 deletions
|
@ -1200,6 +1200,9 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
"lng_profile_send_message" = "Send Message";
|
||||
"lng_info_add_as_contact" = "Add to contacts";
|
||||
"lng_profile_shared_media" = "Shared media";
|
||||
"lng_profile_suggest_photo" = "Suggest Photo for {user}";
|
||||
"lng_profile_set_photo_for" = "Set Photo for {user}";
|
||||
"lng_profile_photo_reset" = "Reset to Original Photo";
|
||||
"lng_media_type_photos" = "Photos";
|
||||
"lng_media_type_gifs" = "GIFs";
|
||||
"lng_media_type_videos" = "Videos";
|
||||
|
|
|
@ -113,6 +113,13 @@ PeerPhoto::PeerPhoto(not_null<ApiWrap*> api)
|
|||
}
|
||||
|
||||
void PeerPhoto::upload(not_null<PeerData*> peer, QImage &&image) {
|
||||
upload(peer, std::move(image), false);
|
||||
}
|
||||
|
||||
void PeerPhoto::upload(
|
||||
not_null<PeerData*> peer,
|
||||
QImage &&image,
|
||||
bool suggestion) {
|
||||
peer = peer->migrateToOrMe();
|
||||
const auto ready = PreparePeerPhoto(
|
||||
_api.instance().mainDcId(),
|
||||
|
@ -128,12 +135,20 @@ void PeerPhoto::upload(not_null<PeerData*> peer, QImage &&image) {
|
|||
[](const auto &pair) { return pair.second; });
|
||||
if (already != end(_uploads)) {
|
||||
_session->uploader().cancel(already->first);
|
||||
_suggestions.remove(already->first);
|
||||
_uploads.erase(already);
|
||||
}
|
||||
_uploads.emplace(fakeId, peer);
|
||||
if (suggestion) {
|
||||
_suggestions.emplace(fakeId);
|
||||
}
|
||||
_session->uploader().uploadMedia(fakeId, ready);
|
||||
}
|
||||
|
||||
void PeerPhoto::suggest(not_null<PeerData*> peer, QImage &&image) {
|
||||
upload(peer, std::move(image), true);
|
||||
}
|
||||
|
||||
void PeerPhoto::clear(not_null<PhotoData*> photo) {
|
||||
const auto self = _session->user();
|
||||
if (self->userpicPhotoId() == photo->id) {
|
||||
|
@ -167,6 +182,27 @@ void PeerPhoto::clear(not_null<PhotoData*> photo) {
|
|||
}
|
||||
}
|
||||
|
||||
void PeerPhoto::clearPersonal(not_null<UserData*> user) {
|
||||
_api.request(MTPphotos_UploadContactProfilePhoto(
|
||||
MTP_flags(MTPphotos_UploadContactProfilePhoto::Flag::f_save),
|
||||
user->inputUser,
|
||||
MTPInputFile(),
|
||||
MTPInputFile(), // video
|
||||
MTPdouble() // video_start_ts
|
||||
)).done([=](const MTPphotos_Photo &result) {
|
||||
result.match([&](const MTPDphotos_photo &data) {
|
||||
_session->data().processPhoto(data.vphoto());
|
||||
_session->data().processUsers(data.vusers());
|
||||
});
|
||||
}).send();
|
||||
if (!user->userpicPhotoUnknown()
|
||||
&& (user->flags() & UserDataFlag::PersonalPhoto)) {
|
||||
_session->storage().remove(Storage::UserPhotosRemoveOne(
|
||||
peerToUser(user->id),
|
||||
user->userpicPhotoId()));
|
||||
}
|
||||
}
|
||||
|
||||
void PeerPhoto::set(not_null<PeerData*> peer, not_null<PhotoData*> photo) {
|
||||
if (peer->userpicPhotoId() == photo->id) {
|
||||
return;
|
||||
|
@ -200,6 +236,8 @@ void PeerPhoto::set(not_null<PeerData*> peer, not_null<PhotoData*> photo) {
|
|||
|
||||
void PeerPhoto::ready(const FullMsgId &msgId, const MTPInputFile &file) {
|
||||
const auto maybePeer = _uploads.take(msgId);
|
||||
const auto suggestion = _suggestions.contains(msgId);
|
||||
_suggestions.remove(msgId);
|
||||
if (!maybePeer) {
|
||||
return;
|
||||
}
|
||||
|
@ -239,6 +277,21 @@ void PeerPhoto::ready(const FullMsgId &msgId, const MTPInputFile &file) {
|
|||
MTPInputFile(), // video
|
||||
MTPdouble()) // video_start_ts
|
||||
)).done(applier).afterRequest(history->sendRequestId).send();
|
||||
} else if (const auto user = peer->asUser()) {
|
||||
using Flag = MTPphotos_UploadContactProfilePhoto::Flag;
|
||||
_api.request(MTPphotos_UploadContactProfilePhoto(
|
||||
MTP_flags(Flag::f_file
|
||||
| (suggestion ? Flag::f_suggest : Flag::f_save)),
|
||||
user->inputUser,
|
||||
file,
|
||||
MTPInputFile(), // video
|
||||
MTPdouble() // video_start_ts
|
||||
)).done([=](const MTPphotos_Photo &result) {
|
||||
result.match([&](const MTPDphotos_photo &data) {
|
||||
_session->data().processPhoto(data.vphoto());
|
||||
_session->data().processUsers(data.vusers());
|
||||
});
|
||||
}).send();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -257,26 +310,35 @@ void PeerPhoto::requestUserPhotos(
|
|||
)).done([this, user](const MTPphotos_Photos &result) {
|
||||
_userPhotosRequests.remove(user);
|
||||
|
||||
const auto fullCount = result.match([](const MTPDphotos_photos &d) {
|
||||
auto fullCount = result.match([](const MTPDphotos_photos &d) {
|
||||
return int(d.vphotos().v.size());
|
||||
}, [](const MTPDphotos_photosSlice &d) {
|
||||
return d.vcount().v;
|
||||
});
|
||||
|
||||
auto &owner = _session->data();
|
||||
auto photoIds = result.match([&](const auto &data) {
|
||||
auto &owner = _session->data();
|
||||
owner.processUsers(data.vusers());
|
||||
|
||||
auto photoIds = std::vector<PhotoId>();
|
||||
photoIds.reserve(data.vphotos().v.size());
|
||||
|
||||
for (const auto &photo : data.vphotos().v) {
|
||||
if (const auto photoData = owner.processPhoto(photo)) {
|
||||
photoIds.push_back(photoData->id);
|
||||
for (const auto &single : data.vphotos().v) {
|
||||
const auto photo = owner.processPhoto(single);
|
||||
if (!photo->isNull()) {
|
||||
photoIds.push_back(photo->id);
|
||||
}
|
||||
}
|
||||
return photoIds;
|
||||
});
|
||||
if (!user->userpicPhotoUnknown()
|
||||
&& (user->flags() & UserDataFlag::PersonalPhoto)) {
|
||||
const auto photo = owner.photo(user->userpicPhotoId());
|
||||
if (!photo->isNull()) {
|
||||
++fullCount;
|
||||
photoIds.insert(begin(photoIds), photo->id);
|
||||
}
|
||||
}
|
||||
|
||||
_session->storage().add(Storage::UserPhotosAddSlice(
|
||||
peerToUser(user->id),
|
||||
|
|
|
@ -25,18 +25,22 @@ public:
|
|||
explicit PeerPhoto(not_null<ApiWrap*> api);
|
||||
|
||||
void upload(not_null<PeerData*> peer, QImage &&image);
|
||||
void suggest(not_null<PeerData*> peer, QImage &&image);
|
||||
void clear(not_null<PhotoData*> photo);
|
||||
void clearPersonal(not_null<UserData*> user);
|
||||
void set(not_null<PeerData*> peer, not_null<PhotoData*> photo);
|
||||
|
||||
void requestUserPhotos(not_null<UserData*> user, UserPhotoId afterId);
|
||||
|
||||
private:
|
||||
void ready(const FullMsgId &msgId, const MTPInputFile &file);
|
||||
void upload(not_null<PeerData*> peer, QImage &&image, bool suggestion);
|
||||
|
||||
const not_null<Main::Session*> _session;
|
||||
MTP::Sender _api;
|
||||
|
||||
base::flat_map<FullMsgId, not_null<PeerData*>> _uploads;
|
||||
base::flat_set<FullMsgId> _suggestions;
|
||||
|
||||
base::flat_map<not_null<UserData*>, mtpRequestId> _userPhotosRequests;
|
||||
|
||||
|
|
|
@ -168,7 +168,7 @@ TextWithEntities ForumTopicIconWithTitle(
|
|||
return (rootId == ForumTopic::kGeneralId)
|
||||
? TextWithEntities{ u"# "_q + title }
|
||||
: iconId
|
||||
? Data::SingleCustomEmoji(iconId).append(title)
|
||||
? Data::SingleCustomEmoji(iconId).append(' ').append(title)
|
||||
: TextWithEntities{ title };
|
||||
}
|
||||
|
||||
|
|
|
@ -423,7 +423,6 @@ private:
|
|||
|
||||
mutable Data::CloudImage _userpic;
|
||||
PhotoId _userpicPhotoId = kUnknownPhotoId;
|
||||
bool _userpicHasVideo = false;
|
||||
|
||||
mutable std::unique_ptr<Ui::EmptyUserpic> _userpicEmpty;
|
||||
|
||||
|
@ -443,6 +442,7 @@ private:
|
|||
Settings _settings = PeerSettings(PeerSetting::Unknown);
|
||||
BlockStatus _blockStatus = BlockStatus::Unknown;
|
||||
LoadedStatus _loadedStatus = LoadedStatus::Not;
|
||||
bool _userpicHasVideo = false;
|
||||
|
||||
QString _requestChatTitle;
|
||||
TimeId _requestChatDate = 0;
|
||||
|
|
|
@ -54,11 +54,17 @@ void UserData::setIsContact(bool is) {
|
|||
// see Serialize::readPeer as well
|
||||
void UserData::setPhoto(const MTPUserProfilePhoto &photo) {
|
||||
photo.match([&](const MTPDuserProfilePhoto &data) {
|
||||
if (data.is_personal()) {
|
||||
addFlags(UserDataFlag::PersonalPhoto);
|
||||
} else {
|
||||
removeFlags(UserDataFlag::PersonalPhoto);
|
||||
}
|
||||
updateUserpic(
|
||||
data.vphoto_id().v,
|
||||
data.vdc_id().v,
|
||||
data.is_has_video());
|
||||
}, [&](const MTPDuserProfilePhotoEmpty &) {
|
||||
removeFlags(UserDataFlag::PersonalPhoto);
|
||||
clearUserpic();
|
||||
});
|
||||
}
|
||||
|
@ -358,6 +364,9 @@ void ApplyUserUpdate(not_null<UserData*> user, const MTPDuserFull &update) {
|
|||
if (const auto photo = update.vprofile_photo()) {
|
||||
user->owner().processPhoto(*photo);
|
||||
}
|
||||
if (const auto photo = update.vpersonal_photo()) {
|
||||
user->owner().processPhoto(*photo);
|
||||
}
|
||||
user->setSettings(update.vsettings());
|
||||
user->owner().notifySettings().apply(user, update.vnotify_settings());
|
||||
|
||||
|
|
|
@ -56,6 +56,7 @@ enum class UserDataFlag {
|
|||
Premium = (1 << 14),
|
||||
CanReceiveGifts = (1 << 15),
|
||||
VoiceMessagesForbidden = (1 << 16),
|
||||
PersonalPhoto = (1 << 17),
|
||||
};
|
||||
inline constexpr bool is_flag_type(UserDataFlag) { return true; };
|
||||
using UserDataFlags = base::flags<UserDataFlag>;
|
||||
|
|
|
@ -11,6 +11,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "data/data_channel.h"
|
||||
#include "data/data_chat.h"
|
||||
#include "data/data_peer.h"
|
||||
#include "data/data_user.h"
|
||||
#include "data/data_document.h"
|
||||
#include "data/data_document_media.h"
|
||||
#include "data/data_changes.h"
|
||||
|
@ -331,12 +332,6 @@ Cover::Cover(
|
|||
setupChildGeometry();
|
||||
|
||||
if (_userpic) {
|
||||
_userpic->uploadPhotoRequests(
|
||||
) | rpl::start_with_next([=] {
|
||||
_peer->session().api().peerPhoto().upload(
|
||||
_peer,
|
||||
_userpic->takeResultImage());
|
||||
}, _userpic->lifetime());
|
||||
} else if (topic->canEdit()) {
|
||||
_iconButton->setClickedCallback([=] {
|
||||
_controller->show(Box(
|
||||
|
@ -388,30 +383,48 @@ void Cover::initViewers(rpl::producer<QString> title) {
|
|||
) | rpl::start_with_next(
|
||||
[=] { refreshStatusText(); },
|
||||
lifetime());
|
||||
if (!_peer->isUser()) {
|
||||
_peer->session().changes().peerFlagsValue(
|
||||
_peer,
|
||||
Flag::Rights
|
||||
) | rpl::start_with_next(
|
||||
[=] { refreshUploadPhotoOverlay(); },
|
||||
lifetime());
|
||||
} else if (_peer->isSelf()) {
|
||||
refreshUploadPhotoOverlay();
|
||||
}
|
||||
_peer->session().changes().peerFlagsValue(
|
||||
_peer,
|
||||
(_peer->isUser() ? Flag::IsContact : Flag::Rights)
|
||||
) | rpl::start_with_next(
|
||||
[=] { refreshUploadPhotoOverlay(); },
|
||||
lifetime());
|
||||
}
|
||||
|
||||
void Cover::refreshUploadPhotoOverlay() {
|
||||
if (!_userpic) {
|
||||
return;
|
||||
}
|
||||
|
||||
_userpic->switchChangePhotoOverlay([&] {
|
||||
if (const auto chat = _peer->asChat()) {
|
||||
return chat->canEditInformation();
|
||||
} else if (const auto channel = _peer->asChannel()) {
|
||||
return channel->canEditInformation();
|
||||
} else if (const auto user = _peer->asUser()) {
|
||||
return user->isSelf()
|
||||
|| (user->isContact()
|
||||
&& !user->isInaccessible()
|
||||
&& !user->isServiceUser());
|
||||
}
|
||||
return _peer->isSelf();
|
||||
}());
|
||||
Unexpected("Peer type in Info::Profile::Cover.");
|
||||
}(), [=](Ui::UserpicButton::ChosenImage chosen) {
|
||||
using ChosenType = Ui::UserpicButton::ChosenType;
|
||||
auto &image = chosen.image;
|
||||
switch (chosen.type) {
|
||||
case ChosenType::Set:
|
||||
_userpic->changeTo(base::duplicate(image));
|
||||
_peer->session().api().peerPhoto().upload(
|
||||
_peer,
|
||||
std::move(image));
|
||||
break;
|
||||
case ChosenType::Suggest:
|
||||
_peer->session().api().peerPhoto().suggest(
|
||||
_peer,
|
||||
std::move(image));
|
||||
break;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
void Cover::refreshStatusText() {
|
||||
|
|
|
@ -296,9 +296,9 @@ void SetupPhoto(
|
|||
const auto upload = CreateUploadButton(wrap, controller);
|
||||
|
||||
upload->chosenImages(
|
||||
) | rpl::start_with_next([=](QImage &&image) {
|
||||
UploadPhoto(self, image);
|
||||
photo->changeTo(std::move(image));
|
||||
) | rpl::start_with_next([=](Ui::UserpicButton::ChosenImage &&chosen) {
|
||||
UploadPhoto(self, chosen.image);
|
||||
photo->changeTo(std::move(chosen.image));
|
||||
}, upload->lifetime());
|
||||
|
||||
const auto name = Ui::CreateChild<Ui::FlatLabel>(
|
||||
|
|
|
@ -138,13 +138,12 @@ Cover::Cover(
|
|||
initViewers();
|
||||
setupChildGeometry();
|
||||
|
||||
_userpic->switchChangePhotoOverlay(_user->isSelf());
|
||||
_userpic->uploadPhotoRequests(
|
||||
) | rpl::start_with_next([=] {
|
||||
_user->session().api().peerPhoto().upload(
|
||||
_user,
|
||||
_userpic->takeResultImage());
|
||||
}, _userpic->lifetime());
|
||||
_userpic->switchChangePhotoOverlay(_user->isSelf(), [=](
|
||||
Ui::UserpicButton::ChosenImage chosen) {
|
||||
auto &image = chosen.image;
|
||||
_userpic->changeTo(base::duplicate(image));
|
||||
_user->session().api().peerPhoto().upload(_user, std::move(image));
|
||||
});
|
||||
|
||||
_badge.setPremiumClickCallback([=] {
|
||||
_emojiStatusPanel.show(
|
||||
|
|
|
@ -43,6 +43,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "lang/lang_keys.h"
|
||||
#include "main/main_session.h"
|
||||
#include "apiwrap.h"
|
||||
#include "api/api_peer_photo.h"
|
||||
#include "styles/style_boxes.h"
|
||||
#include "styles/style_chat.h"
|
||||
|
||||
|
@ -246,13 +247,10 @@ void UserpicButton::prepare() {
|
|||
}
|
||||
setClickHandlerByRole();
|
||||
|
||||
if (_role == Role::ChangePhoto || _role == Role::OpenPhoto) {
|
||||
if (_role == Role::ChangePhoto) {
|
||||
chosenImages(
|
||||
) | rpl::start_with_next([=](QImage &&image) {
|
||||
setImage(std::move(image));
|
||||
if (_requestToUpload) {
|
||||
_uploadPhotoRequests.fire({});
|
||||
}
|
||||
) | rpl::start_with_next([=](ChosenImage &&chosen) {
|
||||
setImage(std::move(chosen.image));
|
||||
}, lifetime());
|
||||
}
|
||||
}
|
||||
|
@ -260,11 +258,8 @@ void UserpicButton::prepare() {
|
|||
void UserpicButton::setClickHandlerByRole() {
|
||||
switch (_role) {
|
||||
case Role::ChoosePhoto:
|
||||
addClickHandler([=] { choosePhotoLocally(); });
|
||||
break;
|
||||
|
||||
case Role::ChangePhoto:
|
||||
addClickHandler([=] { changePhotoLocally(); });
|
||||
addClickHandler([=] { choosePhotoLocally(); });
|
||||
break;
|
||||
|
||||
case Role::OpenPhoto:
|
||||
|
@ -289,10 +284,12 @@ void UserpicButton::choosePhotoLocally() {
|
|||
if (!_window) {
|
||||
return;
|
||||
}
|
||||
auto callback = [=](QImage &&image) {
|
||||
_chosenImages.fire(std::move(image));
|
||||
const auto callback = [=](ChosenType type) {
|
||||
return [=](QImage &&image) {
|
||||
_chosenImages.fire({ std::move(image), type });
|
||||
};
|
||||
};
|
||||
const auto chooseFile = [=] {
|
||||
const auto chooseFile = [=](ChosenType type = ChosenType::Set) {
|
||||
base::call_delayed(
|
||||
_st.changeButton.ripple.hideDuration,
|
||||
crl::guard(this, [=] {
|
||||
|
@ -302,32 +299,52 @@ void UserpicButton::choosePhotoLocally() {
|
|||
((_peer && _peer->isForum())
|
||||
? ImageRoundRadius::Large
|
||||
: ImageRoundRadius::Ellipse),
|
||||
callback);
|
||||
callback(type));
|
||||
}));
|
||||
};
|
||||
if (!IsCameraAvailable()) {
|
||||
chooseFile();
|
||||
} else {
|
||||
_menu = base::make_unique_q<Ui::PopupMenu>(this);
|
||||
_menu->addAction(tr::lng_attach_file(tr::now), chooseFile);
|
||||
_menu->addAction(tr::lng_attach_camera(tr::now), [=] {
|
||||
_window->show(Box(CameraBox, _window, _peer, callback));
|
||||
});
|
||||
const auto user = _peer ? _peer->asUser() : nullptr;
|
||||
if (user && !user->isSelf()) {
|
||||
const auto name = user->firstName.isEmpty()
|
||||
? user->name()
|
||||
: user->firstName;
|
||||
_menu->addAction(
|
||||
tr::lng_profile_set_photo_for(tr::now, lt_user, name),
|
||||
[=] { chooseFile(); });
|
||||
_menu->addAction(
|
||||
tr::lng_profile_suggest_photo(tr::now, lt_user, name),
|
||||
[=] { chooseFile(ChosenType::Suggest); });
|
||||
if (user->flags() & UserDataFlag::PersonalPhoto) {
|
||||
_menu->addAction(
|
||||
tr::lng_profile_photo_reset(tr::now),
|
||||
[=] { user->session().api().peerPhoto().clearPersonal(
|
||||
user); _userpicCustom = false; });
|
||||
}
|
||||
} else {
|
||||
_menu->addAction(tr::lng_attach_file(tr::now), [=] {
|
||||
chooseFile();
|
||||
});
|
||||
_menu->addAction(tr::lng_attach_camera(tr::now), [=] {
|
||||
_window->show(Box(
|
||||
CameraBox,
|
||||
_window,
|
||||
_peer,
|
||||
callback(ChosenType::Set)));
|
||||
});
|
||||
}
|
||||
_menu->popup(QCursor::pos());
|
||||
}
|
||||
}
|
||||
|
||||
void UserpicButton::changePhotoLocally(bool requestToUpload) {
|
||||
_requestToUpload = requestToUpload;
|
||||
choosePhotoLocally();
|
||||
}
|
||||
|
||||
void UserpicButton::openPeerPhoto() {
|
||||
Expects(_peer != nullptr);
|
||||
Expects(_controller != nullptr);
|
||||
|
||||
if (_changeOverlayEnabled && _cursorInChangeOverlay) {
|
||||
changePhotoLocally(true);
|
||||
choosePhotoLocally();
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -720,7 +737,9 @@ void UserpicButton::startAnimation() {
|
|||
_a_appearance.start([this] { update(); }, 0, 1, _st.duration);
|
||||
}
|
||||
|
||||
void UserpicButton::switchChangePhotoOverlay(bool enabled) {
|
||||
void UserpicButton::switchChangePhotoOverlay(
|
||||
bool enabled,
|
||||
Fn<void(ChosenImage)> chosen) {
|
||||
Expects(_role == Role::OpenPhoto);
|
||||
|
||||
if (_changeOverlayEnabled != enabled) {
|
||||
|
@ -731,6 +750,9 @@ void UserpicButton::switchChangePhotoOverlay(bool enabled) {
|
|||
}
|
||||
updateCursorInChangeOverlay(
|
||||
mapFromGlobal(QCursor::pos()));
|
||||
if (chosen) {
|
||||
chosenImages() | rpl::start_with_next(chosen, lifetime());
|
||||
}
|
||||
} else {
|
||||
_changeOverlayShown.stop();
|
||||
update();
|
||||
|
@ -791,6 +813,7 @@ void UserpicButton::setImage(QImage &&image) {
|
|||
: Images::Circle(std::move(small)));
|
||||
_userpic.setDevicePixelRatio(cRetinaFactor());
|
||||
_userpicCustom = _userpicHasImage = true;
|
||||
_userpicUniqueKey = {};
|
||||
_result = std::move(image);
|
||||
|
||||
startNewPhotoShowing();
|
||||
|
|
|
@ -91,18 +91,25 @@ public:
|
|||
Role role,
|
||||
const style::UserpicButton &st);
|
||||
|
||||
void switchChangePhotoOverlay(bool enabled);
|
||||
enum class ChosenType {
|
||||
Set,
|
||||
Suggest,
|
||||
};
|
||||
struct ChosenImage {
|
||||
QImage image;
|
||||
ChosenType type = ChosenType::Set;
|
||||
};
|
||||
|
||||
// Role::OpenPhoto
|
||||
void switchChangePhotoOverlay(
|
||||
bool enabled,
|
||||
Fn<void(ChosenImage)> chosen);
|
||||
void showSavedMessagesOnSelf(bool enabled);
|
||||
|
||||
// Role::ChoosePhoto
|
||||
[[nodiscard]] rpl::producer<QImage> chosenImages() const {
|
||||
// Role::ChoosePhoto or Role::ChangePhoto
|
||||
[[nodiscard]] rpl::producer<ChosenImage> chosenImages() const {
|
||||
return _chosenImages.events();
|
||||
}
|
||||
|
||||
// Role::ChangePhoto
|
||||
[[nodiscard]] rpl::producer<> uploadPhotoRequests() const {
|
||||
return _uploadPhotoRequests.events();
|
||||
}
|
||||
[[nodiscard]] QImage takeResultImage() {
|
||||
return std::move(_result);
|
||||
}
|
||||
|
@ -150,7 +157,6 @@ private:
|
|||
void setClickHandlerByRole();
|
||||
void openPeerPhoto();
|
||||
void choosePhotoLocally();
|
||||
void changePhotoLocally(bool requestToUpload = false);
|
||||
|
||||
const style::UserpicButton &_st;
|
||||
::Window::SessionController *_controller = nullptr;
|
||||
|
@ -164,7 +170,6 @@ private:
|
|||
QPixmap _userpic, _oldUserpic;
|
||||
bool _userpicHasImage = false;
|
||||
bool _userpicCustom = false;
|
||||
bool _requestToUpload = false;
|
||||
InMemoryKey _userpicUniqueKey;
|
||||
Animations::Simple _a_appearance;
|
||||
QImage _result;
|
||||
|
@ -181,8 +186,7 @@ private:
|
|||
bool _changeOverlayEnabled = false;
|
||||
Animations::Simple _changeOverlayShown;
|
||||
|
||||
rpl::event_stream<QImage> _chosenImages;
|
||||
rpl::event_stream<> _uploadPhotoRequests;
|
||||
rpl::event_stream<ChosenImage> _chosenImages;
|
||||
|
||||
};
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue