在QT中绘画首先需要创建QRect容器储存图形的属性,其次再QPainter创建画笔在QImage、QPixmap、QBitmap 和 QPicture中绘制
一、头文件
#include <QPainter>
#include <QRect>
#include <QColor>
#include <QVector>
#include <QPoint>
二、创建容器
(1)创建QRect容器储存直线、矩形、椭圆,vector<QPoint>容器储存铅笔
QVector<int> _shape; //全部容器
QVector<QRect> _allShape; //所有图形
QVector<QVector<QPoint> > _pen; //铅笔线容器
QVector<QRect> _line; //直线容器
QVector<QRect> _ellipse; //椭圆容器
QVector<QRect> _rects; //矩形容器
(2)创建线宽、画笔颜色、填充颜色等属性容器
int _width; //当前线宽
QVector<int> _widths; //线宽容器
QVector<QColor> _colors; //画笔颜色容器
QVector<QColor> _fillcolors; //填充色容器
QVector<int> _isfills; //填充标志容器
int _isfill; //当前填充标志
QColor _color; //当前画笔颜色
QColor _fillcolor; //当前填充颜色
三、进行绘图
QPoint _begin; //开始坐标
bool_lpress = false; //鼠标按下标志
int _drag = 0; //拖拽标志
int _drawType = 0; //当前绘画类型标志
(1)进行对所绘制图形的选择
void MainWindow::Lines()
{
cont._drawType = 1; //铅笔
}
void MainWindow::Rects()
{
cont._drawType = 2; //矩形
cont._drag = 0;
}
void MainWindow::Ellipses()
{
cont._drawType = 3; //椭圆
cont._drag = 0;
}
void MainWindow::Line()
{
cont._drawType = 4; //直线
}
(2)绘制所选图形
对以下四个函数进行重载(paintEvent函数中可使用不同的类进行图像处理)
void MainWindow::mousePressEvent(QMouseEvent* e) //鼠标按下
{
if (e->button() == Qt::LeftButton) //左键按下
{
if (cont._drawType == 1) //铅笔
{
cont._lpress = true; //按下标志为真
QVector<QPoint> line; //新铅笔线写入容器
cont._pen.append(line);
QVector<QPoint>& lastLine = cont._pen.last();
lastLine.append(e->pos()); //新线条的开始坐标
cont._colors.append(cont._color); //记录各种状态
cont._fillcolors.append(Qt::black);
cont._isfills.append(0);
cont._widths.append(cont._width);
cont._shape.append(1);
}
else if (cont._drawType == 2) //矩形
{
cont._lpress = true;
if (!cont._drag) //非拖拽
{
QRect rect;
cont._rects.append(rect);
QRect& lastRect = cont._rects.last();
lastRect.setTopLeft(e->pos());
cont._colors.append(cont._color);
cont._fillcolors.append(cont._fillcolor);
cont._isfills.append(cont._isfill);
cont._widths.append(cont._width);
cont._shape.append(2);
cont._allShape.append(cont._rects.last());
}
else if (cont._rects.last().contains(e->pos())) //拖拽,鼠标在图形内部
{
cont._begin = e->pos(); //记录起始的坐标
}
}
else if (cont._drawType == 3) //椭圆
{
cont._lpress = true;
if (!cont._drag)
{
QRect rect;
cont._ellipse.append(rect);
QRect& lastEllipse = cont._ellipse.last();
lastEllipse.setTopLeft(e->pos());
cont._colors.append(cont._color);
cont._fillcolors.append(cont._fillcolor);
cont._isfills.append(cont._isfill);
cont._widths.append(cont._width);
cont._shape.append(3);
cont._allShape.append(cont._ellipse.last());
}
else if (cont._ellipse.last().contains(e->pos()))
{
cont._begin = e->pos();
}
}
else if (cont._drawType == 4) //直线
{
cont._lpress = true;
QRect rect;
cont._line.append(rect);
QRect& lastLine = cont._line.last();
lastLine.setTopLeft(e->pos());
cont._colors.append(cont._color);
cont._fillcolors.append(Qt::black);
cont._isfills.append(0);
cont._widths.append(cont._width);
cont._shape.append(4);
cont._allShape.append(cont._line.last());
}
}
}
void MainWindow::mouseMoveEvent(QMouseEvent* e) //鼠标移动
{
if (cont._drag && ((cont._drawType == 2 && cont._rects.last().contains(e->pos())) ||
(cont._drawType == 3 && cont._ellipse.last().contains(e->pos())))) //拖拽中
{
setCursor(Qt::SizeAllCursor); //设置十字光标
}
else
{
setCursor(Qt::ArrowCursor); //恢复原始光标形状
cont._drag = 0;
}
if (cont._lpress)
{
if (cont._drawType == 1) //铅笔画线,下同
{
if (cont._pen.size() <= 0) //容器非空
return;
QVector<QPoint>& lastLine = cont._pen.last(); //取得新线条
lastLine.append(e->pos()); //容器内存入线条轨迹
update(); //更新画板
}
else if (cont._drawType == 2) //矩形
{
if (cont._drag == 0) //非拖拽
{
QRect& lastRect = cont._rects.last();
lastRect.setBottomRight(e->pos()); //更新右下角坐标
}
else //拖拽
{
QRect& lastRect = cont._rects.last();
if (lastRect.contains(e->pos())) //在矩形的内部
{
int dx = e->pos().x() - cont._begin.x(); //移动
int dy = e->pos().y() - cont._begin.y();
lastRect = lastRect.adjusted(dx, dy, dx, dy); //更新位置
cont._begin = e->pos(); //刷新拖拽点起始坐标
}
}
update();
}
else if (cont._drawType == 3) //椭圆
{
if (cont._drag == 0)
{
QRect& lastEllipse = cont._ellipse.last(); //拿到椭圆
lastEllipse.setBottomRight(e->pos()); //更新椭圆右下角坐标
}
else
{
QRect& lastEllipse = cont._ellipse.last();
if (lastEllipse.contains(e->pos()))
{
int dx = e->pos().x() - cont._begin.x(); //移动
int dy = e->pos().y() - cont._begin.y();
lastEllipse = lastEllipse.adjusted(dx, dy, dx, dy);
cont._begin = e->pos();
}
}
update();
}
else if (cont._drawType == 4) //直线
{
QRect& lastLine = cont._line.last();
lastLine.setBottomRight(e->pos());
update();
}
}
}
void MainWindow::mouseReleaseEvent(QMouseEvent* e) //鼠标松开
{
if (cont._lpress)
{
if (cont._drawType == 1) //铅笔线
{
QVector<QPoint>& lastLine = cont._pen.last();
lastLine.append(e->pos()); //记录线条的结束坐标
cont._lpress = false; //标志左键释放
}
else if (cont._drawType == 2) //矩形
{
QRect& lastRect = cont._rects.last();
if (!cont._drag) //非拖拽
{
lastRect.setBottomRight(e->pos()); //更新右下角坐标
this->cursor().setPos(this->cursor().pos().x() - lastRect.width() / 2,
this->cursor().pos().y() - lastRect.height() / 2); //光标置图形中心
cont._drag = 1; //拖拽标志
}
cont._lpress = false; //松开标志
}
else if (cont._drawType == 3) //椭圆
{
QRect& lastEllipse = cont._ellipse.last();
if (!cont._drag)
{
lastEllipse.setBottomRight(e->pos());
this->cursor().setPos(this->cursor().pos().x() - lastEllipse.width() / 2,
this->cursor().pos().y() - lastEllipse.height() / 2);
cont._drag = 1;
}
cont._lpress = false;
}
else if (cont._drawType == 4) //直线
{
QRect& lastLine = cont._line.last();
lastLine.setBottomRight(e->pos());
cont._lpress = false;
}
}
}
void MainWindow::paintEvent(QPaintEvent*) //重绘
{
QPicture pic;
QPainter p;
p.begin(&pic);
int ipen = 0, irect = 0, iellipse = 0, iline = 0; //工具索引
for (int c = 0; c < cont._shape.size(); ++c) //循环重绘容器内所有项
{
QPen pen(QColor(cont._colors.at(c))); //每次循环设置画笔
pen.setWidth(cont._widths.at(c)); //线宽
if (cont._isfills.at(c)) //填充
{
QBrush brush(QColor(cont._fillcolors.at(c)));
p.setBrush(brush);
}
else
{
p.setBrush(QBrush(Qt::NoBrush));
}
p.setPen(pen);
if (cont._shape[c] == 1) //铅笔线
{
const QVector<QPoint>& line = cont._pen.at(ipen++); //分段绘制铅笔线
for (int j = 0; j < line.size() - 1; ++j) { p.drawLine(line.at(j), line.at(j + 1)); }
}
else if (cont._shape[c] == 2) //矩形
{
p.drawRect(cont._rects.at(irect));
irect++;
}
else if (cont._shape[c] == 3) //椭圆
{
p.drawEllipse(cont._ellipse.at(iellipse));
iellipse++;
}
else if (cont._shape[c] == 4) //直线
{
p.drawLine(cont._line.at(iline).topLeft(), cont._line.at(iline).bottomRight());
iline++;
}
}
p.end();
p.begin(this);
p.drawPicture(0,0,pic);
}
(3)添加所绘制图形的属性
void MainWindow::ChoseWid() //选线宽
{
QInputDialog* inPut = new QInputDialog(this);
cont._width = inPut->getInt(this, "输入线宽", "请输入线宽(1-50)", cont._width, 1, 50);
//线宽对话框,1-50
}
void MainWindow::ChoseClr() //选画笔颜色
{
QColorDialog* colDig = new QColorDialog(this); //颜色对话框
colDig->setWindowTitle(QString("画笔颜色选择"));
colDig->setGeometry(500, 300, 556, 428);
cont._color = colDig->getColor(); //当前颜色
}
void MainWindow::ChosefilClr() //选填充色
{
QColorDialog* colDig = new QColorDialog(this); //颜色对话框
colDig->setWindowTitle(QString("填充颜色选择"));
colDig->setGeometry(500, 300, 556, 428);
cont._fillcolor = colDig->getColor(); //当前填充色
cont._isfill = 1; //填充标志
}