双线箭头

#ifndef __GV00003_H__
#define __GV00003_H__#include "GVGeometry.h"
#include "Bezier.h"class GV00003 : public GVGeometry
{
public:GV00003();~GV00003();int getControlPointCount();void getControlPoints(std::vector<GVCoord>& vtxBuffer);GVCoord getControlPoint(int idx);void setControlPointsEx(std::vector<GVCoord>& vtxBuffer);void setControlPoints(std::vector<GVCoord>& vtxBuffer);void setControlPoint(int idx, const GVCoord& vtx);bool toVertice(std::vector<GVCoord>& vtxBuffer, std::vector<int>* vtxBuffer2);double brokenLineDistance(int start, int end) const;private:std::vector<GVCoord> _controlPoints;double scale[4];
};#endif //__GV00003_H__
#pragma once#include "GV00003.h"#define Distance_3(coord1, coord2) (sqrt((coord1.lat - coord2.lat) * (coord1.lat - coord2.lat) + (coord1.lon - coord2.lon) * (coord1.lon - coord2.lon)))GV00003::GV00003()
{scale[0] = 0.12;scale[1] = 0.15;scale[2] = 0.4;scale[3] = 0.3;
}GV00003::~GV00003()
{}int GV00003::getControlPointCount()
{std::vector<GVCoord> controlPoints;getControlPoints(controlPoints);return controlPoints.size();
}void GV00003::getControlPoints(std::vector<GVCoord>& vtxBuffer)
{if(_controlPoints.size() <= 0)return ;vtxBuffer = _controlPoints;
}GVCoord GV00003::getControlPoint(int idx)
{if(idx >= 0 && idx < _controlPoints.size())return _controlPoints[idx];return GVCoord();
}void GV00003::setControlPointsEx(std::vector<GVCoord> &vtxBuffer)
{_controlPoints = vtxBuffer;
}void GV00003::setControlPoints(std::vector<GVCoord>& vtxBuffer)
{_controlPoints.clear();_controlPoints = vtxBuffer;if(_controlPoints.size() > 2){GVCoord arrowHead = _controlPoints[_controlPoints.size()-1];GVCoord arrowTailLeft = _controlPoints[0];GVCoord arrowTailRight = _controlPoints[1];double brockenLineLength = Distance_3(GVCoord((arrowTailLeft.lon + arrowTailRight.lon)/2, (arrowTailLeft.lat + arrowTailRight.lat)/2, 0), arrowHead);if(_controlPoints.size() > 3){brockenLineLength = Distance_3(_controlPoints[_controlPoints.size()-2], _controlPoints[_controlPoints.size()-1]);}GVCoord penultimatePointOnAxis;penultimatePointOnAxis.lon = (arrowTailLeft.lon + arrowTailRight.lon)/2;penultimatePointOnAxis.lat = (arrowTailLeft.lat + arrowTailRight.lat)/2;if(_controlPoints.size() > 3){penultimatePointOnAxis = _controlPoints[_controlPoints.size()-2];}double arrowTopLength = 2 * brockenLineLength * scale[0];double arrowNeckWidthHalf = arrowTopLength * scale[1];double arrowEarWidthHalf = arrowTopLength * scale[2];double arrowEarthLength = arrowTopLength * scale[3];GVCoord arrowNeckRight;GVCoord arrowEarLeft;GVCoord arrowEarMiddle;osg::Vec3d vecTop = osg::Vec3d(arrowHead.lon - penultimatePointOnAxis.lon, arrowHead.lat - penultimatePointOnAxis.lat, 0);vecTop.normalize();arrowEarMiddle.lon = arrowHead.lon - arrowTopLength * vecTop.x();arrowEarMiddle.lat = arrowHead.lat - arrowTopLength * vecTop.y();osg::Vec3d vecTopVertical = osg::Vec3d(-vecTop.y(), vecTop.x(), 0);arrowEarLeft.lon = arrowEarMiddle.lon + arrowEarWidthHalf * vecTopVertical.x();arrowEarLeft.lat = arrowEarMiddle.lat + arrowEarWidthHalf * vecTopVertical.y();GVCoord arrowNeckMiddle;arrowNeckMiddle.lon = arrowHead.lon - (arrowTopLength - arrowEarthLength) * vecTop.x();arrowNeckMiddle.lat = arrowHead.lat - (arrowTopLength - arrowEarthLength) * vecTop.y();arrowNeckRight.lon = arrowNeckMiddle.lon - arrowNeckWidthHalf * vecTopVertical.x();arrowNeckRight.lat = arrowNeckMiddle.lat - arrowNeckWidthHalf * vecTopVertical.y();_controlPoints.insert(_controlPoints.begin(), arrowEarMiddle);_controlPoints.insert(_controlPoints.begin(), arrowEarLeft);_controlPoints.insert(_controlPoints.begin(), arrowNeckRight);}
}void GV00003::setControlPoint(int idx, const GVCoord& vtx)
{int cpSize = _controlPoints.size();if(idx < 0 || idx >= cpSize)return ;GVCoord arrowHead = _controlPoints[_controlPoints.size()-1];GVCoord arrowTailLeft = _controlPoints[3];GVCoord arrowTailRight = _controlPoints[4];double brockenLineLength = Distance_3(GVCoord((arrowTailLeft.lon + arrowTailRight.lon)/2, (arrowTailLeft.lat + arrowTailRight.lat)/2, 0), arrowHead);if(_controlPoints.size() > 6){brockenLineLength = Distance_3(_controlPoints[_controlPoints.size()-2], _controlPoints[_controlPoints.size()-1]);}GVCoord penultimatePointOnAxis;penultimatePointOnAxis.lon = (arrowTailLeft.lon + arrowTailRight.lon)/2;penultimatePointOnAxis.lat = (arrowTailLeft.lat + arrowTailRight.lat)/2;if(_controlPoints.size() > 6){penultimatePointOnAxis = _controlPoints[_controlPoints.size()-2];}double arrowTopLength = 2 * brockenLineLength * scale[0];double arrowNeckWidthHalf = arrowTopLength * scale[1];double arrowEarWidthHalf = arrowTopLength * scale[2];double arrowEarthLength = arrowTopLength * scale[3];osg::Vec3d vecTop = osg::Vec3d(arrowHead.lon - penultimatePointOnAxis.lon, arrowHead.lat - penultimatePointOnAxis.lat, 0);vecTop.normalize();osg::Vec3d vecTopVertical = osg::Vec3d(-vecTop.y(), vecTop.x(), 0);if(idx == 0){GVCoord arrowNeckMiddle;arrowNeckMiddle.lon = arrowHead.lon - (arrowTopLength - arrowEarthLength) * vecTop.x();arrowNeckMiddle.lat = arrowHead.lat - (arrowTopLength - arrowEarthLength) * vecTop.y();osg::Vec3d vec = osg::Vec3d(vtx.lon - arrowNeckMiddle.lon, vtx.lat - arrowNeckMiddle.lat, 0);double projectLength = vec * vecTopVertical;if(projectLength >= 0){projectLength = 0.3 * arrowNeckWidthHalf;}else{if(abs(projectLength) > 0.7 * arrowEarWidthHalf){projectLength = 0.7 * arrowEarWidthHalf;}else{projectLength = abs(projectLength);}}_controlPoints[0].lon = arrowNeckMiddle.lon - projectLength * vecTopVertical.x();_controlPoints[0].lat = arrowNeckMiddle.lat - projectLength * vecTopVertical.y();scale[1] = projectLength / arrowTopLength;}else if(idx == 1){double distanceTop = Distance_3(_controlPoints[1], arrowHead);osg::Vec3d vec = osg::Vec3d(arrowHead.lon - vtx.lon, arrowHead.lat - vtx.lat, 0);vec.normalize();_controlPoints[1].lon = arrowHead.lon - distanceTop * vec.x();_controlPoints[1].lat = arrowHead.lat - distanceTop * vec.y();vec.x() = distanceTop * vec.x();vec.y() = distanceTop * vec.y();arrowEarWidthHalf = abs(vec * vecTopVertical);_controlPoints[2].lon = _controlPoints[1].lon - arrowEarWidthHalf * vecTopVertical.x();_controlPoints[2].lat = _controlPoints[1].lat - arrowEarWidthHalf * vecTopVertical.y();double arrowTopLengthNew = Distance_3(_controlPoints[2], arrowHead);scale[0] = (arrowTopLengthNew / 2.0) / brockenLineLength;scale[1] = arrowNeckWidthHalf / arrowTopLengthNew;scale[2] = arrowEarWidthHalf / arrowTopLengthNew;scale[3] = (arrowEarthLength - (arrowTopLength - arrowTopLengthNew)) / arrowTopLengthNew;arrowTopLength = arrowTopLengthNew;}else if(idx == 2){osg::Vec3d vec = osg::Vec3d(arrowHead.lon - vtx.lon, arrowHead.lat - vtx.lat, 0);double projectLength = vec * vecTop;static double maxLength = arrowTopLength;if(projectLength > 0 && projectLength < maxLength){_controlPoints[2].lon = arrowHead.lon - projectLength * vecTop.x();_controlPoints[2].lat = arrowHead.lat - projectLength * vecTop.y();arrowTopLength = projectLength;arrowNeckWidthHalf = arrowTopLength * scale[1];arrowEarWidthHalf = arrowTopLength * scale[2];arrowEarthLength = arrowTopLength * scale[3];scale[0] = (arrowTopLength / 2.0) / brockenLineLength;_controlPoints[1].lon = _controlPoints[2].lon + arrowEarWidthHalf * vecTopVertical.x();_controlPoints[1].lat = _controlPoints[2].lat + arrowEarWidthHalf * vecTopVertical.y();GVCoord arrowNeckMiddle;arrowNeckMiddle.lon = _controlPoints[2].lon + arrowEarthLength * vecTop.x();arrowNeckMiddle.lat = _controlPoints[2].lat + arrowEarthLength * vecTop.y();_controlPoints[0].lon = arrowNeckMiddle.lon - arrowNeckWidthHalf * vecTopVertical.x();_controlPoints[0].lat = arrowNeckMiddle.lat - arrowNeckWidthHalf * vecTopVertical.y();}}else{_controlPoints[idx] = vtx;GVCoord arrowHead = _controlPoints[_controlPoints.size()-1];GVCoord arrowTailLeft = _controlPoints[3];GVCoord arrowTailRight = _controlPoints[4];double brockenLineLength = Distance_3(GVCoord((arrowTailLeft.lon + arrowTailRight.lon)/2, (arrowTailLeft.lat + arrowTailRight.lat)/2, 0), arrowHead);if(_controlPoints.size() > 6){brockenLineLength = Distance_3(_controlPoints[_controlPoints.size()-2], _controlPoints[_controlPoints.size()-1]);}GVCoord penultimatePointOnAxis;penultimatePointOnAxis.lon = (arrowTailLeft.lon + arrowTailRight.lon)/2;penultimatePointOnAxis.lat = (arrowTailLeft.lat + arrowTailRight.lat)/2;if(_controlPoints.size() > 6){penultimatePointOnAxis = _controlPoints[_controlPoints.size()-2];}double arrowTopLength = 2 * brockenLineLength * scale[0];double arrowNeckWidthHalf = arrowTopLength * scale[1];double arrowEarWidthHalf = arrowTopLength * scale[2];double arrowEarthLength = arrowTopLength * scale[3];GVCoord arrowNeckRight;GVCoord arrowEarLeft;GVCoord arrowEarMiddle;osg::Vec3d vecTop = osg::Vec3d(arrowHead.lon - penultimatePointOnAxis.lon, arrowHead.lat - penultimatePointOnAxis.lat, 0);vecTop.normalize();arrowEarMiddle.lon = arrowHead.lon - arrowTopLength * vecTop.x();arrowEarMiddle.lat = arrowHead.lat - arrowTopLength * vecTop.y();osg::Vec3d vecTopVertical = osg::Vec3d(-vecTop.y(), vecTop.x(), 0);arrowEarLeft.lon = arrowEarMiddle.lon + arrowEarWidthHalf * vecTopVertical.x();arrowEarLeft.lat = arrowEarMiddle.lat + arrowEarWidthHalf * vecTopVertical.y();GVCoord arrowNeckMiddle;arrowNeckMiddle.lon = arrowHead.lon - (arrowTopLength - arrowEarthLength) * vecTop.x();arrowNeckMiddle.lat = arrowHead.lat - (arrowTopLength - arrowEarthLength) * vecTop.y();arrowNeckRight.lon = arrowNeckMiddle.lon - arrowNeckWidthHalf * vecTopVertical.x();arrowNeckRight.lat = arrowNeckMiddle.lat - arrowNeckWidthHalf * vecTopVertical.y();_controlPoints[0] = arrowNeckRight;_controlPoints[1] = arrowEarLeft;_controlPoints[2] = arrowEarMiddle;}
}bool GV00003::toVertice(std::vector<GVCoord>& vtxBuffer, std::vector<int>* vtxBuffer2)
{if(_controlPoints.size() < 6)return false;GVCoord arrowHead = _controlPoints[_controlPoints.size()-1];GVCoord arrowTailLeft = _controlPoints[3];GVCoord arrowTailRight = _controlPoints[4];double brockenLineLength = Distance_3(GVCoord((arrowTailLeft.lon + arrowTailRight.lon)/2, (arrowTailLeft.lat + arrowTailRight.lat)/2, 0), arrowHead);if(_controlPoints.size() > 6){brockenLineLength = Distance_3(_controlPoints[_controlPoints.size()-2], _controlPoints[_controlPoints.size()-1]);}GVCoord penultimatePointOnAxis;penultimatePointOnAxis.lon = (arrowTailLeft.lon + arrowTailRight.lon)/2;penultimatePointOnAxis.lat = (arrowTailLeft.lat + arrowTailRight.lat)/2;if(_controlPoints.size() > 6){penultimatePointOnAxis = _controlPoints[_controlPoints.size()-2];}double arrowTopLength = 2 * brockenLineLength * scale[0];double arrowNeckWidthHalf = arrowTopLength * scale[1];double arrowEarWidthHalf = arrowTopLength * scale[2];double arrowEarthLength = arrowTopLength * scale[3];GVCoord arrowNeckRight, arrowNeckLeft;GVCoord arrowEarRight, arrowEarLeft;osg::Vec3d vecTop = osg::Vec3d(arrowHead.lon - penultimatePointOnAxis.lon, arrowHead.lat - penultimatePointOnAxis.lat, 0);vecTop.normalize();osg::Vec3d vecTopVertical = osg::Vec3d(-vecTop.y(), vecTop.x(), 0);arrowEarLeft = _controlPoints[1];arrowEarRight.lon = arrowEarLeft.lon - 2 * arrowEarWidthHalf * vecTopVertical.x();arrowEarRight.lat = arrowEarLeft.lat - 2 * arrowEarWidthHalf * vecTopVertical.y();arrowNeckRight = _controlPoints[0];arrowNeckLeft.lon = arrowNeckRight.lon + 2 * arrowNeckWidthHalf * vecTopVertical.x();arrowNeckLeft.lat = arrowNeckRight.lat + 2 * arrowNeckWidthHalf * vecTopVertical.y();double arrowTailWidth = Distance_3(arrowTailLeft, arrowTailRight);GVCoord arrowTailMiddle;arrowTailMiddle.lon = (arrowTailLeft.lon + arrowTailRight.lon)/2;arrowTailMiddle.lat = (arrowTailLeft.lat + arrowTailRight.lat)/2;double offset = arrowTailWidth/2.0 - arrowNeckWidthHalf;Bezier bezier;if(_controlPoints.size() == 6){osg::Vec3d vecTail = osg::Vec3d(arrowTailLeft.lon - arrowTailRight.lon, arrowTailLeft.lat - arrowTailRight.lat, 0);vecTail.normalize();GVCoord topTailMiddle;topTailMiddle.lon = (arrowHead.lon + arrowTailMiddle.lon) / 2;topTailMiddle.lat = (arrowHead.lat + arrowTailMiddle.lat) / 2;GVCoord arrowBodyLeft, arrowBodyRight;arrowBodyLeft.lon = topTailMiddle.lon + (arrowNeckWidthHalf + 0.25 * offset) * vecTail.x();arrowBodyLeft.lat = topTailMiddle.lat + (arrowNeckWidthHalf + 0.25 * offset) * vecTail.y();arrowBodyRight.lon = topTailMiddle.lon - (arrowNeckWidthHalf + 0.25 * offset) * vecTail.x();arrowBodyRight.lat = topTailMiddle.lat - (arrowNeckWidthHalf + 0.25 * offset) * vecTail.y();std::vector<GVCoord> keyPoints;std::vector<GVCoord> bezierPoints;double t = (_controlPoints[3].lon - _controlPoints[5].lon) * (_controlPoints[4].lat - _controlPoints[5].lat) - (_controlPoints[4].lon - _controlPoints[5].lon) * (_controlPoints[3].lat - _controlPoints[5].lat);keyPoints.clear();bezierPoints.clear();if(t < 0){keyPoints.push_back(arrowTailRight);keyPoints.push_back(arrowBodyRight);}else{keyPoints.push_back(arrowTailLeft);keyPoints.push_back(arrowBodyLeft);}keyPoints.push_back(arrowNeckLeft);bezier.getBezier(keyPoints, &bezierPoints);for(int i=0; i<bezierPoints.size(); i++)vtxBuffer.push_back(bezierPoints[i]);double t1 = 0.0;for(; t1<=1; t1+=0.02){double x = (1-t1) * bezierPoints[bezierPoints.size()-1].lon + t1 * arrowEarLeft.lon;double y = (1-t1) * bezierPoints[bezierPoints.size()-1].lat + t1 * arrowEarLeft.lat;vtxBuffer.push_back(GVCoord(x, y, 0.0));}vtxBuffer.push_back(arrowEarLeft);t1 = 0.0;for(; t1<=1; t1+=0.02){double x = (1-t1) * arrowEarLeft.lon + t1 * arrowHead.lon;double y = (1-t1) * arrowEarLeft.lat + t1 * arrowHead.lat;vtxBuffer.push_back(GVCoord(x, y, 0.0));}vtxBuffer.push_back(arrowHead);t1 = 0.0;for(; t1<=1; t1+=0.02){double x = (1-t1) * arrowHead.lon + t1 * arrowEarRight.lon;double y = (1-t1) * arrowHead.lat + t1 * arrowEarRight.lat;vtxBuffer.push_back(GVCoord(x, y, 0.0));}vtxBuffer.push_back(arrowEarRight);keyPoints.clear();bezierPoints.clear();keyPoints.push_back(arrowNeckRight);if(t < 0){keyPoints.push_back(arrowBodyLeft);keyPoints.push_back(arrowTailLeft);}else{keyPoints.push_back(arrowBodyRight);keyPoints.push_back(arrowTailRight);}bezier.getBezier(keyPoints, &bezierPoints);t1 = 0.0;for(; t1<=1; t1+=0.02){double x = (1-t1) * arrowEarRight.lon + t1 * bezierPoints[0].lon;double y = (1-t1) * arrowEarRight.lat + t1 * bezierPoints[0].lat;vtxBuffer.push_back(GVCoord(x, y, 0.0));}for(int i=0; i<bezierPoints.size(); i++)vtxBuffer.push_back(bezierPoints[i]);vtxBuffer2->push_back(vtxBuffer.size());}else{double axisBrokenLineLength = Distance_3(arrowTailMiddle, _controlPoints[5]);axisBrokenLineLength += brokenLineDistance(5, _controlPoints.size()-1);double currentTopBrokenLineLength = 0;std::vector<GVCoord> keyPointsLeft, keyPointsRight;std::vector<GVCoord> bezierPointsLeft, bezierPointsRight;keyPointsLeft.clear();keyPointsRight.clear();keyPointsLeft.push_back(arrowNeckLeft);keyPointsRight.push_back(arrowNeckRight);for (int i=_controlPoints.size()-2; i>4; i--){currentTopBrokenLineLength = brokenLineDistance(i, _controlPoints.size()-1);double rate = pow(currentTopBrokenLineLength / axisBrokenLineLength, 2);osg::Vec3d vecNear = osg::Vec3d(_controlPoints[i+1].lon - _controlPoints[i].lon, _controlPoints[i+1].lat - _controlPoints[i].lat, 0);vecNear.normalize();osg::Vec3d vecNearVertical = osg::Vec3d(-vecNear.y(), vecNear.x(), 0);GVCoord bodyLeft, bodyRight;bodyLeft.lon = _controlPoints[i].lon + (arrowNeckWidthHalf + rate * offset) * vecNearVertical.x();bodyLeft.lat = _controlPoints[i].lat + (arrowNeckWidthHalf + rate * offset) * vecNearVertical.y();bodyRight.lon = _controlPoints[i].lon - (arrowNeckWidthHalf + rate * offset) * vecNearVertical.x();bodyRight.lat = _controlPoints[i].lat - (arrowNeckWidthHalf + rate * offset) * vecNearVertical.y();keyPointsLeft.push_back(bodyLeft);keyPointsRight.push_back(bodyRight);}keyPointsLeft.push_back(arrowTailLeft);keyPointsRight.push_back(arrowTailRight);double t = (_controlPoints[3].lon - _controlPoints[5].lon) * (_controlPoints[4].lat - _controlPoints[5].lat) - (_controlPoints[4].lon - _controlPoints[5].lon) * (_controlPoints[3].lat - _controlPoints[5].lat);if(t < 0){keyPointsLeft[keyPointsLeft.size()-1] = arrowTailRight;keyPointsRight[keyPointsRight.size()-1] = arrowTailLeft;}bezier.getBezier(keyPointsLeft, &bezierPointsLeft);for (int i=bezierPointsLeft.size()-1; i>=0; i--)vtxBuffer.push_back(bezierPointsLeft[i]);double t1 = 0.0;for (; t1<=1; t1+=0.02){double x = (1-t1) * bezierPointsLeft[0].lon + t1 * arrowEarLeft.lon;double y = (1-t1) * bezierPointsLeft[0].lat + t1 * arrowEarLeft.lat;vtxBuffer.push_back(GVCoord(x, y, 0.0));}vtxBuffer.push_back(arrowEarLeft);t1 = 0;for (; t1<=1; t1+=0.02){double x = (1-t1) * arrowEarLeft.lon + t1 * arrowHead.lon;double y = (1-t1) * arrowEarLeft.lat + t1 * arrowHead.lat;vtxBuffer.push_back(GVCoord(x, y, 0.0));}vtxBuffer.push_back(arrowHead);t1 = 0;for (; t1<=1; t1+=0.02){double x = (1-t1) * arrowHead.lon + t1 * arrowEarRight.lon;double y = (1-t1) * arrowHead.lat + t1 * arrowEarRight.lat;vtxBuffer.push_back(GVCoord(x, y, 0.0));}vtxBuffer.push_back(arrowEarRight);bezier.getBezier(keyPointsRight, &bezierPointsRight);t1 = 0;for (; t1<=1; t1+=0.02){double x = (1-t1) * arrowEarRight.lon + t1 * bezierPointsRight[0].lon;double y = (1-t1) * arrowEarRight.lat + t1 * bezierPointsRight[0].lat;vtxBuffer.push_back(GVCoord(x, y, 0.0));}for(int i=0; i<bezierPointsRight.size(); i++)vtxBuffer.push_back(bezierPointsRight[i]);vtxBuffer2->push_back(vtxBuffer.size());}return true;
}double GV00003::brokenLineDistance(int start, int end) const
{double axisBrokenlineLength = 0;for(int i=start; i<end; i++){axisBrokenlineLength += Distance_3(_controlPoints[i], _controlPoints[i+1]);}return axisBrokenlineLength;
}

