You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

503 lines
16 KiB
C++

#include "StdAfx.h"
#include "LaserPowCheckMgr.h"
#include "LogMgr.h"
#include "FileMgr.h"
#include "WorkTime.h"
#include "CStringFuc.h"
#include "MsgBox.h"
#include "ExceptionMsg.h"
#include "MsgBox.h"
#include "WorkCmdInvoker.h"
#include "Propertie.h"
#include "PropertieMgr.h"
#include "AuthorityMgr.h"
#include "CommonFlowMgr.h"
#include "GlobalFunction.h"
#include "RecipeMgr.h"
#include "Laser.h"
#define POW_CHECK_FILE_PATH _T("\\LaserPowerCheckData\\")
#define POW_CHECK_PAR_FILE _T("\\Parameter\\LaserMeasureData\\LaserPowCheckPar.par")
#define FIX_POW_PARA_FILE _T("\\CommPar\\LaserFixCurrentPower.bin")
#define TAB_STR " "
#define SPECIAL_CHAR '#'
void CPowCheckPar::Serialize( CArchive& ar)
{
if(ar.IsStoring())
{
ar<<m_PulseFre;//激光脉冲频率Hz
ar<<m_StartCurr;//开始电流值A
ar<<m_EndCurr;//结束电流值A
ar<<m_GapCurr;//间隔电流值A
ar<<m_CheckDelay;//每个电流值测量的延时ms
ar<<m_FirstCheckDelay;//第一个电流值测量的延时ms
}
else
{
ar>>m_PulseFre;//激光脉冲频率Hz
ar>>m_StartCurr;//开始电流值A
ar>>m_EndCurr;//结束电流值A
ar>>m_GapCurr;//间隔电流值A
ar>>m_CheckDelay;//每个电流值测量的延时ms
ar>>m_FirstCheckDelay;//第一个电流值测量的延时ms
}
}
CLaserPowCheckMgr *gLaserPowCheckMgr = new CLaserPowCheckMgr;
CLaserPowCheckMgr::CLaserPowCheckMgr(void)
{
m_CurPowCheckType = _LaserDeviceType_MainLaser1;//当前功率点检的类型
m_ParList = NULL;
m_CurSelCheckRecordIdx = -1;
m_CurExtLaserType = 0;
}
CLaserPowCheckMgr::~CLaserPowCheckMgr(void)
{
}
void CLaserPowCheckMgr::OnAppInitialize()
{
//创建功率点检数据目录
CString DirPath = GetPowCheckFilePath();
CFileMgr FileMgr;
if(!FileMgr.IsDirectoryExists(DirPath))
FileMgr.CreatDir(DirPath);
}
//获取功率点检的文件路径
CString CLaserPowCheckMgr::GetPowCheckFilePath()
{
CString DirPath = gProgramLaserTuiHuo->GetLaipuLaserDataDir(POW_CHECK_FILE_PATH);
return DirPath;
}
#if 1
void CLaserPowCheckMgr::InitSelYearComb(CComboBox &ComboBox)
{
CString FilePath = GetPowCheckFilePath();
InitYearComb(FilePath,ComboBox);
}
void CLaserPowCheckMgr::InitSelMonthComb(CComboBox &ComboBox)
{
InitMonthComb(ComboBox);
}
void CLaserPowCheckMgr::InitSelLaserComb(CComboBox &ComboBox)
{
int idx = 0;
ComboBox.InsertString(idx++,"绿光1");
ComboBox.InsertString(idx++,"绿光2");
ComboBox.InsertString(idx++,"红光");
//设置默认选择项
ComboBox.SetCurSel(0);
}
void CLaserPowCheckMgr::IniParList(CListCtrl &list,int AddW)
{
//设置风格
list.SetExtendedStyle(LVS_EX_FULLROWSELECT|LVS_EX_GRIDLINES);
//设置列
int idx = 0;
list.InsertColumn(idx,"Idx",LVCFMT_LEFT,35,-1);
idx++;
list.InsertColumn(idx,"Current(A)",LVCFMT_LEFT,70+AddW,-1);
idx++;
list.InsertColumn(idx,"Laser Po(W)",LVCFMT_LEFT,90+AddW,-1);
idx++;
list.InsertColumn(idx,"Valid Po(W)",LVCFMT_LEFT,90+AddW,-1);
idx++;
}
void CLaserPowCheckMgr::IniRecordList(CListCtrl &list)
{
//设置风格
list.SetExtendedStyle(LVS_EX_FULLROWSELECT|LVS_EX_GRIDLINES);
//设置列
int idx = 0;
list.InsertColumn(idx,"Idx",LVCFMT_LEFT,35,-1);
idx++;
list.InsertColumn(idx,"Time",LVCFMT_LEFT,120,-1);
idx++;
list.InsertColumn(idx,"Fre",LVCFMT_LEFT,70,-1);
idx++;
list.InsertColumn(idx,"K ",LVCFMT_LEFT,100,-1);
idx++;
list.InsertColumn(idx,"Po ",LVCFMT_LEFT,100,-1);
idx++;
}
#endif
#if 1//点检参数相关
//设置当前功率点检的类型
void CLaserPowCheckMgr::SetCurPowCheckType(int idx)
{
eLaserDeviceType Type = (eLaserDeviceType)idx;
m_CurPowCheckType = Type;
}
//设置当前点检的频率(CreatCurPowCheckData之前使用)
void CLaserPowCheckMgr::SetCurPowCheckFre(double Fre)
{
CPowCheckPar &CurPowCheckPar = (*GetCurPowCheckPar());
if(Fre>0)//使用指定的激光频率
{
CurPowCheckPar.m_PulseFre = Fre;
}
}
//获取当前的检测结果
CPowCheckPar *CLaserPowCheckMgr::GetCurPowCheckPar()
{
CPowCheckPar *p;
p = &m_MainPowCheckPar;
return p;
}
void CLaserPowCheckMgr::SetPowCheckPar(CPowCheckPar CheckPar)
{
CPowCheckPar &CurPowCheckPar = (*GetCurPowCheckPar());
CurPowCheckPar = CheckPar;
}
#endif
#if 1
//获取当前的功率密度参数(显示用)
void CLaserPowCheckMgr::GetEnergyDensityPar(double &K,double &Po)
{
K = m_CurPowCheckData.m_EnergyDensityK;
Po = m_CurPowCheckData.m_EnergyDensityPo;
}
//计算功率密度参数(K和Po)(不满足会产生报警信息)
bool CLaserPowCheckMgr::CalEnergyDensityPar()
{
gLogMgr->WriteDebugLog("Func---->CalEnergyDensityPar");
vector<CPowCheckPt>&PowCheckPtVec = m_CurPowCheckData.m_PowCheckPtVec;
int size = PowCheckPtVec.size();
if(size<2)
return false;
double SumK = 0;
double SumP = 0;//功率和
double SumI = 0;//电流和
bool bSaveToPar = true;//是否保存到参数
for(int k=0;k<size;k++)
{
if(k!=size-1)
{
double K = CalTwoPtK(PowCheckPtVec[k],PowCheckPtVec[k+1]);
SumK += K;
}
SumP += PowCheckPtVec[k].m_SurfacePow;
SumI += PowCheckPtVec[k].m_SetCurr;
if(k==1 && PowCheckPtVec[k].m_SetCurr == PowCheckPtVec[0].m_SetCurr)
{
bSaveToPar = false;
}
}
//平均值
double AvgK= SumK/(double)(size-1);//因为两个点算截距要比点数少一个
double AvgP = SumP/(double)(size);
double AvgI = SumI/(double)(size);
//斜率取平均值
m_CurPowCheckData.m_EnergyDensityK = AvgK;
//截距
m_CurPowCheckData.m_EnergyDensityPo = AvgP - AvgK*AvgI;
CString LogStr;
LogStr.Format(_T("[AvgK] = [%0.3f] ,[AvgP] = [%0.3f],[AvgI] = [%0.3f],[Po] = [%0.3f]"),AvgK,AvgP,AvgI,m_CurPowCheckData.m_EnergyDensityPo);
gLogMgr->WriteDebugLog(LogStr);
//将功率点检计算的功率密度参数值设置为保存值
bool Ret = false;
if(bSaveToPar)
{
//获取绿光/红光的点检参数
CPowCheckPar &CheckPar = (*GetCurPowCheckPar());
//检查点检结果是否满足设定条件
//Ret = gLaser->CheckEnergyDensityPar(m_CurPowCheckType,CheckPar.m_PulseFre,m_CurPowCheckData.m_EnergyDensityK,m_CurPowCheckData.m_EnergyDensityPo);
}
return Ret;
}
//计算两个点的功率密度斜率
double CLaserPowCheckMgr::CalTwoPtK(CPowCheckPt CheckPt1,CPowCheckPt CheckPt2)
{
double K = (CheckPt2.m_SurfacePow - CheckPt1.m_SurfacePow)/(CheckPt2.m_SetCurr - CheckPt1.m_SetCurr);
return K;
}
//恢复最近一次的点检数据
void CLaserPowCheckMgr::RecoverLastPowCheckData(eLaserDeviceType LaserDeviceType)
{
if(LaserDeviceType==_LaserDeviceType_MainLaser1)
m_CurPowCheckData = m_LastPow1CheckData;
if(LaserDeviceType==_LaserDeviceType_MainLaser2)
m_CurPowCheckData = m_LastPow2CheckData;
if(LaserDeviceType==_LaserDeviceType_RedLaser)
m_CurPowCheckData = m_LastRedPowCheckData;
}
void CLaserPowCheckMgr::GetLastPowCheckPar(eLaserDeviceType LaserDeviceType,double &K,double &Po)
{
if(LaserDeviceType==_LaserDeviceType_MainLaser1)
{
K = m_LastPow1CheckData.m_EnergyDensityK;
Po = m_LastPow1CheckData.m_EnergyDensityPo;
}
if(LaserDeviceType==_LaserDeviceType_MainLaser2)
{
K = m_LastPow2CheckData.m_EnergyDensityK;
Po = m_LastPow2CheckData.m_EnergyDensityPo;
}
if(LaserDeviceType==_LaserDeviceType_RedLaser)
{
K = m_LastRedPowCheckData.m_EnergyDensityK;
Po = m_LastRedPowCheckData.m_EnergyDensityPo;
}
}
//创建当前的点检数据
void CLaserPowCheckMgr::CreatCurPowCheckData()
{
vector<CPowCheckPt>&PowCheckPtVec = m_CurPowCheckData.m_PowCheckPtVec;
m_CurPowCheckData.m_CheckType = m_CurPowCheckType;
m_CurPowCheckData.m_EnergyDensityK = 0;
m_CurPowCheckData.m_EnergyDensityPo = 0;
PowCheckPtVec.clear();
//获取绿光/红光的点检参数
CPowCheckPar &CheckPar = (*GetCurPowCheckPar());
//生成相同电流的检测点
if(CheckPar.m_StartCurr == CheckPar.m_EndCurr)
{
int Cnt = CheckPar.m_GapCurr;//间隔就是点的个数
for(int k=0;k<Cnt;k++)
{
CPowCheckPt PowCheckPt;
PowCheckPt.m_SetCurr = CheckPar.m_StartCurr;
PowCheckPtVec.push_back(PowCheckPt);
}
}
else
{
double CurCurrent = CheckPar.m_StartCurr;//当前测量电流值
while(CurCurrent <= CheckPar.m_EndCurr)
{
CPowCheckPt PowCheckPt;
PowCheckPt.m_SetCurr = CurCurrent;
PowCheckPtVec.push_back(PowCheckPt);
CurCurrent += CheckPar.m_GapCurr;
}
}
}
//记录功率点数据(一个点)
void CLaserPowCheckMgr::LaserPowSavePt(CPowCheckPt *pCheckPt)
{
}
void CLaserPowCheckMgr::UpdatePowCheckDataList(CListCtrl &List,bool bInsert,int SelIdx)
{
if(SelIdx<0)
{
UpdatePowCheckDataListExt(List,bInsert,m_CurPowCheckData);
}
else
{
int size = m_CurPowCheckRecordVec.size();
if(SelIdx>=0 && SelIdx<size)
{
UpdatePowCheckDataListExt(List,bInsert,m_CurPowCheckRecordVec[SelIdx]);
}
}
//记录当前选择的行
m_CurSelCheckRecordIdx = SelIdx;
}
void CLaserPowCheckMgr::UpdatePowCheckDataListExt(CListCtrl &List,bool bInsert,CPowCheckData &PowCheckData)
{
List.DeleteAllItems();
vector<CPowCheckPt>&PowCheckPtVec = PowCheckData.m_PowCheckPtVec;
int size = PowCheckPtVec.size();
for(int i=0;i<size;i++)
{
CPowCheckPt &CheckPt = PowCheckPtVec[i];
int idx = 0;
List.InsertItem(i," ");//插入一行
List.SetItemText(i,idx++,Int2CString(i+1));//序号
List.SetItemText(i,idx++,Db2CString(CheckPt.m_SetCurr));
List.SetItemText(i,idx++,Db2CString(CheckPt.m_LaserPathPow,2));
List.SetItemText(i,idx++,Db2CString(CheckPt.m_SurfacePow,2));
}
}
#endif
#if 1
//保存当前功率点检的数据
bool CLaserPowCheckMgr::SaveCurPowCheckData()
{
return true;
}
//将当前的点检结果用作recipe 计算依据
void CLaserPowCheckMgr::SaveCurPowCheckDataForRecipe()
{
CMsgBox MsgBox;
if(!m_CurPowCheckData.m_bCheckDataValid)
{
MsgBox.Show("需要先进行点检");
return;
}
//先读取原来的
vector<CPowCheckPt> PowCheckPtPowCheckPVec;
ReadLaserFixedCurrentPowFile(PowCheckPtPowCheckPVec);
vector<CPowCheckPt> &PowCheckPtVec = m_CurPowCheckData.m_PowCheckPtVec;
int PtCnt = PowCheckPtVec.size();
for(int k=0;k<PtCnt;k++)
{
CPowCheckPt &CheckPt = PowCheckPtVec[k];
bool bUpate = false;
int size = PowCheckPtPowCheckPVec.size();
for(int i=0;i<size;i++)
{
CPowCheckPt &ReadPowCheckPt = PowCheckPtPowCheckPVec[k];
}
}
}
//读取固定电流功率对应表
void CLaserPowCheckMgr::ReadLaserFixedCurrentPowFile(vector<CPowCheckPt> &PowCheckPtPowCheckPVec)
{
CFileMgr FileMgr;
CString FilePath;
FileMgr.GetFullFilePath(FilePath,FIX_POW_PARA_FILE);
vector<vector<CString>> StrVec;
FileMgr.ReadFileToStrVec(FilePath,StrVec);
int size = StrVec.size();
for(int k=0;k<size;k++)
{
if(StrVec[k].size() == 4)
{
CPowCheckPt PowCheckPt;
CString LaserTypeStr = (StrVec[k][0]);//激光的类型
if(LaserTypeStr == STR_LASER_1)
PowCheckPt.m_LaserType = _LaserDeviceType_MainLaser1;
if(LaserTypeStr == STR_LASER_2)
PowCheckPt.m_LaserType = _LaserDeviceType_MainLaser2;
PowCheckPt.m_LaserFre= CStringToDouble(StrVec[k][1]);//激光的频率
PowCheckPt.m_SetCurr= CStringToDouble(StrVec[k][2]);//激光的电流
PowCheckPt.m_SurfacePow= CStringToDouble(StrVec[k][3]);//激光的功率
PowCheckPtPowCheckPVec.push_back(PowCheckPt);
}
}
}
//检测数据序列化
void CLaserPowCheckMgr::SerializePowCheckData(CArchive& ar,CPowCheckData &PowCheckData)
{
}
//读取记录
void CLaserPowCheckMgr::ReadPowCheckData(int LaserType,CString Year,CString Month)
{
CWorkTime WorkTime;
if(Year=="")
Year = WorkTime.GetCurYear();
eLaserDeviceType PowCheckType = (eLaserDeviceType)LaserType;
m_CurExtLaserType = LaserType;
CString FilePath = GetPowCheckFilePath();
FilePath += Year;
FilePath += "\\";
//获取目录下所有pow 文件路径到DataFilePathVec
vector<CString> DataFilePathVec;
CFileMgr FileMgr;
FileMgr.GetChildFileOrDirName(false,FilePath,DataFilePathVec,".pow");
m_CurPowCheckRecordVec.clear();
int size = DataFilePathVec.size();
for(int k=0;k<size;k++)
{
CString DataFilePath = DataFilePathVec[k];
//只选择指定的月份
if(Month != SEL_ALL_STR)
{
//提取文件名
CString FileName = FileMgr.GetFileNameFromPath(DataFilePath,true);
CString FileNameMonth = FileName.Left(2);//获取月份
if(Month != FileNameMonth)
continue;
}
CFile file;
if(file.Open(DataFilePath,CFile::modeRead))
{
CArchive ar(&file,CArchive::load);
CPowCheckData CheckData;
SerializePowCheckData(ar,CheckData);
//只读取对应数据
if(CheckData.m_CheckType == PowCheckType)
{
m_CurPowCheckRecordVec.push_back(CheckData);
}
}
}
}
void CLaserPowCheckMgr::UpdatePowCheckRecordList(CListCtrl &List)
{
List.DeleteAllItems();
int size = m_CurPowCheckRecordVec.size();
for(int k=0;k<size;k++)
{
CPowCheckData &CheckData = m_CurPowCheckRecordVec[k];
int idx = 0;
List.InsertItem(k," ");//插入一行
List.SetItemText(k,idx++,Int2CString(k+1));//序号
List.SetItemText(k,idx++,CheckData.m_DateTime);
CString LaserFre("----");
if(!IsDbEqualZero(CheckData.m_LaserFre))
LaserFre = Db2CString(CheckData.m_LaserFre,1);
List.SetItemText(k,idx++,LaserFre);
List.SetItemText(k,idx++,Db2CString(CheckData.m_EnergyDensityK,4));//截距
List.SetItemText(k,idx++,Db2CString(CheckData.m_EnergyDensityPo,4));//斜率
}
}
//保存当前选择的记录到文件
void CLaserPowCheckMgr::SaveSelCheckRecordToFile()
{
int size = m_CurPowCheckRecordVec.size();
if(m_CurSelCheckRecordIdx<0 || m_CurSelCheckRecordIdx>=size)
{
return;
}
CPowCheckData &PowCheckData = m_CurPowCheckRecordVec[m_CurSelCheckRecordIdx];
double Po = PowCheckData.m_EnergyDensityPo;
double K = PowCheckData.m_EnergyDensityK;
TCHAR szFilters[]=("TXT 文件(*.txt)|*.txt");
CString FileName;
FileName = PowCheckData.m_DateTime;
CString s;
s.Format("Laser%ld_",m_CurExtLaserType);
FileName = s+ FileName;
CFileDialog dlg(FALSE,("txt"),FileName,OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT,szFilters);
if(dlg.DoModal()==IDOK)
{
ofstream ar(dlg.GetPathName());
ar<<"斜率K : "<<K<<" 截距Po : "<<Po<<'\n'<<'\n';
ar<<"电流";
ar<<TAB_STR;
ar<<"光路功率";
ar<<TAB_STR;
ar<<"有效功率";
if(gLaser->IsbPowRecordWriteCalPow())
{
ar<<TAB_STR;
ar<<"拟合功率";
ar<<TAB_STR;
ar<<"差值";
}
ar<<'\n';
vector<CPowCheckPt>&PowCheckPtVec = PowCheckData.m_PowCheckPtVec;
int size = PowCheckPtVec.size();
for(int i=0;i<size;i++)
{
CPowCheckPt &CheckPt = PowCheckPtVec[i];
//倒推计算功率值
double CalPower = gLaser->CalPowerByDensityPar(Po,K,CheckPt.m_SetCurr);
ar<<Db2CString(CheckPt.m_SetCurr);
ar<<TAB_STR;
ar<<Db2CString(CheckPt.m_LaserPathPow,2);
ar<<TAB_STR;
ar<<Db2CString(CheckPt.m_SurfacePow,2);
if(gLaser->IsbPowRecordWriteCalPow())
{
ar<<TAB_STR;
ar<<Db2CString(CalPower,2);
ar<<TAB_STR;
ar<<Db2CString(CalPower-CheckPt.m_SurfacePow,2);
}
ar<<'\n';
}
}
}
#endif