media_player_widget.h 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165
  1. /*
  2. This file is part of Telegram Desktop,
  3. the official desktop application for the Telegram messaging service.
  4. For license and copyright information please follow this link:
  5. https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
  6. */
  7. #pragma once
  8. #include "data/data_audio_msg_id.h"
  9. #include "ui/rp_widget.h"
  10. #include "base/object_ptr.h"
  11. class AudioMsgId;
  12. namespace Ui {
  13. class FlatLabel;
  14. class LabelSimple;
  15. class IconButton;
  16. class PlainShadow;
  17. class FilledSlider;
  18. template <typename Widget>
  19. class FadeWrap;
  20. } // namespace Ui
  21. namespace Media {
  22. enum class OrderMode;
  23. } // namespace Media
  24. namespace Media::View {
  25. class PlaybackProgress;
  26. } // namespace Media::View
  27. namespace Window {
  28. class SessionController;
  29. } // namespace Window
  30. namespace Media::Player {
  31. class Dropdown;
  32. class SpeedButton;
  33. class OrderController;
  34. class SpeedController;
  35. struct TrackState;
  36. class Widget final : public Ui::RpWidget {
  37. public:
  38. Widget(
  39. QWidget *parent,
  40. not_null<Ui::RpWidget*> dropdownsParent,
  41. not_null<Window::SessionController*> controller);
  42. ~Widget();
  43. void setCloseCallback(Fn<void()> callback);
  44. void setShowItemCallback(Fn<void(not_null<const HistoryItem*>)> callback);
  45. void stopAndClose();
  46. void setShadowGeometryToLeft(int x, int y, int w, int h);
  47. void hideShadowAndDropdowns();
  48. void showShadowAndDropdowns();
  49. void updateDropdownsGeometry();
  50. void raiseDropdowns();
  51. [[nodiscard]] rpl::producer<bool> togglePlaylistRequests() const {
  52. return _togglePlaylistRequests.events();
  53. }
  54. private:
  55. void resizeEvent(QResizeEvent *e) override;
  56. void paintEvent(QPaintEvent *e) override;
  57. void enterEventHook(QEnterEvent *e) override;
  58. void leaveEventHook(QEvent *e) override;
  59. void mouseMoveEvent(QMouseEvent *e) override;
  60. void mousePressEvent(QMouseEvent *e) override;
  61. void mouseReleaseEvent(QMouseEvent *e) override;
  62. [[nodiscard]] not_null<Ui::RpWidget*> rightControls();
  63. void setupRightControls();
  64. void handleSeekProgress(float64 progress);
  65. void handleSeekFinished(float64 progress);
  66. [[nodiscard]] int getNameLeft() const;
  67. [[nodiscard]] int getNameRight() const;
  68. [[nodiscard]] int getTimeRight() const;
  69. void updateOverLabelsState(QPoint pos);
  70. void updateOverLabelsState(bool over);
  71. void hidePlaylistOn(not_null<Ui::RpWidget*> widget);
  72. void updatePlayPrevNextPositions();
  73. void updateLabelsGeometry();
  74. void updateRepeatToggleIcon();
  75. void updateControlsVisibility();
  76. void updateControlsGeometry();
  77. void updateControlsWrapGeometry();
  78. void updateControlsWrapVisibility();
  79. void createPrevNextButtons();
  80. void destroyPrevNextButtons();
  81. bool hasPlaybackSpeedControl() const;
  82. void updateVolumeToggleIcon();
  83. void checkForTypeChange();
  84. void setType(AudioMsgId::Type type);
  85. void handleSongUpdate(const TrackState &state);
  86. void handleSongChange();
  87. void handlePlaylistUpdate();
  88. void updateTimeText(const TrackState &state);
  89. void updateTimeLabel();
  90. void markOver(bool over);
  91. void saveOrder(OrderMode mode);
  92. [[nodiscard]] float64 speedLookup(bool lastNonDefault) const;
  93. void saveSpeed(float64 speed);
  94. const not_null<Window::SessionController*> _controller;
  95. const not_null<Ui::RpWidget*> _orderMenuParent;
  96. crl::time _seekPositionMs = -1;
  97. crl::time _lastDurationMs = 0;
  98. QString _time;
  99. // We display all the controls according to _type.
  100. // We switch to Type::Voice if a voice/video message is played.
  101. // We switch to Type::Song only if _voiceIsActive == false.
  102. // We change _voiceIsActive to false only manually or from tracksFinished().
  103. AudioMsgId::Type _type = AudioMsgId::Type::Unknown;
  104. AudioMsgId _lastSongId;
  105. bool _lastSongFromAnotherSession = false;
  106. bool _voiceIsActive = false;
  107. Fn<void()> _closeCallback;
  108. Fn<void(not_null<const HistoryItem*>)> _showItemCallback;
  109. bool _labelsOver = false;
  110. bool _labelsDown = false;
  111. rpl::event_stream<bool> _togglePlaylistRequests;
  112. bool _narrow = false;
  113. bool _over = false;
  114. bool _wontBeOver = false;
  115. bool _volumeHidden = false;
  116. object_ptr<Ui::FlatLabel> _nameLabel;
  117. object_ptr<Ui::FadeWrap<Ui::RpWidget>> _rightControls;
  118. object_ptr<Ui::LabelSimple> _timeLabel;
  119. object_ptr<Ui::IconButton> _previousTrack = { nullptr };
  120. object_ptr<Ui::IconButton> _playPause;
  121. object_ptr<Ui::IconButton> _nextTrack = { nullptr };
  122. object_ptr<Ui::IconButton> _volumeToggle;
  123. object_ptr<Ui::IconButton> _repeatToggle;
  124. object_ptr<Ui::IconButton> _orderToggle;
  125. object_ptr<SpeedButton> _speedToggle;
  126. object_ptr<Ui::IconButton> _close;
  127. object_ptr<Ui::PlainShadow> _shadow = { nullptr };
  128. object_ptr<Ui::FilledSlider> _playbackSlider;
  129. base::unique_qptr<Dropdown> _volume;
  130. std::unique_ptr<View::PlaybackProgress> _playbackProgress;
  131. std::unique_ptr<OrderController> _orderController;
  132. std::unique_ptr<SpeedController> _speedController;
  133. rpl::lifetime _playlistChangesLifetime;
  134. };
  135. } // namespace Media::Player