腰子

#ifndef __GV00004_H__
#define __GV00004_H__#include "GVGeometry.h"
#include "KidNey.h"class GV00004 : public GVGeometry
{
public:GV00004();~GV00004();int getControlPointCount();void getControlPoints(std::vector<GVCoord>& vtxBuffer);GVCoord getControlPoint(int idx);void setControlPointsEx(std::vector<GVCoord>& vtxBuffer);void setControlPoints(std::vector<GVCoord>& vtxBuffer);void setControlPoint(int idx, const GVCoord& vtx);bool toVertice(std::vector<GVCoord>& vtxBuffer, std::vector<int>* vtxBuffer2);private:std::vector<GVCoord> _controlPoints;std::vector<double> _s;KidNey kidney;
};#endif //__GV00004_H__
#pragma once#include "GV00004.h"GV00004::GV00004()
{}GV00004::~GV00004()
{}int GV00004::getControlPointCount()
{return _controlPoints.size();
}void GV00004::getControlPoints(std::vector<GVCoord>& vtxBuffer)
{if(_controlPoints.size() <= 0)return ;vtxBuffer = _controlPoints;
}GVCoord GV00004::getControlPoint(int idx)
{if(idx >= 0 && idx < _controlPoints.size())return _controlPoints[idx];return GVCoord();
}void GV00004::setControlPointsEx(std::vector<GVCoord> &vtxBuffer)
{_controlPoints = vtxBuffer;
}void GV00004::setControlPoints(std::vector<GVCoord>& vtxBuffer)
{if (vtxBuffer.size() == 1){return;}if(vtxBuffer.size() > 1){kidney.setKidNeyConreolPoints(_controlPoints, vtxBuffer);kidney.getKidNeyScales(_s);}
}void GV00004::setControlPoint(int idx, const GVCoord& vtx)
{int cpSize = _controlPoints.size();if(idx < 0 || idx >= cpSize)return ;kidney.setKidNeyConreolPoint(_controlPoints, idx, vtx, _s);}bool GV00004::toVertice(std::vector<GVCoord>& vtxBuffer, std::vector<int>* vtxBuffer2)
{if(_controlPoints.size() >= 12){kidney.drawKidNey(_controlPoints);vtxBuffer = kidney.tmpBuffer;vtxBuffer2->push_back(kidney.tmpBuffer2[0]);}return true;
}

