一、应用案例
二、样式展示
注:录制界面为测试界面,实际标尺样式为上半部分
三、源码
qls_qss_global.h
#ifndef QLS_QSS_GLOBAL_H
#define QLS_QSS_GLOBAL_H
#define QLS_PROPERTY(var_, type_) \
private: \
type_ var_; \
\
public: \
inline type_ get_##var_() const { return var_; } \
\
Q_SIGNALS: \
void sig_##var_##changed(); \
\
public Q_SLOTS: \
void set_##var_(type_ var) \
{ \
var_ = var; \
update(); \
emit sig_##var_##changed(); \
} \
\
public: \
Q_PROPERTY(type_ var_ READ get_##var_ WRITE set_##var_)
#define QLS_PROPERTY_NHC(var_, type_) \
QLS_PROPERTY(var_##normal_, type_) \
QLS_PROPERTY(var_##hover_, type_) \
QLS_PROPERTY(var_##check_, type_)
#define QLS_PROPERTY_NP(var_, type_) \
QLS_PROPERTY(var_##normal_, type_) \
QLS_PROPERTY(var_##press_, type_)
#define QLS_PROPERTY_NHPCD(var_, type_) \
QLS_PROPERTY(var_##normal_, type_) \
QLS_PROPERTY(var_##hover_, type_) \
QLS_PROPERTY(var_##press_, type_) \
QLS_PROPERTY(var_##check_, type_) \
QLS_PROPERTY(var_##disable_, type_)
#endif
qls_ruler.h
#ifndef QLSRULER_H
#define QLSRULER_H
#include <QWidget>
#include "qls_qss_global.h"
class QLabel;
class QLsRuler : public QWidget
{
Q_OBJECT
Q_ENUMS(ScaleLabelPosition)
Q_ENUMS(RulerDirection)
Q_ENUMS(ScaleDirection)
Q_ENUMS(RulerType)
Q_ENUMS(ScaleType)
public:
#if 0
enum ScaleLevel{
ScaleLevel_Unit = 0,
ScaleLevel_Label = 1,
};
enum ScaleRange{
ScaleRange_All = 0,
ScaleRange_valid = 1,
};
#endif
enum ScaleLabelPosition{
ScaleLabelPosition_Inside = 0,
ScaleLabelPosition_Outside = 1,
};
enum RulerDirection{
RulerDirection_West = 0,
RulerDirection_North = 1,
RulerDirection_South = 2,
RulerDirection_East = 3,
};
enum ScaleDirection{
ScaleDirection_Left_To_Right = 0,
ScaleDirection_Right_To_Left = 1,
};
enum RulerType{
RulerType_Scale = 0,
RulerType_Cursor = 1,
RulerType_Line = 2,
RulerType_Progress = 3,
RulerType_Slide = 4,
};
enum ScaleType{
ScaleType_Value = 0,
ScaleType_Number = 1,
};
public:
explicit QLsRuler(QWidget *parent = nullptr);
protected:
void paintEvent(QPaintEvent *event) override;
void mousePressEvent(QMouseEvent *event) override;
void mouseReleaseEvent(QMouseEvent *evnet) override;
void mouseMoveEvent(QMouseEvent *event) override;
private:
void updateMinimumSize(QPainter *painter);
void drawProgress(QPainter *painter);
void drawScaleRangeColor(QPainter *painter);
void drawScale(QPainter *painter);
void drawLabel(QPainter *painter);
void drawLine(QPainter *painter);
void drawCursor(QPainter *painter);
QRect getRotateRectAll(QPainter *painter);
QRect getRotateRectTrue(QPainter *painter);
QRect getRotateRectScale(QPainter *painter);
QRect getRotateRectLabel(QPainter *painter);
QPointF getRotatePoint(const QPointF &p0, const QPointF &p1, double a);
private:
QLabel *cursor_label_;
bool press_{false};
bool is_move_triangle_{false};
QPointF triangle_pos_;
QPointF translate_point_;
qreal rotate_angle_;
QPolygonF triangle_{QVector<QPointF>(3, QPointF(0, 0))};
QLS_PROPERTY(padding_top_, double)
QLS_PROPERTY(padding_right_, double)
QLS_PROPERTY(padding_bottom_, double)
QLS_PROPERTY(padding_left_, double)
QLS_PROPERTY(scale_label_space_, double)
QLS_PROPERTY(ruler_type_, RulerType)
QLS_PROPERTY(ruler_direction_, RulerDirection)
QLS_PROPERTY(scale_direction_, ScaleDirection)
QLS_PROPERTY(scale_value_, double)
QLS_PROPERTY(scale_unit_value_, double)
QLS_PROPERTY(scale_label_value_, double)
QLS_PROPERTY(scale_type_, ScaleType)
QLS_PROPERTY(scale_range_all_min_, double)
QLS_PROPERTY(scale_range_all_max_, double)
QLS_PROPERTY(scale_range_valid_enabled_, double)
QLS_PROPERTY(scale_range_valid_min_, double)
QLS_PROPERTY(scale_range_valid_max_, double)
QLS_PROPERTY(scale_range_all_color_, QBrush)
QLS_PROPERTY(scale_range_valid_color_, QBrush)
QLS_PROPERTY(scale_range_all_bgcolor_, QBrush)
QLS_PROPERTY(scale_range_valid_bgcolor_, QBrush)
QLS_PROPERTY(scale_unit_size_, QSize)
QLS_PROPERTY(scale_label_size_, QSize)
QLS_PROPERTY(scale_thickness_, double)
QLS_PROPERTY(scale_label_visiable_, bool)
QLS_PROPERTY(scale_label_position_, ScaleLabelPosition)
QLS_PROPERTY(cursor_visiable_, bool)
QLS_PROPERTY(cursor_color_, QBrush)
QLS_PROPERTY(cursor_side_, double)
QLS_PROPERTY(cursor_label_visiable_, bool)
};
#endif
qls_ruler.cpp
#include "qls_ruler.h"
#include <cmath>
#include <QPainter>
#include <QMouseEvent>
#include <QtMath>
#include <QToolTip>
#include <QLabel>
#include <QMap>
QLsRuler::QLsRuler(QWidget *parent) : QWidget(parent)
{
cursor_label_ = new QLabel(this);
cursor_label_->setFixedSize(40, 20);
cursor_label_->setAlignment(Qt::AlignCenter);
cursor_label_->hide();
padding_top_ = 5;
padding_right_ = 5;
padding_bottom_ = 5;
padding_left_ = 5;
scale_label_space_ = 5;
ruler_type_ = RulerType_Cursor;
connect(this, &QLsRuler::sig_ruler_type_changed, [=]{
switch (get_ruler_type_()) {
case RulerType_Scale:
cursor_visiable_ = false;
scale_label_visiable_ = false;
break;
case RulerType_Cursor:
cursor_visiable_ = true;
scale_label_visiable_ = true;
break;
case RulerType_Line:
cursor_visiable_ = false;
scale_label_visiable_ = true;
break;
case RulerType_Progress:
cursor_visiable_ = false;
scale_label_visiable_ = true;
break;
case RulerType_Slide:
cursor_visiable_ = true;
scale_label_visiable_ = true;
break;
}
});
ruler_direction_ = RulerDirection_West;
scale_direction_ = ScaleDirection_Left_To_Right;
scale_value_ = 20;
scale_unit_value_ = 3;
scale_label_value_ = 1;
scale_type_ = ScaleType_Number;
scale_range_all_min_ = 0;
scale_range_all_max_ = 100;
scale_range_valid_enabled_ = true;
scale_range_valid_min_ = 0;
scale_range_valid_max_ = 100;
scale_range_all_color_ = QColor(204, 204, 204);
scale_range_valid_color_ = QColor(129 , 126, 121);
scale_range_all_bgcolor_ = QColor(238, 238, 238);
scale_range_valid_bgcolor_ = QColor(0, 255, 0);
scale_unit_size_ = QSize(3, 5);
scale_label_size_ = QSize(3, 10);
scale_thickness_ = 3;
scale_label_position_ = ScaleLabelPosition_Outside;
cursor_visiable_ = true;
cursor_color_ = QColor(255, 129, 0);
cursor_side_ = 15;
cursor_label_visiable_ = false;
}
void QLsRuler::paintEvent(QPaintEvent *event)
{
QPainter painter(this);
painter.setRenderHints(QPainter::Antialiasing | QPainter::TextAntialiasing);
drawProgress(&painter);
drawScaleRangeColor(&painter);
drawScale(&painter);
drawLabel(&painter);
drawLine(&painter);
drawCursor(&painter);
updateMinimumSize(&painter);
QWidget::paintEvent(event);
}
void QLsRuler::mousePressEvent(QMouseEvent *event)
{
press_ = true;
if(get_ruler_type_() == RulerType_Slide &&
triangle_.containsPoint(
getRotatePoint(
translate_point_, event->pos(), rotate_angle_
), Qt::OddEvenFill)){
triangle_pos_ = event->pos();
is_move_triangle_ = true;
if(cursor_label_visiable_ && cursor_label_->isHidden()){
cursor_label_->show();
cursor_label_->setText(QString::number(get_scale_value_(), 'f', 0));
if(event->pos().x() + 10 + cursor_label_->width() >= width()){
cursor_label_->move(event->pos() - QPoint(-cursor_label_->width() - 10, 0));
} else {
cursor_label_->move(event->pos() + QPoint(10, 0));
}
}
}
update();
QWidget::mousePressEvent(event);
}
void QLsRuler::mouseReleaseEvent(QMouseEvent *event)
{
press_ = false;
is_move_triangle_ = false;
if(cursor_label_visiable_ && cursor_label_->isVisible()){
cursor_label_->hide();
}
update();
QWidget::mouseReleaseEvent(event);
}
void QLsRuler::mouseMoveEvent(QMouseEvent *event)
{
if(is_move_triangle_){
if(get_ruler_direction_() == RulerDirection_West || get_ruler_direction_() == RulerDirection_South){
double x = event->pos().x() - triangle_pos_.x();
QPainter painter(this);
scale_value_ = get_scale_value_() +
(get_ruler_direction_() == RulerDirection_West ||
get_ruler_direction_() == RulerDirection_North ? 1.0 : -1.0) *
(get_scale_direction_() == ScaleDirection_Left_To_Right ? 1.0 : -1.0) *
x * (get_scale_range_all_max_() - get_scale_range_all_min_()) /
getRotateRectScale(&painter).width();
}
else {
double y = event->pos().y() - triangle_pos_.y();
QPainter painter(this);
scale_value_ = get_scale_value_() +
(get_ruler_direction_() == RulerDirection_West ||
get_ruler_direction_() == RulerDirection_North ? 1.0 : -1.0) *
(get_scale_direction_() == ScaleDirection_Left_To_Right ? 1.0 : -1.0) *
y * (get_scale_range_all_max_() - get_scale_range_all_min_()) /
getRotateRectScale(&painter).width();
}
triangle_pos_ = event->pos();
if(cursor_label_visiable_ && cursor_label_->isVisible()){
cursor_label_->setText(QString::number(get_scale_value_(), 'f', 0));
if(event->pos().x() + 10 + cursor_label_->width() >= width()){
cursor_label_->move(event->pos() - QPoint(cursor_label_->width() + 10, 0));
} else {
cursor_label_->move(event->pos() + QPoint(10, 0));
}
}
update();
return;
}
QWidget::mouseMoveEvent(event);
}
void QLsRuler::updateMinimumSize(QPainter *painter)
{
painter->save();
switch (get_ruler_direction_()) {
case RulerDirection_West:
case RulerDirection_South:
setMinimumWidth(0);
setMinimumHeight(getRotateRectTrue(painter).adjusted(
-get_padding_left_(), -get_padding_top_(),
get_padding_right_(), get_padding_bottom_()).height());
break;
case RulerDirection_East:
case RulerDirection_North:
setMinimumHeight(0);
setMinimumWidth(getRotateRectTrue(painter).adjusted(
-get_padding_left_(), -get_padding_top_(),
get_padding_right_(), get_padding_bottom_()).width());
break;
default: break;
}
painter->restore();
}
void QLsRuler::drawProgress(QPainter *painter)
{
if(get_ruler_type_() != RulerType_Progress){
return;
}
painter->save();
painter->setPen(Qt::NoPen);
QRect rect_all = getRotateRectAll(painter);
if(get_scale_direction_() == ScaleDirection_Left_To_Right){
painter->setBrush(get_scale_range_all_bgcolor_());
painter->drawRect(rect_all.adjusted(rect_all.width() * get_scale_value_() / (get_scale_range_all_max_() - get_scale_range_all_min_()), 0, 0, 0));
painter->setBrush(get_scale_range_valid_bgcolor_());
painter->drawRect(rect_all.adjusted(0, 0, -rect_all.width() * (1 - get_scale_value_() / (get_scale_range_all_max_() - get_scale_range_all_min_())), 0));
}
else {
painter->setBrush(get_scale_range_all_bgcolor_());
painter->drawRect(rect_all.adjusted(0, 0, -rect_all.width() * get_scale_value_() / (get_scale_range_all_max_() - get_scale_range_all_min_()), 0));
painter->setBrush(get_scale_range_valid_bgcolor_());
painter->drawRect(rect_all.adjusted(rect_all.width() * (1 - get_scale_value_() / (get_scale_range_all_max_() - get_scale_range_all_min_())), 0, 0, 0));
}
painter->restore();
}
void QLsRuler::drawScaleRangeColor(QPainter *painter)
{
painter->save();
painter->setPen(Qt::NoPen);
QRect rect_scale = getRotateRectScale(painter);
painter->setBrush(get_scale_range_all_color_());
painter->drawRect(rect_scale.adjusted(0, rect_scale.height() - get_scale_thickness_(), 0, 0));
painter->setBrush(get_scale_range_valid_color_());
if(get_scale_direction_() == ScaleDirection_Left_To_Right) {
painter->drawRect(
rect_scale.adjusted(
rect_scale.width() * (get_scale_range_valid_min_() - get_scale_range_all_min_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()),
rect_scale.height() - get_scale_thickness_(),
-rect_scale.width() * (get_scale_range_all_max_() - get_scale_range_valid_max_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()),
0));
}
else {
painter->drawRect(
rect_scale.adjusted(
rect_scale.width() * (get_scale_range_all_max_() - get_scale_range_valid_max_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()),
rect_scale.height() - get_scale_thickness_(),
-rect_scale.width() * (get_scale_range_valid_min_() - get_scale_range_all_min_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()),
0));
}
painter->restore();
}
void QLsRuler::drawScale(QPainter *painter)
{
painter->save();
painter->setPen(Qt::NoPen);
painter->setBrush(get_scale_range_all_color_());
QRect rect_scale = getRotateRectScale(painter);
painter->drawRect(rect_scale.left() - get_scale_label_size_().width() / 2, rect_scale.top(), get_scale_label_size_().width(), get_scale_label_size_().height());
painter->drawRect(rect_scale.right() - get_scale_label_size_().width() / 2, rect_scale.top(),
get_scale_label_size_().width(), get_scale_label_size_().height());
if(get_scale_type_() == ScaleType_Value){
if(get_scale_direction_() == ScaleDirection_Left_To_Right){
for(int i = get_scale_range_all_min_() + get_scale_unit_value_();
i < get_scale_range_all_max_(); i += get_scale_unit_value_()){
if(i % QString::number(get_scale_label_value_()).toInt() == 0){
painter->drawRect(rect_scale.left() + rect_scale.width() *
(i - get_scale_range_all_min_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_())
- get_scale_label_size_().width() / 2,
rect_scale.top(),
get_scale_label_size_().width(), get_scale_label_size_().height());
}
else if(i % QString::number(get_scale_unit_value_()).toInt() == 0) {
painter->drawRect(rect_scale.left() + rect_scale.width() *
(i - get_scale_range_all_min_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_())
- get_scale_unit_size_().width() / 2,
rect_scale.top() + get_scale_label_size_().height() - get_scale_unit_size_().height(),
get_scale_unit_size_().width(), get_scale_unit_size_().height());
}
}
}
else {
for(int i = get_scale_range_all_min_() + get_scale_unit_value_();
i < get_scale_range_all_max_(); i += get_scale_unit_value_()){
if(i % QString::number(get_scale_label_value_()).toInt() == 0){
painter->drawRect(rect_scale.left() + rect_scale.width() *
(get_scale_range_all_max_() - i) /
(get_scale_range_all_max_() - get_scale_range_all_min_())
- get_scale_label_size_().width() / 2,
rect_scale.top(),
get_scale_label_size_().width(), get_scale_label_size_().height());
}
else if(i % QString::number(get_scale_unit_value_()).toInt() == 0) {
painter->drawRect(rect_scale.left() + rect_scale.width() *
(get_scale_range_all_max_() - i) /
(get_scale_range_all_max_() - get_scale_range_all_min_())
- get_scale_unit_size_().width() / 2,
rect_scale.top() + get_scale_label_size_().height() - get_scale_unit_size_().height(),
get_scale_unit_size_().width(), get_scale_unit_size_().height());
}
}
}
}
else {
if(get_scale_direction_() == ScaleDirection_Left_To_Right){
auto num = get_scale_unit_value_() * (get_scale_label_value_() + 1) + get_scale_label_value_();
auto unit_val = (get_scale_range_all_max_() - get_scale_range_all_min_()) / (num + 1);
for(int index = 1; index <= num; index++){
auto i = index * unit_val + get_scale_range_all_min_();
if(index % (QString::number(get_scale_unit_value_()).toInt() + 1) == 0){
painter->drawRect(rect_scale.left() + rect_scale.width() *
(i - get_scale_range_all_min_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_())
- get_scale_label_size_().width() / 2,
rect_scale.top(),
get_scale_label_size_().width(), get_scale_label_size_().height());
}
else {
painter->drawRect(rect_scale.left() + rect_scale.width() *
(i - get_scale_range_all_min_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_())
- get_scale_unit_size_().width() / 2,
rect_scale.top() + get_scale_label_size_().height() - get_scale_unit_size_().height(),
get_scale_unit_size_().width(), get_scale_unit_size_().height());
}
}
}
else {
auto num = get_scale_unit_value_() * (get_scale_label_value_() + 1) + get_scale_label_value_();
auto unit_val = (get_scale_range_all_max_() - get_scale_range_all_min_()) / (num + 1);
for(int index = 1; index <= num; index++){
auto i = index * unit_val + get_scale_range_all_min_();
if(index % (QString::number(get_scale_unit_value_()).toInt() + 1) == 0){
painter->drawRect(rect_scale.left() + rect_scale.width() *
(get_scale_range_all_max_() - i) /
(get_scale_range_all_max_() - get_scale_range_all_min_())
- get_scale_label_size_().width() / 2,
rect_scale.top(),
get_scale_label_size_().width(), get_scale_label_size_().height());
}
else {
painter->drawRect(rect_scale.left() + rect_scale.width() *
(get_scale_range_all_max_() - i) /
(get_scale_range_all_max_() - get_scale_range_all_min_())
- get_scale_unit_size_().width() / 2,
rect_scale.top() + get_scale_label_size_().height() - get_scale_unit_size_().height(),
get_scale_unit_size_().width(), get_scale_unit_size_().height());
}
}
}
}
painter->restore();
}
bool operator<(const QPointF &p1, const QPointF &p2){
return p1.x() == p2.x() ? p1.y() < p2.y() : p1.x() < p2.x();
}
void QLsRuler::drawLabel(QPainter *painter)
{
if(!get_scale_label_visiable_()){
return;
}
painter->save();
QRect rect_label = getRotateRectLabel(painter);
QFontMetrics fm(font());
QMap<QPointF, QString> map_label_points;
QPointF left_point, right_point;
if(get_scale_type_() == ScaleType_Value){
if(get_scale_direction_() == ScaleDirection_Left_To_Right){
QString str_min = QString::number(get_scale_range_all_min_(), 'f', 0);
map_label_points.insert(left_point = QPointF(rect_label.left(), rect_label.bottom()), str_min);
QString str_max = QString::number(get_scale_range_all_max_(), 'f', 0);
map_label_points.insert(right_point = QPointF(rect_label.right() - fm.horizontalAdvance(str_max),
rect_label.bottom()), str_max);
auto label_pix = rect_label.width() / ((get_scale_range_all_max_() - get_scale_range_all_min_()) /
get_scale_label_value_());
for(int i = get_scale_range_all_min_() + get_scale_unit_value_();
i < get_scale_range_all_max_(); i += get_scale_unit_value_()){
if(i % QString::number(get_scale_label_value_()).toInt()){
continue;
}
auto index = (i - get_scale_range_all_min_()) / get_scale_label_value_();
QString str_i = QString::number(i, 'f', 0);
map_label_points.insert(QPointF(rect_label.left() + index * label_pix - fm.horizontalAdvance(str_i) / 2,
rect_label.bottom()), str_i);
}
}
else {
QString str_max = QString::number(get_scale_range_all_max_(), 'f', 0);
map_label_points.insert(left_point = QPointF(rect_label.left(), rect_label.bottom()), str_max);
QString str_min = QString::number(get_scale_range_all_min_(), 'f', 0);
map_label_points.insert(right_point = QPointF(rect_label.right() - fm.horizontalAdvance(str_min),
rect_label.bottom()), str_min);
auto label_pix = rect_label.width() / ((get_scale_range_all_max_() - get_scale_range_all_min_()) /
get_scale_label_value_());
for(int i = get_scale_range_all_min_() + get_scale_unit_value_();
i < get_scale_range_all_max_(); i += get_scale_unit_value_()){
if(i % QString::number(get_scale_label_value_()).toInt()){
continue;
}
auto index = (i - get_scale_range_all_min_()) / get_scale_label_value_();
QString str_i = QString::number(i, 'f', 0);
map_label_points.insert(QPointF(rect_label.right() - index * label_pix - fm.horizontalAdvance(str_i) / 2,
rect_label.bottom()), str_i);
}
}
}
else {
if(get_scale_direction_() == ScaleDirection_Left_To_Right){
QString str_min = QString::number(get_scale_range_all_min_(), 'f', 0);
map_label_points.insert(left_point = QPointF(rect_label.left(), rect_label.bottom()), str_min);
QString str_max = QString::number(get_scale_range_all_max_(), 'f', 0);
map_label_points.insert(right_point = QPointF(rect_label.right() - fm.horizontalAdvance(str_max),
rect_label.bottom()), str_max);
auto label_pix = rect_label.width() / (get_scale_label_value_() + 1);
auto label_value_unit = (get_scale_range_all_max_() - get_scale_range_all_min_()) / (get_scale_label_value_() + 1);
for(int i = 1; i <= get_scale_label_value_(); i++){
QString str_i = QString::number(i * label_value_unit + get_scale_range_all_min_(), 'f', 0);
map_label_points.insert(QPointF(rect_label.left() + i * label_pix -
fm.horizontalAdvance(str_i) / 2,
rect_label.bottom()), str_i);
}
}
else {
QString str_max = QString::number(get_scale_range_all_max_(), 'f', 0);
map_label_points.insert(left_point = QPointF(rect_label.left(), rect_label.bottom()), str_max);
QString str_min = QString::number(get_scale_range_all_min_(), 'f', 0);
map_label_points.insert(right_point = QPointF(rect_label.right() - fm.horizontalAdvance(str_min),
rect_label.bottom()), str_min);
auto label_pix = rect_label.width() / (get_scale_label_value_() + 1);
auto label_value_unit = (get_scale_range_all_max_() - get_scale_range_all_min_()) / (get_scale_label_value_() + 1);
for(int i = 1; i <= get_scale_label_value_(); i++){
QString str_i = QString::number(i * label_value_unit + get_scale_range_all_min_(), 'f', 0);
map_label_points.insert(QPointF(rect_label.right() - i * label_pix - fm.horizontalAdvance(str_i) / 2,
rect_label.bottom()), str_i);
}
}
}
painter->restore();
painter->save();
for(auto it = map_label_points.begin(); it != map_label_points.end(); it++){
auto p = getRotatePoint(translate_point_, it.key(), rotate_angle_);
if(rotate_angle_ == 180.){
p = getRotatePoint(translate_point_, it.key() -
QPointF(-fm.horizontalAdvance(it.value()), fm.height() / 2),
rotate_angle_);
}
if(rotate_angle_ == -90.){
if(it.key() == left_point){
p = getRotatePoint(QPointF(translate_point_.y(), translate_point_.x()), it.key() +
QPointF(0, - fm.horizontalAdvance(it.value())),
rotate_angle_);
} else if(it.key() == right_point){
p = getRotatePoint(QPointF(translate_point_.y(), translate_point_.x()), it.key() +
QPointF(fm.horizontalAdvance(it.value()) - fm.height() / 2.,
-fm.horizontalAdvance(it.value())),
rotate_angle_);
} else {
p = getRotatePoint(QPointF(translate_point_.y(), translate_point_.x()), it.key() +
QPointF((fm.horizontalAdvance(it.value()) - fm.height() / 2.) / 2.,
-fm.horizontalAdvance(it.value())),
rotate_angle_);
}
if(get_scale_label_position_() == ScaleLabelPosition_Outside){
p.setX(p.x() + fm.horizontalAdvance(it.value()) - fm.height());
}
}
if(rotate_angle_ == 90.){
if(it.key() == left_point){
p = getRotatePoint(QPointF(translate_point_.y(), translate_point_.x()), it.key() +
QPointF(fm.height() / 2., 0),
rotate_angle_);
} else if(it.key() == right_point){
p = getRotatePoint(QPointF(translate_point_.y(), translate_point_.x()), it.key() +
QPointF(fm.horizontalAdvance(it.value()), 0),
rotate_angle_);
} else {
p = getRotatePoint(QPointF(translate_point_.y(), translate_point_.x()), it.key() +
QPointF((fm.horizontalAdvance(it.value()) + fm.height() / 2.) / 2.,
0),
rotate_angle_);
}
if(get_scale_label_position_() == ScaleLabelPosition_Outside){
p.setX(p.x() - fm.horizontalAdvance(it.value()) + fm.height());
}
}
painter->drawText(p, it.value());
}
painter->restore();
}
void QLsRuler::drawLine(QPainter *painter)
{
if(get_ruler_type_() != RulerType_Line){
return;
}
painter->save();
painter->setPen(Qt::NoPen);
QRect rect_all = getRotateRectAll(painter);
if(get_scale_direction_() == ScaleDirection_Left_To_Right){
painter->setBrush(get_scale_range_valid_bgcolor_());
painter->drawRect(
rect_all.left() + rect_all.width() *
(get_scale_value_() - get_scale_range_all_min_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()) -
(get_scale_label_size_().width() + 2) / 2,
0,
get_scale_label_size_().width() + 2,
rect_all.height()
);
}
else {
painter->setBrush(get_scale_range_valid_bgcolor_());
painter->drawRect(
rect_all.left() + rect_all.width() *
(get_scale_range_all_max_() - get_scale_value_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()),
0,
get_scale_label_size_().width() + 2,
rect_all.height()
);
}
painter->restore();
}
void QLsRuler::drawCursor(QPainter *painter)
{
if(!cursor_visiable_){
return;
}
painter->save();
painter->setPen(Qt::NoPen);
QRect rect_scale = getRotateRectScale(painter);
if(get_scale_label_position_() == ScaleLabelPosition_Outside){
QPointF p;
if(get_scale_direction_() == ScaleDirection_Left_To_Right){
p.setX(rect_scale.left() + rect_scale.width() *
(get_scale_value_() - get_scale_range_all_min_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()));
p.setY(rect_scale.top() + get_scale_label_size_().height());
}
else {
p.setX(rect_scale.left() + rect_scale.width() *
(get_scale_range_all_max_() - get_scale_value_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()));
p.setY(rect_scale.top() + get_scale_label_size_().height());
}
triangle_[0] = QPointF(p.x(), p.y() - sqrt(3) * get_cursor_side_() / 4);
triangle_[1] = QPointF(p.x() - get_cursor_side_() / 2, p.y() + sqrt(3) * get_cursor_side_() / 4);
triangle_[2] = QPointF(p.x() + get_cursor_side_() / 2, p.y() + sqrt(3) * get_cursor_side_() / 4);
painter->setBrush(get_cursor_color_());
painter->drawPolygon(triangle_);
} else {
QPointF p;
if(get_scale_direction_() == ScaleDirection_Left_To_Right){
p.setX(rect_scale.left() + rect_scale.width() *
(get_scale_value_() - get_scale_range_all_min_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()));
p.setY(rect_scale.top() - sqrt(3) * get_cursor_side_() / 4);
}
else {
p.setX(rect_scale.left() + rect_scale.width() *
(get_scale_range_all_max_() - get_scale_value_()) /
(get_scale_range_all_max_() - get_scale_range_all_min_()));
p.setY(rect_scale.top() - sqrt(3) * get_cursor_side_() / 4);
}
triangle_[0] = QPointF(p.x(), p.y() + sqrt(3) * get_cursor_side_() / 4);
triangle_[1] = QPointF(p.x() - get_cursor_side_() / 2, p.y() - sqrt(3) * get_cursor_side_() / 4);
triangle_[2] = QPointF(p.x() + get_cursor_side_() / 2, p.y() - sqrt(3) * get_cursor_side_() / 4);
painter->setBrush(get_cursor_color_());
painter->drawPolygon(triangle_);
}
painter->restore();
}
QRect QLsRuler::getRotateRectAll(QPainter *painter)
{
QRect rect_all = rect().adjusted(get_padding_left_(), get_padding_top_(), -get_padding_right_(), -get_padding_bottom_());
switch (get_ruler_direction_()) {
case RulerDirection_West:
translate_point_ = QPointF(0, 0);
rotate_angle_ = 0;
break;
case RulerDirection_North:{
painter->translate(width(), 0);
painter->rotate(90);
auto w = rect_all.width();
rect_all.setWidth(rect_all.height());
rect_all.setHeight(w);
translate_point_ = QPointF(width(), 0);
rotate_angle_ = 90;
break;
}
case RulerDirection_South:
painter->translate(width(), height());
painter->rotate(180);
translate_point_ = QPointF(width(), height());
rotate_angle_ = 180;
break;
case RulerDirection_East:{
painter->translate(0, height());
painter->rotate(-90);
auto w = rect_all.width();
rect_all.setWidth(rect_all.height());
rect_all.setHeight(w);
translate_point_ = QPointF(0, height());
rotate_angle_ = -90;
break;
}
default: break;
}
return rect_all;
}
QRect QLsRuler::getRotateRectTrue(QPainter *painter)
{
QRect rect_all = getRotateRectAll(painter);
QFontMetrics fm(font());
auto h = (!get_scale_label_visiable_() ? 0 : fm.height() + get_scale_label_space_()) +
get_scale_label_size_().height() + get_scale_thickness_();
return QRect(rect_all.left(), rect_all.top() + (rect_all.height() - h) / 2,
rect_all.width(), h);
}
QRect QLsRuler::getRotateRectScale(QPainter *painter)
{
QRect rect_true = getRotateRectTrue(painter);
QFontMetrics fm(font());
QRect rect_scale;
if(scale_label_position_ == ScaleLabelPosition_Inside){
rect_scale = rect_true.adjusted(
0, (!get_scale_label_visiable_()
? 0 : fm.height() + get_scale_label_space_()),
0, 0);
} else {
rect_scale = rect_true.adjusted(
0, 0, 0,
-((!get_scale_label_visiable_()
? 0 : fm.height() + get_scale_label_space_())));
}
return rect_scale;
}
QRect QLsRuler::getRotateRectLabel(QPainter *painter)
{
QRect rect_true = getRotateRectTrue(painter);
QRect rect_label;
if(scale_label_position_ == ScaleLabelPosition_Inside){
rect_label = rect_true.adjusted(0, 0, 0, -(get_scale_label_space_() + get_scale_label_size_().height() +
get_scale_thickness_()));
} else {
rect_label = rect_true.adjusted(0, get_scale_label_space_() + get_scale_label_size_().height() +
get_scale_thickness_(), 0, 0);
}
return rect_label;
}
QPointF QLsRuler::getRotatePoint(const QPointF &p0, const QPointF &p1, double a)
{
auto p = p0 - p1;
p.setX(qFabs(p.x()));
p.setY(qFabs(p.y()));
if(qFabs(a) == 90){
return QPointF(p.y(), p.x());
}
return p;
}
|