mirror of
https://github.com/ClickHouse/ClickHouse.git
synced 2024-11-24 00:22:29 +00:00
63 lines
1.3 KiB
C++
63 lines
1.3 KiB
C++
#pragma once
|
||
|
||
#include <cstring>
|
||
#include <cmath>
|
||
#include <string>
|
||
|
||
|
||
#define UNICODE_BAR_CHAR_SIZE (strlen("█"))
|
||
|
||
|
||
/** Позволяет нарисовать unicode-art полоску, ширина которой отображается с разрешением 1/8 символа.
|
||
*/
|
||
|
||
|
||
namespace UnicodeBar
|
||
{
|
||
template <typename T>
|
||
double getWidth(T x, int64_t min, int64_t max, double max_width)
|
||
{
|
||
if (x <= min)
|
||
return 0;
|
||
|
||
if (x >= max)
|
||
return max_width;
|
||
|
||
return (x - min) * max_width / (max - min);
|
||
}
|
||
|
||
inline size_t getWidthInBytes(double width)
|
||
{
|
||
return ceil(width - 1.0 / 8) * UNICODE_BAR_CHAR_SIZE;
|
||
}
|
||
|
||
/// В dst должно быть место для barWidthInBytes(width) символов и завершающего нуля.
|
||
inline void render(double width, char * dst)
|
||
{
|
||
size_t floor_width = floor(width);
|
||
|
||
for (size_t i = 0; i < floor_width; ++i)
|
||
{
|
||
memcpy(dst, "█", UNICODE_BAR_CHAR_SIZE);
|
||
dst += UNICODE_BAR_CHAR_SIZE;
|
||
}
|
||
|
||
size_t remainder = floor((width - floor_width) * 8);
|
||
|
||
if (remainder)
|
||
{
|
||
memcpy(dst, &"▏▎▍▌▋▋▊▉"[(remainder - 1) * UNICODE_BAR_CHAR_SIZE], UNICODE_BAR_CHAR_SIZE);
|
||
dst += UNICODE_BAR_CHAR_SIZE;
|
||
}
|
||
|
||
*dst = 0;
|
||
}
|
||
|
||
inline std::string render(double width)
|
||
{
|
||
std::string res(getWidthInBytes(width), '\0');
|
||
render(width, &res[0]);
|
||
return res;
|
||
}
|
||
}
|