单线箭头

#ifndef __GV00005_H__
#define __GV00005_H__#include "GVGeometry.h"
#include "Bezier.h"class GV00005 : public GVGeometry
{
public:GV00005();~GV00005();int getControlPointCount();void getControlPoints(std::vector<GVCoord>& vtxBuffer);GVCoord getControlPoint(int idx);void setControlPointsEx(std::vector<GVCoord>& vtxBuffer);void setControlPoints(std::vector<GVCoord>& vtxBuffer);void setControlPoint(int idx, const GVCoord& vtx);bool toVertice(std::vector<GVCoord>& vtxBuffer, std::vector<int>* vtxBuffer2);private:std::vector<GVCoord> _controlPoints;
};#endif //__GV00005_H__
#pragma once#include "GV00005.h"static double getLen(GVCoord coord0, GVCoord coord1)
{return sqrt(pow(coord1.lon - coord0.lon, 2) + pow(coord1.lat - coord0.lat, 2));
}static double cal_angle(const GVCoord &start_point, const GVCoord &end_point)
{double PI = osg::PI;double x01 = end_point.lon - start_point.lon;double y01 = end_point.lat - start_point.lat;double alpha;if(fabs(x01) <= 0.00001){alpha = PI / 2.0;if(y01 < 0)alpha = -alpha + PI * 2.0;}elsealpha = atan(y01 / x01);if(x01 < 0)alpha += PI;else if(y01 < 0)alpha += 2.0 * PI;return alpha;
}GV00005::GV00005()
{}GV00005::~GV00005()
{}int GV00005::getControlPointCount()
{std::vector<GVCoord> controlPoints;getControlPoints(controlPoints);return controlPoints.size();
}void GV00005::getControlPoints(std::vector<GVCoord>& vtxBuffer)
{if(_controlPoints.size() <= 0)return ;vtxBuffer = _controlPoints;
}GVCoord GV00005::getControlPoint(int idx)
{if(idx >= 0 && idx < _controlPoints.size())return _controlPoints[idx];return GVCoord();
}void GV00005::setControlPointsEx(std::vector<GVCoord> &vtxBuffer)
{_controlPoints = vtxBuffer;
}void GV00005::setControlPoints(std::vector<GVCoord>& vtxBuffer)
{_controlPoints = vtxBuffer;
}void GV00005::setControlPoint(int idx, const GVCoord& vtx)
{int cpSize = _controlPoints.size();if(idx < 0 || idx >= cpSize)return ;_controlPoints[idx] = vtx;}bool GV00005::toVertice(std::vector<GVCoord>& vtxBuffer, std::vector<int>* vtxBuffer2)
{if(_controlPoints.size() < 2)return true;Bezier bezier;std::vector<GVCoord> bezierPoints;bezier.getBezier(_controlPoints, &bezierPoints);vtxBuffer = bezierPoints;vtxBuffer2->push_back(bezierPoints.size());double length = 0.0;for(int i=0; i<bezierPoints.size()-1; i++){length += sqrt((bezierPoints[i].lon - bezierPoints[i+1].lon) * (bezierPoints[i].lon - bezierPoints[i+1].lon)+ (bezierPoints[i].lat - bezierPoints[i+1].lat) * (bezierPoints[i].lat - bezierPoints[i+1].lat));}double r = length / 50.0;int position = bezierPoints.size();for(int i=bezierPoints.size()-1; i>0; i--){if (getLen(bezierPoints[i], bezierPoints[bezierPoints.size()-1]) > r){position = i;break;}}double angle1 = cal_angle(bezierPoints[position], _controlPoints[_controlPoints.size()-1]);GVCoord arrowP0, arrowP1, arrowP2;arrowP0.lon = bezierPoints[position].lon + r * 0.2 * cos(angle1 + osg::PI/2);arrowP0.lat = bezierPoints[position].lat + r * 0.2 * sin(angle1 + osg::PI/2);arrowP1.lon = bezierPoints[position].lon + r * 0.2 * cos(angle1 - osg::PI/2);arrowP1.lat = bezierPoints[position].lat + r * 0.2 * sin(angle1 - osg::PI/2);arrowP2 = _controlPoints[_controlPoints.size()-1];vtxBuffer.push_back(arrowP0);vtxBuffer.push_back(arrowP1);vtxBuffer.push_back(arrowP2);vtxBuffer.push_back(arrowP0);vtxBuffer2->push_back(4);return true;
}

