init
Some checks failed
Docker. / Ubuntu (push) Has been cancelled
User-agent updater. / User-agent (push) Failing after 15s
Lock Threads / lock (push) Failing after 10s
Waiting for answer. / waiting-for-answer (push) Failing after 22s
Needs user action. / needs-user-action (push) Failing after 8s
Can't reproduce. / cant-reproduce (push) Failing after 8s
Close stale issues and PRs / stale (push) Has been cancelled
Some checks failed
Docker. / Ubuntu (push) Has been cancelled
User-agent updater. / User-agent (push) Failing after 15s
Lock Threads / lock (push) Failing after 10s
Waiting for answer. / waiting-for-answer (push) Failing after 22s
Needs user action. / needs-user-action (push) Failing after 8s
Can't reproduce. / cant-reproduce (push) Failing after 8s
Close stale issues and PRs / stale (push) Has been cancelled
This commit is contained in:
205
Telegram/SourceFiles/statistics/view/chart_rulers_view.cpp
Normal file
205
Telegram/SourceFiles/statistics/view/chart_rulers_view.cpp
Normal file
@@ -0,0 +1,205 @@
|
||||
/*
|
||||
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 "statistics/view/chart_rulers_view.h"
|
||||
|
||||
#include "info/channel_statistics/earn/earn_format.h"
|
||||
#include "lang/lang_keys.h"
|
||||
#include "statistics/chart_lines_filter_controller.h"
|
||||
#include "statistics/statistics_common.h"
|
||||
#include "statistics/statistics_graphics.h"
|
||||
#include "styles/style_basic.h"
|
||||
#include "styles/style_statistics.h"
|
||||
|
||||
#include <QtCore/QLocale>
|
||||
|
||||
namespace Statistic {
|
||||
namespace {
|
||||
|
||||
[[nodiscard]] QString FormatF(float64 absoluteValue) {
|
||||
static constexpr auto kTooMuch = int(10'000);
|
||||
static constexpr auto kTooSmall = 1e-9;
|
||||
return (std::abs(absoluteValue) <= kTooSmall)
|
||||
? u"0"_q
|
||||
: (absoluteValue >= kTooMuch)
|
||||
? Lang::FormatCountToShort(absoluteValue).string
|
||||
: QLocale().toString(absoluteValue);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
ChartRulersView::ChartRulersView() = default;
|
||||
|
||||
void ChartRulersView::setChartData(
|
||||
const Data::StatisticalChart &chartData,
|
||||
ChartViewType type,
|
||||
std::shared_ptr<LinesFilterController> linesFilter) {
|
||||
_rulers.clear();
|
||||
_isDouble = (type == ChartViewType::DoubleLinear)
|
||||
|| chartData.currencyRate;
|
||||
if (chartData.currencyRate) {
|
||||
_currencyIcon = ChartCurrencyIcon(chartData, {});
|
||||
if (chartData.currency == Data::StatisticalCurrency::Ton) {
|
||||
_leftCustomCaption = [=](float64 value) {
|
||||
return FormatF(value / float64(kOneStarInNano));
|
||||
};
|
||||
_rightCustomCaption = [=, rate = chartData.currencyRate](float64 v) {
|
||||
return Info::ChannelEarn::ToUsd(v / float64(kOneStarInNano), rate, 0);
|
||||
};
|
||||
} else {
|
||||
_leftCustomCaption = [=](float64 value) {
|
||||
return FormatF(value);
|
||||
};
|
||||
_rightCustomCaption = [=, rate = chartData.currencyRate](float64 v) {
|
||||
return Info::ChannelEarn::ToUsd(v, rate, 0);
|
||||
};
|
||||
}
|
||||
_rightPen = QPen(st::windowSubTextFg);
|
||||
}
|
||||
if (_isDouble && (chartData.lines.size() == 2)) {
|
||||
_linesFilter = std::move(linesFilter);
|
||||
_leftPen = QPen(chartData.lines.front().color);
|
||||
_rightPen = QPen(chartData.lines.back().color);
|
||||
_leftLineId = chartData.lines.front().id;
|
||||
_rightLineId = chartData.lines.back().id;
|
||||
|
||||
const auto firstMax = chartData.lines.front().maxValue;
|
||||
const auto secondMax = chartData.lines.back().maxValue;
|
||||
if (firstMax > secondMax) {
|
||||
_isLeftLineScaled = false;
|
||||
_scaledLineRatio = firstMax / float64(secondMax);
|
||||
} else {
|
||||
_isLeftLineScaled = true;
|
||||
_scaledLineRatio = secondMax / float64(firstMax);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ChartRulersView::paintRulers(
|
||||
QPainter &p,
|
||||
const QRect &r) {
|
||||
const auto alpha = p.opacity();
|
||||
for (auto &ruler : _rulers) {
|
||||
p.setOpacity(alpha * ruler.alpha * kRulerLineAlpha);
|
||||
for (const auto &line : ruler.lines) {
|
||||
const auto lineRect = QRect(
|
||||
0,
|
||||
r.y() + r.height() * line.relativeValue,
|
||||
r.x() + r.width(),
|
||||
st::lineWidth);
|
||||
p.fillRect(lineRect, st::boxTextFg);
|
||||
}
|
||||
}
|
||||
p.setOpacity(alpha);
|
||||
}
|
||||
|
||||
void ChartRulersView::paintCaptionsToRulers(
|
||||
QPainter &p,
|
||||
const QRect &r) {
|
||||
const auto offset = r.y() - st::statisticsChartRulerCaptionSkip;
|
||||
p.setFont(st::statisticsDetailsBottomCaptionStyle.font);
|
||||
const auto alpha = p.opacity();
|
||||
for (auto &ruler : _rulers) {
|
||||
const auto rulerAlpha = alpha * ruler.alpha;
|
||||
p.setOpacity(rulerAlpha);
|
||||
const auto left = _currencyIcon.isNull()
|
||||
? 0
|
||||
: _currencyIcon.width() / style::DevicePixelRatio();
|
||||
for (const auto &line : ruler.lines) {
|
||||
const auto y = offset + r.height() * line.relativeValue;
|
||||
const auto hasLinesFilter = _isDouble && _linesFilter;
|
||||
if (hasLinesFilter) {
|
||||
p.setPen(_leftPen);
|
||||
p.setOpacity(rulerAlpha * _linesFilter->alpha(_leftLineId));
|
||||
} else {
|
||||
p.setPen(st::windowSubTextFg);
|
||||
}
|
||||
if (!_currencyIcon.isNull()) {
|
||||
const auto iconTop = y
|
||||
- _currencyIcon.height() / style::DevicePixelRatio()
|
||||
+ st::statisticsChartRulerCaptionSkip;
|
||||
p.drawImage(0, iconTop, _currencyIcon);
|
||||
}
|
||||
p.drawText(
|
||||
left,
|
||||
y,
|
||||
(!_isDouble)
|
||||
? line.caption
|
||||
: _isLeftLineScaled
|
||||
? line.scaledLineCaption
|
||||
: line.caption);
|
||||
if (hasLinesFilter || _rightCustomCaption) {
|
||||
if (_linesFilter) {
|
||||
p.setOpacity(rulerAlpha * _linesFilter->alpha(_rightLineId));
|
||||
}
|
||||
p.setPen(_rightPen);
|
||||
p.drawText(
|
||||
r.width() - line.rightCaptionWidth,
|
||||
y,
|
||||
_isLeftLineScaled
|
||||
? line.caption
|
||||
: line.scaledLineCaption);
|
||||
}
|
||||
}
|
||||
}
|
||||
p.setOpacity(alpha);
|
||||
}
|
||||
|
||||
void ChartRulersView::computeRelative(
|
||||
int newMaxHeight,
|
||||
int newMinHeight) {
|
||||
for (auto &ruler : _rulers) {
|
||||
ruler.computeRelative(newMaxHeight, newMinHeight);
|
||||
}
|
||||
}
|
||||
|
||||
void ChartRulersView::setAlpha(float64 value) {
|
||||
for (auto &ruler : _rulers) {
|
||||
ruler.alpha = ruler.fixedAlpha * (1. - value);
|
||||
}
|
||||
_rulers.back().alpha = value;
|
||||
if (value == 1.) {
|
||||
while (_rulers.size() > 1) {
|
||||
const auto startIt = begin(_rulers);
|
||||
if (!startIt->alpha) {
|
||||
_rulers.erase(startIt);
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ChartRulersView::add(Limits newHeight, bool animated) {
|
||||
auto newLinesData = ChartRulersData(
|
||||
newHeight.max,
|
||||
newHeight.min,
|
||||
true,
|
||||
_isDouble ? _scaledLineRatio : 0.,
|
||||
_leftCustomCaption,
|
||||
_rightCustomCaption);
|
||||
if (_isDouble) {
|
||||
const auto &font = st::statisticsDetailsBottomCaptionStyle.font;
|
||||
for (auto &line : newLinesData.lines) {
|
||||
line.rightCaptionWidth = font->width(_isLeftLineScaled
|
||||
? line.caption
|
||||
: line.scaledLineCaption);
|
||||
}
|
||||
}
|
||||
if (!animated) {
|
||||
_rulers.clear();
|
||||
}
|
||||
for (auto &ruler : _rulers) {
|
||||
ruler.fixedAlpha = ruler.alpha;
|
||||
}
|
||||
_rulers.push_back(newLinesData);
|
||||
if (!animated) {
|
||||
_rulers.back().alpha = 1.;
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace Statistic
|
||||
Reference in New Issue
Block a user