rate_call_box.cpp 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149
  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. #include "ui/boxes/rate_call_box.h"
  8. #include "lang/lang_keys.h"
  9. #include "ui/widgets/buttons.h"
  10. #include "ui/widgets/fields/input_field.h"
  11. #include "styles/style_layers.h"
  12. #include "styles/style_calls.h"
  13. namespace Ui {
  14. namespace {
  15. constexpr auto kMaxRating = 5;
  16. constexpr auto kRateCallCommentLengthMax = 200;
  17. } // namespace
  18. RateCallBox::RateCallBox(QWidget*, InputSubmitSettings sendWay)
  19. : _sendWay(sendWay) {
  20. }
  21. void RateCallBox::prepare() {
  22. setTitle(tr::lng_call_rate_label());
  23. addButton(tr::lng_cancel(), [=] { closeBox(); });
  24. for (auto i = 0; i < kMaxRating; ++i) {
  25. _stars.emplace_back(this, st::callRatingStar);
  26. _stars.back()->setClickedCallback([this, value = i + 1] {
  27. ratingChanged(value);
  28. });
  29. _stars.back()->show();
  30. }
  31. updateMaxHeight();
  32. }
  33. void RateCallBox::resizeEvent(QResizeEvent *e) {
  34. BoxContent::resizeEvent(e);
  35. const auto starsWidth = (_stars.size() * st::callRatingStar.width);
  36. auto starLeft = (width() - starsWidth) / 2;
  37. const auto starTop = st::callRatingStarTop;
  38. for (auto &star : _stars) {
  39. star->moveToLeft(starLeft, starTop);
  40. starLeft += star->width();
  41. }
  42. if (_comment) {
  43. _comment->moveToLeft(
  44. st::callRatingPadding.left(),
  45. _stars.back()->bottomNoMargins() + st::callRatingCommentTop);
  46. }
  47. }
  48. void RateCallBox::ratingChanged(int value) {
  49. Expects(value > 0 && value <= kMaxRating);
  50. if (!_rating) {
  51. clearButtons();
  52. addButton(tr::lng_send_button(), [=] { send(); });
  53. addButton(tr::lng_cancel(), [=] { closeBox(); });
  54. }
  55. _rating = value;
  56. for (auto i = 0; i < kMaxRating; ++i) {
  57. _stars[i]->setIconOverride((i < value)
  58. ? &st::callRatingStarFilled
  59. : nullptr);
  60. _stars[i]->setRippleColorOverride((i < value)
  61. ? &st::lightButtonBgOver
  62. : nullptr);
  63. }
  64. if (value < kMaxRating) {
  65. if (!_comment) {
  66. _comment.create(
  67. this,
  68. st::callRatingComment,
  69. Ui::InputField::Mode::MultiLine,
  70. tr::lng_call_rate_comment());
  71. _comment->show();
  72. _comment->setSubmitSettings(_sendWay);
  73. _comment->setMaxLength(kRateCallCommentLengthMax);
  74. _comment->resize(
  75. width()
  76. - st::callRatingPadding.left()
  77. - st::callRatingPadding.right(),
  78. _comment->height());
  79. updateMaxHeight();
  80. _comment->heightChanges(
  81. ) | rpl::start_with_next([=] {
  82. commentResized();
  83. }, _comment->lifetime());
  84. _comment->submits(
  85. ) | rpl::start_with_next([=] { send(); }, _comment->lifetime());
  86. _comment->cancelled(
  87. ) | rpl::start_with_next([=] {
  88. closeBox();
  89. }, _comment->lifetime());
  90. }
  91. _comment->setFocusFast();
  92. } else if (_comment) {
  93. _comment.destroy();
  94. updateMaxHeight();
  95. }
  96. }
  97. void RateCallBox::setInnerFocus() {
  98. if (_comment) {
  99. _comment->setFocusFast();
  100. } else {
  101. BoxContent::setInnerFocus();
  102. }
  103. }
  104. void RateCallBox::commentResized() {
  105. updateMaxHeight();
  106. update();
  107. }
  108. void RateCallBox::send() {
  109. Expects(_rating > 0 && _rating <= kMaxRating);
  110. _sends.fire({
  111. .rating = _rating,
  112. .comment = _comment ? _comment->getLastText().trimmed() : QString(),
  113. });
  114. }
  115. void RateCallBox::updateMaxHeight() {
  116. auto newHeight = st::callRatingPadding.top()
  117. + st::callRatingStarTop
  118. + _stars.back()->heightNoMargins()
  119. + st::callRatingPadding.bottom();
  120. if (_comment) {
  121. newHeight += st::callRatingCommentTop + _comment->height();
  122. }
  123. setDimensions(st::boxWideWidth, newHeight);
  124. }
  125. rpl::producer<RateCallBox::Result> RateCallBox::sends() const {
  126. return _sends.events();
  127. }
  128. } // namespace Ui