车辆行进

#ifndef __GV00006_H__
#define __GV00006_H__#include "GVGeometry.h"
#include "Bezier.h"
#include "ConfigControlPoints.h"class GV00006 : public GVGeometry
{
public:GV00006();~GV00006();int getControlPointCount();void getControlPoints(std::vector<GVCoord>& vtxBuffer);GVCoord getControlPoint(int idx);void setControlPointsEx(std::vector<GVCoord>& vtxBuffer);void setControlPoints(std::vector<GVCoord>& vtxBuffer);void setControlPoint(int idx, const GVCoord& vtx);bool toVertice(std::vector<GVCoord>& vtxBuffer, std::vector<int>* vtxBuffer2);private:std::vector<GVCoord> _controlPoints;double s0;Bezier bezier;ConfigControlPoints cfcp;
};#endif //__GV00006_H__
#pragma once#include "GV00006.h"static double getLen(GVCoord coord0, GVCoord coord1)
{return sqrt(pow(coord1.lon - coord0.lon, 2) + pow(coord1.lat - coord0.lat, 2));
}static double cal_angle(const GVCoord &start_point, const GVCoord &end_point)
{double PI = osg::PI;double x01 = end_point.lon - start_point.lon;double y01 = end_point.lat - start_point.lat;double alpha;if(fabs(x01) <= 0.00001){alpha = PI / 2.0;if(y01 < 0)alpha = -alpha + PI * 2.0;}elsealpha = atan(y01 / x01);if(x01 < 0)alpha += PI;else if(y01 < 0)alpha += 2.0 * PI;return alpha;
}GV00006::GV00006()
{s0 = 0.5;
}GV00006::~GV00006()
{}int GV00006::getControlPointCount()
{std::vector<GVCoord> controlPoints;getControlPoints(controlPoints);return controlPoints.size();
}void GV00006::getControlPoints(std::vector<GVCoord>& vtxBuffer)
{if(_controlPoints.size() <= 0)return ;vtxBuffer = _controlPoints;
}GVCoord GV00006::getControlPoint(int idx)
{if(idx >= 0 && idx < _controlPoints.size())return _controlPoints[idx];return GVCoord();
}void GV00006::setControlPointsEx(std::vector<GVCoord> &vtxBuffer)
{cfcp.configControlPoints(vtxBuffer);_controlPoints = vtxBuffer;
}void GV00006::setControlPoints(std::vector<GVCoord>& vtxBuffer)
{cfcp.configControlPoints(vtxBuffer);if (vtxBuffer.size() < 2){return;}_controlPoints = vtxBuffer;std::vector<GVCoord> bezierPoints;bezier.getBezier(_controlPoints, &bezierPoints);double len1 = 0.0;for (int i=1; i<bezierPoints.size(); i++){len1 += getLen(bezierPoints[i], bezierPoints[i-1]);}double tempLen = 0.0;int num = 0;for (int i=1; i<bezierPoints.size(); i++){tempLen += getLen(bezierPoints[i], bezierPoints[i-1]);if (tempLen >= (len1 * s0)){num = i;break;}}_controlPoints.push_back(bezierPoints[num]);
}void GV00006::setControlPoint(int idx, const GVCoord& vtx)
{int cpSize = _controlPoints.size();if(idx < 0 || idx >= cpSize)return ;GVCoord modify = vtx;cfcp.configControlPoints(modify, _controlPoints);if (idx >= 0 && idx <= _controlPoints.size()-2){_controlPoints[idx] = modify;std::vector<GVCoord> myControlPoints;for (int i=0; i<_controlPoints.size()-1; i++){myControlPoints.push_back(_controlPoints[i]);}std::vector<GVCoord> bezierPoints;bezier.getBezier(myControlPoints, &bezierPoints);double len1 = 0.0;for (int i=1; i<bezierPoints.size(); i++){len1 += getLen(bezierPoints[i], bezierPoints[i-1]);}double tempLen = 0.0;int num = 0;for (int i=1; i<bezierPoints.size(); i++){tempLen += getLen(bezierPoints[i], bezierPoints[i-1]);if (tempLen >= (len1 * s0)){num = i;break;}}_controlPoints[cpSize-1] = bezierPoints[num];}if (idx == _controlPoints.size()-1){std::vector<GVCoord> myControlPoints;for (int i=0; i<_controlPoints.size()-1; i++){myControlPoints.push_back(_controlPoints[i]);}std::vector<GVCoord> tempBezierPoints;bezier.getBezier(myControlPoints, &tempBezierPoints);double length = 0.0;for (int k=1; k<tempBezierPoints.size(); k++){length += getLen(tempBezierPoints[k], tempBezierPoints[k-1]);}double min = getLen(tempBezierPoints[0], modify);int minPoint = 0;for (int i=0; i<tempBezierPoints.size(); i++){if (getLen(tempBezierPoints[i], modify) < min){min = getLen(tempBezierPoints[i], modify);minPoint = i;}}_controlPoints[idx] = tempBezierPoints[minPoint];double pointLength = 0.0;for (int i=1; i<=minPoint; i++){pointLength += getLen(tempBezierPoints[i], tempBezierPoints[i-1]);}s0 = pointLength / length;}}bool GV00006::toVertice(std::vector<GVCoord>& vtxBuffer, std::vector<int>* vtxBuffer2)
{if(_controlPoints.size() < 3)return true;std::vector<GVCoord> bezierPoints;std::vector<GVCoord> myControlPoints;for (int i=0; i<_controlPoints.size()-1; i++){myControlPoints.push_back(_controlPoints[i]);}bezier.getBezier(myControlPoints, &bezierPoints);double length = 0.0;for(int i=0; i<bezierPoints.size()-1; i++){length += sqrt((bezierPoints[i].lon - bezierPoints[i+1].lon) * (bezierPoints[i].lon - bezierPoints[i+1].lon)+ (bezierPoints[i].lat - bezierPoints[i+1].lat) * (bezierPoints[i].lat - bezierPoints[i+1].lat));}double r = length / 50.0;int start = 0;int end = bezierPoints.size() - 1;for(int i=0; i<bezierPoints.size(); i++){if (getLen(bezierPoints[i], _controlPoints[_controlPoints.size()-1]) < r){start = i;break;}}for(int i=start; i<bezierPoints.size(); i++){if (getLen(bezierPoints[i], _controlPoints[_controlPoints.size()-1]) > r){end = i;break;}}for (int i=0; i<=start; i++){vtxBuffer.push_back(bezierPoints[i]);}vtxBuffer2->push_back(start+1);double angle2 = cal_angle(bezierPoints[start], bezierPoints[end]);double distance = getLen(bezierPoints[start], bezierPoints[end]);GVCoord p0, p1, p2, p3, p4;p0.lon = bezierPoints[start].lon + distance * 0.35 * cos(angle2 + osg::PI/2);p0.lat = bezierPoints[start].lat + distance * 0.35 * sin(angle2 + osg::PI/2);p1.lon = bezierPoints[start].lon + distance * 0.15 * cos(angle2 - osg::PI/2);p1.lat = bezierPoints[start].lat + distance * 0.15 * sin(angle2 - osg::PI/2);p2.lon = p1.lon + distance * cos(angle2);p2.lat = p1.lat + distance * sin(angle2);p3.lon = p2.lon + distance * 0.25 * cos(angle2 + osg::PI/2);p3.lat = p2.lat + distance * 0.25 * sin(angle2 + osg::PI/2);p4.lon = p0.lon + distance * 0.7 * cos(angle2);p4.lat = p0.lat + distance * 0.7 * sin(angle2);vtxBuffer.push_back(p0);vtxBuffer.push_back(p1);vtxBuffer.push_back(p2);vtxBuffer.push_back(p3);vtxBuffer.push_back(p4);vtxBuffer.push_back(p0);vtxBuffer2->push_back(6);int position = bezierPoints.size();for(int i=bezierPoints.size()-1; i>0; i--){if (getLen(bezierPoints[i], bezierPoints[bezierPoints.size()-1]) > r){position = i;break;}}double angle1 = cal_angle(bezierPoints[position], _controlPoints[_controlPoints.size()-2]);GVCoord arrowP0, arrowP1, arrowP2;arrowP0.lon = bezierPoints[position].lon + r * 0.2 * cos(angle1 + osg::PI/2);arrowP0.lat = bezierPoints[position].lat + r * 0.2 * sin(angle1 + osg::PI/2);arrowP1.lon = bezierPoints[position].lon + r * 0.2 * cos(angle1 - osg::PI/2);arrowP1.lat = bezierPoints[position].lat + r * 0.2 * sin(angle1 - osg::PI/2);arrowP2 = _controlPoints[_controlPoints.size()-2];vtxBuffer.push_back(arrowP0);vtxBuffer.push_back(arrowP1);vtxBuffer.push_back(arrowP2);vtxBuffer.push_back(arrowP0);vtxBuffer2->push_back(4);for (int i=end; i<=position; i++){vtxBuffer.push_back(bezierPoints[i]);}vtxBuffer2->push_back(position-end+1);return true;
}

