Qt 坐标系统和坐标变换

一、概述:
1、QPainter在QPaintDevice上绘图的默认坐标系统是,原点(0,0)在左上角,x轴正方向水平向右,y轴正方向竖直向下的坐标系。


2、为了绘图的方便,QPainter提供了一些坐标变换的功能,通过平移、旋转、缩放等坐标变换,得到一个逻辑坐标系统(变换坐标系),有时候绘图更方便。


二、QPainter有关坐标变换操作的函数:
1、坐标平移:
  (1)、void translate(qreal dx, qreal dy)。
  (2)、表示将坐标系统水平方向平移dx个单位,垂直方向平移dy个单位,坐标原点平移到新的点。 在缺省的坐标系统中,单位是像素。
  (3)、假设一个绘图窗口宽300像素,高200像素,原始坐标系统执行translate(150,100),则平移后的坐标系统,原点在窗口的中心,x轴正方向水平向右,y轴正方向竖直向下,左上角点坐标变为(-150,-100),右下角点坐标变为(150,100)。


2、坐标旋转:
  (1)、void rotate(qreal angle)。
  (2)、表示将坐标系统绕坐标原点顺时针旋转angle角度,单位是度。
  (3)、当angle是正数时是顺时针旋转,是负数时是逆时针旋转。
  (4)、假设将1平移后的坐标系统,执行rotate(90),则旋转后的坐标系统,原点在窗口的中心,x轴正方向竖直向下,y轴正方向水平向左,左上角点坐标为(-100, 150),右下角点坐标为(100, -150)。


3、坐标缩放:
  (1)、void scale(qreal sx, qreal sy)。
  (2)、表示将坐标系统x方向缩放sx,y方向缩放sy,比例大于1是放大,小于1是缩小。 (理解: sx=2,则坐标系x轴每个间隔变为原先2倍)


4、状态保存:
  (1)、void save()。
  (2)、QPainter内部有一个坐标变换矩阵,save()保存当前坐标状态,就是将当前状态压入堆栈。


5、状态恢复:
  (1)、void restore()。
  (2)、Qpainter恢复上次保存的坐标状态,就是从堆栈中弹出上次的状态。
  (3)、save()和restore()得配对使用,操作的是一个堆栈对象。


6、复位所有坐标变换:
  (1)、void resetTransform()。
  (2)、QPainter复位所有坐标变换,恢复原始的坐标系统。
  


  
三、绘制3个五角星的程序实例:

void Widget::paintEvent(QPaintEvent * event)
{
    QPainter painter(this);
    painter.setRenderHint(QPainter::Antialiasing);

    QPen pen;
    pen.setColor(Qt::blue);
    pen.setStyle(Qt::SolidLine);
    painter.setPen(pen);

    QBrush brush;
    brush.setColor(Qt::yellow);
    brush.setStyle(Qt::SolidPattern);
    painter.setBrush(brush);

    QFont font;
    font.setPointSize(10);
    font.setBold(true);
    painter.setFont(font);

    qreal R = 100;

    //度转弧的公式: 弧度 = 角度 * (Pie / 180)
    //1度等于Pie/180弧度
    qreal deg = (360 / 5) * (3.14159 / 180);

    QPoint points[5] = {
        QPoint(R, 0),
        QPoint(R * std::cos(deg), -R * std::sin(deg)),
        QPoint(R * std::cos(2 * deg), -R * std::sin(2 * deg)),
        QPoint(R * std::cos(3 * deg), -R * std::sin(3 * deg)),
        QPoint(R * std::cos(4 * deg), -R * std::sin(4 * deg))
    };

    QPainterPath starPath;
    starPath.moveTo(points[0]);
    starPath.lineTo(points[2]);
    starPath.lineTo(points[4]);
    starPath.lineTo(points[1]);
    starPath.lineTo(points[3]);
    starPath.closeSubpath();
    starPath.addText(points[0], font, "0");
    starPath.addText(points[1], font, "1");
    starPath.addText(points[2], font, "2");
    starPath.addText(points[3], font, "3");
    starPath.addText(points[4], font, "4");

    painter.save();
    painter.translate(120, 120);
    painter.drawPath(starPath);
    painter.drawText(0, 0, "S1");

    painter.restore();
    painter.translate(300, 120);
    painter.rotate(90);
    painter.scale(0.8, 0.8);
    painter.drawPath(starPath);
    painter.drawText(0, 0, "S2");

    painter.resetTransform();
    painter.translate(500, 120);
    painter.rotate(-90);
    painter.scale(1.1, 0.8);
    painter.drawPath(starPath);
    painter.drawText(0, 0, "S3");
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

清醒的兰

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值