diff --git a/Telegram/SourceFiles/info/profile/info_profile_actions.cpp b/Telegram/SourceFiles/info/profile/info_profile_actions.cpp index f0b21ead5..837d72517 100644 --- a/Telegram/SourceFiles/info/profile/info_profile_actions.cpp +++ b/Telegram/SourceFiles/info/profile/info_profile_actions.cpp @@ -25,6 +25,8 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "ui/wrap/padding_wrap.h" #include "ui/wrap/slide_wrap.h" #include "ui/widgets/shadow.h" +#include "ui/widgets/labels.h" +#include "ui/toast/toast.h" #include "boxes/abstract_box.h" #include "boxes/confirm_box.h" #include "boxes/peer_list_box.h" @@ -42,7 +44,9 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "window/window_peer_menu.h" #include "mainwidget.h" #include "auth_session.h" +#include "messenger.h" #include "apiwrap.h" +#include "application.h" #include "styles/style_info.h" #include "styles/style_boxes.h" @@ -180,37 +184,72 @@ object_ptr DetailsFiller::setupInfo() { auto addInfoLine = [&]( LangKey label, rpl::producer &&text, - bool selectByDoubleClick = false, const style::FlatLabel &textSt = st::infoLabeled) { - auto line = result->add(CreateTextWithLabel( + auto line = CreateTextWithLabel( result, Lang::Viewer(label) | WithEmptyEntities(), std::move(text), textSt, - st::infoProfileLabeledPadding, - selectByDoubleClick)); - tracker.track(line); - return line; + st::infoProfileLabeledPadding); + tracker.track(result->add(std::move(line.wrap))); + return line.text; }; auto addInfoOneLine = [&]( LangKey label, - rpl::producer &&text) { - addInfoLine( + rpl::producer &&text, + const QString &contextCopyText) { + auto result = addInfoLine( label, std::move(text), - true, st::infoLabeledOneLine); + result->setDoubleClickSelectsParagraph(true); + result->setContextCopyText(contextCopyText); + return result; }; if (auto user = _peer->asUser()) { - addInfoOneLine(lng_info_mobile_label, PhoneValue(user)); + addInfoOneLine( + lng_info_mobile_label, + PhoneValue(user), + lang(lng_profile_copy_phone)); if (user->botInfo) { addInfoLine(lng_info_about_label, AboutValue(user)); } else { addInfoLine(lng_info_bio_label, BioValue(user)); } - addInfoOneLine(lng_info_username_label, UsernameValue(user)); + addInfoOneLine( + lng_info_username_label, + UsernameValue(user), + lang(lng_context_copy_mention)); } else { - addInfoOneLine(lng_info_link_label, LinkValue(_peer)); + auto linkText = LinkValue(_peer) + | rpl::map([](const QString &link) { + auto result = TextWithEntities{ link, {} }; + if (!link.isEmpty()) { + auto remove = qstr("https://"); + if (result.text.startsWith(remove)) { + result.text.remove(0, remove.size()); + } + result.entities.push_back(EntityInText( + EntityInTextCustomUrl, + 0, + result.text.size(), + link)); + } + return result; + }); + auto link = addInfoOneLine( + lng_info_link_label, + std::move(linkText), + QString()); + link->setClickHandlerHook([peer = _peer](auto&&...) { + auto link = Messenger::Instance().createInternalLinkFull( + peer->userName()); + if (!link.isEmpty()) { + Application::clipboard()->setText(link); + Ui::Toast::Show(lang(lng_username_copied)); + } + return false; + }); addInfoLine(lng_info_about_label, AboutValue(_peer)); } result->add(object_ptr>( diff --git a/Telegram/SourceFiles/info/profile/info_profile_cover.cpp b/Telegram/SourceFiles/info/profile/info_profile_cover.cpp index f217be9a3..b7eb16caa 100644 --- a/Telegram/SourceFiles/info/profile/info_profile_cover.cpp +++ b/Telegram/SourceFiles/info/profile/info_profile_cover.cpp @@ -228,6 +228,7 @@ Cover::Cover(QWidget *parent, not_null peer) _peer->updateFull(); _name->setSelectable(true); + _name->setContextCopyText(lang(lng_profile_copy_fullname)); _status->setAttribute(Qt::WA_TransparentForMouseEvents); initUserpicButton(); diff --git a/Telegram/SourceFiles/info/profile/info_profile_text.cpp b/Telegram/SourceFiles/info/profile/info_profile_text.cpp index 58b260d3c..77360eb03 100644 --- a/Telegram/SourceFiles/info/profile/info_profile_text.cpp +++ b/Telegram/SourceFiles/info/profile/info_profile_text.cpp @@ -31,13 +31,12 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org namespace Info { namespace Profile { -object_ptr> CreateTextWithLabel( +TextWithLabel CreateTextWithLabel( QWidget *parent, rpl::producer &&label, rpl::producer &&text, const style::FlatLabel &textSt, - const style::margins &padding, - bool doubleClickSelects) { + const style::margins &padding) { auto result = object_ptr>( parent, object_ptr(parent), @@ -62,14 +61,13 @@ object_ptr> CreateTextWithLabel( std::move(nonEmptyText), textSt)); labeled->setSelectable(true); - labeled->setDoubleClickSelectsParagraph(doubleClickSelects); layout->add(Ui::CreateSkipWidget(layout, st::infoLabelSkip)); layout->add(object_ptr( layout, std::move(label), st::infoLabel)); result->finishAnimating(); - return result; + return { std::move(result), labeled }; } } // namespace Profile diff --git a/Telegram/SourceFiles/info/profile/info_profile_text.h b/Telegram/SourceFiles/info/profile/info_profile_text.h index 99d181adc..985eaa17d 100644 --- a/Telegram/SourceFiles/info/profile/info_profile_text.h +++ b/Telegram/SourceFiles/info/profile/info_profile_text.h @@ -28,6 +28,7 @@ struct FlatLabel; namespace Ui { class VerticalLayout; +class FlatLabel; template class SlideWrap; } // namespace Ui @@ -35,13 +36,17 @@ class SlideWrap; namespace Info { namespace Profile { -object_ptr> CreateTextWithLabel( +struct TextWithLabel { + object_ptr> wrap; + not_null text; +}; + +TextWithLabel CreateTextWithLabel( QWidget *parent, rpl::producer &&label, rpl::producer &&text, const style::FlatLabel &textSt, - const style::margins &padding, - bool doubleClickSelects); + const style::margins &padding); } // namespace Profile } // namespace Info diff --git a/Telegram/SourceFiles/info/profile/info_profile_values.cpp b/Telegram/SourceFiles/info/profile/info_profile_values.cpp index 5bbc677b3..e83708974 100644 --- a/Telegram/SourceFiles/info/profile/info_profile_values.cpp +++ b/Telegram/SourceFiles/info/profile/info_profile_values.cpp @@ -105,15 +105,14 @@ rpl::producer AboutValue( return rpl::single(TextWithEntities{}); } -rpl::producer LinkValue( +rpl::producer LinkValue( not_null peer) { return PlainUsernameValue(peer) | rpl::map([](QString &&username) { return username.isEmpty() ? QString() - : Messenger::Instance().createInternalLink(username); - }) - | WithEmptyEntities(); + : Messenger::Instance().createInternalLinkFull(username); + }); } rpl::producer NotificationsEnabledValue( diff --git a/Telegram/SourceFiles/info/profile/info_profile_values.h b/Telegram/SourceFiles/info/profile/info_profile_values.h index 79ead5e86..f127d12ca 100644 --- a/Telegram/SourceFiles/info/profile/info_profile_values.h +++ b/Telegram/SourceFiles/info/profile/info_profile_values.h @@ -59,7 +59,7 @@ rpl::producer UsernameValue( not_null user); rpl::producer AboutValue( not_null peer); -rpl::producer LinkValue( +rpl::producer LinkValue( not_null peer); rpl::producer NotificationsEnabledValue( not_null peer);