源码地址:https://download.csdn.net/download/sailingw/20340551

OsgEarth下战术标图相关推荐

  1. OsgEarth下给地球添加网格、鹰眼

    void QtGuiAppEarth::slotGride() {if (ui.actionGride->isChecked()){if (m_pGraticule == nullptr){m_ ...

  2. osgearth+vs2010安装

    OSGEARTH + VS2010 安装 *VS 平台不重要,本教程也适用于VS2008等.假设我的OSG目录为:D:/OSG *本教程参考网上osgearth+vs2008安装. 一.准备工作 下载 ...

  3. DDD 实战 (7):战术设计、整体流程与首次冲刺

    上篇<DDD 实战 (6):战略设计之技术决策>已经完成了"群买菜"的全局性("全局性"的意思,是说整个系统只会有一次)战略设计.从本篇开始,我们就 ...

  4. [转]秀下我的瓦伦西亚

    秀下我的瓦伦西亚~ 这是我新开的 瓦伦西亚~玩的是PLCD更新了08年转会补丁的新版本~ VDV花了3.2M拿下的~AD和ROSICKY都是7.5M拿下的~ 阵型不需要我多说了~理想的人员配置是: 前 ...

  5. osgEarth学习笔记

    这是个人在学习osgEarth时根据体会或从别的地方看到的做的一个简单整理,有些东东就是官方文档翻译过来的,都是根据自己的需要感觉需要记录下来什么东西就随便记录下来了,也没有个条理,都是用到哪记到哪, ...

  6. 领域驱动应对业务复杂度

    领域驱动应对业务复杂度 之前的文章提到过,领域驱动设计分成战略层次和战术层次,战略层次我们讨论的很多了,接下来我们主要看下战术层次要搞哪些事情,以及领域驱动如何以架构的形式落地呢. 分层架构 在进行软 ...

  7. matlab计算幂律分布,Matlab拟合曲线之幂律分布

    收集的问题: 如何用matlab来拟合幂律分布,怎样将拟合值和实际值进行对比,放在一个图中,又如何检验实际数据是否符合拟合函数. 如果不符合,如何来直接判断实际数据服从什么样的函数分布呢 在MATLA ...

  8. 一个疯子的DK马历程(易中天说:悲剧啊)

    第一季 ------------------------------------------------------------------------------------------------ ...

  9. 领域驱动设计(DDD)在爱奇艺打赏业务的实践

    领域驱动设计(Domain-Driven Design,以下简称DDD)思潮的形成要追述到30几年前,17年前,Eirc Evans定义了领域驱动设计的概念.DDD一直为传统行业的软件工程师提供软件设 ...

最新文章

  1. C#调用win32 api程序实例
  2. 多个sphinx配置文件合并
  3. 019_Vue子组件向父组件传值
  4. 用Python处理图片九宫格
  5. epoll实现压测工具
  6. python subprocess-更优雅的创建子进程
  7. xtrabackup支持的engine
  8. YII2 随笔 视图最佳实践
  9. 奇淫巧技-Flutter调用C#
  10. AX2012 referencegroup
  11. (92)多人投票器(七人投票器)
  12. linux查看宽带ip是否动态,linux CentOS系统查看实时宽带的办法
  13. python 收发邮件_Python 【收发邮件】
  14. My in 2007
  15. 特大动作:OLAMI 在线语音识别 API SDK 上线!
  16. 如何删除后缀.Tater勒索病毒并解密.tater勒索病毒加密的病毒文件
  17. Python 鞭炮题
  18. 赶紧看看吧 Linksys路由器 出事了
  19. 别再用浏览器一句句翻译了,华为手机点击这个按钮,一键轻松翻译
  20. throw 和 throws

热门文章

  1. 使用Weka进行K-近邻算法和K-均值算法的使用
  2. 赴美参加学术会议办理流程
  3. 使用php简单网页抓取和内容分析,PHP抓取分析网页的方法
  4. chromium Mojo (译)
  5. 50道PMP考试样题
  6. 微博 帖子转发下 json字段描述
  7. linux mysql 建表 ddl,linux安装mysql和mysqlDDL语言
  8. 2020-03-项目申报书框架
  9. Freenas emby 安装插件
  10. 私有云计算机械硬盘还是固态硬盘,实力悬殊!5400转居然完胜7200转?NAS私有云硬盘选择的几大误区...