|
|
|
|
|
|
|
|
#pragma once
|
|
|
|
|
|
#ifndef AFX_EXT_CLASS
|
|
|
#define AFX_EXT_CLASS Q_DECL_IMPORT
|
|
|
#endif
|
|
|
#include "Triangulation.h"
|
|
|
#include <list>
|
|
|
|
|
|
namespace NVoronoi
|
|
|
{
|
|
|
|
|
|
class CVoronoi;
|
|
|
//单个Voronoi图元
|
|
|
class AFX_EXT_CLASS CVoronoiUnit
|
|
|
{
|
|
|
public:
|
|
|
CVoronoiUnit(CVoronoi* pParent);
|
|
|
|
|
|
/** @brief判断该图元是否闭合 */
|
|
|
bool IsClosed();
|
|
|
/** @brief 添加边界,返回1表示添加成功 */
|
|
|
bool AddBorder(CMyCurve& border);
|
|
|
/** @brief 添加断层,即由断层进行切割*/
|
|
|
bool ClipWithFlts(vector<CMyCurve*>* pFlts, vector<CRect8>* pRects = 0);
|
|
|
//获取多边形曲线
|
|
|
bool GetPolygon(CMyCurve& curve);
|
|
|
//清除不含中心点的多边形曲线
|
|
|
void EraseOtherPgns(void);
|
|
|
list<CMyCurve*>& GetOtherPgns(void);
|
|
|
int npt; //相关中心点序号
|
|
|
CPoint3D* ppt; //相关中心点指针
|
|
|
list<CPoint3D> m_nodPoints; //包含中心点的多边形
|
|
|
list<CMyCurve*> m_otherPgns; //不含中心点的多边形曲线
|
|
|
|
|
|
private:
|
|
|
/** @brief 找到中心点最小包围曲线,将点存入ptlist,如果存在其他不含井点的多边形,存入otherpgns*/
|
|
|
bool MinClosedCurve(CMyCurve& nodCur, CMyCurve& border,CPointList& ptlist, list<CMyCurve*>& otherPgns);
|
|
|
//父龟背图
|
|
|
CVoronoi* m_pParent;
|
|
|
};
|
|
|
|
|
|
//vorono多边形
|
|
|
class CVoronoiPolygon
|
|
|
{
|
|
|
public:
|
|
|
CVoronoiPolygon();
|
|
|
~CVoronoiPolygon();
|
|
|
int GetWell(void){return m_iWellPt; }
|
|
|
bool ContainWell(void) {return m_bWellInside;}
|
|
|
CMyCurve* GetPolygon(void) {return m_pPolygon; }
|
|
|
//判断两个多边形是否相邻
|
|
|
bool IsAdjacent(CVoronoiPolygon* pOther);
|
|
|
|
|
|
int m_iWellPt; //相关井点序号
|
|
|
bool m_bWellInside; // 是否包含井点
|
|
|
CMyCurve* m_pPolygon;
|
|
|
};
|
|
|
|
|
|
class AFX_EXT_CLASS CVoronoi : public CTriangulation
|
|
|
{
|
|
|
public:
|
|
|
CVoronoi(void);
|
|
|
virtual ~CVoronoi(void);
|
|
|
|
|
|
public:
|
|
|
/** @brief 设置相关的边界曲线:工区边界、断层等,pFlt为断层 pFltRects为断层对应矩形范围 */
|
|
|
int InitBoundary(CMyCurve* border = NULL, vector<CMyCurve*>* pFlts = 0, vector<CRect8>* pFltRects = 0);
|
|
|
/** @brief 生成Voronoi图,获得生成的曲线元素 */
|
|
|
int CreateVoronoiMap(TPtrList& curveVoronoiList);
|
|
|
|
|
|
/** @brief 读取2D散点数据 */
|
|
|
virtual int ReadPoints(vector<double>& X, vector<double>& Y);
|
|
|
virtual int ReadPoints(int num, double* X, double* Y);
|
|
|
|
|
|
//标记需要图元劈分的中心点(井点)序号
|
|
|
void SetMarkedPoints(vector<int>& markVec);
|
|
|
//拆分所有标记龟背图元Polygon到相邻图元Polygon中
|
|
|
void SplitMarkedUnits(void);
|
|
|
|
|
|
//由断层分割多个voronoi单元 分离出的部分由相邻单元瓜分,并更新 返回分割掉的原始vunit个数
|
|
|
int SplitVUnitWithFlts(void);
|
|
|
//由断层分割龟背单元pScrVUnit生成多个voronoi多边形存入dstVUnits,若断层未分割,则v unit边界生成多边形
|
|
|
bool SplitVUnitWithFlts(CVoronoiUnit* pScrVUnit,list<CVoronoiPolygon*>& dstVPgns,
|
|
|
vector<CMyCurve*>* pFlts);
|
|
|
|
|
|
//由每口井的最大区域ctCurs,序号与点序号一一对应重新分配m_vPolygons & m_VUnitList
|
|
|
//用于单晶储量运算
|
|
|
void ReassignWithConstraintRects( double width, double height );
|
|
|
|
|
|
|
|
|
//由给定的若干v多边形重新生成局部龟背图
|
|
|
|
|
|
|
|
|
/** @brief 清空类*/
|
|
|
virtual void ClearAll();
|
|
|
/** @brief 清空类成员*/
|
|
|
void ClearVoronoi();
|
|
|
//获取相邻多边形的组合边界 返回个数
|
|
|
int CreateUnitedBoundaries( vector<CMyCurve*>& pgns, vector<CMyCurve*>& borders );
|
|
|
////////////////////////////////////////////////////////////////////////
|
|
|
//图件生成之后的调用函数
|
|
|
//
|
|
|
//获取Voronoi单元曲线
|
|
|
int GetVUnitCurves(vector<CMyCurve*>& curs);
|
|
|
//获取V多边形曲线
|
|
|
int GetVPolygonCurves(vector<CMyCurve*>& curs);
|
|
|
//获取水井劈分线曲线
|
|
|
int GetMWSplitterCurves(vector<CMyCurve*>& curs);
|
|
|
|
|
|
/** @brief 获得生成的所有图元多边形,curveVoronoiList存放生成的曲线(CCurveEx)结果*/
|
|
|
int GetUnitCurve(TPtrList& curveVoronoiList);
|
|
|
/** @brief 获得生成的Voronoi图元多边形*/
|
|
|
int GetUnitCurve(int nIndex, CMyCurve& pCurve);
|
|
|
/** @brief 获得生成的Voronoi图的区域线个数*/
|
|
|
int GetUnitCount() { return (int)m_VUnitList.size(); }
|
|
|
/** @brief 返回voronoi单元*/
|
|
|
CVoronoiUnit* GetUnit(int index);
|
|
|
|
|
|
/** @brief 将Voronoi图写入文件*/
|
|
|
void Write(char* filename);
|
|
|
/** @brief 由边界条件生成Voronoi图*/
|
|
|
virtual int Create();
|
|
|
//查找位于断层内部的井点
|
|
|
void FindWellInFlts(void);
|
|
|
|
|
|
|
|
|
|
|
|
list<VSegment>& GetSplitterSegments(void);
|
|
|
|
|
|
private:
|
|
|
//拆分指定的voronoi图元到相邻图元中 idx为中心点序号
|
|
|
void SplitMarkedUnit(int wellIndex);
|
|
|
//dest合并subject相邻部分
|
|
|
void MergeAdjacentPart(CVoronoiPolygon* pSubjectUnit, CVoronoiPolygon* pDestUnit);
|
|
|
|
|
|
/** @brief 求取两结点中点*/
|
|
|
bool MidPoint(int npt1, int npt2,CPoint3D& mpt);
|
|
|
/** @brief 求取两结点中点*/
|
|
|
bool MidPoint(CPoint3D& pt1, CPoint3D& pt2,CPoint3D& mpt);
|
|
|
|
|
|
/** @brief 由边界选择数据点,删除边界外的数据点*/
|
|
|
void SelectPointsByBorder();
|
|
|
/** @brief 生成单个龟背图元*/
|
|
|
bool CreateVoronoiUnit(int npt, int nTri, CVoronoiUnit& vunit);
|
|
|
/** @brief 单方向追踪nTri相邻三角形中的Voronoi结点,addMode == 0为尾部添加点,1 为头部添加 */
|
|
|
virtual int DirectionalTrace(int& nTri, int& npt1, int& npt2, set<int>& FDTriNos,list<CPoint3D>& nodlist, int addMode = 0);
|
|
|
/**@brief 准备追踪,确定首点 m_LastPoint*/
|
|
|
int PrepareTrace(int nTri, int npt1, int bot0,int bot1,list<CPoint3D>& nodlist, int addMode);
|
|
|
/**@brief 单方向追踪到边界 进行结束处理*/
|
|
|
int EndDirectionalTrace(int nTri, int nTop, int nBottom,list<CPoint3D>& nodlist, int addMode);
|
|
|
/** @brief 追踪ntri三角形中的Voronoi结点,addMode == 0为尾部添加点,1 为头部添加 */
|
|
|
int GetVNodePoint(int nTri, int npt1, int npt2, int npt3,list<CPoint3D>& nodlist, int addMode );
|
|
|
/** @brief 曲线延伸到边界,求交点桩号*/
|
|
|
bool ExtendToBorder(list<CPoint3D>& nodlist, double& l0 , double extlen);
|
|
|
/** @brief 生成包络曲线 */
|
|
|
bool CreateEnvelopeCurve();
|
|
|
/** @brief生成外心点数组*/
|
|
|
bool CreateCirCenterPoints();
|
|
|
/* @brief 判断向量(x1,y1)(x3,y3)在向量(x1,y1)(x2,y2)的右侧还是左侧,右侧返回0,左侧返回1,线上返回2 **/
|
|
|
int VectorSide(double x1, double y1, double x2, double y2, double x3, double y3);
|
|
|
/**@brief 判断向量(pt0-pt2)在向量(pt0,pt1)的右侧还是左侧,右返回0 左返回1,线上返回2*/
|
|
|
int VectorSide(CPoint2D& pt0, CPoint2D& pt1,CPoint2D& pt2);
|
|
|
//生成井点序号与龟背图对应关系
|
|
|
void MapPointVoronoiUnit(void);
|
|
|
//生成井点序号与VPolygon的对应map
|
|
|
void MapPointVoronoiPolygon(void);
|
|
|
//点与多边形中的点是否有重合
|
|
|
bool IsAdjacent(CPoint3D& pt, list<CPoint3D>& polygon,CRect8* pRect );
|
|
|
|
|
|
//获取目标vector中所有点与polygon的邻接关系,将邻接点序号存入vecAdjacent中 返回邻接点个数
|
|
|
int GetAdjacentPoint(list<CPoint3D>& targetPts, list<CPoint3D>& polygon,set<CPoint3D*>& adjResult);
|
|
|
//将点添加到链表中
|
|
|
void AddPoint(list<CPoint3D>& nodlist, CPoint3D& pt, int addMode=0);
|
|
|
|
|
|
//判断坐标数组是否共线 如果是 返回true 否 返回false
|
|
|
bool IsCollinear(double prec);
|
|
|
|
|
|
//当井点共线时,或只有一个井点时,生成voronoi单元,
|
|
|
int CreateCollinearVoronoiMap();
|
|
|
//当井点共线时,生成voronoi单元,curveVoronoiList存放生成的曲线(CCurveEx)结果
|
|
|
int CreateCollinearVoronoiMap(TPtrList& curveVoronoiList);
|
|
|
//获取V多边形相邻的多边形,相同井点的多边形除外,bCompareAllPgns= true 与图中所有井点区域比较,false= 只与关联井点比较
|
|
|
int GetAdjacentPolygons(CVoronoiPolygon* pscrPgn, list<CVoronoiPolygon*>& dstpgns, bool bCompareAllPgns = false);
|
|
|
//查找相邻Voronoi单元井点
|
|
|
int GetNeighborWells(int iWell, vector<int>& neighborWells);
|
|
|
|
|
|
//获取相邻多边形的大边界
|
|
|
CMyCurve* CreateBoundary( list<CVoronoiPolygon*>& pgns );
|
|
|
//获取一组相邻多边形的大边界线段
|
|
|
void GetBoundarySegs( list<CVoronoiPolygon*>& scrPgns, list<VSegment>& dstSegs );
|
|
|
//获取一组相邻多边形的大边界线段
|
|
|
void GetBoundarySegs( vector<CMyCurve*>& scrPgns, list<VSegment>& dstSegs );
|
|
|
|
|
|
//连接两条有公共点的曲线 如公共点 返回0
|
|
|
CMyCurve* CreateBoundary(list<VSegment>& scrSegs);
|
|
|
|
|
|
//生成子VORONOI图
|
|
|
bool CreateSubVoronoi(list<CVoronoiPolygon*>& pgns, CMyCurve* pBoundary,CVoronoi& dstVrn,
|
|
|
std::map<int,int>& subwell2origwell,vector<CMyCurve*>* pFlts);
|
|
|
//由子voronoi图更新原图
|
|
|
void UpdateWithSubVoronoi(CVoronoi& dstVrn, std::map<int,int>& subwell2origwell);
|
|
|
//由vpolygon更新vunit
|
|
|
void UpdateVUnitWithVPolygon(CVoronoiUnit* pDstUnit, CVoronoiPolygon* pScrPolygon);
|
|
|
//清空vpolygons
|
|
|
void ClearVPolygons(void);
|
|
|
|
|
|
//根据坐标获取井点序号
|
|
|
int GetWellIndex(double x, double y);
|
|
|
//两线段减去相同部分,得到不同部分的线段个数,若无相交(或仅有一点相交) 返回0
|
|
|
int SubtractSegment(VSegment& v1, VSegment& v2, vector<VSegment>& dstSegs);
|
|
|
//设置在断层中的井点序号
|
|
|
set<int>& GetWellInFlt(void);
|
|
|
//获取矩形四边 etdLen 为每条边延伸长度,缺省-1
|
|
|
void GetRectLines(double x0, double y0, double w, double h,CMyCurve* lines, double etdLen = -0.1);
|
|
|
|
|
|
private:
|
|
|
/** @brief 三角形外心*/
|
|
|
vector<CPoint3D*> m_CCPoints;
|
|
|
/** @brief 所有龟背图元容器*/
|
|
|
vector<CVoronoiUnit*> m_VUnitList;
|
|
|
/** @brief voronoi单元被断层分割后的多边形*/
|
|
|
list<CVoronoiPolygon*> m_vPolygons;
|
|
|
typedef list<CVoronoiPolygon*>::iterator VPITER;
|
|
|
|
|
|
/** @brief Voronoi图边界线 */
|
|
|
CMyCurve m_Border;
|
|
|
/** @brief 网格包络线*/
|
|
|
CMyCurve m_OutlineCurve;
|
|
|
|
|
|
vector<CMyCurve*>* m_pFlts;
|
|
|
vector<CRect8> m_fltRects;
|
|
|
|
|
|
//标记中心点劈分///////////////////////
|
|
|
CPoint3D m_LastPoint;
|
|
|
set<int> m_markedPoints; //标记的井点序号
|
|
|
map<int, int> m_mapPtVUnit; //点序号与voronoi unit序号的map
|
|
|
map<int,CVoronoiPolygon*> m_mapPtVPng; //点序号与对应VPolygon指针的map
|
|
|
set<int> m_wellinflt; //位于断层内部的井点序号 用于断层分割
|
|
|
CSize8* m_pConstrainSize; //用于分割的矩形长宽
|
|
|
list<VSegment> m_splitterSegments; //分割水井(标记井)的线段
|
|
|
};
|
|
|
|
|
|
}; //NTriangle
|