實作思路:采取畫多個圓進行疊加實作3D的效果(參考另外的一個部落格内容,忘記具體是哪個了
![](https://img.laitimes.com/img/_0nNw4CM6IyYiwiM6ICdiwiIml2ZuQWYz9CX0xWdhZWZk9CX09Wbl9lcvRXakVGa49CXy9GdpRWZoh3LcRXZu5ibkN3Yuc2bsJmLjlGdhR3cvw1LcpDc0RHaiojIsJye.gif)
)。
效果1:
代碼實作:
void CPieWidget::drawDefault3DPie( QPainter *painter )
{
qreal sum = getSumValue();
int radius = m_radius; //直徑
//QRect rect = m_pierect;//(w/2-radius/2,h/2-radius/2,radius,radius);
painter->save();
QPoint centerp = m_pierect.center();
QTransform tr;
tr.translate(centerp.x(),centerp.y());
tr.rotate(-20,Qt::ZAxis);
tr.rotate(0,Qt::YAxis);
painter->setTransform(tr);
QRect rect(-radius/2,-radius/2,radius,radius);
//畫底圖
int dep = 20/*radius/30*/;
QPen pen;
pen.setWidthF(0.2);
painter->setPen(pen);
//painter->setPen(Qt::NoPen);
QStringList keylist = m_datamap.keys();
for (int j = 0 ; j < dep; ++j)
{
qreal index = 30; //啟始位置
int colorindex = 0;
for (int i = 0; i < keylist.count(); ++i)
{
qreal v = m_datamap.value(keylist.at(i));
v =v/sum*(360);
QRect newrect = rect;
if (m_explodedindex == i || m_isexploded)
{
QPoint newcenter = newrect.center();
int midangel = index+v/2;
QPoint tp = getMovePoint(midangel);
newcenter += tp;
newrect.moveCenter(newcenter);
}
QPoint cp = newrect.center() + QPoint(j/2,-j);
newrect.moveCenter(cp);
QPoint centerPoint = newrect.center();
QColor firstColor = m_colorlist.at(colorindex);
QRadialGradient firstGradient(centerPoint, radius/2);
if (j == 19)
{
firstGradient.setColorAt(0, firstColor.lighter(120));
firstGradient.setColorAt(1.0, firstColor.lighter(100));
}
else
firstGradient.setColorAt(1.0, firstColor.dark(150));
painter->setBrush(firstGradient);
painter->drawPie(newrect, index * 16, v * 16);
index+=v;
colorindex++;
if (colorindex==m_colorlist.count())
{
colorindex = 0;
}
}
}
painter->restore();
}
效果2:
代碼如下:
void CPieWidget::drawDount3DPie( QPainter *painter )
{
qreal sum = getSumValue();
int radius = m_radius; //直徑
QPoint centerp = m_pierect.center();
painter->save();
QTransform tr;
tr.translate(centerp.x(),centerp.y());
tr.rotate(-20,Qt::ZAxis);
tr.rotate(0,Qt::YAxis);
painter->setTransform(tr);
//QRect rect(w/2-radius/2,h/2-radius/2,radius,radius);
QRect rect(-radius/2,-radius/2,radius,radius);
//畫底圖
int dep = 20/*radius/30*/;
QPen pen;
pen.setWidthF(0.2);
painter->setPen(pen);
painter->setPen(Qt::NoPen);
QStringList keylist = m_datamap.keys();
for (int j = 0 ; j < dep; ++j)
{
qreal index = 30; //啟始位置
int colorindex = 0;
for (int i = 0; i < keylist.count(); ++i)
{
qreal v = m_datamap.value(keylist.at(i));
v =v/sum*(360);
QRect newrect = rect;
if (m_explodedindex == i || m_isexploded)
{
QPoint newcenter = newrect.center();
int midangel = index+v/2;
QPoint tp = getMovePoint(midangel);
newcenter += tp;
newrect.moveCenter(newcenter);
}
QPoint cp = newrect.center() + QPoint(j/2,-j);
newrect.moveCenter(cp);
QPoint centerPoint = newrect.center();
QColor firstColor = m_colorlist.at(colorindex);
QRadialGradient firstGradient(centerPoint, radius/2);
firstGradient.setColorAt(0, Qt::transparent);
firstGradient.setColorAt(0.6, Qt::transparent);
if (j == 19)
{
firstGradient.setColorAt(0.61, firstColor.lighter(120));
firstGradient.setColorAt(1.0, firstColor.lighter(100));
}
else
{
firstGradient.setColorAt(0.61, firstColor.dark(120));
firstGradient.setColorAt(1.0, firstColor.dark(150));
}
painter->setBrush(firstGradient);
painter->drawPie(newrect, index * 16, v * 16);
index+=v;
colorindex++;
if (colorindex==m_colorlist.count())
{
colorindex = 0;
}
}
}
painter->restore();
}
相關變量說明
QHash<QString,float> m_datamap;
QList<QColor> m_colorlist;
QRect m_pierect;
QRect m_legendrect;
int m_radius;
///
這種方式實作可能會影響效率,因為循環畫了多次。