3093 lines
146 KiB
C++
3093 lines
146 KiB
C++
#pragma warning(push,0)
|
||
|
||
#include <QPainter>
|
||
#include <QtDebug>
|
||
#include <QGraphicsWidget>
|
||
#include <QGraphicsView>
|
||
#include <QStyleOptionGraphicsItem>
|
||
#include "LogmudItemDrawer.h"
|
||
#include <QtSvg/QSvgRenderer>
|
||
#include <QtGlobal>
|
||
#include <float.h>
|
||
#include "geometryutils.h"
|
||
#pragma warning(pop)
|
||
|
||
extern double g_dPixelPerCm;//每厘米像素数
|
||
|
||
LogmudItemDrawer::LogmudItemDrawer()
|
||
{
|
||
m_pViewInfoLogmud = new ViewInfoLogmud;
|
||
}
|
||
|
||
|
||
QPointF LogmudItemDrawer::DrawItem(QPainter* painter, LogmudResultItem* item,
|
||
const QRectF& tmprt,
|
||
bool IsWellSectonHorizonLayout ) const
|
||
{
|
||
float dd=0;
|
||
QPointF pt;
|
||
LogmudResultItem* resultitem = item;
|
||
if(resultitem != NULL)
|
||
{
|
||
//CObjLogmudResult *pCore = dynamic_cast<CObjLogmudResult *>(m_NodeBuilder->GetOSGObject());
|
||
QRectF rt=tmprt;//viewInfoItem.rect;// 获取绘图区域矩形
|
||
QPointF pt1(rt.x()+rt.width()*0.5,rt.center().y());
|
||
QPointF pt2(rt.x()+rt.width()*0.5,rt.center().y()-resultitem->GetNumber()/2);
|
||
QPointF pt3(rt.x()+rt.width()*0.5,rt.center().y()+5.0);
|
||
float lscalelen=0;
|
||
painter->save();// 保存当前绘图状态,以便后面恢复
|
||
QFont font("黑体", 10);// =m_pSceneManager->GetZoomedFont(m_pViewInfoLogmud->GetLogScaleFont());
|
||
painter->setFont(font);
|
||
pt1=painter->transform().map(pt1);// 将点转换到当前坐标系
|
||
pt2=painter->transform().map(pt2);
|
||
pt3=painter->transform().map(pt3);
|
||
//pCore->m_R=(pt3.y()-pt1.y())/5.0/m_pSceneManager->GetCoordinate()->GetPixelPerCm();// 计算半径
|
||
rt=painter->transform().mapRect(rt);
|
||
QRectF rc=painter->transform().mapRect(rc); // 将矩形rc转换到当前坐标系
|
||
QTransform transform;
|
||
transform.reset();
|
||
painter->setWorldTransform(transform);
|
||
|
||
QFont ft("黑体", 13);// = GetSceneManager()->GetZoomedFont(m_pViewInfoLogmud->GetFont());// 获取缩放后的字体
|
||
painter->setFont(ft);
|
||
QFontMetrics fm(ft);
|
||
if(m_isOneScale||!m_bisHi){
|
||
dd=rt.width()*2.0/10;// 设置边距为宽度的20%
|
||
if(dd>1* g_dPixelPerCm) // 如果边距太大
|
||
dd=1* g_dPixelPerCm;
|
||
}
|
||
// else {
|
||
// dd=fm.height()*((pCore->GetFieldName().size()-1)*2+1);// 根据字段名数量计算边距
|
||
// }
|
||
//设置高度和设置画笔
|
||
float h = m_fHei;// m_pViewInfoLogmud->GetrHeight();
|
||
float timemin = m_fTimemin;// m_pViewInfoLogmud->GetTimeMin();// 获取时间最小值
|
||
float timemax = m_fTimemax;// m_pViewInfoLogmud->GetTimeMax();// 获取时间最大值
|
||
if(h<=0) h=1;
|
||
h*= g_dPixelPerCm;
|
||
QPen pen1=painter->pen();
|
||
QColor cl(0,0,0);
|
||
pen1.setColor(cl);
|
||
pen1.setWidth(1);
|
||
painter->setPen(pen1);
|
||
float len=0,w=0;
|
||
|
||
//开始绘制
|
||
{
|
||
painter->save();
|
||
pt=pt1;
|
||
len=rt.width()-2*dd;
|
||
w=len;
|
||
dd+=dd/2;
|
||
{
|
||
///刻度
|
||
int m_nLogarithmic=m_pViewInfoLogmud->GetLogarithmic();
|
||
|
||
//m_LeftVal=m_pViewInfoLogmud->GetPropertyMin();
|
||
//m_RightVal=m_pViewInfoLogmud->GetPropertyMax();
|
||
float lval=m_LeftVal;
|
||
if(m_nLogarithmic ==AXIS_LOGARITHMIC){
|
||
if(lval<=0) lval=0.1;
|
||
lval=log10(lval);
|
||
}
|
||
float rval=m_RightVal;
|
||
if(m_nLogarithmic ==AXIS_LOGARITHMIC)
|
||
{
|
||
if(m_RightVal<=0) rval=0.1;
|
||
rval=log10(rval);
|
||
}
|
||
if(lval==rval)
|
||
{
|
||
if(lval==0) rval=0.1;
|
||
else rval=10*lval;
|
||
}
|
||
//if(m_pViewInfoLogmud->GetTLogarithmic()) {
|
||
if(m_nTLogarithmic) {
|
||
if(timemin<=0) timemin=0.1;
|
||
if(timemax<=0) timemin=0.1;
|
||
if(timemin==timemax) timemax=timemin*10;
|
||
}
|
||
float dtime=timemax-timemin;
|
||
if(m_nTLogarithmic ==AXIS_LOGARITHMIC) {
|
||
dtime=log10(timemax)-log10(timemin);
|
||
}
|
||
if(dtime==0) dtime=1;
|
||
/////////////////
|
||
// 如果是3H图版类型
|
||
if(resultitem->type==1){
|
||
// 保存原始坐标系设置
|
||
int originalLogarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
int originalTLogarithmic = m_pViewInfoLogmud->GetTLogarithmic();
|
||
|
||
// 临时设置为对数坐标系
|
||
m_pViewInfoLogmud->SetLogarithmic(AXIS_LOGARITHMIC); // 设置Y轴为对数坐标系
|
||
m_pViewInfoLogmud->SetTLogarithmic(AXIS_LOGARITHMIC); // 设置X轴为对数坐标系
|
||
//定义颜色和阈值
|
||
QColor _valueAreaColors[] = {
|
||
QColor(149,239,149),
|
||
QColor(107,154,238),
|
||
QColor(45,144,45),
|
||
QColor(253,144,10),
|
||
QColor(208,99,99)
|
||
};
|
||
double WhThreshes[] = { 0.5, 17.5, 40.0, 100.0 };
|
||
QString ValueAreaLabels[] = { "干气", "凝析气天然气", "凝析油", "油", "氧化油" };
|
||
//painter->drawEllipse(pt1,30,30);
|
||
float a = (float)WhThreshes[0];
|
||
float b = (float)WhThreshes[1];
|
||
float c = (float)WhThreshes[2];
|
||
float d = (float)WhThreshes[3];
|
||
|
||
///刻度
|
||
//float m_LeftVal;//=pCore->m_LeftVals[k];
|
||
//float m_RightVal;//=pCore->m_RightVals[k];
|
||
int Logarithmic=m_pViewInfoLogmud->GetLogarithmic();
|
||
|
||
//m_LeftVal=m_pViewInfoLogmud->GetPropertyMin();
|
||
//m_RightVal=m_pViewInfoLogmud->GetPropertyMax();
|
||
timemin = 0.1f;
|
||
timemax = 1000.0f;
|
||
float m_LeftVal = 0.1f;
|
||
float m_RightVal = 10000.0f;
|
||
float lval=m_LeftVal;
|
||
if(Logarithmic==AXIS_LOGARITHMIC){
|
||
if(lval<=0) lval=0.1;
|
||
lval=log10(lval);
|
||
}
|
||
float rval=m_RightVal;
|
||
if(Logarithmic==AXIS_LOGARITHMIC)
|
||
{
|
||
if(m_RightVal<=0) rval=0.1;
|
||
rval=log10(rval);
|
||
}
|
||
if(lval==rval)
|
||
{
|
||
if(lval==0) rval=0.1;
|
||
else rval=10*lval;
|
||
}
|
||
if(m_pViewInfoLogmud->GetTLogarithmic()) {
|
||
if(timemin<=0) timemin=0.1;
|
||
if(timemax<=0) timemax=0.1;
|
||
if(timemin==timemax) timemax=timemin*10;
|
||
}
|
||
float dtime=timemax-timemin;
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() ==AXIS_LOGARITHMIC) {
|
||
dtime=log10(timemax)-log10(timemin);
|
||
}
|
||
if(dtime==0) dtime=1;
|
||
if (resultitem->WH > timemax) {
|
||
// 将最大值扩展到下一个10的幂次方
|
||
timemax = pow(10, ceil(log10(resultitem->WH)));
|
||
}
|
||
|
||
// 检查Y轴 (BH值)
|
||
if (resultitem->BH > m_RightVal) {
|
||
// 将最大值扩展到下一个10的幂次方
|
||
m_RightVal = pow(10, ceil(log10(resultitem->BH)));
|
||
}
|
||
|
||
int fnum= m_xGrid;// 默认网格数为5
|
||
//fnum=m_pViewInfoLogmud->GetxGrid();
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() ==AXIS_LOGARITHMIC)// 如果X轴是对数坐标系
|
||
{
|
||
DrawXAxisLogarithmicGrid(painter, timemin, timemax, dd, w, h, rt, pt, fm, lscalelen);
|
||
}
|
||
else //如果y轴是线性坐标系
|
||
{
|
||
DrawXAxisLinearGrid(painter, timemin, timemax, dd, len, h, rt, pt, pt1, fm, fnum);
|
||
}
|
||
//设置Y轴网格数和开始绘制Y轴对数网格
|
||
fnum = m_yGrid;// m_pViewInfoLogmud->GetyGrid();
|
||
if(m_pViewInfoLogmud->GetLogarithmic() ==AXIS_LOGARITHMIC) // 如果Y轴是对数坐标系
|
||
{
|
||
DrawYAxisLogarithmicGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen);
|
||
}
|
||
else // 如果Y轴是线性坐标系,循环绘制fnum+1条网格线
|
||
{
|
||
DrawYAxisLinearGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen, fnum);
|
||
}
|
||
/// DRAW RECT
|
||
for(int m=0;m<5;m++){
|
||
int n=4;
|
||
QPointF Points[5];
|
||
if(m==0) {
|
||
QPointF Points1[] ={
|
||
QPointF(0.1f, 10000),
|
||
QPointF(a, 10000),
|
||
QPointF(a, 1000),
|
||
QPointF(0.1f, 1000),
|
||
};
|
||
for(int j=0;j<4;j++) Points[j]=Points1[j];
|
||
}
|
||
else if(m==1)
|
||
{
|
||
QPointF Points1[] ={
|
||
QPointF(a, 1000),
|
||
QPointF(d, 1000),
|
||
QPointF(d, 100),
|
||
QPointF(a, a),
|
||
};
|
||
for(int j=0;j<4;j++) Points[j]=(Points1[j]);
|
||
}
|
||
else if(m==2)
|
||
{
|
||
QPointF Points1[] ={
|
||
QPointF(b, b),
|
||
QPointF(b, a),
|
||
QPointF(a, a),
|
||
};
|
||
n=3;
|
||
for(int j=0;j<3;j++) Points[j]=(Points1[j]);
|
||
}
|
||
else if(m==3)
|
||
{
|
||
QPointF Points1[] ={
|
||
QPointF(b, b),
|
||
QPointF(c, c),
|
||
QPointF(c, a),
|
||
QPointF(b, a),
|
||
};
|
||
for(int j=0;j<4;j++) Points[j]=(Points1[j]);
|
||
}
|
||
else if(m==4)
|
||
{
|
||
QPointF Points1[] ={
|
||
QPointF(c, c),
|
||
QPointF(d, d),
|
||
QPointF(d, a),
|
||
QPointF(c, a),
|
||
};
|
||
for(int j=0;j<4;j++) Points[j]=(Points1[j]);
|
||
}
|
||
QVector<QPointF> points;
|
||
points.resize(n+1);
|
||
float yval=0;
|
||
int jj=0;
|
||
for(int j=0;j<n;j++)
|
||
{
|
||
if(Points[j].x()<timemin) continue;
|
||
if(Points[j].x()>timemax) continue;
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() ==AXIS_LOGARITHMIC) // 如果X轴是对数坐标系
|
||
{
|
||
float val=Points[j].x();
|
||
if(val<=0) val=timemin;
|
||
points[jj].setX(rt.left()+dd+(log10(val)-log10(timemin))*len/dtime);// 计算对数x坐标
|
||
}
|
||
else {// 如果X轴是线性坐标系
|
||
points[jj].setX(rt.left()+dd+(Points[j].x()-timemin)*len/dtime);
|
||
}
|
||
if(Logarithmic==AXIS_LINEAR) {// 如果Y轴是线性坐标系
|
||
yval=(Points[j].y()-m_LeftVal)/(m_RightVal-m_LeftVal)*h;
|
||
}
|
||
else if(Logarithmic==AXIS_LOGARITHMIC) // 如果Y轴是对数坐标系
|
||
{
|
||
float val=Points[j].y();
|
||
if(val<=0) val=0.1;
|
||
yval=(log10(val)-lval)/(rval-lval)*h;
|
||
|
||
}
|
||
if(yval<0) yval=0;
|
||
if(yval>h) yval=h;
|
||
points[jj++].setY(pt1.y()+h-yval);
|
||
}
|
||
// 在循环前,定义每个区域标签的坐标(人工设置)
|
||
QPointF labelPositions[5] = {
|
||
QPointF(rt.left() + dd + len * (30.0/376.0), rt.top() + h * (20.0/187.0)), // m=0
|
||
QPointF(rt.left() + dd + len * (150.0/376.0), rt.top() + h * (75.0/187.0)), // m=1
|
||
QPointF(rt.left() + dd + len * (170.0/376.0), rt.top() + h * (145.0/187.0)), // m=2
|
||
QPointF(rt.left() + dd + len * (227.0/376.0), rt.top() + h * (135.0/187.0)), // m=3
|
||
QPointF(rt.left() + dd + len * (265.0/376.0), rt.top() + h * (130.0/187.0)) // m=4
|
||
};
|
||
|
||
//绘制多边形
|
||
if(jj>0){// 如果有有效点
|
||
// if(pCore->dotdeps.indexOf(resultitem->GetNumber()) < 0){
|
||
// pCore->dotdeps.append(resultitem->GetNumber());
|
||
// pCore->curves.append(points);
|
||
// }
|
||
painter->save();
|
||
|
||
QColor color=Qt::black;
|
||
QPen pPen=painter->pen();
|
||
pPen.setStyle(Qt::SolidLine);
|
||
float penw=GetLineWidth(painter,1);
|
||
if(penw<1) penw=1;
|
||
pPen.setWidthF(penw);
|
||
pPen.setColor(color);
|
||
painter->setPen(pPen);
|
||
painter->setBrush(_valueAreaColors[m]);
|
||
points[n]=(points[0]);
|
||
painter->drawPolygon(&points[0],jj+1);// 绘制多边形
|
||
// ★ 在这里加区域标签
|
||
QString label = ValueAreaLabels[m];
|
||
QFont font("Microsoft YaHei", 6);
|
||
painter->setFont(font);
|
||
QFontMetrics fm(font);
|
||
|
||
// 文字宽高
|
||
int textWidth = fm.width(label); // 老版本用 width()
|
||
int textHeight = fm.height();
|
||
|
||
// 偏移文字,使坐标为中心
|
||
QPointF centerPos = labelPositions[m];
|
||
QPointF drawPos(centerPos.x() - textWidth/2.0, centerPos.y());
|
||
|
||
painter->drawText(drawPos, label);
|
||
painter->restore();
|
||
}
|
||
}
|
||
painter->save();
|
||
painter->restore();
|
||
// 绘制投点
|
||
DrawDataPoint(painter, resultitem->WH, resultitem->BH, timemin, timemax,
|
||
m_LeftVal, m_RightVal, dd, len, h, rt, pt1, Logarithmic);
|
||
// 绘制深度和轴标题
|
||
DrawDepthAndAxisLabels(painter, resultitem->depth, dd, w, h, rt, pt, fm, lscalelen, "湿度比WH","平衡比BH");
|
||
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
m_pViewInfoLogmud->SetLogarithmic(originalLogarithmic);
|
||
m_pViewInfoLogmud->SetTLogarithmic(originalTLogarithmic);
|
||
|
||
QImage image(400, 300, QImage::Format_RGB32);
|
||
// 用白色填充整个图像
|
||
image.fill(Qt::white);
|
||
QPainter pter(&image);
|
||
|
||
}//判断3H图版的右括号
|
||
|
||
//绘制对数图版
|
||
else if(resultitem->type==2){
|
||
// 保存原始坐标系设置
|
||
int originalLogarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
int originalTLogarithmic = m_pViewInfoLogmud->GetTLogarithmic();
|
||
auto ClampPositiveFinite = [](float v, float minV, float maxV)->float
|
||
{
|
||
if(!IsFiniteNumber(v)||v<=minV) return minV;
|
||
if(v>maxV) return maxV;
|
||
return v;
|
||
};
|
||
float wh = ClampPositiveFinite(resultitem->WH,1.0f,1000000.0f);
|
||
float bh = ClampPositiveFinite(resultitem->BH,1.0f,1000000.0f);
|
||
|
||
// 临时设置为对数坐标系
|
||
m_pViewInfoLogmud->SetLogarithmic(AXIS_LOGARITHMIC); // 设置Y轴为对数坐标系
|
||
m_pViewInfoLogmud->SetTLogarithmic(AXIS_LOGARITHMIC); // 设置X轴为对数坐标系
|
||
//绘制对数图版
|
||
painter->save();
|
||
float timemin = 1.0f;
|
||
float timemax = 1000.0f;
|
||
float m_LeftVal = 1.0f;
|
||
float m_RightVal = 1000.0f;
|
||
if (wh > timemax) {
|
||
// 将最大值扩展到下一个10的幂次方
|
||
timemax = pow(10, ceil(log10(wh)));
|
||
}
|
||
|
||
// 检查Y轴 (BH值)
|
||
if (bh > m_RightVal) {
|
||
// 将最大值扩展到下一个10的幂次方
|
||
m_RightVal = pow(10, ceil(log10(bh)));
|
||
}
|
||
if(!IsFiniteNumber(timemax)||timemax<=timemin) timemax=1000.0f;
|
||
if(!IsFiniteNumber(m_RightVal)||m_RightVal<=m_LeftVal) m_RightVal=1000.0f;
|
||
float lval = m_LeftVal;
|
||
int Logarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
if(Logarithmic == AXIS_LOGARITHMIC){
|
||
if(lval <= 0) lval = 0.1f;
|
||
lval = log10(lval);
|
||
}
|
||
|
||
float rval = m_RightVal;
|
||
if(Logarithmic == AXIS_LOGARITHMIC){
|
||
if(rval <= 0) rval = 0.1f;
|
||
rval = log10(rval);
|
||
}
|
||
|
||
// 重新计算X轴范围
|
||
float dtime = timemax - timemin;
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
dtime = log10(timemax) - log10(timemin);
|
||
}
|
||
if(dtime == 0) dtime = 1;
|
||
// 定义区域标签
|
||
QString labelA = "A";
|
||
QString labelB = "B";
|
||
QString labelC = "C";
|
||
QString labelD = "D";
|
||
// 先绘制坐标系
|
||
int fnum=5;// 默认网格数为5
|
||
fnum=m_pViewInfoLogmud->GetxGrid();
|
||
DrawXAxisLogarithmicGrid(painter, timemin, timemax, dd, w, h, rt, pt, fm, lscalelen);
|
||
//设置Y轴网格数和开始绘制Y轴对数网格
|
||
fnum=m_pViewInfoLogmud->GetyGrid();
|
||
DrawYAxisLogarithmicGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen);
|
||
painter->restore();
|
||
painter->save();
|
||
|
||
// 定义分界线坐标
|
||
QPointF lineABottom(8.0f, m_LeftVal);
|
||
QPointF lineATop(30.0f, m_RightVal);
|
||
|
||
QPointF lineBBottom(30.0f, m_LeftVal);
|
||
QPointF lineBTop(120.0f, m_RightVal);
|
||
|
||
QPointF lineCBottom(120.0f, m_LeftVal);
|
||
QPointF lineCTop(500.0f, m_RightVal);
|
||
|
||
painter->setPen(QPen(Qt::black, 2));
|
||
// 绘制线A
|
||
{
|
||
float x1, y1, x2, y2;
|
||
|
||
// X坐标转换
|
||
if(lineABottom.x() <= 0) lineABottom.setX(timemin);
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
x1 = rt.left()+dd+(log10(lineABottom.x())-log10(timemin))*len/dtime;
|
||
}
|
||
|
||
// Y坐标转换
|
||
if(lineABottom.y() <= 0) lineABottom.setY(m_LeftVal);
|
||
if(Logarithmic == AXIS_LOGARITHMIC) {
|
||
float val = lineABottom.y();
|
||
if(val <= 0) val = 0.1f;
|
||
y1 = (log10(val)-lval)/(rval-lval)*h;
|
||
}
|
||
if(y1 < 0) y1 = 0;
|
||
if(y1 > h) y1 = h;
|
||
y1 = pt1.y()+h-y1;
|
||
|
||
// X坐标转换
|
||
if(lineATop.x() <= 0) lineATop.setX(timemin);
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
x2 = rt.left()+dd+(log10(lineATop.x())-log10(timemin))*len/dtime;
|
||
}
|
||
|
||
|
||
// Y坐标转换
|
||
if(lineATop.y() <= 0) lineATop.setY(m_LeftVal);
|
||
if(Logarithmic == AXIS_LOGARITHMIC) {
|
||
float val = lineATop.y();
|
||
if(val <= 0) val = 0.1f;
|
||
y2 = (log10(val)-lval)/(rval-lval)*h;
|
||
}
|
||
if(y2 < 0) y2 = 0;
|
||
if(y2 > h) y2 = h;
|
||
y2 = pt1.y()+h-y2;
|
||
|
||
painter->drawLine(QPointF(x1, y1), QPointF(x2, y2));
|
||
}
|
||
|
||
// 绘制线B
|
||
{
|
||
float x1, y1, x2, y2;
|
||
|
||
// X坐标转换
|
||
if(lineBBottom.x() <= 0) lineBBottom.setX(timemin);
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
x1 = rt.left()+dd+(log10(lineBBottom.x())-log10(timemin))*len/dtime;
|
||
}
|
||
|
||
|
||
// Y坐标转换
|
||
if(lineBBottom.y() <= 0) lineBBottom.setY(m_LeftVal);
|
||
if(Logarithmic == AXIS_LOGARITHMIC) {
|
||
float val = lineBBottom.y();
|
||
if(val <= 0) val = 0.1f;
|
||
y1 = (log10(val)-lval)/(rval-lval)*h;
|
||
}
|
||
if(y1 < 0) y1 = 0;
|
||
if(y1 > h) y1 = h;
|
||
y1 = pt1.y()+h-y1;
|
||
|
||
// X坐标转换
|
||
if(lineBTop.x() <= 0) lineBTop.setX(timemin);
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
x2 = rt.left()+dd+(log10(lineBTop.x())-log10(timemin))*len/dtime;
|
||
}
|
||
|
||
|
||
// Y坐标转换
|
||
if(lineBTop.y() <= 0) lineBTop.setY(m_LeftVal);
|
||
if(Logarithmic == AXIS_LOGARITHMIC) {
|
||
float val = lineBTop.y();
|
||
if(val <= 0) val = 0.1f;
|
||
y2 = (log10(val)-lval)/(rval-lval)*h;
|
||
}
|
||
if(y2 < 0) y2 = 0;
|
||
if(y2 > h) y2 = h;
|
||
y2 = pt1.y()+h-y2;
|
||
|
||
painter->drawLine(QPointF(x1, y1), QPointF(x2, y2));
|
||
}
|
||
|
||
// 绘制线C
|
||
{
|
||
float x1, y1, x2, y2;
|
||
|
||
// X坐标转换
|
||
if(lineCBottom.x() <= 0) lineCBottom.setX(timemin);
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
x1 = rt.left()+dd+(log10(lineCBottom.x())-log10(timemin))*len/dtime;
|
||
}
|
||
|
||
|
||
// Y坐标转换
|
||
if(lineCBottom.y() <= 0) lineCBottom.setY(m_LeftVal);
|
||
if(Logarithmic == AXIS_LOGARITHMIC) {
|
||
float val = lineCBottom.y();
|
||
if(val <= 0) val = 0.1f;
|
||
y1 = (log10(val)-lval)/(rval-lval)*h;
|
||
}
|
||
if(y1 < 0) y1 = 0;
|
||
if(y1 > h) y1 = h;
|
||
y1 = pt1.y()+h-y1;
|
||
|
||
// X坐标转换
|
||
if(lineCTop.x() <= 0) lineCTop.setX(timemin);
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
x2 = rt.left()+dd+(log10(lineCTop.x())-log10(timemin))*len/dtime;
|
||
}
|
||
|
||
// Y坐标转换
|
||
if(lineCTop.y() <= 0) lineCTop.setY(m_LeftVal);
|
||
if(Logarithmic == AXIS_LOGARITHMIC) {
|
||
float val = lineCTop.y();
|
||
if(val <= 0) val = 0.1f;
|
||
y2 = (log10(val)-lval)/(rval-lval)*h;
|
||
}
|
||
if(y2 < 0) y2 = 0;
|
||
if(y2 > h) y2 = h;
|
||
y2 = pt1.y()+h-y2;
|
||
|
||
painter->drawLine(QPointF(x1, y1), QPointF(x2, y2));
|
||
}
|
||
// 添加区域标签
|
||
painter->setPen(m_pViewInfoLogmud->GetColor());
|
||
|
||
// 计算标签位置
|
||
float labelY = pt1.y() + h*0.3f; // 在高度的1/3处
|
||
|
||
// 计算各标签X坐标
|
||
float labelAX, labelBX, labelCX, labelDX;
|
||
|
||
// X坐标转换
|
||
labelAX = rt.left()+dd+(log10(15.0f)-log10(timemin))*len/dtime - fm.width(labelA)/2;
|
||
labelBX = rt.left()+dd+(log10(60.0f)-log10(timemin))*len/dtime - fm.width(labelB)/2;
|
||
labelCX = rt.left()+dd+(log10(300.0f)-log10(timemin))*len/dtime - fm.width(labelC)/2;
|
||
labelDX = rt.left()+dd+(log10(700.0f)-log10(timemin))*len/dtime - fm.width(labelD)/2;
|
||
|
||
|
||
painter->drawText(QPointF(labelAX-5, labelY), labelA);
|
||
painter->drawText(QPointF(labelBX-5, labelY), labelB);
|
||
painter->drawText(QPointF(labelCX-5, labelY), labelC);
|
||
painter->drawText(QPointF(labelDX-2, labelY), labelD);
|
||
|
||
|
||
// 添加深度值和坐标轴标题
|
||
DrawDepthAndAxisLabels(painter, resultitem->depth, dd, w, h, rt, pt, fm, lscalelen,
|
||
"C2/C1(X1000)", "C3/C1(X1000)");
|
||
// 绘制投点
|
||
DrawDataPoint(painter, wh, bh, timemin, timemax,
|
||
m_LeftVal, m_RightVal, dd, len, h, rt, pt1, Logarithmic);
|
||
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/10, pt1.y()));
|
||
// 图例左上角位置
|
||
float legendX = rt.left() + dd + 5;
|
||
float legendY = pt1.y() + 5;
|
||
float lineSpacing = fm.height() + 2;
|
||
|
||
// 图例文字
|
||
QVector<QString> legendItems;
|
||
legendItems.append("A: 干气或水层气");
|
||
legendItems.append("B: 天然气 → 凝析油");
|
||
legendItems.append("C: 伴生气 → 油");
|
||
legendItems.append("D: 向氧化油过渡");
|
||
|
||
for(int i=0; i<legendItems.size(); ++i){
|
||
float y = legendY + i*lineSpacing;
|
||
painter->drawText(QPointF(legendX, y + fm.ascent()), legendItems[i]);
|
||
}
|
||
// 绘制完成后恢复原始设置
|
||
m_pViewInfoLogmud->SetLogarithmic(originalLogarithmic);
|
||
m_pViewInfoLogmud->SetTLogarithmic(originalTLogarithmic);
|
||
painter->restore();
|
||
}//绘制对数图版右括号
|
||
// 如果是交会图版类型
|
||
/* else if(resultitem->type==3){
|
||
int originalLogarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
int originalTLogarithmic = m_pViewInfoLogmud->GetTLogarithmic();
|
||
|
||
// 临时设置为对数坐标系
|
||
m_pViewInfoLogmud->SetLogarithmic(AXIS_LINEAR); // 设置Y轴为线性坐标系
|
||
m_pViewInfoLogmud->SetTLogarithmic(AXIS_LINEAR); // 设置X轴为线性坐标系
|
||
|
||
float timemin = 0.0f;
|
||
float timemax = 5.0f;
|
||
float m_LeftVal = 0.0f;
|
||
float m_RightVal = 1.0f;
|
||
if (resultitem->WH > timemax) {
|
||
// 将最大值扩展到下一个10的幂次方
|
||
timemax = pow(10, ceil(log10(resultitem->WH)));
|
||
}
|
||
|
||
// 检查Y轴 (BH值)
|
||
if (resultitem->BH > m_RightVal) {
|
||
// 将最大值扩展到下一个10的幂次方
|
||
m_RightVal = pow(10, ceil(log10(resultitem->BH)));
|
||
}
|
||
|
||
float lval = m_LeftVal;
|
||
int Logarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
|
||
float rval = m_RightVal;
|
||
if(Logarithmic == AXIS_LOGARITHMIC){
|
||
if(rval <= 0) rval = 0.1f;
|
||
rval = log10(rval);
|
||
}
|
||
|
||
// 重新计算X轴范围
|
||
float dtime = timemax - timemin;
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
dtime = log10(timemax) - log10(timemin);
|
||
}
|
||
if(dtime == 0) dtime = 1;
|
||
|
||
int fnum=10;// 默认网格数为10
|
||
//设置X轴网格数和开始绘制X轴线性网格
|
||
if(m_pViewInfoLogmud->GetTLogarithmic()==AXIS_LINEAR) //如果X轴是线性坐标系
|
||
{
|
||
DrawXAxisLinearGrid(painter, timemin, timemax, dd, len, h, rt, pt, pt1, fm, fnum);
|
||
}
|
||
//设置Y轴网格数和开始绘制Y轴线性网格
|
||
fnum=10;
|
||
if(m_pViewInfoLogmud->GetLogarithmic()==AXIS_LOGARITHMIC) // 如果Y轴是对数坐标系
|
||
{
|
||
DrawYAxisLogarithmicGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen);
|
||
}
|
||
else // 如果Y轴是线性坐标系,循环绘制fnum+1条网格线
|
||
{
|
||
DrawYAxisLinearGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen, fnum);
|
||
}
|
||
// 绘制深度和轴标题
|
||
DrawDepthAndAxisLabels(painter, resultitem->depth, dd, w, h, rt, pt, fm, lscalelen, pCore,"C1/TG","C2/C3");
|
||
// 绘制投点
|
||
DrawDataPoint(painter, resultitem->WH, resultitem->BH, timemin, timemax,
|
||
m_LeftVal, m_RightVal, dd, len, h, rt, pt1, Logarithmic);
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
// 绘制完成后恢复原始设置
|
||
m_pViewInfoLogmud->SetLogarithmic(originalLogarithmic);
|
||
m_pViewInfoLogmud->SetTLogarithmic(originalTLogarithmic);
|
||
|
||
}//判断交会图版的右括号
|
||
|
||
else if(resultitem->type==4){
|
||
painter->save();
|
||
// 设置坐标范围
|
||
float timemax = 0.17f; // 三角图版的坐标轴逻辑长度
|
||
// 从resultitem中获取比例值
|
||
float ratioC2 = resultitem->WH; // 左侧
|
||
float ratioC3 = resultitem->BH; // 底边
|
||
float ratioNC4 = resultitem->DH; // 右侧
|
||
// 约束异常比例值,避免内三角计算把图形拉到图道外。
|
||
if(ratioC2!=ratioC2||ratioC2<0) ratioC2=0;
|
||
if(ratioC3!=ratioC3||ratioC3<0) ratioC3=0;
|
||
if(ratioNC4!=ratioNC4||ratioNC4<0) ratioNC4=0;
|
||
if(ratioC2>timemax) ratioC2=timemax;
|
||
if(ratioC3>timemax) ratioC3=timemax;
|
||
if(ratioNC4>timemax) ratioNC4=timemax;
|
||
float ratioSum=ratioC2+ratioC3+ratioNC4;
|
||
if(ratioSum>timemax*0.98f&&ratioSum>1e-6f)
|
||
{
|
||
float scaleDown=timemax*0.98f/ratioSum;
|
||
ratioC2*=scaleDown;
|
||
ratioC3*=scaleDown;
|
||
ratioNC4*=scaleDown;
|
||
}
|
||
float scaleFactor = 1.5f;
|
||
|
||
// 计算等边三角形的实际尺寸
|
||
float availableWidth = len;
|
||
float availableHeight = h * 1.2f;
|
||
float triangleSide = qMin(availableWidth, availableHeight * 2.0f / sqrt(3.0f)) * scaleFactor;
|
||
|
||
// 确保缩放后三角形不超出可用空间
|
||
if (triangleSide > availableWidth) {
|
||
triangleSide = availableWidth;
|
||
}
|
||
if (triangleSide * sqrt(3.0f) / 2.0f > availableHeight) {
|
||
triangleSide = availableHeight * 2.0f / sqrt(3.0f);
|
||
}
|
||
//坐标设置
|
||
float scale = triangleSide / timemax; // 计算缩放比例
|
||
float offsetX = rt.left() + dd + (availableWidth - triangleSide) / 2.0f; // 居中显示
|
||
float offsetY = pt1.y() + h;
|
||
float sin60 = sqrt(3.0f) / 2.0f;
|
||
float cos60 = 0.5f;
|
||
float tan60 = sqrt(3.0f);
|
||
float triangleHeight = timemax * sin60;
|
||
// 逻辑坐标转像素坐标
|
||
auto GetPoint = [&](float x, float y) -> QPointF {
|
||
return QPointF(
|
||
offsetX + x * scale,
|
||
offsetY - y * scale
|
||
);
|
||
};
|
||
QPointF pointA = GetPoint(0.0f, 0.0f); // 左下角
|
||
QPointF pointB = GetPoint(timemax/2.0f, triangleHeight); // 顶部
|
||
QPointF pointC = GetPoint(timemax, 0.0f); // 右下角
|
||
// 绘制三角形框架
|
||
QPen penAxis(Qt::black, 2);
|
||
painter->setPen(penAxis);
|
||
painter->drawPolygon(QPolygonF() << pointA << pointB << pointC);
|
||
|
||
// 绘制辅助线网格
|
||
QPen penGuide(QColor(220, 220, 220), 1);
|
||
painter->setPen(penGuide);
|
||
|
||
int steps = 17;
|
||
float step = timemax / steps;
|
||
// 计算网格线点集
|
||
QVector<QPointF> pointsBottom;
|
||
QVector<QPointF> pointsLeft;
|
||
QVector<QPointF> pointsRight;
|
||
//绘制辅助线
|
||
for (int i = 0; i <= steps; i++) {
|
||
float ratio = (float)i / steps;
|
||
|
||
// 底边上的点 (从A到C)
|
||
pointsBottom.append(GetPoint(timemax * ratio, 0.0f));
|
||
|
||
// 左侧边上的点 (从A到B)
|
||
float leftX = timemax * ratio / 2.0f;
|
||
float leftY = timemax * ratio * sin60;
|
||
pointsLeft.append(GetPoint(leftX, leftY));
|
||
|
||
// 右侧边上的点 (从C到B)
|
||
float rightX = timemax - (timemax * ratio / 2.0f);
|
||
float rightY = timemax * ratio * sin60;
|
||
pointsRight.append(GetPoint(rightX, rightY));
|
||
}
|
||
|
||
// 绘制网格线
|
||
for (int i = 1; i < steps; i++) {
|
||
// 绘制三条方向的网格线
|
||
painter->drawLine(pointsBottom[i], pointsLeft[i]);
|
||
painter->drawLine(pointsLeft[i], pointsRight[i]);
|
||
painter->drawLine(pointsBottom[i], pointsRight[steps - i]);
|
||
}
|
||
painter->restore();
|
||
//绘制价值区(气产区和油产区)
|
||
painter->save();
|
||
QPainterPath outerTriClipPath;
|
||
outerTriClipPath.addPolygon(QPolygonF() << pointA << pointB << pointC);
|
||
painter->setClipPath(outerTriClipPath,Qt::IntersectClip);
|
||
|
||
// 气产区(黄色)
|
||
QVector<QPointF> gasArea;
|
||
gasArea.append(QPointF(0.06445464f, 0.1097643f));
|
||
gasArea.append(QPointF(0.07913243f, 0.13444f));
|
||
gasArea.append(QPointF(0.08508863f, 0.1333764f));
|
||
gasArea.append(QPointF(0.09147028f, 0.1206131f));
|
||
gasArea.append(QPointF(0.09402294f, 0.1065735f));
|
||
gasArea.append(QPointF(0.08998123f, 0.09338477f));
|
||
gasArea.append(QPointF(0.06445464f, 0.1097643f));
|
||
|
||
// 油产区(橙色)
|
||
QVector<QPointF> oilArea;
|
||
oilArea.append(QPointF(0.06445464f, 0.1097643f));
|
||
oilArea.append(QPointF(0.05870667f, 0.09656f));
|
||
oilArea.append(QPointF(0.05666667f, 0.068f));
|
||
oilArea.append(QPointF(0.06573334f, 0.05168f));
|
||
oilArea.append(QPointF(0.08613333f, 0.0374f));
|
||
oilArea.append(QPointF(0.09633333f, 0.04465333f));
|
||
oilArea.append(QPointF(0.09814667f, 0.06074667f));
|
||
oilArea.append(QPointF(0.09293333f, 0.08658667f));
|
||
oilArea.append(QPointF(0.08998123f, 0.09338477f));
|
||
oilArea.append(QPointF(0.06445464f, 0.1097643f));
|
||
|
||
// 转换逻辑坐标到像素坐标
|
||
QVector<QPointF> gasPixelPoints;
|
||
for (int i = 0; i < gasArea.size(); i++) {
|
||
gasPixelPoints.append(GetPoint(gasArea[i].x(), gasArea[i].y()));
|
||
}
|
||
// 使用平滑曲线绘制气产区
|
||
QPainterPath gasPath;
|
||
if (gasPixelPoints.size() > 0) {
|
||
gasPath.moveTo(gasPixelPoints[0]);
|
||
|
||
// 创建平滑曲线
|
||
for (int i = 1; i < gasPixelPoints.size(); i++) {
|
||
QPointF p1 = gasPixelPoints[i-1];
|
||
QPointF p2 = gasPixelPoints[i];
|
||
QPointF midPoint = (p1 + p2) / 2.0;
|
||
gasPath.quadTo(p1, midPoint);
|
||
}
|
||
|
||
// 闭合路径
|
||
if (gasPixelPoints.size() > 2) {
|
||
QPointF p1 = gasPixelPoints.last();
|
||
QPointF p2 = gasPixelPoints.first();
|
||
QPointF midPoint = (p1 + p2) / 2.0;
|
||
gasPath.quadTo(p1, midPoint);
|
||
gasPath.quadTo(p2, gasPixelPoints[0]);
|
||
}
|
||
}
|
||
// 绘制气产区
|
||
painter->setBrush(QColor(0xfe, 0xfa, 0xb2, 200)); // 黄色,200透明度
|
||
painter->setPen(Qt::NoPen);
|
||
painter->drawPath(gasPath);
|
||
|
||
// 转换油产区逻辑坐标到像素坐标
|
||
QPainterPath oilPath;
|
||
QVector<QPointF> oilPixelPoints;
|
||
for (int i = 0; i < oilArea.size(); i++) {
|
||
oilPixelPoints.append(GetPoint(oilArea[i].x(), oilArea[i].y()));
|
||
}
|
||
if (oilPixelPoints.size() > 0) {
|
||
oilPath.moveTo(oilPixelPoints[0]);
|
||
|
||
// 创建平滑曲线
|
||
for (int i = 1; i < oilPixelPoints.size(); i++) {
|
||
QPointF p1 = oilPixelPoints[i-1];
|
||
QPointF p2 = oilPixelPoints[i];
|
||
QPointF midPoint = (p1 + p2) / 2.0;
|
||
oilPath.quadTo(p1, midPoint);
|
||
}
|
||
|
||
// 闭合路径
|
||
if (oilPixelPoints.size() > 2) {
|
||
QPointF p1 = oilPixelPoints.last();
|
||
QPointF p2 = oilPixelPoints.first();
|
||
QPointF midPoint = (p1 + p2) / 2.0;
|
||
oilPath.quadTo(p1, midPoint);
|
||
oilPath.quadTo(p2, oilPixelPoints[0]);
|
||
}
|
||
}
|
||
// 绘制油产区
|
||
painter->setBrush(QColor(0xf7, 0xb7, 0x89, 200)); // 橙色,200透明度
|
||
painter->drawPath(oilPath);
|
||
// 气产区文字
|
||
QPointF gasLabelPos = GetPoint(0.067f, 0.11f); // 根据气产区大概位置
|
||
painter->setPen(Qt::black);
|
||
painter->setFont(QFont("Arial", 10, QFont::Bold));
|
||
painter->drawText(gasLabelPos, "气产区");
|
||
|
||
// 油产区文字
|
||
QPointF oilLabelPos = GetPoint(0.064f, 0.07f); // 根据油产区大概位置
|
||
painter->setPen(Qt::black);
|
||
painter->setFont(QFont("Arial", 10, QFont::Bold));
|
||
painter->drawText(oilLabelPos, "油产区");
|
||
// 计算内三角顶点
|
||
|
||
// 顶点A' (C2比例)
|
||
float aXp = ratioC2 * cos60 + ratioNC4;
|
||
float aYp = ratioC2 * sin60;
|
||
|
||
// 顶点B' (C3比例)
|
||
float bXp = (timemax - ratioC3 - ratioNC4) / 2 + ratioNC4;
|
||
float bYp = (bXp - ratioNC4) * tan60;
|
||
|
||
// 顶点C' (nC4比例)
|
||
float cYp = aYp;
|
||
float cXp = timemax - cYp / tan60 - ratioC3;
|
||
auto ClampToTriangle = [timemax,triangleHeight,tan60](float& x,float& y)
|
||
{
|
||
if(y<0) y=0;
|
||
if(y>triangleHeight) y=triangleHeight;
|
||
float minX=y/tan60;
|
||
float maxX=timemax-y/tan60;
|
||
if(x<minX) x=minX;
|
||
if(x>maxX) x=maxX;
|
||
};
|
||
ClampToTriangle(aXp,aYp);
|
||
ClampToTriangle(bXp,bYp);
|
||
ClampToTriangle(cXp,cYp);
|
||
// 计算价值点M(两条直线的交点)
|
||
float lineAk = qAbs(aXp)>1e-6f ? aYp / aXp : 0.0f; // 从原点(0,0)到A'的斜率
|
||
float lineCk = qAbs(cXp-timemax)>1e-6f ? cYp / (cXp - timemax) : 0.0f; // 从底边右顶点到C'的斜率
|
||
float lineCb = -lineCk * timemax; // 截距
|
||
|
||
float mX = qAbs(lineAk-lineCk)>1e-6f ? lineCb / (lineAk - lineCk) : bXp; // 交点X
|
||
float mY = mX * lineAk; // 交点Y
|
||
ClampToTriangle(mX,mY);
|
||
// 转换内三角形顶点到像素坐标
|
||
QPointF pointAp = GetPoint(aXp, aYp);
|
||
QPointF pointBp = GetPoint(bXp, bYp);
|
||
QPointF pointCp = GetPoint(cXp, cYp);
|
||
QPointF pointM = GetPoint(mX, mY);
|
||
|
||
// 绘制内价值三角(红色边框)
|
||
QPen penTriangle(QColor(255, 0, 0), 2);
|
||
painter->setPen(penTriangle);
|
||
painter->setBrush(Qt::NoBrush);
|
||
painter->drawPolygon(QPolygonF() << pointAp << pointBp << pointCp);
|
||
|
||
// 绘制价值点(红色实心圆)
|
||
QPen penPoint(QColor(255, 0, 0), 1);
|
||
painter->setPen(penPoint);
|
||
painter->setBrush(QBrush(QColor(255, 0, 0)));
|
||
float pointRadius = 2.0f * (scaleFactor > 1.0f ? scaleFactor * 0.8f : 1.0f);
|
||
painter->drawEllipse(pointM, pointRadius, pointRadius);
|
||
|
||
painter->restore();
|
||
// 恢复原始坐标系绘制文字
|
||
painter->resetTransform();
|
||
painter->save();
|
||
|
||
// 绘制坐标轴标签
|
||
painter->setPen(m_pViewInfoLogmud->GetColor());
|
||
QString bottomLabel = "C3/Tg";
|
||
QString leftLabel = "C2/Tg";
|
||
QString rightLabel = "nC4/Tg";
|
||
// 计算标签位置
|
||
QFontMetrics fm = painter->fontMetrics();
|
||
int textHeight = fm.height();
|
||
|
||
// 调整标签位置
|
||
QPointF leftMid((pointA.x() + pointB.x()) / 2, (pointA.y() + pointB.y()) / 2);
|
||
painter->drawText(
|
||
QPointF(pointA.x() - fm.width(leftLabel) - 5,
|
||
leftMid.y()),
|
||
leftLabel);
|
||
|
||
// 右侧标签
|
||
QPointF rightMid((pointC.x() + pointB.x()) / 2, (pointC.y() + pointB.y()) / 2);
|
||
painter->drawText(
|
||
QPointF(pointC.x() - fm.width(rightLabel) + 15,
|
||
rightMid.y() - 15),
|
||
rightLabel);
|
||
|
||
// 绘制坐标刻度
|
||
QPen scalePen(Qt::black, 1);
|
||
|
||
// 在三角形边上绘制刻度 - 调整刻度长度
|
||
float tickLength = 3.0f * (scaleFactor > 1.0f ? scaleFactor * 0.8f : 1.0f); // 调整刻度长度
|
||
for (int i = 1; i < steps; i++) {
|
||
if (i % 5 == 0) {
|
||
float ratio = (float)i / steps;
|
||
float value = i * 0.01f;
|
||
|
||
// 底部刻度
|
||
QPointF bottomPt(pointA.x() + (pointC.x() - pointA.x()) * ratio, pointA.y());
|
||
painter->setPen(scalePen);
|
||
painter->drawLine(bottomPt.x(), bottomPt.y(), bottomPt.x(), bottomPt.y() - tickLength);
|
||
painter->setPen(m_pViewInfoLogmud->GetColor());
|
||
|
||
if (i == 5 ||i == 15) {
|
||
painter->drawText(
|
||
QPointF(bottomPt.x() - 15, bottomPt.y() + 14),
|
||
QString::number(value, 'f', 2));
|
||
}
|
||
else
|
||
{
|
||
painter->drawText(
|
||
QPointF(bottomPt.x() - 10, bottomPt.y() + 14),
|
||
QString::number(value, 'f', 1));
|
||
}
|
||
|
||
// 左侧刻度
|
||
QPointF leftPt(pointA.x() + (pointB.x() - pointA.x()) * ratio, pointA.y() + (pointB.y() - pointA.y()) * ratio);
|
||
painter->setPen(scalePen);
|
||
painter->drawLine(leftPt.x(), leftPt.y(), leftPt.x() + tickLength, leftPt.y());
|
||
painter->setPen(m_pViewInfoLogmud->GetColor());
|
||
|
||
// 调整左侧刻度标签位置
|
||
painter->drawText(
|
||
QPointF(leftPt.x() - fm.width(QString::number(value, 'f', 2)) - 3,
|
||
leftPt.y() + fm.height()/4),
|
||
QString::number(value, 'f', 2));
|
||
|
||
// 右侧刻度
|
||
QPointF rightPt(pointC.x() + (pointB.x() - pointC.x()) * ratio, pointC.y() + (pointB.y() - pointC.y()) * ratio);
|
||
painter->setPen(scalePen);
|
||
painter->drawLine(rightPt.x(), rightPt.y(), rightPt.x() - tickLength, rightPt.y());
|
||
painter->setPen(m_pViewInfoLogmud->GetColor());
|
||
// 调整右侧刻度标签位置
|
||
painter->drawText(
|
||
QPointF(rightPt.x() + 4,
|
||
rightPt.y() + fm.height()/4 + 3),
|
||
QString::number(value, 'f', 2));
|
||
}
|
||
}
|
||
// 重新组织底部标签和深度值位置
|
||
float baseY = pointA.y() + fm.height() + 12;
|
||
|
||
// 绘制底部标签
|
||
painter->drawText(
|
||
QPointF(rt.left() + dd + (w - fm.width(bottomLabel)) / 2,
|
||
baseY),
|
||
bottomLabel);
|
||
|
||
// 在底部绘制深度值
|
||
QString depthText = toString(resultitem->depth) + "米";
|
||
float depthTextWidth = fm.width(depthText);
|
||
float depthY = baseY + fm.height() -2;
|
||
|
||
// 根据视图配置确定深度值位置
|
||
if (m_pViewInfoLogmud->GetisBottom() == 0 || m_pViewInfoLogmud->GetisBottom() == 1) {
|
||
painter->drawText(
|
||
QPointF(rt.left() + dd + (w - depthTextWidth) / 2,
|
||
depthY),
|
||
depthText);
|
||
} else if (m_pViewInfoLogmud->GetisBottom() == 2) {
|
||
painter->drawText(
|
||
QPointF(rt.left() + rt.width() / 20,
|
||
depthY),
|
||
depthText);
|
||
} else if (m_pViewInfoLogmud->GetisBottom() == 3) {
|
||
painter->drawText(
|
||
QPointF(rt.right() - depthTextWidth,
|
||
depthY),
|
||
depthText);
|
||
}
|
||
|
||
painter->restore();
|
||
// 与其他图版保持一致:补绘左侧顶部辅助短线。
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/10, pt1.y()));
|
||
}//判断三角图版的右括号
|
||
//绘制星形图版
|
||
else if(resultitem->type==5) {
|
||
painter->save();
|
||
// 定义七个比值名称
|
||
QStringList expressionList;
|
||
expressionList << "C1/C2" << "C1/C3" << "C2/C3" << "C2/IC4" << "C3/IC4" << "IC4/NC4" << "IC5/NC5";
|
||
// 获取七个比值数据
|
||
float values[7];
|
||
values[0] = resultitem->BH; // ration1 (C1/C2)
|
||
values[1] = resultitem->WH; // ration2 (C1/C3)
|
||
values[2] = resultitem->DH; // ration3 (C2/C3)
|
||
values[3] = resultitem->A; // ration4 (C2/IC4)
|
||
values[4] = resultitem->B; // ration5 (C3/IC4)
|
||
values[5] = resultitem->C; // ration6 (IC4/NC4)
|
||
values[6] = resultitem->D; // ration7 (IC5/NC5)
|
||
|
||
// 计算最大值并确定坐标轴范围
|
||
float maxValue = 0;
|
||
for(int i = 0; i < 7; i++) {
|
||
if(!(values[i] != values[i]) && values[i] > maxValue)
|
||
maxValue = values[i];
|
||
}
|
||
|
||
// 确定坐标轴最大值和网格线数量
|
||
float logicLen = 10.0f;
|
||
int logicSepNum = 10;
|
||
|
||
if(maxValue <= 1.0f) {
|
||
logicLen = ceil(maxValue * 10) / 10;
|
||
logicSepNum = (int)(logicLen * 10);
|
||
} else if(maxValue <= 10.0f) {
|
||
logicLen = ceil(maxValue / 2) * 2;
|
||
logicSepNum = (int)logicLen / 2;
|
||
} else if(maxValue <= 50.0f) {
|
||
logicLen = ceil(maxValue / 5) * 5;
|
||
logicSepNum = (int)logicLen / 5;
|
||
} else {
|
||
logicLen = ceil(maxValue / 10) * 10;
|
||
logicSepNum = 10;
|
||
}
|
||
|
||
if(maxValue == 0) {
|
||
maxValue = 10;
|
||
logicLen = 10;
|
||
logicSepNum = 10;
|
||
}
|
||
|
||
// 计算绘图区域和缩放比例
|
||
float scale = h / logicLen / 2;
|
||
float offsetX = rt.left() + dd + len/2;
|
||
float offsetY = pt1.y() + h/2;
|
||
|
||
// 绘制中心点
|
||
painter->setBrush(QBrush(QColor(211, 211, 211)));
|
||
painter->setPen(Qt::NoPen);
|
||
painter->drawEllipse(QPointF(offsetX, offsetY), 3, 3);
|
||
|
||
// 绘制雷达刻度线
|
||
int angleNum = expressionList.size();
|
||
QPen gridPen(QColor(220, 220, 220), 1);
|
||
|
||
// 循环绘制刻度线
|
||
for(int i = 0; i < logicSepNum; i++) {
|
||
painter->save();
|
||
float value = logicLen / logicSepNum;
|
||
float polarLen = (i + 1) * value;
|
||
|
||
// 绘制多边形网格
|
||
painter->setPen(gridPen);
|
||
for(int j = 0; j < angleNum; j++) {
|
||
float angle1 = j * 2 * M_PI / angleNum;
|
||
float angle2 = ((j + 1) % angleNum) * 2 * M_PI / angleNum;
|
||
|
||
float x1 = polarLen * sin(angle1) * scale;
|
||
float y1 = polarLen * cos(angle1) * scale;
|
||
float x2 = polarLen * sin(angle2) * scale;
|
||
float y2 = polarLen * cos(angle2) * scale;
|
||
|
||
painter->drawLine(
|
||
QPointF(offsetX + x1, offsetY - y1),
|
||
QPointF(offsetX + x2, offsetY - y2)
|
||
);
|
||
}
|
||
|
||
// 绘制刻度值
|
||
painter->setPen(m_pViewInfoLogmud->GetColor());
|
||
QString scaleText = toString(polarLen);
|
||
float textWidth = fm.width(scaleText);
|
||
painter->drawText(
|
||
QPointF(offsetX - textWidth/2, offsetY - polarLen * scale - 5),
|
||
scaleText
|
||
);
|
||
painter->restore();
|
||
}
|
||
|
||
// 绘制坐标轴名称
|
||
painter->setPen(m_pViewInfoLogmud->GetColor());
|
||
for(int i = 0; i < angleNum; i++) {
|
||
float angle = i * 2 * M_PI / angleNum;
|
||
float sin_val = sin(angle);
|
||
float cos_val = cos(angle);
|
||
|
||
float x = (logicLen + logicLen * 0.1) * sin_val * scale;
|
||
float y = (logicLen + logicLen * 0.1) * cos_val * scale;
|
||
|
||
QString axisName = expressionList[i];
|
||
float textWidth = fm.width(axisName);
|
||
float textHeight = fm.height();
|
||
|
||
// 根据象限调整文字位置
|
||
float textX = offsetX + x;
|
||
float textY = offsetY - y;
|
||
|
||
if(sin_val >= 0) {
|
||
// 右侧
|
||
textX += 2;
|
||
} else {
|
||
// 左侧
|
||
textX -= textWidth + 2;
|
||
}
|
||
|
||
if(cos_val >= 0) {
|
||
// 上方
|
||
textY -= 2;
|
||
} else {
|
||
// 下方
|
||
textY += textHeight + 2;
|
||
}
|
||
|
||
painter->drawText(QPointF(textX, textY), axisName);
|
||
}
|
||
|
||
// 绘制数据多边形
|
||
QPolygonF dataPolygon;
|
||
for(int i = 0; i < angleNum; i++) {
|
||
float angle = i * 2 * M_PI / angleNum;
|
||
float value = values[i];
|
||
|
||
// 处理无效值
|
||
if((value != value) || value < 0) value = 0;
|
||
if(value > logicLen) value = logicLen;
|
||
|
||
float x = value * sin(angle) * scale;
|
||
float y = value * cos(angle) * scale;
|
||
dataPolygon << QPointF(offsetX + x, offsetY - y);
|
||
}
|
||
dataPolygon << dataPolygon[0]; // 闭合多边形
|
||
|
||
// 绘制数据连线
|
||
painter->setPen(QPen(Qt::red, 2));
|
||
painter->setBrush(QBrush(QColor(255, 0, 0, 50)));
|
||
painter->drawPolygon(dataPolygon);
|
||
|
||
// 在多边形顶点绘制数据点
|
||
painter->setBrush(QBrush(Qt::red));
|
||
for(int i = 0; i < dataPolygon.size() - 1; i++) {
|
||
painter->drawEllipse(dataPolygon[i], 3, 3);
|
||
}
|
||
|
||
// 绘制深度值和标题
|
||
DrawDepthAndAxisLabels(painter, resultitem->depth, dd, w, h, rt, pt, fm, lscalelen,
|
||
pCore, " ", " ");
|
||
painter->restore();
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
}//星形图版右括号
|
||
else if(resultitem->type==6){
|
||
painter->save();
|
||
// 设置坐标范围
|
||
float mgMin = 0.0f;
|
||
float mgMax = 13.0f;
|
||
float caMin = 21.7f;
|
||
float caMax = 40.0f;
|
||
float siMin = 0.0f;
|
||
float siMax = 28.0f;
|
||
float scaleFactor = 1.5f;
|
||
|
||
// 从resultitem中获取元素含量
|
||
float mg = resultitem->WH; // Mg含量
|
||
float si = resultitem->BH; // Si含量
|
||
float ca = 100.0f - mg - si; // 计算Ca含量
|
||
|
||
// 计算等边三角形的实际尺寸
|
||
float availableWidth = len;
|
||
float availableHeight = h * 1.2f;
|
||
float triangleSide = qMin(availableWidth, availableHeight * 2.0f / sqrt(3.0f)) * scaleFactor;
|
||
if (triangleSide > availableWidth) {
|
||
triangleSide = availableWidth;
|
||
}
|
||
if (triangleSide * sqrt(3.0f) / 2.0f > availableHeight) {
|
||
triangleSide = availableHeight * 2.0f / sqrt(3.0f);
|
||
}
|
||
|
||
// 坐标设置
|
||
float xLen = mgMax - mgMin;
|
||
float scale = len / xLen; // 计算缩放比例
|
||
float offsetX = rt.left() + dd + (availableWidth - len) / 2.0f; // 居中显示
|
||
float offsetY = pt1.y() + h;
|
||
float sin60 = sqrt(3.0f) / 2.0f;
|
||
float cos60 = 0.5f;
|
||
// 设置边距和坐标轴长度
|
||
float picMarginLeft = rt.left() + dd + (availableWidth - triangleSide) / 2.0f;
|
||
float picMarginBottom = pt1.y() + h;
|
||
float axisXLen = triangleSide;
|
||
float axisYLen = triangleSide * sqrt(3.0f) / 2.0f;
|
||
|
||
// 缩放比例
|
||
float scaleX = axisXLen / (mgMax - mgMin);
|
||
float scaleY = axisYLen / (siMax - siMin);
|
||
|
||
auto TranslateMgPos = [&](float mgVal) -> float {
|
||
return picMarginLeft + (mgVal - mgMin) * scaleX;
|
||
};
|
||
|
||
auto TranslateCaPos = [&](float caVal) -> float {
|
||
return picMarginLeft + ((caVal - caMin) / (caMax - caMin)) * axisXLen;
|
||
};
|
||
|
||
auto TranslateSiPos = [&](float siVal) -> float {
|
||
return picMarginBottom - (siVal - siMin) * scaleY;
|
||
};
|
||
|
||
// 计算 形的三个点
|
||
QPointF pointA = QPointF(TranslateMgPos(0), TranslateSiPos(0)); // 左下角
|
||
QPointF pointB = QPointF(TranslateMgPos(6.5), TranslateSiPos(28)); // 顶部
|
||
QPointF pointC = QPointF(TranslateMgPos(13), TranslateSiPos(0)); // 右下角
|
||
|
||
// 绘制三角形框架
|
||
QPen penAxis(Qt::black, 2);
|
||
painter->setPen(penAxis);
|
||
painter->drawPolygon(QPolygonF() << pointA << pointB << pointC);
|
||
|
||
// 计算中点
|
||
float xMid = 6.5f;
|
||
|
||
// 辅助函数计算两侧点的水平偏移
|
||
auto GetMgDelta = [&](float siVal) -> float {
|
||
return (siMax - siVal) * (xMid - mgMin) / (siMax - siMin);
|
||
};
|
||
|
||
|
||
// 价值区域定义和绘制
|
||
QVector<QPair<QString, QVector<QPointF>>> valueAreaList;
|
||
|
||
// 添加所有价值区
|
||
// 1. 泥岩
|
||
QVector<QPointF> mudstone;
|
||
mudstone.append(QPointF(xMid - GetMgDelta(25.2f), 25.2f));
|
||
mudstone.append(QPointF(xMid - GetMgDelta(28.0f), 28.0f));
|
||
mudstone.append(QPointF(xMid + GetMgDelta(25.2f), 25.2f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("泥岩", mudstone));
|
||
|
||
// 2. 含灰泥岩
|
||
QVector<QPointF> calcareous;
|
||
calcareous.append(QPointF(xMid - GetMgDelta(21.0f), 21.0f));
|
||
calcareous.append(QPointF(xMid - GetMgDelta(25.2f), 25.2f));
|
||
calcareous.append(QPointF(xMid, 25.2f));
|
||
calcareous.append(QPointF(xMid, 21.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("含灰泥岩", calcareous));
|
||
|
||
// 3. 含云泥岩
|
||
QVector<QPointF> dolomitic;
|
||
dolomitic.append(QPointF(xMid + GetMgDelta(21.0f), 21.0f));
|
||
dolomitic.append(QPointF(xMid + GetMgDelta(25.2f), 25.2f));
|
||
dolomitic.append(QPointF(xMid, 25.2f));
|
||
dolomitic.append(QPointF(xMid, 21.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("含云泥岩", dolomitic));
|
||
|
||
// 4. 灰质泥岩
|
||
QVector<QPointF> calcareous2;
|
||
calcareous2.append(QPointF(xMid - GetMgDelta(14.0f), 14.0f));
|
||
calcareous2.append(QPointF(xMid - GetMgDelta(21.0f), 21.0f));
|
||
calcareous2.append(QPointF(xMid, 21.0f));
|
||
calcareous2.append(QPointF(xMid, 14.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("灰质泥岩", calcareous2));
|
||
|
||
// 5. 云质泥岩
|
||
QVector<QPointF> dolomitic2;
|
||
dolomitic2.append(QPointF(xMid + GetMgDelta(14.0f), 14.0f));
|
||
dolomitic2.append(QPointF(xMid + GetMgDelta(21.0f), 21.0f));
|
||
dolomitic2.append(QPointF(xMid, 21.0f));
|
||
dolomitic2.append(QPointF(xMid, 14.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("云质泥岩", dolomitic2));
|
||
|
||
// 6. 泥灰岩
|
||
QVector<QPointF> marlstone;
|
||
marlstone.append(QPointF(xMid - GetMgDelta(7.0f), 7.0f));
|
||
marlstone.append(QPointF(xMid - GetMgDelta(14.0f), 14.0f));
|
||
marlstone.append(QPointF(xMid, 14.0f));
|
||
marlstone.append(QPointF(xMid, 7.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("泥灰岩", marlstone));
|
||
|
||
// 7. 泥云岩
|
||
QVector<QPointF> marlyDolomite;
|
||
marlyDolomite.append(QPointF(xMid + GetMgDelta(7.0f), 7.0f));
|
||
marlyDolomite.append(QPointF(xMid + GetMgDelta(14.0f), 14.0f));
|
||
marlyDolomite.append(QPointF(xMid, 14.0f));
|
||
marlyDolomite.append(QPointF(xMid, 7.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("泥云岩", marlyDolomite));
|
||
|
||
// 8. 含泥灰岩
|
||
QVector<QPointF> argillaceousLimestone;
|
||
argillaceousLimestone.append(QPointF(xMid - GetMgDelta(2.8f), 2.8f));
|
||
argillaceousLimestone.append(QPointF(xMid - GetMgDelta(7.0f), 7.0f));
|
||
argillaceousLimestone.append(QPointF(xMid, 7.0f));
|
||
argillaceousLimestone.append(QPointF(xMid, 2.8f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("含泥灰岩", argillaceousLimestone));
|
||
|
||
// 9. 含泥云岩
|
||
QVector<QPointF> argillaceousDolomite;
|
||
argillaceousDolomite.append(QPointF(xMid + GetMgDelta(2.8f), 2.8f));
|
||
argillaceousDolomite.append(QPointF(xMid + GetMgDelta(7.0f), 7.0f));
|
||
argillaceousDolomite.append(QPointF(xMid, 7.0f));
|
||
argillaceousDolomite.append(QPointF(xMid, 2.8f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("含泥云岩", argillaceousDolomite));
|
||
|
||
// 10. 灰岩
|
||
QVector<QPointF> limestone;
|
||
limestone.append(QPointF(0.0f, 0.0f));
|
||
limestone.append(QPointF(xMid - GetMgDelta(2.8f), 2.8f));
|
||
limestone.append(QPointF(xMid - GetMgDelta(2.8f) + 1.3f * ((28.0f - 2.8f) / 28.0f), 2.8f));
|
||
limestone.append(QPointF(1.3f, 0.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("灰岩", limestone));
|
||
|
||
// 11. 云岩
|
||
QVector<QPointF> dolomite;
|
||
dolomite.append(QPointF(13.0f, 0.0f));
|
||
dolomite.append(QPointF(xMid + GetMgDelta(2.8f), 2.8f));
|
||
dolomite.append(QPointF(xMid + GetMgDelta(2.8f) - 1.3f * ((28.0f - 2.8f) / 28.0f), 2.8f));
|
||
dolomite.append(QPointF(11.7f, 0.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("云岩", dolomite));
|
||
|
||
// 12. 含云灰岩
|
||
QVector<QPointF> dolomiteLimestone;
|
||
dolomiteLimestone.append(QPointF(1.3f, 0.0f));
|
||
dolomiteLimestone.append(QPointF(xMid - GetMgDelta(2.8f) + 1.3f * ((28.0f - 2.8f) / 28.0f), 2.8f));
|
||
dolomiteLimestone.append(QPointF(xMid - GetMgDelta(2.8f) + 3.2f * ((28.0f - 2.8f) / 28.0f), 2.8f));
|
||
dolomiteLimestone.append(QPointF(3.2f, 0.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("含云灰岩", dolomiteLimestone));
|
||
|
||
// 13. 含灰云岩
|
||
QVector<QPointF> calcareousDolomite;
|
||
calcareousDolomite.append(QPointF(11.7f, 0.0f));
|
||
calcareousDolomite.append(QPointF(xMid + GetMgDelta(2.8f) - 1.3f * ((28.0f - 2.8f) / 28.0f), 2.8f));
|
||
calcareousDolomite.append(QPointF(xMid + GetMgDelta(2.8f) - (13.0f - 9.7f) * ((28.0f - 2.8f) / 28.0f), 2.8f));
|
||
calcareousDolomite.append(QPointF(9.7f, 0.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("含灰云岩", calcareousDolomite));
|
||
|
||
// 14. 云质灰岩
|
||
QVector<QPointF> dolomiticalLimestone;
|
||
dolomiticalLimestone.append(QPointF(3.2f, 0.0f));
|
||
dolomiticalLimestone.append(QPointF(xMid - GetMgDelta(2.8f) + 3.2f * ((28.0f - 2.8f) / 28.0f), 2.8f));
|
||
dolomiticalLimestone.append(QPointF(6.5f, 2.8f));
|
||
dolomiticalLimestone.append(QPointF(6.5f, 0.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("云质灰岩", dolomiticalLimestone));
|
||
|
||
// 15. 灰质云岩
|
||
QVector<QPointF> calcDolomite;
|
||
calcDolomite.append(QPointF(9.7f, 0.0f));
|
||
calcDolomite.append(QPointF(xMid + GetMgDelta(2.8f) - (13.0f - 9.7f) * ((28.0f - 2.8f) / 28.0f), 2.8f));
|
||
calcDolomite.append(QPointF(6.5f, 2.8f));
|
||
calcDolomite.append(QPointF(6.5f, 0.0f));
|
||
valueAreaList.append(QPair<QString, QVector<QPointF>>("灰质云岩", calcDolomite));
|
||
|
||
// 绘制所有价值区域
|
||
QVector<QRectF> placedAreaLabelRects;
|
||
auto IsAreaLabelOverlap = [&placedAreaLabelRects](const QRectF& rect)->bool
|
||
{
|
||
for(int idx=0;idx<placedAreaLabelRects.size();idx++)
|
||
{
|
||
if(placedAreaLabelRects[idx].adjusted(-2,-1,2,1).intersects(rect))
|
||
{
|
||
return true;
|
||
}
|
||
}
|
||
return false;
|
||
};
|
||
QFont originFont=painter->font();
|
||
QFont areaLabelFont=originFont;
|
||
areaLabelFont.setPointSize(qMax(7,originFont.pointSize()-1));
|
||
painter->setFont(areaLabelFont);
|
||
QFontMetrics areaFm(areaLabelFont);
|
||
for (int i = 0; i < valueAreaList.size(); i++) {
|
||
QVector<QPointF> pixelPoints;
|
||
for (int j = 0; j < valueAreaList[i].second.size(); j++) {
|
||
pixelPoints.append(QPointF(
|
||
TranslateMgPos(valueAreaList[i].second[j].x()),
|
||
TranslateSiPos(valueAreaList[i].second[j].y())
|
||
));
|
||
}
|
||
|
||
// 绘制价值区
|
||
QColor areaColor;
|
||
// 根据区域类型设置不同颜色
|
||
switch (i % 5) {
|
||
case 0: areaColor = QColor(255, 240, 200, 150); break; // 浅黄色
|
||
case 1: areaColor = QColor(200, 240, 255, 150); break; // 浅蓝色
|
||
case 2: areaColor = QColor(200, 255, 200, 150); break; // 浅绿色
|
||
case 3: areaColor = QColor(255, 200, 200, 150); break; // 浅红色
|
||
case 4: areaColor = QColor(240, 200, 255, 150); break; // 浅紫色
|
||
}
|
||
|
||
// 绘制价值区域
|
||
painter->setBrush(areaColor);
|
||
painter->setPen(Qt::black);
|
||
painter->drawPolygon(pixelPoints);
|
||
|
||
// 绘制价值区名称
|
||
float centerX = 0, centerY = 0;
|
||
for (int j = 0; j < pixelPoints.size(); j++) {
|
||
centerX += pixelPoints[j].x();
|
||
centerY += pixelPoints[j].y();
|
||
}
|
||
centerX /= pixelPoints.size();
|
||
centerY /= pixelPoints.size();
|
||
QString labelText=valueAreaList[i].first;
|
||
float textW=areaFm.width(labelText)+4;
|
||
float textH=areaFm.height()+2;
|
||
QVector<QPointF> labelOffsets;
|
||
labelOffsets.append(QPointF(0,0));
|
||
labelOffsets.append(QPointF(0,-textH*0.6f));
|
||
labelOffsets.append(QPointF(0,textH*0.6f));
|
||
labelOffsets.append(QPointF(-textW*0.2f,0));
|
||
labelOffsets.append(QPointF(textW*0.2f,0));
|
||
bool isPlaced=false;
|
||
for(int offsetIdx=0;offsetIdx<labelOffsets.size();offsetIdx++)
|
||
{
|
||
QRectF labelRect(
|
||
centerX-textW*0.5f+labelOffsets[offsetIdx].x(),
|
||
centerY-textH*0.5f+labelOffsets[offsetIdx].y(),
|
||
textW,textH);
|
||
if(labelRect.left()<rt.left()+dd||labelRect.right()>rt.left()+dd+w||
|
||
labelRect.top()<pt1.y()-2||labelRect.bottom()>pt1.y()+h+2)
|
||
{
|
||
continue;
|
||
}
|
||
if(IsAreaLabelOverlap(labelRect)) continue;
|
||
painter->drawText(labelRect,Qt::AlignCenter,labelText);
|
||
placedAreaLabelRects.append(labelRect);
|
||
isPlaced=true;
|
||
break;
|
||
}
|
||
if(!isPlaced)
|
||
{
|
||
// 保底策略:即使挤也要显示,避免出现区域名丢失。
|
||
QRectF fallbackRect(centerX-textW*0.5f,centerY-textH*0.5f,textW,textH);
|
||
painter->drawText(fallbackRect,Qt::AlignCenter,labelText);
|
||
placedAreaLabelRects.append(fallbackRect);
|
||
}
|
||
}
|
||
painter->setFont(originFont);
|
||
|
||
// 绘制价值点
|
||
float pointX = TranslateMgPos(mg);
|
||
float pointY = TranslateSiPos(si);
|
||
painter->setBrush(QBrush(QColor(255, 0, 0)));
|
||
painter->setPen(QPen(Qt::red, 1));
|
||
float pointRadius = 3.0f * (scaleFactor > 1.0f ? scaleFactor * 0.8f : 1.0f);
|
||
painter->drawEllipse(QPointF(pointX, pointY), pointRadius, pointRadius);
|
||
|
||
// 绘制刻度值
|
||
QPen textPen(Qt::black, 1);
|
||
painter->setPen(textPen);
|
||
|
||
// Mg和Ca刻度
|
||
float mgX[] = { 0, 1.3, 3.2, 6.5, 9.7, 11.7, 13.0 };
|
||
float caX[] = { 40, 38.2, 35.4, 30.8, 26.3, 23.5, 21.7 };
|
||
|
||
for (int i = 0; i < 7; i++) {
|
||
// mg刻度
|
||
QString mgStr = QString::number(mgX[i], 'f', 1);
|
||
QFontMetrics fm = painter->fontMetrics();
|
||
painter->drawText(
|
||
QPointF(TranslateMgPos(mgX[i]) - fm.width(mgStr)/2,
|
||
TranslateSiPos(0) + 16),
|
||
mgStr);
|
||
|
||
// ca刻度
|
||
QString caStr = QString::number(caX[i], 'f', 1);
|
||
painter->drawText(
|
||
QPointF(TranslateCaPos(caX[i]) - fm.width(caStr)/2,
|
||
TranslateSiPos(0) + 34),
|
||
caStr);
|
||
}
|
||
|
||
// Si刻度
|
||
float siY[] = { 0, 2.8, 7.0, 14.0, 21.0, 25.2, 28.0 };
|
||
for (int i = 0; i < 7; i++) {
|
||
QString siStr = QString::number(siY[i], 'f', 1);
|
||
QFontMetrics fm = painter->fontMetrics();
|
||
|
||
// 左侧Si刻度
|
||
painter->drawText(
|
||
QPointF(TranslateMgPos(xMid - GetMgDelta(siY[i])) - fm.width(siStr) - 5,
|
||
TranslateSiPos(siY[i]) + fm.height()/4),
|
||
siStr);
|
||
|
||
// 右侧Si刻度
|
||
painter->drawText(
|
||
QPointF(TranslateMgPos(xMid + GetMgDelta(siY[i])) + 5,
|
||
TranslateSiPos(siY[i]) + fm.height()/4),
|
||
siStr);
|
||
}
|
||
|
||
// 坐标轴标签
|
||
QFontMetrics fm = painter->fontMetrics();
|
||
painter->drawText(
|
||
QPointF(TranslateMgPos(0) - 50, TranslateSiPos(0) + 54),
|
||
"Ca%");
|
||
painter->drawText(
|
||
QPointF(TranslateMgPos(13) + 20, TranslateSiPos(0) + 54),
|
||
"Mg%");
|
||
painter->drawText(
|
||
QPointF(TranslateMgPos(6.5) - 15, TranslateSiPos(28) - 16),
|
||
"Si%");
|
||
|
||
// 绘制深度信息和标题
|
||
QString depthText = toString(resultitem->depth) + "米";
|
||
QString resultText = "碳酸盐三角图版";
|
||
int textWidth = fm.width(depthText);
|
||
|
||
painter->drawText(
|
||
QPointF(rt.left() + dd + (w - textWidth) / 2,
|
||
offsetY + 70),
|
||
depthText);
|
||
|
||
painter->drawText(
|
||
QPointF(rt.left() + dd + (w - fm.width(resultText)) / 2,
|
||
offsetY + 86),
|
||
resultText);
|
||
painter->restore();
|
||
// 与其他图版保持一致:补绘左侧顶部辅助短线。
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/10, pt1.y()));
|
||
}
|
||
//TAS图版
|
||
else if(resultitem -> type == 7)
|
||
{
|
||
//定义颜色和阈值
|
||
QColor _valueAreaColors[] = {
|
||
// 近似 “玄武岩” 区域颜色(浅绿一类)
|
||
|
||
// 补充 “碱玄/碧玄岩” 区域(假设浅黄绿 )
|
||
QColor(180, 230, 120),
|
||
// 补充 “响岩质碱玄岩” 区域(假设浅灰绿 )
|
||
QColor(150, 200, 150),
|
||
// 补充 “粗面玄武岩” 区域(假设浅棕黄 )
|
||
QColor(240, 200, 120),
|
||
// 补充 “玄武粗安岩” 区域(假设浅青 )
|
||
QColor(120, 200, 220),
|
||
// 补充 “玄武安山岩” 区域(假设浅粉黄 )
|
||
QColor(250, 200, 180),
|
||
QColor(149, 239, 149),
|
||
// 近似 “粗面/粗面英安岩” 区域颜色(浅蓝一类)
|
||
QColor(107, 154, 238),
|
||
// 近似 “响岩” 区域颜色(深绿一类,比如图中黄绿色区域可微调 )
|
||
QColor(45, 144, 45),
|
||
// 近似 “英安岩、流纹岩” 等粉色系区域(图中粉色调 )
|
||
QColor(253, 144, 10),
|
||
// 近似 “安山岩” 等浅粉、浅红区域(调整后更贴近 )
|
||
QColor(208, 99, 99),
|
||
// 补充 “副长岩” 区域(假设图中粉色偏深部分 )
|
||
QColor(239, 100, 100),
|
||
};
|
||
|
||
float yLabelMin = 0;
|
||
float yLabelMax = 16;
|
||
float xLabelMin = 35;
|
||
float xLabelMax = 79;
|
||
int fnum;// 默认网格数
|
||
|
||
int xTicks = 44; // 刻度数 = 网格数
|
||
int yTicks = 16;
|
||
// 设置画笔
|
||
// 设置画笔(加粗轴线)
|
||
QPen axisPen(Qt::black);
|
||
axisPen.setWidth(2);
|
||
painter->setPen(axisPen);
|
||
QFontMetrics fm = painter -> fontMetrics();
|
||
// ==== 坐标框区域 ====
|
||
int x0 = rt.left() + dd;
|
||
int x1 = rt.left() + dd + len;
|
||
int y0 = pt1.y();
|
||
int y1 = pt1.y() + h;
|
||
|
||
// ==== 绘制四边形坐标轴边框 ====
|
||
painter->drawLine(x0, y0, x1, y0); // 顶部横线
|
||
painter->drawLine(x0, y1, x1, y1); // 底部横线
|
||
painter->drawLine(x0, y0, x0, y1); // 左侧竖线
|
||
painter->drawLine(x1, y0, x1, y1); // 右侧竖线
|
||
|
||
// ==== 设置细画笔绘制刻度 ====
|
||
QPen tickPen(Qt::black);
|
||
tickPen.setWidth(1);
|
||
painter->setPen(tickPen);
|
||
// ==== 中心X轴(画X轴刻度和文字) ====
|
||
int yAxisPos = y1; // 中间横轴在底部
|
||
|
||
for (int i = 0; i <= xTicks; ++i) {
|
||
float val = xLabelMin + (xLabelMax - xLabelMin) * i / xTicks;
|
||
int x = x0 + i * len / xTicks;
|
||
|
||
// 小刻度
|
||
if (static_cast<int>(val) % 5 != 0) {
|
||
painter->drawLine(x, yAxisPos, x, yAxisPos + 5);
|
||
}
|
||
|
||
// 每 5 单位画一次文字
|
||
if (static_cast<int>(val) % 5 == 0) {
|
||
painter->drawLine(x, yAxisPos, x, yAxisPos + 10);
|
||
QString label = QString::number(val, 'f', 0);
|
||
painter->drawText(x - fm.width(label) / 2, yAxisPos + 30, label);
|
||
}
|
||
}
|
||
//绘制其他X轴标识符号
|
||
// X轴额外信息
|
||
QString labels[] = { "超基性", "基性", "中性", "酸性" };
|
||
int xThresh[] = { 35, 45, 52, 62, 79 };
|
||
|
||
// 画 5 条竖线
|
||
int xLinePos[5];
|
||
xLinePos[0] = x0;
|
||
xLinePos[1] = x0 + 10 * len / xTicks;
|
||
xLinePos[2] = x0 + 17 * len / xTicks;
|
||
xLinePos[3] = x0 + 27 * len / xTicks;
|
||
xLinePos[4] = x0 + 44 * len / xTicks;
|
||
|
||
for (int i = 0; i < 5; ++i) {
|
||
painter->drawLine(xLinePos[i], y1 + 35, xLinePos[i], y1 + 60);
|
||
}
|
||
|
||
// 在每两个线之间写文字
|
||
for (int i = 0; i < 4; ++i) {
|
||
int xCenter = (xLinePos[i] + xLinePos[i + 1]) / 2;
|
||
QString label = labels[i];
|
||
int textWidth = fm.width(label); // 若 Qt >= 5.11 可改为 horizontalAdvance(label)
|
||
painter->drawText(xCenter - textWidth / 2, y1 + 48, label);
|
||
}
|
||
|
||
// ==== 中心Y轴(画Y轴刻度和文字) ====
|
||
int xAxisPos = x0; // 中间纵轴在左侧
|
||
|
||
for (int i = 0; i <= yTicks; ++i) {
|
||
float val = yLabelMin + (yLabelMax - yLabelMin) * i / yTicks;
|
||
int y = y1 - i * h / yTicks;
|
||
|
||
// 小刻度
|
||
if (static_cast<int>(val) % 2 != 0) {
|
||
painter->drawLine(xAxisPos - 5, y, xAxisPos, y);
|
||
}
|
||
// 每 2 单位画一次文字
|
||
if (static_cast<int>(val) % 2 == 0) {
|
||
painter->drawLine(xAxisPos - 10, y, xAxisPos, y);
|
||
QString label = QString::number(val, 'f', 0);
|
||
painter->drawText(xAxisPos - 20 - fm.width(label), y + 5, label);
|
||
}
|
||
}
|
||
// ==== 绘制深度值和横纵坐标标题) ====
|
||
QString depthText = QString::number(resultitem->depth, 'f', 1) + "米";
|
||
int offsetY = 80; // 向下偏移像素数
|
||
|
||
// --- 绘制深度值 ---
|
||
int depthX = x0 + (x1 - x0 - fm.width(depthText)) / 2;
|
||
int depthY = y1 + offsetY;
|
||
painter->drawText(depthX, depthY, depthText);
|
||
|
||
// --- 绘制横坐标标题(X轴) ---
|
||
QString xTitle = "(SiO2(wt.%))";
|
||
int xTitleX = x0 + (x1 - x0 - fm.width(xTitle)) / 2;
|
||
int xTitleY = depthY + fm.height() + 4;
|
||
painter->drawText(xTitleX, xTitleY, xTitle);
|
||
|
||
// --- 绘制纵坐标标题(Y轴) ---
|
||
QString yTitle = "Na2O+K2O(wt.%)";
|
||
QTransform oldTransform = painter->worldTransform();
|
||
|
||
int yCenter = y0 + (y1 - y0) / 2;
|
||
int yTitleX = x0 - 45; // 可微调位置
|
||
int yTitleY = yCenter + fm.width(yTitle) / 2;
|
||
|
||
// 旋转 -90 度写竖排标题
|
||
QTransform transform;
|
||
transform.translate(yTitleX, yTitleY);
|
||
transform.rotate(-90);
|
||
transform.translate(-yTitleX, -yTitleY);
|
||
painter->setWorldTransform(transform);
|
||
painter->drawText(QPointF(yTitleX, yTitleY), yTitle);
|
||
|
||
// 恢复变换
|
||
painter->setWorldTransform(oldTransform);
|
||
//绘制价值区
|
||
// 坐标转换函数:将实际坐标点转换为屏幕像素点
|
||
QString stoneLabels[] = { "副长岩", "苦橄玄武岩","碱玄/碧玄岩", "响岩质碱玄岩", "碱玄质响岩", "响岩", "玄武岩", "粗面玄武岩", "玄武粗安岩", "玄武安山岩", "粗安岩", "安山岩", "粗面/粗面英安岩", "英安岩", "流纹岩" };
|
||
// 构造区域点集
|
||
QPolygonF areaPolygon[15];
|
||
// 副长岩
|
||
areaPolygon[0].append(QPointF(41.0, 0.0));
|
||
areaPolygon[0].append(QPointF(41.0, 7.0));
|
||
areaPolygon[0].append(QPointF(45.0, 9.4));
|
||
areaPolygon[0].append(QPointF(48.4, 11.5));
|
||
areaPolygon[0].append(QPointF(52.5, 14.0));
|
||
areaPolygon[0].append(QPointF(48.0, 16.0));
|
||
areaPolygon[0].append(QPointF(35.0, 16.0));
|
||
areaPolygon[0].append(QPointF(35.0, 0.0));
|
||
|
||
// 苦橄玄武岩
|
||
areaPolygon[1].append(QPointF(41, 0.0));
|
||
areaPolygon[1].append(QPointF(45, 0.0));
|
||
areaPolygon[1].append(QPointF(45, 3));
|
||
areaPolygon[1].append(QPointF(41, 3));
|
||
|
||
// 碱玄/碧玄岩
|
||
areaPolygon[2].append(QPointF(41, 3));
|
||
areaPolygon[2].append(QPointF(45, 3));
|
||
areaPolygon[2].append(QPointF(45, 5));
|
||
areaPolygon[2].append(QPointF(49.4, 7.3));
|
||
areaPolygon[2].append(QPointF(45, 9.4));
|
||
areaPolygon[2].append(QPointF(41, 7));
|
||
|
||
// 响岩质碱玄岩
|
||
areaPolygon[3].append(QPointF(49.4, 7.3));
|
||
areaPolygon[3].append(QPointF(53, 9.3));
|
||
areaPolygon[3].append(QPointF(48.4, 11.5));
|
||
areaPolygon[3].append(QPointF(45, 9.4));
|
||
|
||
// 碱玄质响岩
|
||
areaPolygon[4].append(QPointF(53, 9.3));
|
||
areaPolygon[4].append(QPointF(57.6, 11.7));
|
||
areaPolygon[4].append(QPointF(52.5, 14));
|
||
areaPolygon[4].append(QPointF(48.4, 11.5));
|
||
|
||
// 响岩
|
||
areaPolygon[5].append(QPointF(57.6, 11.7));
|
||
areaPolygon[5].append(QPointF(65.7, 16));
|
||
areaPolygon[5].append(QPointF(48, 16));
|
||
areaPolygon[5].append(QPointF(52.5, 14));
|
||
|
||
// 玄武岩
|
||
areaPolygon[6].append(QPointF(45, 0.0));
|
||
areaPolygon[6].append(QPointF(52, 0.0));
|
||
areaPolygon[6].append(QPointF(52, 5));
|
||
areaPolygon[6].append(QPointF(45, 5));
|
||
|
||
// 粗面玄武岩
|
||
areaPolygon[7].append(QPointF(45, 5));
|
||
areaPolygon[7].append(QPointF(52, 5));
|
||
areaPolygon[7].append(QPointF(49.4, 7.3));
|
||
|
||
// 玄武粗安岩
|
||
areaPolygon[8].append(QPointF(52, 5));
|
||
areaPolygon[8].append(QPointF(57, 5.9));
|
||
areaPolygon[8].append(QPointF(53, 9.3));
|
||
areaPolygon[8].append(QPointF(49.4, 7.3));
|
||
|
||
// 玄武安山岩
|
||
areaPolygon[9].append(QPointF(52, 0.0));
|
||
areaPolygon[9].append(QPointF(57, 0.0));
|
||
areaPolygon[9].append(QPointF(57, 5.9));
|
||
areaPolygon[9].append(QPointF(52, 5));
|
||
|
||
// 粗安岩
|
||
areaPolygon[10].append(QPointF(57, 5.9));
|
||
areaPolygon[10].append(QPointF(63, 7));
|
||
areaPolygon[10].append(QPointF(57.6, 11.7));
|
||
areaPolygon[10].append(QPointF(53, 9.3));
|
||
|
||
// 安山岩
|
||
areaPolygon[11].append(QPointF(57, 0.0));
|
||
areaPolygon[11].append(QPointF(63, 0.0));
|
||
areaPolygon[11].append(QPointF(63, 7));
|
||
areaPolygon[11].append(QPointF(57, 5.9));
|
||
|
||
// 粗面/粗面英安岩
|
||
areaPolygon[12].append(QPointF(63, 7));
|
||
areaPolygon[12].append(QPointF(69, 8));
|
||
areaPolygon[12].append(QPointF(69, 16));
|
||
areaPolygon[12].append(QPointF(65.7, 16));
|
||
areaPolygon[12].append(QPointF(57.6, 11.7));
|
||
|
||
// 英安岩
|
||
areaPolygon[13].append(QPointF(63, 0.0));
|
||
areaPolygon[13].append(QPointF(77, 0.0));
|
||
areaPolygon[13].append(QPointF(69, 8));
|
||
areaPolygon[13].append(QPointF(63, 7));
|
||
|
||
// 流纹岩
|
||
areaPolygon[14].append(QPointF(77, 0.0));
|
||
areaPolygon[14].append(QPointF(79, 0.0));
|
||
areaPolygon[14].append(QPointF(79, 16));
|
||
areaPolygon[14].append(QPointF(69, 16));
|
||
areaPolygon[14].append(QPointF(69, 8));
|
||
for(int tem = 0; tem < 15; tem++)
|
||
{
|
||
//构建路径并进行坐标转换(直接转换逻辑坐标为屏幕坐标)
|
||
QPainterPath path;
|
||
if (!areaPolygon[tem].isEmpty()) {
|
||
QPointF pt0 = areaPolygon[tem][0];
|
||
float x0Pix = x0 + (pt0.x() - 35) * len / xTicks;
|
||
float y0Pix = y1 - pt0.y() * h / yTicks;
|
||
path.moveTo(QPointF(x0Pix, y0Pix));
|
||
|
||
for (int i = 1; i < areaPolygon[tem].size(); ++i) {
|
||
QPointF pt = areaPolygon[tem][i];
|
||
float xPix = x0 + (pt.x() - 35) * len / xTicks;
|
||
float yPix = y1 - pt.y() * h / yTicks;
|
||
path.lineTo(QPointF(xPix, yPix));
|
||
}
|
||
|
||
path.closeSubpath(); // 闭合路径
|
||
}
|
||
//区域填充
|
||
painter -> setPen(QPen(Qt::black, 2)); // 粗边框线
|
||
painter -> setBrush(_valueAreaColors[tem % 11]); // 你给的颜色
|
||
// 获取当前字体并设置更小的字体大小
|
||
|
||
painter -> drawPath(path);
|
||
}
|
||
//最后绘制文字
|
||
// 绘制居中文本
|
||
// 保存画笔状态
|
||
painter->save();
|
||
|
||
// 设置字体并减小字体大小
|
||
QFont font = painter->font();
|
||
int newPointSize = qMax(6, font.pointSize() - 4); // 确保字体大小不小于6点
|
||
font.setPointSize(newPointSize);
|
||
painter->setFont(font);
|
||
// x 和 y 坐标
|
||
double xValues[] = {40, 43, 43, 48, 53, 57, 48.5, 48.5, 53, 54.5, 57.5, 60, 64, 68.5, 75};
|
||
double yValues[] = {10, 2, 6, 9, 11, 14, 2.5, 5.5, 6.8, 2.5, 8, 2.5, 11, 2.5, 9};
|
||
|
||
int labelCount = sizeof(stoneLabels) / sizeof(stoneLabels[0]);
|
||
|
||
for (int i = 0; i < labelCount; ++i) {
|
||
int textWidth = fm.width(stoneLabels[i]);
|
||
int textHeight = fm.height();
|
||
|
||
int x = x0 + (xValues[i] - 35) * len / xTicks - textWidth / 2;
|
||
int y = y1 - yValues[i] * h / yTicks - textHeight / 2;
|
||
|
||
QRect rect(x, y, textWidth, textHeight);
|
||
painter->drawText(rect, Qt::AlignCenter, stoneLabels[i]);
|
||
}
|
||
// 绘制投点
|
||
|
||
// 设置投点样式
|
||
QPen pointPen;
|
||
pointPen.setColor(Qt::red);
|
||
pointPen.setWidth(2);
|
||
painter->setPen(pointPen);
|
||
painter->setBrush(Qt::red);
|
||
|
||
// 绘制投点(圆形)
|
||
float pointSize = 3.0f;
|
||
painter->drawEllipse(QPointF(x0 + (resultitem->LABEL_X - 35) * len / xTicks, y1 - resultitem->LABEL_Y * h / yTicks), pointSize, pointSize);
|
||
painter -> restore();
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
}
|
||
//绘制比值图版
|
||
else if(resultitem -> type == 8)
|
||
{
|
||
// ==== 坐标框区域 ====
|
||
int x0 = rt.left() + dd;
|
||
int x1 = rt.left() + dd + len;
|
||
int y0 = pt1.y();
|
||
int y1 = pt1.y() + h;
|
||
// 保存原始坐标系设置
|
||
int originalLogarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
int originalTLogarithmic = m_pViewInfoLogmud->GetTLogarithmic();
|
||
|
||
m_pViewInfoLogmud->SetLogarithmic(AXIS_LOGARITHMIC); // 设置Y轴为对数坐标系
|
||
|
||
//绘制比值图版
|
||
//先建一个样子,横轴实际坐标为比值
|
||
float yLabelMin = 1.0f;
|
||
float yLabelMax = 1000.0f;
|
||
float lval = yLabelMin;
|
||
int Logarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
if(Logarithmic == AXIS_LOGARITHMIC){
|
||
if(lval <= 0) lval = 1.0f;
|
||
lval = log10(lval);
|
||
}
|
||
|
||
float rval = yLabelMax;
|
||
if(Logarithmic == AXIS_LOGARITHMIC){
|
||
if(rval <= 0) rval = 1.0f;
|
||
rval = log10(rval);
|
||
}
|
||
|
||
// 定义横坐标标签
|
||
QString xLabels[] = { "C1/C2", "C1/C3", "C1/(IC4 + NC4)", "C1/(IC5 + NC5)" };
|
||
// 先绘制坐标系
|
||
int fnum=3;//横轴固定三网格
|
||
for (int i = 0; i < 4; ++i) {
|
||
// 计算每条竖线的 x 坐标(等间距)
|
||
double x = x0 + i * (x1 - x0) / fnum;
|
||
painter->save();
|
||
// 设置浅灰色画笔
|
||
QPen grayPen(Qt::gray, 1);
|
||
painter->setPen(grayPen);
|
||
// 画竖线
|
||
painter->drawLine(QPointF(x, y0), QPointF(x, y1));
|
||
int textWidth = fm.width(xLabels[i]);
|
||
int textHeight = fm.height();
|
||
painter->restore();
|
||
// 画文字
|
||
QPen blackPen(Qt::black, 1);
|
||
painter->setPen(blackPen);
|
||
QRect rect(x - textWidth / 2, y1 + 15, textWidth, textHeight);
|
||
painter->drawText(rect, Qt::AlignCenter, xLabels[i]);
|
||
|
||
}
|
||
//设置Y轴网格数和开始绘制Y轴对数网格
|
||
fnum=3;
|
||
fnum=m_pViewInfoLogmud->GetyGrid();
|
||
float d1;
|
||
float lsc = yLabelMin, rsc = yLabelMax;
|
||
float ddd = lsc;
|
||
float mm = lsc / ddd;
|
||
float x;
|
||
float logBase = log10(rsc / lsc);
|
||
for (d1 = lsc; d1 <= rsc; d1 = ((int)(d1 / mm + 1.5f)) * mm) {
|
||
// 计算当前刻度在画布中的 y 坐标
|
||
x = log10(d1 / lsc) / logBase * h;
|
||
float yPos = pt.y() + h - x;
|
||
bool isMajorTick = fmod(log10(d1), 1.0f) == 0.0f;
|
||
if (isMajorTick) {
|
||
// 保存画笔状态
|
||
painter->save();
|
||
// 设置灰色画笔画主刻度线
|
||
QPen grayPen(Qt::lightGray, 1);
|
||
painter->setPen(grayPen);
|
||
painter->drawLine(rt.left() + dd, yPos, rt.left() + dd + len, yPos);
|
||
|
||
// 设置黑色画笔画刻度标签
|
||
QString cs = QString::number(d1, 'g', 4); // 格式化成紧凑浮点数
|
||
QRectF tempRect = fm.boundingRect(cs);
|
||
QRectF textRect;
|
||
textRect.setX(rt.left());
|
||
textRect.setY(yPos - tempRect.height() / 2.0f);
|
||
textRect.setWidth(dd - fm.width("0") / 2);
|
||
textRect.setHeight(tempRect.height());
|
||
|
||
painter->setPen(Qt::black);
|
||
painter->drawText(textRect, Qt::AlignRight | Qt::AlignVCenter, cs);
|
||
|
||
painter->restore();
|
||
} else {
|
||
// 次刻度线(浅灰色)
|
||
painter->save();
|
||
painter->setPen(QPen(Qt::lightGray, 1));
|
||
painter->drawLine(rt.left() + dd, yPos, rt.left() + dd + len, yPos);
|
||
painter->restore();
|
||
}
|
||
|
||
// 更新刻度递增参数
|
||
ddd = d1;
|
||
if (ddd < 1.0f) {
|
||
while (ddd < 1.0f) ddd *= 10.0f;
|
||
} else {
|
||
while (ddd > 1.0f) ddd /= 10.0f;
|
||
if (ddd < 1.0f) ddd *= 10.0f;
|
||
}
|
||
mm = d1 / ddd;
|
||
}
|
||
|
||
// 画上下边框线(灰色)
|
||
painter->setPen(QPen(Qt::lightGray, 1));
|
||
painter->drawLine(rt.left() + dd, pt.y(), rt.left() + dd + len, pt.y());
|
||
painter->drawLine(rt.left() + dd, pt.y() + h, rt.left() + dd + len, pt.y() + h);
|
||
//从这里结束坐标轴绘制
|
||
//绘制折线分界线
|
||
// 分界数据
|
||
double DataOfLines[3][4] = {
|
||
{ 2, 2, 2, 2 },
|
||
{ 10, 25, 35, 80 },
|
||
{ 90, 500, 800, 1000 }
|
||
};
|
||
// 创建虚线笔
|
||
QPen dashedPen(Qt::black); // 设置颜色为黑色
|
||
dashedPen.setWidth(2); // 设置线宽
|
||
dashedPen.setStyle(Qt::CustomDashLine); // 使用自定义虚线样式
|
||
dashedPen.setDashPattern(QVector<qreal>() << 6.0 << 6.0); // 虚线段长12,间隔6
|
||
|
||
painter->save();
|
||
painter->setPen(dashedPen);
|
||
|
||
// 绘制三条折线
|
||
for (int row = 0; row < 3; ++row)
|
||
{
|
||
QPointF pts[4]; // 每条折线 4 个点
|
||
|
||
for (int col = 0; col < 4; ++col)
|
||
{
|
||
double logicX = static_cast<double>(col); // 逻辑 X: 0 ~ 3
|
||
double logicY = DataOfLines[row][col]; // 逻辑 Y: 实际数据
|
||
|
||
// ---------- X轴(线性) ----------
|
||
float screenX = static_cast<float>(x0 + logicX * (x1 - x0) / 3.0); // 横轴分三格
|
||
|
||
// ---------- Y轴(对数) ----------
|
||
float screenY;
|
||
float logBase = log10(yLabelMax / yLabelMin);
|
||
if (logicY <= 0.0) {
|
||
screenY = pt.y() + h; // 小于等于0 → 画在底部
|
||
} else {
|
||
float logRatio = log10(logicY / yLabelMin) / logBase;
|
||
screenY = pt.y() + h * (1.0f - logRatio); // 上大下小
|
||
}
|
||
|
||
pts[col] = QPointF(screenX, screenY);
|
||
}
|
||
|
||
// 用 Qt 的 drawPolyline 绘制线段
|
||
painter->drawPolyline(pts, 4);
|
||
}
|
||
|
||
painter->restore();
|
||
//绘制其他标识文字
|
||
QPen blackPen(Qt::black, 1);
|
||
painter->setPen(blackPen);
|
||
QString areaLabel[] = {"非产能", "油区", "气区", "非产能"};
|
||
double yLabel[4] = {1.7, 8, 190, 950};
|
||
for(int i = 0; i < 4; i++)
|
||
{
|
||
float screenX = static_cast<float>(x0 + 1.5 * (x1 - x0) / 3.0);
|
||
float screenY;
|
||
float logBase = log10(yLabelMax / yLabelMin);
|
||
if (yLabel[i] <= 0.0) {
|
||
screenY = pt.y() + h; // 小于等于0 → 画在底部
|
||
} else {
|
||
float logRatio = log10(yLabel[i] / yLabelMin) / logBase;
|
||
screenY = pt.y() + h * (1.0f - logRatio); // 上大下小
|
||
}
|
||
int textWidth = fm.width(areaLabel[i]);
|
||
int textHeight = fm.height();
|
||
// 设置字体并减小字体大小
|
||
painter -> save();
|
||
QFont font = painter->font();
|
||
int newPointSize = qMax(6, font.pointSize() - 2); // 确保字体大小不小于6点
|
||
font.setPointSize(newPointSize);
|
||
painter->setFont(font);
|
||
QRect rect(screenX - textWidth / 2, screenY, textWidth, textHeight);
|
||
painter->drawText(rect, Qt::AlignCenter, areaLabel[i]);
|
||
painter ->restore();
|
||
}
|
||
//投点
|
||
QPointF pts[4]; // 每条折线 4 个点
|
||
for (int col = 0; col < 4; ++col)
|
||
{
|
||
double logicX = static_cast<double>(col); // 逻辑 X: 0 ~ 3
|
||
double logicY = resultitem->RATION_Y[col]; // 逻辑 Y: 实际数据
|
||
|
||
// ---------- X轴(线性) ----------
|
||
float screenX = static_cast<float>(x0 + logicX * (x1 - x0) / 3.0); // 横轴分三格
|
||
|
||
// ---------- Y轴(对数) ----------
|
||
float screenY;
|
||
float logBase = log10(yLabelMax / yLabelMin);
|
||
if (logicY <= 0.0) {
|
||
screenY = pt.y() + h; // 小于等于0 → 画在底部
|
||
} else {
|
||
float logRatio = log10(logicY / yLabelMin) / logBase;
|
||
screenY = pt.y() + h * (1.0f - logRatio); // 上大下小
|
||
}
|
||
pts[col] = QPointF(screenX, screenY);
|
||
}
|
||
painter->setPen(QPen(Qt::blue, 2.5));
|
||
// 用 Qt 的 drawPolyline 绘制线段
|
||
painter->drawPolyline(pts, 4);
|
||
//绘制其他包含深度标签和辅助列
|
||
// ==== 绘制深度值和横纵坐标标题 ====
|
||
painter -> save();
|
||
painter->setPen(Qt::black);
|
||
QString depthText = QString::number(resultitem->depth, 'f', 1) + "米";
|
||
int offsetY = 40; // 向下偏移像素数
|
||
|
||
// --- 绘制深度值 ---
|
||
int depthX = x0 + (x1 - x0 - fm.width(depthText)) / 2;
|
||
int depthY = y1 + offsetY;
|
||
painter->drawText(depthX, depthY, depthText);
|
||
|
||
// --- 绘制横坐标标题(X轴) ---
|
||
QString xTitle = "油区";
|
||
int xTitleX = x0 + (x1 - x0 - fm.width(xTitle)) / 2;
|
||
int xTitleY = depthY + fm.height() + 4;
|
||
|
||
painter->drawText(xTitleX, xTitleY, xTitle);
|
||
//绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
painter -> restore();
|
||
}
|
||
// 湿度比-烃斜率图版
|
||
else if(resultitem->type == 9)
|
||
{
|
||
// 保存原始坐标系设置
|
||
int originalLogarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
int originalTLogarithmic = m_pViewInfoLogmud->GetTLogarithmic();
|
||
|
||
// 临时设置为线性坐标系
|
||
m_pViewInfoLogmud->SetLogarithmic(AXIS_LINEAR); // 设置Y轴为线性坐标系
|
||
m_pViewInfoLogmud->SetTLogarithmic(AXIS_LINEAR); // 设置X轴为线性坐标系
|
||
|
||
// 初始坐标轴范围(与C#一致:0-1)
|
||
float timemin = 0.0f;
|
||
float timemax = 1.0f;
|
||
float m_LeftVal = 0.0f;
|
||
float m_RightVal = 1.0f; // 保持为1
|
||
|
||
if (resultitem->WH > timemax) {
|
||
// 将最大值扩展到整数
|
||
timemax = ceil(resultitem->WH);
|
||
}
|
||
|
||
// 检查Y轴 (BH值)
|
||
if (resultitem->BH > m_RightVal) {
|
||
// 将最大值扩展到10的倍数
|
||
m_RightVal = ceil(resultitem->BH/10)*10;
|
||
}
|
||
|
||
float lval = m_LeftVal;
|
||
int Logarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
|
||
float rval = m_RightVal;
|
||
if(Logarithmic == AXIS_LOGARITHMIC){
|
||
if(rval <= 0) rval = 0.1f;
|
||
rval = log10(rval);
|
||
}
|
||
|
||
// 重新计算X轴范围
|
||
float dtime = timemax - timemin;
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
dtime = log10(timemax) - log10(timemin);
|
||
}
|
||
if(dtime == 0) dtime = 1;
|
||
|
||
int fnum=10;// 默认网格数为10
|
||
//设置X轴网格数和开始绘制X轴线性网格
|
||
if(m_pViewInfoLogmud->GetTLogarithmic()==AXIS_LINEAR) //如果X轴是线性坐标系
|
||
{
|
||
DrawXAxisLinearGrid(painter, timemin, timemax, dd, len, h, rt, pt, pt1, fm, fnum);
|
||
}
|
||
//设置Y轴网格数和开始绘制Y轴线性网格
|
||
fnum=10;
|
||
if(m_pViewInfoLogmud->GetLogarithmic()==AXIS_LOGARITHMIC) // 如果Y轴是对数坐标系
|
||
{
|
||
DrawYAxisLogarithmicGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen);
|
||
}
|
||
else // 如果Y轴是线性坐标系,循环绘制fnum+1条网格线
|
||
{
|
||
DrawYAxisLinearGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen, fnum);
|
||
}
|
||
// 绘制深度和轴标题
|
||
DrawDepthAndAxisLabels(painter, resultitem->depth, dd, w, h, rt, pt, fm, lscalelen, pCore,
|
||
"湿度比Wh(%)", "烃斜率Gh(C2/C3)");
|
||
|
||
// 绘制投点
|
||
DrawDataPoint(painter, resultitem->WH, resultitem->BH, timemin, timemax,
|
||
m_LeftVal, m_RightVal, dd, len, h, rt, pt1, Logarithmic);
|
||
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
|
||
// 恢复原始坐标系设置
|
||
m_pViewInfoLogmud->SetLogarithmic(originalLogarithmic);
|
||
m_pViewInfoLogmud->SetTLogarithmic(originalTLogarithmic);
|
||
}//判断湿度比-烃斜率的右括号
|
||
|
||
// 平衡比-特征比图版
|
||
else if(resultitem->type == 10){
|
||
// 保存原始坐标系设置
|
||
int originalLogarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
int originalTLogarithmic = m_pViewInfoLogmud->GetTLogarithmic();
|
||
|
||
// 临时设置为线性坐标系
|
||
m_pViewInfoLogmud->SetLogarithmic(AXIS_LINEAR);
|
||
m_pViewInfoLogmud->SetTLogarithmic(AXIS_LINEAR);
|
||
|
||
// 初始坐标轴范围
|
||
float timemin = 0.0f;
|
||
float timemax = 1.0f;
|
||
float m_LeftVal = 0.0f;
|
||
float m_RightVal = 1.0f;
|
||
|
||
// 检查X轴 (平衡比值)
|
||
if (resultitem->WH > timemax) {
|
||
timemax = ceil(resultitem->WH);
|
||
}
|
||
|
||
// 检查Y轴 (特征比值)
|
||
if (resultitem->BH > m_RightVal) {
|
||
m_RightVal = ceil(resultitem->BH/10)*10;
|
||
}
|
||
|
||
float lval = m_LeftVal;
|
||
int Logarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
|
||
float rval = m_RightVal;
|
||
if(Logarithmic == AXIS_LOGARITHMIC){
|
||
if(rval <= 0) rval = 0.1f;
|
||
rval = log10(rval);
|
||
}
|
||
|
||
// 重新计算X轴范围
|
||
float dtime = timemax - timemin;
|
||
if(m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
dtime = log10(timemax) - log10(timemin);
|
||
}
|
||
if(dtime == 0) dtime = 1;
|
||
|
||
int fnum=10;// 默认网格数为10
|
||
//设置X轴网格数和开始绘制X轴线性网格
|
||
if(m_pViewInfoLogmud->GetTLogarithmic()==AXIS_LINEAR) //如果X轴是线性坐标系
|
||
{
|
||
DrawXAxisLinearGrid(painter, timemin, timemax, dd, len, h, rt, pt, pt1, fm, fnum);
|
||
}
|
||
//设置Y轴网格数和开始绘制Y轴线性网格
|
||
if(m_pViewInfoLogmud->GetLogarithmic()==AXIS_LOGARITHMIC) // 如果Y轴是对数坐标系
|
||
{
|
||
DrawYAxisLogarithmicGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen);
|
||
}
|
||
else // 如果Y轴是线性坐标系,循环绘制fnum+1条网格线
|
||
{
|
||
DrawYAxisLinearGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen, fnum);
|
||
}
|
||
// 绘制深度和轴标题
|
||
DrawDepthAndAxisLabels(painter, resultitem->depth, dd, w, h, rt, pt, fm, lscalelen, pCore,
|
||
"平衡比Bh", "特征比Ch");
|
||
|
||
// 绘制投点
|
||
DrawDataPoint(painter, resultitem->WH, resultitem->BH, timemin, timemax,
|
||
m_LeftVal, m_RightVal, dd, len, h, rt, pt1, Logarithmic);
|
||
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
|
||
// 恢复原始坐标系设置
|
||
m_pViewInfoLogmud->SetLogarithmic(originalLogarithmic);
|
||
m_pViewInfoLogmud->SetTLogarithmic(originalTLogarithmic);
|
||
|
||
painter->restore();
|
||
|
||
} //判断平衡比-特征比的右括号
|
||
|
||
// 火成岩-沉积岩图版
|
||
else if(resultitem->type == 11)
|
||
{
|
||
// 保存原始坐标系设置
|
||
int originalLogarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
int originalTLogarithmic = m_pViewInfoLogmud->GetTLogarithmic();
|
||
|
||
// 临时设置为线性坐标系
|
||
m_pViewInfoLogmud->SetLogarithmic(AXIS_LINEAR);
|
||
m_pViewInfoLogmud->SetTLogarithmic(AXIS_LINEAR);
|
||
|
||
// 初始坐标轴范围(与C#一致)
|
||
float timemin = 0.0f;
|
||
float timemax = 35.0f; // X轴最大值35
|
||
float m_LeftVal = 0.0f;
|
||
float m_RightVal = 12.0f; // Y轴最大值12
|
||
|
||
|
||
|
||
float lval = m_LeftVal;
|
||
int Logarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
|
||
float rval = m_RightVal;
|
||
|
||
// 重新计算X轴范围
|
||
float dtime = timemax - timemin;
|
||
if(dtime == 0) dtime = 1;
|
||
|
||
// 保存原始网格数
|
||
int originalXGrid = m_pViewInfoLogmud->GetxGrid();
|
||
int originalYGrid = m_pViewInfoLogmud->GetyGrid();
|
||
|
||
// 设置网格数
|
||
// X轴:0, 5, 10, 15, 20, 25, 30, 35 (间隔5,共7个间隔)
|
||
m_pViewInfoLogmud->SetxGrid(7);
|
||
// Y轴:0, 2, 4, 6, 8, 10, 12 (间隔2,共6个间隔)
|
||
m_pViewInfoLogmud->SetyGrid(6);
|
||
|
||
// 绘制网格
|
||
DrawXAxisLinearGrid(painter, timemin, timemax, dd, len, h, rt, pt, pt1, fm, 7);
|
||
DrawYAxisLinearGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen, 6);
|
||
|
||
// 恢复原始网格数
|
||
m_pViewInfoLogmud->SetxGrid(originalXGrid);
|
||
m_pViewInfoLogmud->SetyGrid(originalYGrid);
|
||
|
||
// 绘制分界线 (0, 6) 到 (18, 0)
|
||
// 绘制分界线 (0, 6) 到 (18, 0)
|
||
painter->save();
|
||
QPen linePen;
|
||
linePen.setColor(QColor(192, 192, 192)); // 浅灰色
|
||
linePen.setWidth(2);
|
||
painter->setPen(linePen);
|
||
// 计算分界线的屏幕坐标
|
||
float x1 = 0.0f;
|
||
float y1 = 6.0f;
|
||
float x2 = 18.0f;
|
||
float y2 = 0.0f;
|
||
|
||
// X坐标转换
|
||
float screenX1 = rt.left() + dd + (x1 - timemin) * len / dtime;
|
||
float screenX2 = rt.left() + dd + (x2 - timemin) * len / dtime;
|
||
|
||
// Y坐标转换(注意Y轴是反向的)
|
||
float dval = m_RightVal - m_LeftVal;
|
||
if(dval == 0) dval = 1;
|
||
|
||
float screenY1 = pt1.y() + h - (y1 - m_LeftVal) * h / dval;
|
||
float screenY2 = pt1.y() + h - (y2 - m_LeftVal) * h / dval;
|
||
|
||
// 绘制分界线
|
||
painter->drawLine(QPointF(screenX1, screenY1), QPointF(screenX2, screenY2));
|
||
|
||
// 在分界线两侧添加标签
|
||
QFont labelFont = painter->font();
|
||
labelFont.setBold(true);
|
||
painter->setFont(labelFont);
|
||
painter->setPen(Qt::black);
|
||
|
||
// 火成岩标签 - 放在分界线左上方区域
|
||
float igneousX = rt.left() + dd + len * 0.15f; // X轴15%位置(约5.25)
|
||
float igneousY = pt1.y() + h * (1 - 8.0f/12.0f); // Y轴位置对应Y=8
|
||
|
||
QString igneousText = QString::fromLocal8Bit("火成岩");
|
||
QRectF igneousRect = fm.boundingRect(igneousText);
|
||
painter->drawText(QPointF(igneousX - igneousRect.width()/2, igneousY), igneousText);
|
||
|
||
// 沉积岩标签 - 放在分界线左下方区域
|
||
float sedimentaryX = rt.left() + dd + len * 0.1f; // X轴10%位置(约3.5)
|
||
float sedimentaryY = pt1.y() + h * (1 - 2.0f/12.0f); // Y轴位置对应Y=2
|
||
|
||
QString sedimentaryText = QString::fromLocal8Bit("沉积岩");
|
||
QRectF sedimentaryRect = fm.boundingRect(sedimentaryText);
|
||
painter->drawText(QPointF(sedimentaryX - sedimentaryRect.width()/2, sedimentaryY), sedimentaryText);
|
||
|
||
painter->restore();
|
||
|
||
// 绘制深度和轴标题
|
||
DrawDepthAndAxisLabels(painter, resultitem->depth, dd, w, h, rt, pt, fm, lscalelen, pCore,
|
||
"Fe+Mg %", "Na+K %");
|
||
|
||
// 绘制投点
|
||
DrawDataPoint(painter, resultitem->WH, resultitem->BH, timemin, timemax,
|
||
m_LeftVal, m_RightVal, dd, len, h, rt, pt1, AXIS_LINEAR);
|
||
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
|
||
// 恢复原始坐标系设置
|
||
m_pViewInfoLogmud->SetLogarithmic(originalLogarithmic);
|
||
m_pViewInfoLogmud->SetTLogarithmic(originalTLogarithmic);
|
||
|
||
painter->restore();
|
||
|
||
}//判断火成岩-沉积岩的右括号
|
||
|
||
|
||
// 碳酸盐-砂泥岩图版
|
||
else if(resultitem->type == 12)
|
||
{
|
||
// 保存原始坐标系设置
|
||
int originalLogarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
int originalTLogarithmic = m_pViewInfoLogmud->GetTLogarithmic();
|
||
|
||
// 临时设置为线性坐标系
|
||
m_pViewInfoLogmud->SetLogarithmic(AXIS_LINEAR);
|
||
m_pViewInfoLogmud->SetTLogarithmic(AXIS_LINEAR);
|
||
|
||
// 初始坐标轴范围
|
||
float timemin = 0.0f;
|
||
float timemax = 50.0f; // X轴最大值50 (Si %)
|
||
float m_LeftVal = 0.0f;
|
||
float m_RightVal = 50.0f; // Y轴最大值50 (Mg+Ca %)
|
||
|
||
// 检查X轴 (Si值)
|
||
if (resultitem->WH > timemax) {
|
||
// 将最大值扩展到5的倍数
|
||
timemax = ceil(resultitem->WH/5)*5;
|
||
}
|
||
|
||
// 检查Y轴 (Mg+Ca值)
|
||
if (resultitem->BH > m_RightVal) {
|
||
// 将最大值扩展到5的倍数
|
||
m_RightVal = ceil(resultitem->BH/5)*5;
|
||
}
|
||
|
||
float lval = m_LeftVal;
|
||
int Logarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
|
||
float rval = m_RightVal;
|
||
|
||
// 重新计算X轴范围
|
||
float dtime = timemax - timemin;
|
||
if(dtime == 0) dtime = 1;
|
||
|
||
// 保存原始网格数
|
||
int originalXGrid = m_pViewInfoLogmud->GetxGrid();
|
||
int originalYGrid = m_pViewInfoLogmud->GetyGrid();
|
||
|
||
// 设置网格数
|
||
// X轴:0, 5, 10, 15, 20, 25, 30, 35, 40, 45, 50 (间隔5,共10个间隔)
|
||
m_pViewInfoLogmud->SetxGrid(10);
|
||
// Y轴:0, 5, 10, 15, 20, 25, 30, 35, 40, 45, 50 (间隔5,共10个间隔)
|
||
m_pViewInfoLogmud->SetyGrid(10);
|
||
|
||
// 绘制网格
|
||
DrawXAxisLinearGrid(painter, timemin, timemax, dd, len, h, rt, pt, pt1, fm, 10);
|
||
DrawYAxisLinearGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen, 10);
|
||
|
||
// 恢复原始网格数
|
||
m_pViewInfoLogmud->SetxGrid(originalXGrid);
|
||
m_pViewInfoLogmud->SetyGrid(originalYGrid);
|
||
|
||
// 绘制分界线 (0, 0) 到 (50, 50) - 45度对角线
|
||
painter->save();
|
||
QPen linePen;
|
||
linePen.setColor(QColor(192, 192, 192)); // 浅灰色
|
||
linePen.setWidth(2);
|
||
painter->setPen(linePen);
|
||
|
||
// 计算分界线的屏幕坐标
|
||
float x1 = 0.0f;
|
||
float y1 = 0.0f;
|
||
float x2 = 50.0f;
|
||
float y2 = 50.0f;
|
||
|
||
// 如果坐标范围扩展了,需要调整线的终点
|
||
if (timemax > 50.0f || m_RightVal > 50.0f) {
|
||
// 延长线到新的边界
|
||
float maxVal = std::max(timemax, m_RightVal);
|
||
x2 = maxVal;
|
||
y2 = maxVal;
|
||
}
|
||
|
||
// X坐标转换
|
||
float screenX1 = rt.left() + dd + (x1 - timemin) * len / dtime;
|
||
float screenX2 = rt.left() + dd + (x2 - timemin) * len / dtime;
|
||
|
||
// Y坐标转换(注意Y轴是反向的)
|
||
float dval = m_RightVal - m_LeftVal;
|
||
if(dval == 0) dval = 1;
|
||
|
||
float screenY1 = pt1.y() + h - (y1 - m_LeftVal) * h / dval;
|
||
float screenY2 = pt1.y() + h - (y2 - m_LeftVal) * h / dval;
|
||
|
||
// 绘制分界线
|
||
painter->drawLine(QPointF(screenX1, screenY1), QPointF(screenX2, screenY2));
|
||
|
||
// 在分界线两侧添加标签
|
||
QFont labelFont = painter->font();
|
||
labelFont.setBold(true);
|
||
painter->setFont(labelFont);
|
||
painter->setPen(Qt::black);
|
||
|
||
// 碳酸盐标签 - 放在对角线上方区域(左上方)
|
||
float carbonateX = rt.left() + dd + len * 0.2f; // X轴20%位置(约10)
|
||
// Y=30对应的屏幕位置
|
||
float carbonateY = pt1.y() + h * (1 - 30.0f/m_RightVal); // Y轴位置对应Y=30
|
||
|
||
QString carbonateText = QString::fromLocal8Bit("碳酸盐");
|
||
QRectF carbonateRect = fm.boundingRect(carbonateText);
|
||
painter->drawText(QPointF(carbonateX - carbonateRect.width()/2, carbonateY), carbonateText);
|
||
|
||
// 砂泥岩标签 - 放在对角线下方区域(右下方)
|
||
float sandstoneMudstoneX = rt.left() + dd + len * 0.7f; // X轴70%位置(约35)
|
||
// Y=20对应的屏幕位置
|
||
float sandstoneMudstoneY = pt1.y() + h * (1 - 20.0f/m_RightVal); // Y轴位置对应Y=20
|
||
|
||
QString sandstoneMudstoneText = QString::fromLocal8Bit("砂泥岩");
|
||
QRectF sandstoneMudstoneRect = fm.boundingRect(sandstoneMudstoneText);
|
||
painter->drawText(QPointF(sandstoneMudstoneX - sandstoneMudstoneRect.width()/2,
|
||
sandstoneMudstoneY), sandstoneMudstoneText);
|
||
|
||
painter->restore();
|
||
|
||
// 绘制深度和轴标题
|
||
DrawDepthAndAxisLabels(painter, resultitem->depth, dd, w, h, rt, pt, fm, lscalelen, pCore,
|
||
"Si %", "Mg+Ca %");
|
||
|
||
// 绘制投点
|
||
DrawDataPoint(painter, resultitem->WH, resultitem->BH, timemin, timemax,
|
||
m_LeftVal, m_RightVal, dd, len, h, rt, pt1, AXIS_LINEAR);
|
||
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
|
||
// 恢复原始坐标系设置
|
||
m_pViewInfoLogmud->SetLogarithmic(originalLogarithmic);
|
||
m_pViewInfoLogmud->SetTLogarithmic(originalTLogarithmic);
|
||
|
||
painter->restore();
|
||
|
||
}//判断碳酸盐-砂泥岩的右括号
|
||
|
||
//泥岩-砂岩图版
|
||
else if(resultitem->type == 13)
|
||
{
|
||
// 保存原始坐标系设置
|
||
int originalLogarithmic = m_pViewInfoLogmud->GetLogarithmic();
|
||
int originalTLogarithmic = m_pViewInfoLogmud->GetTLogarithmic();
|
||
|
||
// 临时设置为线性坐标系
|
||
m_pViewInfoLogmud->SetLogarithmic(AXIS_LINEAR);
|
||
m_pViewInfoLogmud->SetTLogarithmic(AXIS_LINEAR);
|
||
|
||
// 固定坐标轴范围
|
||
float timemin = 20.0f; // X轴最小值20
|
||
float timemax = 47.0f; // X轴最大值47 (Si %)
|
||
float m_LeftVal = 0.0f;
|
||
float m_RightVal = 25.0f; // Y轴最大值25 (Al+Fe %)
|
||
|
||
float lval = m_LeftVal;
|
||
float rval = m_RightVal;
|
||
|
||
// 计算X轴范围
|
||
float dtime = timemax - timemin;
|
||
if(dtime == 0) dtime = 1;
|
||
|
||
// 保存原始网格数
|
||
int originalXGrid = m_pViewInfoLogmud->GetxGrid();
|
||
int originalYGrid = m_pViewInfoLogmud->GetyGrid();
|
||
|
||
// 设置网格数
|
||
m_pViewInfoLogmud->SetxGrid(6); // 20到47之间,每5一格,约6格
|
||
m_pViewInfoLogmud->SetyGrid(5); // 0到25,每5一格,5格
|
||
|
||
// 绘制网格 - 使用正确的起始值
|
||
DrawXAxisLinearGrid(painter, timemin, timemax, dd, len, h, rt, pt, pt1, fm, 6);
|
||
DrawYAxisLinearGrid(painter, m_LeftVal, m_RightVal, dd, len, h, rt, pt, fm, lscalelen, 5);
|
||
|
||
// 恢复原始网格数
|
||
m_pViewInfoLogmud->SetxGrid(originalXGrid);
|
||
m_pViewInfoLogmud->SetyGrid(originalYGrid);
|
||
|
||
// 绘制分界线 (20, 0) 到 (47, 25)
|
||
painter->save();
|
||
QPen linePen;
|
||
linePen.setColor(QColor(128, 128, 128)); // 灰色
|
||
linePen.setWidth(2);
|
||
painter->setPen(linePen);
|
||
|
||
// 计算分界线的屏幕坐标
|
||
float x1 = 20.0f;
|
||
float y1 = 0.0f;
|
||
float x2 = 47.0f;
|
||
float y2 = 25.0f;
|
||
|
||
// X坐标转换
|
||
float screenX1 = rt.left() + dd; // x1=20是起始点
|
||
float screenX2 = rt.left() + dd + len; // x2=47是结束点
|
||
|
||
// Y坐标转换(注意Y轴是反向的)
|
||
float screenY1 = pt1.y() + h; // y1=0是底部
|
||
float screenY2 = pt1.y(); // y2=25是顶部
|
||
|
||
// 绘制分界线
|
||
painter->drawLine(QPointF(screenX1, screenY1), QPointF(screenX2, screenY2));
|
||
|
||
// 在分界线两侧添加标签
|
||
QFont labelFont = painter->font();
|
||
labelFont.setBold(true);
|
||
painter->setFont(labelFont);
|
||
|
||
painter->setPen(Qt::black);
|
||
|
||
// 泥岩标签 - 放在左上方
|
||
QString mudstoneText = QString::fromLocal8Bit("泥岩");
|
||
painter->drawText(QPointF(rt.left() + dd + len * 0.25f, pt1.y() + h * 0.3f), mudstoneText);
|
||
|
||
// 砂岩标签 - 放在右下方
|
||
QString sandstoneText = QString::fromLocal8Bit("砂岩");
|
||
painter->drawText(QPointF(rt.left() + dd + len * 0.65f, pt1.y() + h * 0.7f), sandstoneText);
|
||
|
||
painter->restore();
|
||
|
||
// 绘制深度和轴标题
|
||
DrawDepthAndAxisLabels(painter, resultitem->depth, dd, w, h, rt, pt, fm, lscalelen, pCore,
|
||
"Si %", "Al+Fe %");
|
||
|
||
// 绘制投点
|
||
DrawDataPoint(painter, resultitem->WH, resultitem->BH, timemin, timemax,
|
||
m_LeftVal, m_RightVal, dd, len, h, rt, pt1, AXIS_LINEAR);
|
||
|
||
// 绘制辅助线
|
||
painter->drawLine(QPointF(rt.left(), pt1.y()), QPointF(rt.left()+rt.width()/20, pt1.y()));
|
||
|
||
// 恢复原始坐标系设置
|
||
m_pViewInfoLogmud->SetLogarithmic(originalLogarithmic);
|
||
m_pViewInfoLogmud->SetTLogarithmic(originalTLogarithmic);
|
||
|
||
painter->restore();
|
||
}//判断泥岩-砂岩的右括号
|
||
|
||
|
||
*/
|
||
|
||
|
||
|
||
painter->restore();
|
||
}
|
||
painter->restore();
|
||
}
|
||
return pt;
|
||
}
|
||
return pt;
|
||
}
|
||
// 绘制X轴对数刻度
|
||
void LogmudItemDrawer::DrawXAxisLogarithmicGrid(QPainter* painter, float timemin, float timemax,
|
||
float dd, float w, float h, QRectF rt, QPointF pt,
|
||
QFontMetrics& fm, float& lscalelen) const
|
||
{
|
||
|
||
float d1;
|
||
float lsc = timemin, rsc = timemax;
|
||
if(!IsFiniteNumber(lsc)||lsc <= 0) lsc = 0.1f;
|
||
if(!IsFiniteNumber(rsc)||rsc <= 0) rsc = lsc * 10.0f;
|
||
if(rsc <= lsc) rsc = lsc * 10.0f;
|
||
if(rsc/lsc > 100000000.0f) rsc = lsc * 100000000.0f;
|
||
float ddd = lsc;
|
||
float mm = lsc/ddd;
|
||
float x;
|
||
float logRange = log10(rsc/lsc);
|
||
if(!IsFiniteNumber(logRange)||qAbs(logRange)<1e-6f) return;
|
||
int safetyCounter = 0;
|
||
|
||
for (d1 = lsc; d1 <= rsc; d1 = ((int)(d1/mm+1.5f))*mm) // 循环生成刻度
|
||
{
|
||
if(++safetyCounter>20000) break;
|
||
if(!IsFiniteNumber(d1)||!IsFiniteNumber(mm)||qAbs(mm)<1e-20f) break;
|
||
QPen penGuide(QColor(220, 220, 220), 1);
|
||
painter->setPen(penGuide);
|
||
x = log10(d1/lsc)/logRange*w;
|
||
if (fmod(log10(d1), (float)1.0f) == 0.0f)
|
||
{
|
||
painter->save();
|
||
|
||
QPen penw = painter->pen();
|
||
float pww = penw.widthF();
|
||
if(pww <= 0) pww = 1.0f;
|
||
float pw = pww * 0.5f;
|
||
penw.setWidthF(pw);
|
||
painter->setPen(penw);
|
||
painter->drawLine(rt.left()+dd+x, pt.y(), rt.left()+dd+x, pt.y()+h);
|
||
painter->setPen(m_Color);// m_pViewInfoLogmud->GetColor());
|
||
QString cs = toString(d1);
|
||
QTransform transform;
|
||
transform.reset();
|
||
qreal rotatex=0;
|
||
qreal rotatey=0;
|
||
rotatex = rt.left()+dd+x;
|
||
rotatey = pt.y()+h+fm.height()/3;
|
||
//=============================================
|
||
QRectF tempRect,drawRect;
|
||
////===================层号旋转===========================
|
||
// 绘制刻度标签
|
||
transform = painter->worldTransform();
|
||
transform.translate(rotatex, rotatey);
|
||
transform.rotate(0);
|
||
transform.translate(-rotatex, -rotatey);
|
||
painter->setWorldTransform(transform);
|
||
QRectF textRect;
|
||
if(!cs.isEmpty())
|
||
{
|
||
tempRect = fm.boundingRect(cs);
|
||
if(lscalelen < tempRect.width()) lscalelen = tempRect.width();
|
||
textRect.setX(rotatex-tempRect.width()/2);
|
||
textRect.setY(rotatey);
|
||
textRect.setWidth(tempRect.width());
|
||
textRect.setHeight(tempRect.height());
|
||
painter->drawText(textRect, Qt::AlignHCenter|Qt::AlignVCenter, cs);
|
||
}
|
||
painter->restore();
|
||
}
|
||
else
|
||
{
|
||
painter->drawLine(rt.left()+dd+x, pt.y(), rt.left()+dd+x, pt.y()+h);
|
||
}
|
||
|
||
// 更新刻度计算参数
|
||
ddd = d1;
|
||
if(!IsFiniteNumber(ddd)||ddd<=0) break;
|
||
if(ddd < 1.0f)
|
||
{
|
||
int k=0;
|
||
while(ddd < 1.0f && ++k<20) ddd *= 10.0f;
|
||
}
|
||
else
|
||
{
|
||
int k=0;
|
||
while(ddd > 1.0f && ++k<20) ddd /= 10.0f;
|
||
if(ddd < 1.0f) ddd = ddd * 10.0f;
|
||
}
|
||
mm = d1/ddd;
|
||
if(!IsFiniteNumber(mm)||qAbs(mm)<1e-20f) break;
|
||
}
|
||
|
||
// 绘制边界线
|
||
painter->drawLine(rt.left()+dd, pt.y(), rt.left()+dd, pt.y()+h);
|
||
painter->drawLine(rt.left()+dd+w, pt.y(), rt.left()+dd+w, pt.y()+h);
|
||
}
|
||
// 绘制X轴线性刻度
|
||
void LogmudItemDrawer::DrawXAxisLinearGrid(QPainter* painter, float timemin, float timemax,
|
||
float dd, float len, float h, QRectF rt, QPointF pt,
|
||
QPointF pt1, QFontMetrics& fm, int fnum) const
|
||
{
|
||
for(int i = 0; i < fnum + 1; i++)
|
||
{
|
||
painter->save();
|
||
painter->setPen(m_CGrid);// m_pViewInfoLogmud->GetCGrid());
|
||
painter->drawLine(QPointF(rt.left()+dd+i*len/fnum, pt1.y()),
|
||
QPointF(rt.left()+dd+i*len/fnum, pt1.y()+h));
|
||
|
||
QString cs = toString(timemin+(timemax-timemin)/fnum*i);
|
||
painter->setPen(m_Color);// m_pViewInfoLogmud->GetColor());
|
||
QTransform transform;
|
||
transform.reset();
|
||
qreal rotatex=0;
|
||
qreal rotatey=0;
|
||
rotatex = rt.left()+dd+i*len/fnum;
|
||
rotatey = pt.y()+h+fm.height()/3;
|
||
//=============================================
|
||
QRectF tempRect,drawRect;
|
||
painter->setPen(m_Color);// m_pViewInfoLogmud->GetColor());
|
||
////===================层号旋转===========================
|
||
// 绘制刻度标签
|
||
transform = painter->worldTransform();
|
||
transform.translate(rotatex, rotatey);
|
||
transform.rotate(0);
|
||
transform.translate(-rotatex, -rotatey);
|
||
painter->setWorldTransform(transform);
|
||
QRectF textRect;
|
||
if(!cs.isEmpty())
|
||
{
|
||
tempRect = fm.boundingRect(cs);
|
||
textRect.setX(rotatex-tempRect.width()/2);
|
||
textRect.setY(rotatey);
|
||
textRect.setWidth(tempRect.width());
|
||
textRect.setHeight(tempRect.height());
|
||
painter->drawText(textRect, Qt::AlignHCenter|Qt::AlignTop, cs);
|
||
}
|
||
painter->restore();
|
||
}
|
||
}
|
||
// 绘制Y轴对数刻度
|
||
void LogmudItemDrawer::DrawYAxisLogarithmicGrid(QPainter* painter, float minVal, float maxVal,
|
||
float dd, float len, float h, QRectF rt, QPointF pt,
|
||
QFontMetrics& fm, float& lscalelen) const
|
||
{
|
||
float d1;
|
||
float lsc = minVal, rsc = maxVal;
|
||
if(!IsFiniteNumber(lsc)||lsc <= 0) lsc = 0.1f;
|
||
if(!IsFiniteNumber(rsc)||rsc <= 0) rsc = lsc * 10.0f;
|
||
if(rsc <= lsc) rsc = lsc * 10.0f;
|
||
if(rsc/lsc > 100000000.0f) rsc = lsc * 100000000.0f;
|
||
float ddd = lsc;
|
||
float mm = lsc/ddd;
|
||
float x;
|
||
float logRange = log10(rsc/lsc);
|
||
if(!IsFiniteNumber(logRange)||qAbs(logRange)<1e-6f) return;
|
||
int safetyCounter = 0;
|
||
|
||
for (d1 = lsc; d1 <= rsc; d1 = ((int)(d1/mm+1.5f))*mm)
|
||
{
|
||
if(++safetyCounter>20000) break;
|
||
if(!IsFiniteNumber(d1)||!IsFiniteNumber(mm)||qAbs(mm)<1e-20f) break;
|
||
QPen penGuide(QColor(220, 220, 220), 1);
|
||
painter->setPen(penGuide);
|
||
x = log10(d1/lsc)/logRange*h;
|
||
if (fmod(log10(d1), (float)1.0f) == 0.0f)
|
||
{
|
||
painter->save();
|
||
QPen penw = painter->pen();
|
||
float pww = penw.widthF();
|
||
if(pww <= 0) pww = 1.0f;
|
||
float pw = pww * 0.5f;
|
||
penw.setWidthF(pw);
|
||
painter->setPen(penw);
|
||
painter->drawLine(rt.left()+dd, pt.y()+h-x, rt.left()+dd+len, pt.y()+h-x);
|
||
painter->setPen(m_Color);// m_pViewInfoLogmud->GetColor());
|
||
QString cs = toString(d1);
|
||
QTransform transform;
|
||
transform.reset();
|
||
qreal rotatex=0;
|
||
qreal rotatey=0;
|
||
rotatex = rt.left();
|
||
rotatey = pt.y()+h-x;
|
||
//=============================================
|
||
QRectF tempRect,drawRect;
|
||
////===================层号旋转===========================
|
||
// 绘制刻度标签
|
||
transform = painter->worldTransform();
|
||
transform.translate(rotatex, rotatey);
|
||
transform.rotate(0);
|
||
transform.translate(-rotatex, -rotatey);
|
||
painter->setWorldTransform(transform);
|
||
QRectF textRect;
|
||
if(!cs.isEmpty() && m_isOneScale)//m_pViewInfoLogmud->GetisOneScale())
|
||
{
|
||
tempRect = fm.boundingRect(cs);
|
||
if(lscalelen < tempRect.width()) lscalelen = tempRect.width();
|
||
textRect.setX(rt.left());
|
||
textRect.setY(rotatey-tempRect.height()/2.0f);
|
||
textRect.setWidth(dd-fm.width("0")/2);
|
||
textRect.setHeight(tempRect.height());
|
||
painter->drawText(textRect, Qt::AlignRight|Qt::AlignVCenter, cs);
|
||
}
|
||
painter->restore();
|
||
}
|
||
else
|
||
{
|
||
painter->drawLine(rt.left()+dd, pt.y()+h-x, rt.left()+dd+len, pt.y()+h-x);
|
||
}
|
||
|
||
// 更新刻度计算参数
|
||
ddd = d1;
|
||
if(!IsFiniteNumber(ddd)||ddd<=0) break;
|
||
if(ddd < 1.0f)
|
||
{
|
||
int k=0;
|
||
while(ddd < 1.0f && ++k<20) ddd *= 10.0f;
|
||
}
|
||
else
|
||
{
|
||
int k=0;
|
||
while(ddd > 1.0f && ++k<20) ddd /= 10.0f;
|
||
if(ddd < 1.0f) ddd = ddd * 10.0f;
|
||
}
|
||
mm = d1/ddd;
|
||
if(!IsFiniteNumber(mm)||qAbs(mm)<1e-20f) break;
|
||
}
|
||
|
||
// 绘制边界线
|
||
painter->drawLine(rt.left()+dd, pt.y(), rt.left()+dd+len, pt.y());
|
||
painter->drawLine(rt.left()+dd, pt.y()+h, rt.left()+dd+len, pt.y()+h);
|
||
}
|
||
|
||
// 绘制Y轴线性刻度
|
||
void LogmudItemDrawer::DrawYAxisLinearGrid(QPainter* painter, float minVal, float maxVal,
|
||
float dd, float len, float h, QRectF rt, QPointF pt,
|
||
QFontMetrics& fm, float& lscalelen, int fnum) const
|
||
{
|
||
// 防止fnum为0
|
||
if(fnum <= 0) fnum = 1;
|
||
|
||
// 确保最大值大于最小值
|
||
if(maxVal <= minVal) maxVal = minVal + 1.0f;
|
||
|
||
for(int i = 0; i < fnum + 1; i++)
|
||
{
|
||
painter->save();
|
||
painter->setPen(m_CGrid);// m_pViewInfoLogmud->GetCGrid());
|
||
painter->drawLine(QPointF(rt.left()+dd, pt.y()+i*h/fnum),
|
||
QPointF(rt.left()+dd+len, pt.y()+i*h/fnum));
|
||
|
||
painter->setPen(m_Color);// m_pViewInfoLogmud->GetColor());
|
||
QString cs = toString(maxVal-(maxVal-minVal)/fnum*i);
|
||
QTransform transform;
|
||
transform.reset();
|
||
qreal rotatex=0;
|
||
qreal rotatey=0;
|
||
rotatex = rt.left();
|
||
rotatey = pt.y()+i*h/fnum;
|
||
//=============================================
|
||
QRectF tempRect,drawRect;
|
||
painter->setPen(m_Color);// m_pViewInfoLogmud->GetColor());
|
||
////===================层号旋转===========================
|
||
// 绘制刻度标签
|
||
transform = painter->worldTransform();
|
||
transform.translate(rotatex, rotatey);
|
||
transform.rotate(0);
|
||
transform.translate(-rotatex, -rotatey);
|
||
painter->setWorldTransform(transform);
|
||
QRectF textRect;
|
||
if(!cs.isEmpty() && m_isOneScale)//m_pViewInfoLogmud->GetisOneScale())
|
||
{
|
||
tempRect = fm.boundingRect(cs);
|
||
if(lscalelen < tempRect.width()) lscalelen = tempRect.width();
|
||
textRect.setX(rt.left());
|
||
textRect.setY(rotatey-tempRect.height()/2.0f);
|
||
textRect.setWidth(dd-fm.width("0")/2);
|
||
textRect.setHeight(tempRect.height());
|
||
painter->drawText(textRect, Qt::AlignRight|Qt::AlignVCenter, cs);
|
||
}
|
||
painter->restore();
|
||
}
|
||
}
|
||
//绘制深度和轴标题
|
||
void LogmudItemDrawer::DrawDepthAndAxisLabels(QPainter* painter, float depth, float dd, float w, float h,
|
||
QRectF rt, QPointF pt, QFontMetrics& fm,
|
||
float lscalelen,
|
||
const QString& xAxisTitle, const QString& yAxisTitle) const
|
||
{
|
||
painter->save();
|
||
// 设置黑色画笔
|
||
painter->setPen(Qt::black);
|
||
// 绘制深度值
|
||
QString cs = toString(depth);
|
||
cs += "米";
|
||
float zw = fm.width(cs);
|
||
|
||
if(m_isBottom == 0) {
|
||
painter->drawText(QPointF(rt.left()+dd+(rt.width()-2*rt.width()*2/10-fm.width(cs))/2, pt.y()-fm.height()),
|
||
cs, Qt::AlignRight|Qt::AlignVCenter, 0);
|
||
}
|
||
else if(m_isBottom == 1) {
|
||
painter->drawText(QPointF(rt.left()+dd+(w-fm.width(cs))/2,
|
||
pt.y()+h+((m_bisHi ?2.3:(0/*pCore->GetFieldName().size()*/?0:1.5))+1)*fm.height()),
|
||
cs, Qt::AlignRight|Qt::AlignVCenter, 0);
|
||
}
|
||
else if(m_isBottom == 2) {
|
||
painter->drawText(QPointF(rt.left()+rt.width()/20, pt.y()-fm.height()/2),
|
||
cs, Qt::AlignRight|Qt::AlignVCenter, 0);
|
||
}
|
||
else if(m_isBottom == 3) {
|
||
painter->drawText(QPointF(rt.right()-fm.width(cs), pt.y()-fm.height()/2),
|
||
cs, Qt::AlignRight|Qt::AlignVCenter, 0);
|
||
}
|
||
|
||
// 绘制X轴标题
|
||
QString xTitle = xAxisTitle.isEmpty() ? m_TimeName : xAxisTitle;
|
||
if(!m_isOneScale && xAxisTitle.isEmpty()) xTitle = "";
|
||
|
||
painter->drawText(QPointF(rt.left()+dd+(w-fm.width(xTitle))/2,
|
||
pt.y()+h+((m_bisHi ?1.3:(m_isBottom==0?1:0))+1)*fm.height()),
|
||
xTitle, Qt::AlignRight|Qt::AlignVCenter, 0);
|
||
|
||
// 绘制Y轴标题
|
||
QString yTitle = yAxisTitle.isEmpty() ? m_CurveName : yAxisTitle;
|
||
|
||
// 如果提供了自定义Y轴标题,则旋转绘制
|
||
if (!yAxisTitle.isEmpty()) {
|
||
QTransform transform;
|
||
transform = painter->worldTransform();
|
||
qreal rotatex = rt.left() + dd/3;
|
||
qreal rotatey = pt.y() + h/2 + fm.width(yTitle)/2;
|
||
transform.translate(rotatex, rotatey);
|
||
transform.rotate(-90);
|
||
transform.translate(-rotatex, -rotatey);
|
||
painter->setWorldTransform(transform);
|
||
painter->drawText(QPointF(rotatex, rotatey), yTitle);
|
||
|
||
// 恢复变换
|
||
transform.reset();
|
||
painter->setWorldTransform(transform);
|
||
}
|
||
else {
|
||
// 原有的多行Y轴标题绘制方式
|
||
yTitle.replace("\\n", "\n");
|
||
QStringList strs = yTitle.split("\n");
|
||
float mw = 0;
|
||
|
||
for(int i = 0; i < strs.size(); i++) {
|
||
if(mw < fm.width(strs.at(i))) mw = fm.width(strs.at(i));
|
||
}
|
||
|
||
for(int i = 0; i < strs.size(); i++) {
|
||
QRectF temp(rt.left()+dd-lscalelen-fm.width("0")/2-mw,
|
||
pt.y()+(h-strs.size()*fm.height())/2+i*fm.height()+fm.height(), mw, fm.height());
|
||
QTextOption op(Qt::AlignHCenter|Qt::AlignVCenter);
|
||
painter->drawText(temp, strs.at(i), op);
|
||
}
|
||
}
|
||
painter->restore();
|
||
}
|
||
|
||
|
||
// 绘制投点
|
||
void LogmudItemDrawer::DrawDataPoint(QPainter* painter, float wh, float bh, float timemin, float timemax,
|
||
float minVal, float maxVal, float dd, float len, float h,
|
||
QRectF rt, QPointF pt1, int logarithmic) const
|
||
{
|
||
// 保存当前绘图状态
|
||
painter->save();
|
||
|
||
// 重置变换,确保在设备坐标系中绘制
|
||
QTransform transform;
|
||
transform.reset();
|
||
painter->setWorldTransform(transform);
|
||
// 计算屏幕坐标
|
||
float pointX = 0;
|
||
float pointY = 0;
|
||
|
||
// X坐标转换(WH)
|
||
if (m_pViewInfoLogmud->GetTLogarithmic() == AXIS_LOGARITHMIC) {
|
||
// 对数坐标系
|
||
float safeMinX = timemin;
|
||
float safeMaxX = timemax;
|
||
if(!IsFiniteNumber(safeMinX) || safeMinX <= 0) safeMinX = 0.1f;
|
||
if(!IsFiniteNumber(safeMaxX) || safeMaxX <= safeMinX) safeMaxX = safeMinX * 10.0f;
|
||
float logRangeX = log10(safeMaxX) - log10(safeMinX);
|
||
if(!IsFiniteNumber(logRangeX) || qAbs(logRangeX) < 1e-6f) logRangeX = 1.0f;
|
||
float val = wh;
|
||
if (!IsFiniteNumber(val) || val <= 0) val = safeMinX;
|
||
if (val > safeMaxX) val = safeMaxX;
|
||
pointX = rt.left() + dd + (log10(val) - log10(safeMinX)) * len / logRangeX;
|
||
} else {
|
||
// 线性坐标系
|
||
float rangeX = timemax - timemin;
|
||
if(!IsFiniteNumber(rangeX) || qAbs(rangeX) < 1e-6f) rangeX = 1.0f;
|
||
pointX = rt.left() + dd + (wh - timemin) * len / rangeX;
|
||
}
|
||
|
||
// Y坐标转换(BH)
|
||
if (logarithmic == AXIS_LINEAR) {
|
||
// 线性坐标系
|
||
float rangeY = maxVal - minVal;
|
||
if(!IsFiniteNumber(rangeY) || qAbs(rangeY) < 1e-6f) rangeY = 1.0f;
|
||
pointY = (bh - minVal) / rangeY * h;
|
||
} else if (logarithmic == AXIS_LOGARITHMIC) {
|
||
// 对数坐标系
|
||
float val = bh;
|
||
if (!IsFiniteNumber(val) || val <= 0) val = 0.1f;
|
||
float lval = (minVal <= 0) ? log10(0.1f) : log10(minVal);
|
||
float rval = (maxVal <= 0) ? log10(0.1f) : log10(maxVal);
|
||
float rangeY = rval - lval;
|
||
if(!IsFiniteNumber(rangeY) || qAbs(rangeY) < 1e-6f) rangeY = 1.0f;
|
||
pointY = (log10(val) - lval) / rangeY * h;
|
||
}
|
||
|
||
if (pointY < 0) pointY = 0;
|
||
if (pointY > h) pointY = h;
|
||
pointY = pt1.y() + h - pointY;
|
||
|
||
// 设置投点样式
|
||
QPen pointPen;
|
||
pointPen.setColor(Qt::red);
|
||
pointPen.setWidth(2);
|
||
painter->setPen(pointPen);
|
||
painter->setBrush(Qt::red);
|
||
|
||
// 绘制投点(圆形)
|
||
float pointSize = 3.0f;
|
||
painter->drawEllipse(QPointF(pointX, pointY), pointSize, pointSize);
|
||
|
||
// 恢复绘图状态
|
||
painter->restore();
|
||
}
|
||
|