mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-15 21:57:10 +02:00
Update API scheme on layer 143 + transcribe.
This commit is contained in:
parent
3fac522bbc
commit
0b2a5a22ba
14 changed files with 421 additions and 29 deletions
|
@ -155,6 +155,8 @@ PRIVATE
|
|||
api/api_text_entities.h
|
||||
api/api_toggling_media.cpp
|
||||
api/api_toggling_media.h
|
||||
api/api_transcribes.cpp
|
||||
api/api_transcribes.h
|
||||
api/api_unread_things.cpp
|
||||
api/api_unread_things.h
|
||||
api/api_updates.cpp
|
||||
|
@ -690,6 +692,8 @@ PRIVATE
|
|||
history/view/history_view_service_message.h
|
||||
history/view/history_view_spoiler_click_handler.cpp
|
||||
history/view/history_view_spoiler_click_handler.h
|
||||
history/view/history_view_transcribe_button.cpp
|
||||
history/view/history_view_transcribe_button.h
|
||||
history/view/history_view_top_bar_widget.cpp
|
||||
history/view/history_view_top_bar_widget.h
|
||||
history/view/history_view_view_button.cpp
|
||||
|
|
|
@ -390,6 +390,7 @@ updateAttachMenuBots#17b7a20b = Update;
|
|||
updateWebViewResultSent#1592b79d query_id:long = Update;
|
||||
updateBotMenuButton#14b85813 bot_id:long button:BotMenuButton = Update;
|
||||
updateSavedRingtones#74d8be99 = Update;
|
||||
updateTranscribeAudio#88617090 flags:# final:flags.0?true transcription_id:long text:string = Update;
|
||||
|
||||
updates.state#a56c2a3e pts:int qts:int date:int seq:int unread_count:int = updates.State;
|
||||
|
||||
|
@ -1383,7 +1384,7 @@ inputInvoiceSlug#c326caef slug:string = InputInvoice;
|
|||
|
||||
payments.exportedInvoice#aed0cbd9 url:string = payments.ExportedInvoice;
|
||||
|
||||
messages.transcribedAudio#bfcd7e0a transcription_id:long text:string = messages.TranscribedAudio;
|
||||
messages.transcribedAudio#93752c52 flags:# pending:flags.0?true transcription_id:long text:string = messages.TranscribedAudio;
|
||||
|
||||
---functions---
|
||||
|
||||
|
@ -1790,6 +1791,7 @@ payments.clearSavedInfo#d83d70c1 flags:# credentials:flags.0?true info:flags.1?t
|
|||
payments.getBankCardData#2e79d779 number:string = payments.BankCardData;
|
||||
payments.exportInvoice#f91b065 invoice_media:InputMedia = payments.ExportedInvoice;
|
||||
payments.assignAppStoreTransaction#6299a12f transaction_id:string = Updates;
|
||||
payments.assignPlayMarketTransaction#4faa4aed purchase_token:string = Updates;
|
||||
|
||||
stickers.createStickerSet#9021ab67 flags:# masks:flags.0?true animated:flags.1?true videos:flags.4?true user_id:InputUser title:string short_name:string thumb:flags.2?InputDocument stickers:Vector<InputStickerSetItem> software:flags.3?string = messages.StickerSet;
|
||||
stickers.removeStickerFromSet#f7760f51 sticker:InputDocument = messages.StickerSet;
|
||||
|
|
97
Telegram/SourceFiles/api/api_transcribes.cpp
Normal file
97
Telegram/SourceFiles/api/api_transcribes.cpp
Normal file
|
@ -0,0 +1,97 @@
|
|||
/*
|
||||
This file is part of Telegram Desktop,
|
||||
the official desktop application for the Telegram messaging service.
|
||||
|
||||
For license and copyright information please follow this link:
|
||||
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
*/
|
||||
#include "api/api_transcribes.h"
|
||||
|
||||
#include "history/history_item.h"
|
||||
#include "history/history.h"
|
||||
#include "main/main_session.h"
|
||||
#include "data/data_session.h"
|
||||
#include "data/data_peer.h"
|
||||
#include "apiwrap.h"
|
||||
|
||||
namespace Api {
|
||||
|
||||
Transcribes::Transcribes(not_null<ApiWrap*> api)
|
||||
: _session(&api->session())
|
||||
, _api(&api->instance()) {
|
||||
}
|
||||
|
||||
void Transcribes::toggle(not_null<HistoryItem*> item) {
|
||||
const auto id = item->fullId();
|
||||
auto i = _map.find(id);
|
||||
if (i == _map.end()) {
|
||||
load(item);
|
||||
//_session->data().requestItemRepaint(item);
|
||||
_session->data().requestItemResize(item);
|
||||
} else if (!i->second.requestId) {
|
||||
i->second.shown = !i->second.shown;
|
||||
_session->data().requestItemResize(item);
|
||||
}
|
||||
}
|
||||
|
||||
const Transcribes::Entry &Transcribes::entry(
|
||||
not_null<HistoryItem*> item) const {
|
||||
static auto empty = Entry();
|
||||
const auto i = _map.find(item->fullId());
|
||||
return (i != _map.end()) ? i->second : empty;
|
||||
}
|
||||
|
||||
void Transcribes::apply(const MTPDupdateTranscribeAudio &update) {
|
||||
const auto id = update.vtranscription_id().v;
|
||||
const auto i = _ids.find(id);
|
||||
if (i == _ids.end()) {
|
||||
return;
|
||||
}
|
||||
const auto j = _map.find(i->second);
|
||||
if (j == _map.end()) {
|
||||
return;
|
||||
}
|
||||
const auto text = qs(update.vtext());
|
||||
j->second.result = text;
|
||||
j->second.pending = !update.is_final();
|
||||
if (const auto item = _session->data().message(i->second)) {
|
||||
_session->data().requestItemResize(item);
|
||||
}
|
||||
}
|
||||
|
||||
void Transcribes::load(not_null<HistoryItem*> item) {
|
||||
if (!item->isHistoryEntry() || item->isLocal()) {
|
||||
return;
|
||||
}
|
||||
const auto id = item->fullId();
|
||||
const auto requestId = _api.request(MTPmessages_TranscribeAudio(
|
||||
item->history()->peer->input,
|
||||
MTP_int(item->id)
|
||||
)).done([=](const MTPmessages_TranscribedAudio &result) {
|
||||
result.match([&](const MTPDmessages_transcribedAudio &data) {
|
||||
auto &entry = _map[id];
|
||||
entry.requestId = 0;
|
||||
entry.pending = data.is_pending();
|
||||
entry.result = qs(data.vtext());
|
||||
_ids.emplace(data.vtranscription_id().v, id);
|
||||
if (const auto item = _session->data().message(id)) {
|
||||
_session->data().requestItemResize(item);
|
||||
}
|
||||
});
|
||||
}).fail([=] {
|
||||
auto &entry = _map[id];
|
||||
entry.requestId = 0;
|
||||
entry.pending = false;
|
||||
entry.failed = true;
|
||||
if (const auto item = _session->data().message(id)) {
|
||||
_session->data().requestItemResize(item);
|
||||
}
|
||||
}).send();
|
||||
auto &entry = _map.emplace(id).first->second;
|
||||
entry.requestId = requestId;
|
||||
entry.shown = true;
|
||||
entry.failed = false;
|
||||
entry.pending = false;
|
||||
}
|
||||
|
||||
} // namespace Api
|
48
Telegram/SourceFiles/api/api_transcribes.h
Normal file
48
Telegram/SourceFiles/api/api_transcribes.h
Normal file
|
@ -0,0 +1,48 @@
|
|||
/*
|
||||
This file is part of Telegram Desktop,
|
||||
the official desktop application for the Telegram messaging service.
|
||||
|
||||
For license and copyright information please follow this link:
|
||||
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "mtproto/sender.h"
|
||||
|
||||
class ApiWrap;
|
||||
|
||||
namespace Main {
|
||||
class Session;
|
||||
} // namespace Main
|
||||
|
||||
namespace Api {
|
||||
|
||||
class Transcribes final {
|
||||
public:
|
||||
explicit Transcribes(not_null<ApiWrap*> api);
|
||||
|
||||
struct Entry {
|
||||
QString result;
|
||||
bool shown = false;
|
||||
bool failed = false;
|
||||
bool pending = false;
|
||||
mtpRequestId requestId = 0;
|
||||
};
|
||||
|
||||
void toggle(not_null<HistoryItem*> item);
|
||||
[[nodiscard]] const Entry &entry(not_null<HistoryItem*> item) const;
|
||||
|
||||
void apply(const MTPDupdateTranscribeAudio &update);
|
||||
|
||||
private:
|
||||
void load(not_null<HistoryItem*> item);
|
||||
|
||||
const not_null<Main::Session*> _session;
|
||||
MTP::Sender _api;
|
||||
|
||||
base::flat_map<FullMsgId, Entry> _map;
|
||||
base::flat_map<uint64, FullMsgId> _ids;
|
||||
|
||||
};
|
||||
|
||||
} // namespace Api
|
|
@ -13,6 +13,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "api/api_text_entities.h"
|
||||
#include "api/api_user_privacy.h"
|
||||
#include "api/api_unread_things.h"
|
||||
#include "api/api_transcribes.h"
|
||||
#include "main/main_session.h"
|
||||
#include "main/main_account.h"
|
||||
#include "mtproto/mtp_instance.h"
|
||||
|
@ -2387,6 +2388,11 @@ void Updates::feedUpdate(const MTPUpdate &update) {
|
|||
session().api().ringtones().applyUpdate();
|
||||
} break;
|
||||
|
||||
case mtpc_updateTranscribeAudio: {
|
||||
const auto &data = update.c_updateTranscribeAudio();
|
||||
_session->api().transcribes().apply(data);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -28,6 +28,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "api/api_confirm_phone.h"
|
||||
#include "api/api_unread_things.h"
|
||||
#include "api/api_ringtones.h"
|
||||
#include "api/api_transcribes.h"
|
||||
#include "data/notify/data_notify_settings.h"
|
||||
#include "data/stickers/data_stickers.h"
|
||||
#include "data/data_drafts.h"
|
||||
|
@ -145,7 +146,8 @@ ApiWrap::ApiWrap(not_null<Main::Session*> session)
|
|||
, _polls(std::make_unique<Api::Polls>(this))
|
||||
, _chatParticipants(std::make_unique<Api::ChatParticipants>(this))
|
||||
, _unreadThings(std::make_unique<Api::UnreadThings>(this))
|
||||
, _ringtones(std::make_unique<Api::Ringtones>(this)) {
|
||||
, _ringtones(std::make_unique<Api::Ringtones>(this))
|
||||
, _transcribes(std::make_unique<Api::Transcribes>(this)) {
|
||||
crl::on_main(session, [=] {
|
||||
// You can't use _session->lifetime() in the constructor,
|
||||
// only queued, because it is not constructed yet.
|
||||
|
@ -4105,3 +4107,7 @@ Api::UnreadThings &ApiWrap::unreadThings() {
|
|||
Api::Ringtones &ApiWrap::ringtones() {
|
||||
return *_ringtones;
|
||||
}
|
||||
|
||||
Api::Transcribes &ApiWrap::transcribes() {
|
||||
return *_transcribes;
|
||||
}
|
||||
|
|
|
@ -70,6 +70,7 @@ class Polls;
|
|||
class ChatParticipants;
|
||||
class UnreadThings;
|
||||
class Ringtones;
|
||||
class Transcribes;
|
||||
|
||||
namespace details {
|
||||
|
||||
|
@ -361,6 +362,7 @@ public:
|
|||
[[nodiscard]] Api::ChatParticipants &chatParticipants();
|
||||
[[nodiscard]] Api::UnreadThings &unreadThings();
|
||||
[[nodiscard]] Api::Ringtones &ringtones();
|
||||
[[nodiscard]] Api::Transcribes &transcribes();
|
||||
|
||||
void updatePrivacyLastSeens();
|
||||
|
||||
|
@ -644,6 +646,7 @@ private:
|
|||
const std::unique_ptr<Api::ChatParticipants> _chatParticipants;
|
||||
const std::unique_ptr<Api::UnreadThings> _unreadThings;
|
||||
const std::unique_ptr<Api::Ringtones> _ringtones;
|
||||
const std::unique_ptr<Api::Transcribes> _transcribes;
|
||||
|
||||
mtpRequestId _wallPaperRequestId = 0;
|
||||
QString _wallPaperSlug;
|
||||
|
|
|
@ -63,6 +63,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "data/data_streaming.h"
|
||||
#include "data/data_media_rotation.h"
|
||||
#include "data/data_histories.h"
|
||||
#include "data/data_peer_values.h"
|
||||
#include "base/platform/base_platform_info.h"
|
||||
#include "base/unixtime.h"
|
||||
#include "base/call_delayed.h"
|
||||
|
@ -274,6 +275,20 @@ Session::Session(not_null<Main::Session*> session)
|
|||
session->saveSettingsDelayed();
|
||||
}
|
||||
}, _lifetime);
|
||||
|
||||
crl::on_main(_session, [=] {
|
||||
AmPremiumValue(
|
||||
_session
|
||||
) | rpl::start_with_next([=] {
|
||||
for (const auto &[document, items] : _documentItems) {
|
||||
if (document->isVoiceMessage()) {
|
||||
for (const auto &item : items) {
|
||||
requestItemResize(item);
|
||||
}
|
||||
}
|
||||
}
|
||||
}, _lifetime);
|
||||
});
|
||||
}
|
||||
|
||||
void Session::clear() {
|
||||
|
@ -1175,7 +1190,6 @@ void Session::setupPeerNameViewer() {
|
|||
const auto &oldLetters = update.oldFirstLetters;
|
||||
_contactsNoChatsList.peerNameChanged(peer, oldLetters);
|
||||
_contactsList.peerNameChanged(peer, oldLetters);
|
||||
|
||||
}, _lifetime);
|
||||
}
|
||||
|
||||
|
|
|
@ -937,3 +937,23 @@ void HistoryDocumentVoice::stopSeeking() {
|
|||
_seeking = false;
|
||||
Media::Player::instance()->cancelSeeking(AudioMsgId::Type::Voice);
|
||||
}
|
||||
|
||||
bool HistoryDocumentVoice::seeking() const {
|
||||
return _seeking;
|
||||
}
|
||||
|
||||
float64 HistoryDocumentVoice::seekingStart() const {
|
||||
return _seekingStart / kFloatToIntMultiplier;
|
||||
}
|
||||
|
||||
void HistoryDocumentVoice::setSeekingStart(float64 seekingStart) const {
|
||||
_seekingStart = qRound(seekingStart * kFloatToIntMultiplier);
|
||||
}
|
||||
|
||||
float64 HistoryDocumentVoice::seekingCurrent() const {
|
||||
return _seekingCurrent / kFloatToIntMultiplier;
|
||||
}
|
||||
|
||||
void HistoryDocumentVoice::setSeekingCurrent(float64 seekingCurrent) {
|
||||
_seekingCurrent = qRound(seekingCurrent * kFloatToIntMultiplier);
|
||||
}
|
||||
|
|
|
@ -27,6 +27,7 @@ class Session;
|
|||
namespace HistoryView {
|
||||
class Element;
|
||||
class Document;
|
||||
class TranscribeButton;
|
||||
} // namespace HistoryView
|
||||
|
||||
struct HistoryMessageVia : public RuntimeComponent<HistoryMessageVia, HistoryItem> {
|
||||
|
@ -444,23 +445,16 @@ public:
|
|||
std::shared_ptr<VoiceSeekClickHandler> _seekl;
|
||||
mutable int _lastDurationMs = 0;
|
||||
|
||||
bool seeking() const {
|
||||
return _seeking;
|
||||
}
|
||||
[[nodiscard]] bool seeking() const;
|
||||
void startSeeking();
|
||||
void stopSeeking();
|
||||
float64 seekingStart() const {
|
||||
return _seekingStart / kFloatToIntMultiplier;
|
||||
}
|
||||
void setSeekingStart(float64 seekingStart) const {
|
||||
_seekingStart = qRound(seekingStart * kFloatToIntMultiplier);
|
||||
}
|
||||
float64 seekingCurrent() const {
|
||||
return _seekingCurrent / kFloatToIntMultiplier;
|
||||
}
|
||||
void setSeekingCurrent(float64 seekingCurrent) {
|
||||
_seekingCurrent = qRound(seekingCurrent * kFloatToIntMultiplier);
|
||||
}
|
||||
[[nodiscard]] float64 seekingStart() const;
|
||||
void setSeekingStart(float64 seekingStart) const;
|
||||
[[nodiscard]] float64 seekingCurrent() const;
|
||||
void setSeekingCurrent(float64 seekingCurrent);
|
||||
|
||||
std::unique_ptr<HistoryView::TranscribeButton> transcribe;
|
||||
Ui::Text::String transcribeText;
|
||||
|
||||
private:
|
||||
bool _seeking = false;
|
||||
|
|
|
@ -0,0 +1,58 @@
|
|||
/*
|
||||
This file is part of Telegram Desktop,
|
||||
the official desktop application for the Telegram messaging service.
|
||||
|
||||
For license and copyright information please follow this link:
|
||||
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
*/
|
||||
#include "history/view/history_view_transcribe_button.h"
|
||||
|
||||
#include "history/history.h"
|
||||
#include "history/history_item.h"
|
||||
#include "data/data_session.h"
|
||||
#include "main/main_session.h"
|
||||
#include "ui/chat/chat_style.h"
|
||||
#include "ui/click_handler.h"
|
||||
#include "api/api_transcribes.h"
|
||||
#include "apiwrap.h"
|
||||
#include "styles/style_chat.h"
|
||||
|
||||
namespace HistoryView {
|
||||
|
||||
TranscribeButton::TranscribeButton(not_null<HistoryItem*> item)
|
||||
: _item(item) {
|
||||
}
|
||||
|
||||
QSize TranscribeButton::size() const {
|
||||
return QSize(st::historyTranscribeSize, st::historyTranscribeSize);
|
||||
}
|
||||
|
||||
void TranscribeButton::paint(
|
||||
QPainter &p,
|
||||
int x,
|
||||
int y,
|
||||
const PaintContext &context) {
|
||||
auto hq = PainterHighQualityEnabler(p);
|
||||
const auto stm = context.messageStyle();
|
||||
p.setBrush(stm->msgWaveformInactive);
|
||||
const auto radius = size().width() / 4;
|
||||
p.drawRoundedRect(QRect{ QPoint(x, y), size() }, radius, radius);
|
||||
}
|
||||
|
||||
ClickHandlerPtr TranscribeButton::link() {
|
||||
if (!_item->isHistoryEntry() || _item->isLocal()) {
|
||||
return nullptr;
|
||||
} else if (_link) {
|
||||
return _link;
|
||||
}
|
||||
const auto session = &_item->history()->session();
|
||||
const auto id = _item->fullId();
|
||||
_link = std::make_shared<LambdaClickHandler>([=] {
|
||||
if (const auto item = session->data().message(id)) {
|
||||
session->api().transcribes().toggle(item);
|
||||
}
|
||||
});
|
||||
return _link;
|
||||
}
|
||||
|
||||
} // namespace HistoryView
|
|
@ -0,0 +1,38 @@
|
|||
/*
|
||||
This file is part of Telegram Desktop,
|
||||
the official desktop application for the Telegram messaging service.
|
||||
|
||||
For license and copyright information please follow this link:
|
||||
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
namespace Ui {
|
||||
struct ChatPaintContext;
|
||||
} // namespace Ui
|
||||
|
||||
namespace HistoryView {
|
||||
|
||||
using PaintContext = Ui::ChatPaintContext;
|
||||
|
||||
class TranscribeButton final {
|
||||
public:
|
||||
explicit TranscribeButton(not_null<HistoryItem*> item);
|
||||
|
||||
[[nodiscard]] QSize size() const;
|
||||
|
||||
void paint(QPainter &p, int x, int y, const PaintContext &context);
|
||||
|
||||
[[nodiscard]] ClickHandlerPtr link();
|
||||
|
||||
private:
|
||||
const not_null<HistoryItem*> _item;
|
||||
|
||||
ClickHandlerPtr _link;
|
||||
QString _text;
|
||||
bool _loaded = false;
|
||||
bool _loading = false;
|
||||
|
||||
};
|
||||
|
||||
} // namespace HistoryView
|
|
@ -9,12 +9,14 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
|
||||
#include "lang/lang_keys.h"
|
||||
#include "storage/localstorage.h"
|
||||
#include "main/main_session.h"
|
||||
#include "media/audio/media_audio.h"
|
||||
#include "media/player/media_player_instance.h"
|
||||
#include "history/history_item_components.h"
|
||||
#include "history/history.h"
|
||||
#include "history/view/history_view_element.h"
|
||||
#include "history/view/history_view_cursor_state.h"
|
||||
#include "history/view/history_view_transcribe_button.h"
|
||||
#include "history/view/media/history_view_media_common.h"
|
||||
#include "ui/image/image.h"
|
||||
#include "ui/text/format_values.h"
|
||||
|
@ -30,6 +32,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "data/data_media_types.h"
|
||||
#include "data/data_file_click_handler.h"
|
||||
#include "data/data_file_origin.h"
|
||||
#include "api/api_transcribes.h"
|
||||
#include "apiwrap.h"
|
||||
#include "styles/style_chat.h"
|
||||
|
||||
namespace HistoryView {
|
||||
|
@ -226,6 +230,41 @@ void Document::fillNamedFromData(HistoryDocumentNamed *named) {
|
|||
|
||||
QSize Document::countOptimalSize() {
|
||||
auto captioned = Get<HistoryDocumentCaptioned>();
|
||||
auto hasTranscribe = false;
|
||||
const auto voice = Get<HistoryDocumentVoice>();
|
||||
if (voice) {
|
||||
const auto session = &_realParent->history()->session();
|
||||
if (!session->premium()) {
|
||||
voice->transcribe = nullptr;
|
||||
voice->transcribeText = {};
|
||||
} else {
|
||||
if (!voice->transcribe) {
|
||||
voice->transcribe = std::make_unique<TranscribeButton>(
|
||||
_realParent);
|
||||
}
|
||||
const auto &entry = session->api().transcribes().entry(
|
||||
_realParent);
|
||||
auto text = entry.requestId
|
||||
? "Transcribing..."
|
||||
: entry.failed
|
||||
? "Transcribing Failed."
|
||||
: entry.shown
|
||||
? ((entry.pending ? "Still Transcribing...\n" : "")
|
||||
+ entry.result)
|
||||
: QString();
|
||||
if (text.isEmpty()) {
|
||||
voice->transcribeText = {};
|
||||
} else {
|
||||
const auto minResizeWidth = st::minPhotoSize
|
||||
- st::msgPadding.left()
|
||||
- st::msgPadding.right();
|
||||
voice->transcribeText = Ui::Text::String(minResizeWidth);
|
||||
voice->transcribeText.setText(st::messageTextStyle, text);
|
||||
hasTranscribe = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (_parent->media() != this && !_realParent->groupId()) {
|
||||
if (captioned) {
|
||||
RemoveComponents(HistoryDocumentCaptioned::Bit());
|
||||
|
@ -236,6 +275,7 @@ QSize Document::countOptimalSize() {
|
|||
_parent->skipBlockWidth(),
|
||||
_parent->skipBlockHeight());
|
||||
}
|
||||
|
||||
auto thumbed = Get<HistoryDocumentThumbed>();
|
||||
const auto &st = thumbed ? st::msgFileThumbLayout : st::msgFileLayout;
|
||||
if (thumbed) {
|
||||
|
@ -264,15 +304,30 @@ QSize Document::countOptimalSize() {
|
|||
accumulate_max(maxWidth, tleft + named->_namew + tright);
|
||||
accumulate_min(maxWidth, st::msgMaxWidth);
|
||||
}
|
||||
if (voice && voice->transcribe) {
|
||||
maxWidth += st::historyTranscribeSkip
|
||||
+ voice->transcribe->size().width();
|
||||
}
|
||||
|
||||
auto minHeight = st.padding.top() + st.thumbSize + st.padding.bottom();
|
||||
if (!captioned && _parent->bottomInfoIsWide()) {
|
||||
if (!captioned && !hasTranscribe && _parent->bottomInfoIsWide()) {
|
||||
minHeight += st::msgDateFont->height - st::msgDateDelta.y();
|
||||
}
|
||||
if (!isBubbleTop()) {
|
||||
minHeight -= st::msgFileTopMinus;
|
||||
}
|
||||
|
||||
if (hasTranscribe) {
|
||||
auto captionw = maxWidth
|
||||
- st::msgPadding.left()
|
||||
- st::msgPadding.right();
|
||||
minHeight += voice->transcribeText.countHeight(captionw);
|
||||
if (captioned) {
|
||||
minHeight += st::mediaCaptionSkip;
|
||||
} else if (isBubbleBottom()) {
|
||||
minHeight += st::msgPadding.bottom();
|
||||
}
|
||||
}
|
||||
if (captioned) {
|
||||
auto captionw = maxWidth
|
||||
- st::msgPadding.left()
|
||||
|
@ -287,7 +342,9 @@ QSize Document::countOptimalSize() {
|
|||
|
||||
QSize Document::countCurrentSize(int newWidth) {
|
||||
const auto captioned = Get<HistoryDocumentCaptioned>();
|
||||
if (!captioned) {
|
||||
const auto voice = Get<HistoryDocumentVoice>();
|
||||
const auto hasTranscribe = voice && !voice->transcribeText.isEmpty();
|
||||
if (!captioned && !hasTranscribe) {
|
||||
return File::countCurrentSize(newWidth);
|
||||
}
|
||||
|
||||
|
@ -299,9 +356,19 @@ QSize Document::countCurrentSize(int newWidth) {
|
|||
newHeight -= st::msgFileTopMinus;
|
||||
}
|
||||
auto captionw = newWidth - st::msgPadding.left() - st::msgPadding.right();
|
||||
newHeight += captioned->_caption.countHeight(captionw);
|
||||
if (isBubbleBottom()) {
|
||||
newHeight += st::msgPadding.bottom();
|
||||
if (hasTranscribe) {
|
||||
newHeight += voice->transcribeText.countHeight(captionw);
|
||||
if (captioned) {
|
||||
newHeight += st::mediaCaptionSkip;
|
||||
} else if (isBubbleBottom()) {
|
||||
newHeight += st::msgPadding.bottom();
|
||||
}
|
||||
}
|
||||
if (captioned) {
|
||||
newHeight += captioned->_caption.countHeight(captionw);
|
||||
if (isBubbleBottom()) {
|
||||
newHeight += st::msgPadding.bottom();
|
||||
}
|
||||
}
|
||||
|
||||
return { newWidth, newHeight };
|
||||
|
@ -498,7 +565,8 @@ void Document::draw(
|
|||
auto statuswidth = namewidth;
|
||||
|
||||
auto voiceStatusOverride = QString();
|
||||
if (const auto voice = Get<HistoryDocumentVoice>()) {
|
||||
const auto voice = Get<HistoryDocumentVoice>();
|
||||
if (voice) {
|
||||
ensureDataMediaCreated();
|
||||
|
||||
if (const auto voiceData = _data->voice()) {
|
||||
|
@ -527,9 +595,19 @@ void Document::draw(
|
|||
base::SafeRound(progress * voice->_lastDurationMs) / 1000,
|
||||
voice->_lastDurationMs / 1000);
|
||||
}
|
||||
|
||||
if (voice->transcribe) {
|
||||
const auto size = voice->transcribe->size();
|
||||
namewidth -= st::historyTranscribeSkip + size.width();
|
||||
const auto x = nameleft + namewidth + st::historyTranscribeSkip;
|
||||
const auto y = st.padding.top()
|
||||
- topMinus
|
||||
+ st::msgWaveformMax
|
||||
- size.height();
|
||||
voice->transcribe->paint(p, x, y, context);
|
||||
}
|
||||
p.save();
|
||||
p.translate(nameleft, st.padding.top() - topMinus);
|
||||
|
||||
PaintWaveform(p,
|
||||
context,
|
||||
_data->voice(),
|
||||
|
@ -564,9 +642,15 @@ void Document::draw(
|
|||
}
|
||||
}
|
||||
|
||||
auto captiontop = bottom;
|
||||
if (voice && !voice->transcribeText.isEmpty()) {
|
||||
p.setPen(stm->historyTextFg);
|
||||
voice->transcribeText.draw(p, st::msgPadding.left(), bottom, captionw, style::al_left, 0, -1, context.selection);
|
||||
captiontop += voice->transcribeText.countHeight(captionw) + st::mediaCaptionSkip;
|
||||
}
|
||||
if (auto captioned = Get<HistoryDocumentCaptioned>()) {
|
||||
p.setPen(stm->historyTextFg);
|
||||
captioned->_caption.draw(p, st::msgPadding.left(), bottom, captionw, style::al_left, 0, -1, context.selection);
|
||||
captioned->_caption.draw(p, st::msgPadding.left(), captiontop, captionw, style::al_left, 0, -1, context.selection);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -745,9 +829,23 @@ TextState Document::textState(
|
|||
}
|
||||
}
|
||||
|
||||
if (const auto voice = Get<HistoryDocumentVoice>()) {
|
||||
auto namewidth = width - nameleft - nameright;
|
||||
const auto voice = Get<HistoryDocumentVoice>();
|
||||
auto namewidth = width - nameleft - nameright;
|
||||
if (voice) {
|
||||
auto waveformbottom = st.padding.top() - topMinus + st::msgWaveformMax + st::msgWaveformMin;
|
||||
if (voice->transcribe) {
|
||||
const auto size = voice->transcribe->size();
|
||||
namewidth -= st::historyTranscribeSkip + size.width();
|
||||
const auto x = nameleft + namewidth + st::historyTranscribeSkip;
|
||||
const auto y = st.padding.top()
|
||||
- topMinus
|
||||
+ st::msgWaveformMax
|
||||
- size.height();
|
||||
if (QRect(QPoint(x, y), size).contains(point)) {
|
||||
result.link = voice->transcribe->link();
|
||||
return result;
|
||||
}
|
||||
}
|
||||
if (QRect(nameleft, nametop, namewidth, waveformbottom - nametop).contains(point)) {
|
||||
const auto state = ::Media::Player::instance()->getState(AudioMsgId::Type::Voice);
|
||||
if (state.id == AudioMsgId(_data, _realParent->fullId(), state.id.externalPlayId())
|
||||
|
@ -776,7 +874,8 @@ TextState Document::textState(
|
|||
painth -= st::msgPadding.bottom();
|
||||
}
|
||||
}
|
||||
if (QRect(0, 0, width, painth).contains(point)
|
||||
const auto till = voice ? (nameleft + namewidth) : width;
|
||||
if (QRect(0, 0, till, painth).contains(point)
|
||||
&& (!_data->loading() || downloadInCorner())
|
||||
&& !_data->uploading()
|
||||
&& !_data->isNull()) {
|
||||
|
|
|
@ -655,6 +655,9 @@ msgWaveformSkip: 1px;
|
|||
msgWaveformMin: 2px;
|
||||
msgWaveformMax: 20px;
|
||||
|
||||
historyTranscribeSkip: 10px;
|
||||
historyTranscribeSize: 24px;
|
||||
|
||||
historyVideoMessageMute: icon {{ "volume_mute", historyFileThumbIconFg }};
|
||||
historyVideoMessageMuteSelected: icon {{ "volume_mute", historyFileThumbIconFgSelected }};
|
||||
historyVideoMessageMuteSize: 25px;
|
||||
|
|
Loading…
Add table
Reference in a new issue