void GuiDecalEditorCtrl::_renderDecalEdge( const Vector<Point3F> &verts, const ColorI &color ) { U32 vertCount = verts.size(); GFXTransformSaver saver; PrimBuild::color( color ); Point3F endPt( 0, 0, 0 ); for ( U32 i = 0; i < vertCount; i++ ) { const Point3F &vert = verts[i]; if ( i + 1 < vertCount ) endPt = verts[i + 1]; else break; PrimBuild::begin( GFXLineList, 2 ); PrimBuild::vertex3f( vert.x, vert.y, vert.z ); PrimBuild::vertex3f( endPt.x, endPt.y, endPt.z ); PrimBuild::end(); } }
std::string packLineData(LineData lineData) { rapidjson::Document document; document.SetObject(); rapidjson::Value startPt(rapidjson::kObjectType); startPt.AddMember("x", lineData.startPoint.x, document.GetAllocator()); startPt.AddMember("y", lineData.startPoint.y, document.GetAllocator()); rapidjson::Value endPt(rapidjson::kObjectType); endPt.AddMember("x", lineData.endPoint.x, document.GetAllocator()); endPt.AddMember("y", lineData.endPoint.y, document.GetAllocator()); rapidjson::Value lineColor(rapidjson::kObjectType); lineColor.AddMember("r", lineData.color.r, document.GetAllocator()); lineColor.AddMember("g", lineData.color.g, document.GetAllocator()); lineColor.AddMember("b", lineData.color.b, document.GetAllocator()); lineColor.AddMember("a", lineData.color.a, document.GetAllocator()); document.AddMember("startPoint", startPt, document.GetAllocator()); document.AddMember("endPoint", endPt, document.GetAllocator()); document.AddMember("radius", lineData.radius, document.GetAllocator()); document.AddMember("color", lineColor, document.GetAllocator()); rapidjson::StringBuffer buffer; rapidjson::Writer<rapidjson::StringBuffer> writer(buffer); document.Accept(writer); return std::string(buffer.GetString(), buffer.GetSize()); }
//---------------------------------------------------------- void ofxVectorGraphics::endShape(bool bClose){ if(bDraw){ ofEndShape(bClose); } if(bRecord){ //catmull roms - we need at least 4 points to draw if( whichShapeMode == 1 && curvePts.size() > 3){ //we go through and we calculate the bezier of each //catmull rom curve - smart right? :) for (int i = 1; i< curvePts.size()-2; i++) { ofPoint3 prevPt( curvePts[i-1][0], curvePts[i-1][1]); ofPoint3 startPt(curvePts[i][0], curvePts[i][1]); ofPoint3 endPt( curvePts[i+1][0], curvePts[i+1][1]); ofPoint3 nextPt( curvePts[i+2][0], curvePts[i+2][1]); //SUPER WEIRD MAGIC CONSTANT = 1/6 //Someone please explain this!!! //It works and is 100% accurate but wtf! ofPoint3 cp1 = startPt + ( endPt - prevPt ) * (1.0/6); ofPoint3 cp2 = endPt + ( startPt - nextPt ) * (1.0/6); //if this is the first line we are drawing //we have to start the path at a location if( i == 1 ){ creeps.startPath(startPt.x, startPt.y); bShouldClose = true; } creeps.addCurve( cp1.x, cp1.y, cp2.x, cp2.y, endPt.x, endPt.y); } } if(bShouldClose){ //we close the path if requested if(bClose)creeps.closeSubpath(); //render the stroke as either a fill or a stroke. if(bFill){ creeps.endPath(CreEPS::FILL); }else{ creeps.endPath(CreEPS::STROKE); } bShouldClose = false; } //we want to clear all the vertices //otherwise we keep adding points from //the previous file - cool but not what we want! clearAllVertices(); } }
void CXMLExporter::WriteEdge(CComPtr<ISkpEdge> pEdge) { HResult hr; m_Stats.m_nEdges += 1; if (m_pOptions->GetExportLayers()) { CComPtr<ISkpDrawingElement> pDE; hr = pEdge->QueryInterface(IID_ISkpDrawingElement, (void**) &pDE); CComPtr<ISkpLayer> pLayer; hr = pDE->get_Layer(&pLayer); long layerId = GetEntityId(pLayer); Write("<Edge layer=\"%d\">\n", layerId); } else { Write("<Edge>\n"); } IncreaseIndent(); CComPtr<ISkpPoint3d> pStartPoint; hr = pEdge->get_StartPoint(&pStartPoint); CPoint3d startPt(pStartPoint); CPoint3d startPoint = m_InheritanceManager.GetCurrentTransform() * startPt; Write("<Start x=\"%f\" y=\"%f\" z=\"%f\" />\n", startPoint.X(), startPoint.Y(), startPoint.Z()); CComPtr<ISkpPoint3d> pEndPoint; hr = pEdge->get_EndPoint(&pEndPoint); CPoint3d endPt(pEndPoint); CPoint3d endPoint = m_InheritanceManager.GetCurrentTransform() * endPt; Write("<End x=\"%f\" y=\"%f\" z=\"%f\" />\n", endPoint.X(), endPoint.Y(), endPoint.Z()); DecreaseIndent(); Write("</Edge>\n"); }
bool MgArc::_setHandlePoint2(int index, const Point2d& pt, float, int& data) { static float lastSweepAngle; if (index == 1 || index == 2) { // 起点、终点 return setCenterRadius(getCenter(), pt.distanceTo(getCenter()), getStartAngle(), getSweepAngle()); } if (index == 3) { // 弧线中点 return setStartMidEnd(getStartPoint(), pt, getEndPoint()); } if (index == 4) { // 改变起始角度 if (data == 0) { lastSweepAngle = getSweepAngle(); data++; } Point2d startPt(getCenter().polarPoint((pt - getCenter()).angle2(), getRadius())); bool ret = setCSE(getCenter(), startPt, getEndPoint(), lastSweepAngle); lastSweepAngle = getSweepAngle(); return ret; } if (index == 5) { // 改变终止角度 if (data == 0) { lastSweepAngle = getSweepAngle(); data++; } Point2d endPt(getCenter().polarPoint((pt - getCenter()).angle2(), getRadius())); bool ret = setCSE(getCenter(), getStartPoint(), endPt, lastSweepAngle); lastSweepAngle = getSweepAngle(); return ret; } if (index == 6) { return setTanStartEnd(pt - getStartPoint(), getStartPoint(), getEndPoint()); } if (index == 7) { return (setTanStartEnd(getEndPoint() - pt, getEndPoint(), getStartPoint()) && _reverse()); } return offset(pt - getCenter(), -1); }
int seg:: contains ( const seg& segIn ) const { // TODO: Remove direction vector normalization?? User's responsibility??? vec3 tDir ( segIn.dir ); tDir.normalize (); // vec3 endPt = segIn.pos + tDir * segIn.length; vec3 endPt ( tDir ); endPt *= segIn.length; endPt += segIn.pos; int c1 = contains ( segIn.pos ); int c2 = contains ( endPt ); if ( c1 ) { if ( c2 ) return containsResult::AllIn; return containsResult::SomeIn; } if ( c2 ) return containsResult::SomeIn; // OPTIMIZE: Expensive... if ( segIn.contains ( pos ) ) return containsResult::SomeIn; vec3 endPos = pos + dir * length; if ( segIn.contains ( endPos ) ) return containsResult::SomeIn; return containsResult::NoneIn; }
// OPTIMIZE: NON-OPTIMAL int seg:: contains ( const vec3& pt ) const { // TODO: There are some expensive calls in here. Find a more optimal means of doing this. if ( pt.equal ( pos ) ) return containsResult::AllIn; vec3 endPt ( dir ); endPt *= length; endPt += pos; if ( pt.equal ( endPt ) ) return containsResult::AllIn; // vec3 ptDir = pt - pos; vec3 ptDir ( pt ); ptDir -= pos; vec3 a = ptDir; a.normalize (); // Direction vectors the same? if ( ! a.equal ( dir ) ) { // Nope. We're not in/on the segment. return containsResult::NoneIn; } // The direction vectors are the same, so what is our distance from the endpoint? if ( ptDir.length () <= length ) { return containsResult::AllIn; } return containsResult::NoneIn; }
PointObject* calcPoint(const std::vector<int>& v) { PointObject* pO = nullptr; int start_point = 0; int end_point = 0; auto it = std::find_if(v.begin(), v.end(), [](const int a) { return (a != 0); }); auto it2 = std::find_if(v.rbegin(), v.rend(), [](int a) { return (a != 0); }); if ((it != v.end())) { Point startPt(std::distance(v.begin(), it)); Point endPt(std::distance(it2, v.rend()) - 1); pO = new Point(average(startPt, endPt)); } else { pO = new NullPoint(); } return pO; }
int testPoint() { int numErr = 0; logMessage(_T("TESTING - class GM_3dPoint ...\n\n")); // Default constructor, point must be invalid GM_3dPoint pt; if (pt.isValid()) { logMessage(_T("\tERROR - Default constructor creates valid points\n")); numErr++; } else { logMessage(_T("\tOK - Default constructor creates invalid points\n")); } // Get/Set points coordinates double x = getRandomDouble(); double y = getRandomDouble(); double z = getRandomDouble(); pt.x(x); pt.y(y); pt.z(z); if (pt.x() != x || pt.y() != y || pt.z() != z) { logMessage(_T("\tERROR - Get/Set not working\n")); numErr++; } else { logMessage(_T("\tOK - Get/Set working\n")); } // Copy constructor GM_3dPoint pt1(pt); if (pt.isValid() != pt1.isValid() || pt1.x() != pt.x() || pt1.y() != pt.y() || pt1.z() != pt.z()) { logMessage(_T("\tERROR - Copy constructor not working\n")); numErr++; } else { logMessage(_T("\tOK - Copy constructor working\n")); } // Constructor (coordinates) x = getRandomDouble(); y = getRandomDouble(); z = getRandomDouble(); GM_3dPoint pt2(x, y, z); if (!pt2.isValid() || pt2.x() != x || pt2.y() != y || pt2.z() != z) { logMessage(_T("\tERROR - Coordinate constructor not working\n")); numErr++; } else { logMessage(_T("\tOK - Coordinate constructor working\n")); } // Constructor (angle) double ang = getRandomAngle(); GM_3dPoint pt3(ang); if (!pt2.isValid() || pt3.x() != cos(ang) || pt3.y() != sin(ang) || pt3.z() != 0.0) { logMessage(_T("\tERROR - XY angle constructor not working\n")); numErr++; } else { logMessage(_T("\tOK - XY angle constructor working\n")); } // Invalidation pt.invalidate(); if (pt.isValid()) { logMessage(_T("\tERROR - Invalidation not working\n")); numErr++; } else { logMessage(_T("\tOK - Invalidation working\n")); } // Inversion GM_3dPoint invPt(pt2); invPt.xyInvert(); if (invPt.isValid() != pt2.isValid() || invPt.x() != -pt2.x() || invPt.y() != -pt2.y() || invPt.z() != pt2.z()) { logMessage(_T("\tERROR - Inversion not working\n")); numErr++; } else { logMessage(_T("\tOK - Inversion working\n")); } // Origin check GM_3dPoint origPt(GM_NULL_TOLERANCE / 2.0, -GM_NULL_TOLERANCE / 2.0, 0.0); if (pt2.isOrigin() || !origPt.isOrigin()) { logMessage(_T("\tERROR - Origin check not working\n")); numErr++; } else { logMessage(_T("\tOK - Origin check working\n")); } // Distance GM_3dPoint startPt(getRandomDouble(), getRandomDouble(), getRandomDouble()); GM_3dPoint endPt(getRandomDouble(), getRandomDouble(), getRandomDouble()); double dx = startPt.x() - endPt.x(); double dy = startPt.y() - endPt.y(); double dz = startPt.z() - endPt.z(); double dist = sqrt(dx*dx + dy*dy + dz*dz); if (!startPt.isValid() || !endPt.isValid() || startPt.distFrom(endPt) != dist) { logMessage(_T("\tERROR - Distance computation not working\n")); numErr++; } else { logMessage(_T("\tOK - Distance computation working\n")); } // Equality GM_3dPoint ptEq1(getRandomDouble(), getRandomDouble(), getRandomDouble()); GM_3dPoint ptEq2(ptEq1); GM_3dPoint ptEq3(ptEq1.x() + getRandomDouble(), ptEq1.y() + getRandomDouble(), ptEq1.z() + getRandomDouble()); if (ptEq1 != ptEq2 || ptEq1 == ptEq3) { logMessage(_T("\tERROR - Equality check not working\n")); numErr++; } else { logMessage(_T("\tOK - Equality check working\n")); } return numErr; }
int testLine() { int numErr = 0; logMessage(_T("TESTING - class GM_3dLine ...\n\n")); // Default constructor, line must be invalid GM_3dLine ln; if (ln.isValid()) { logMessage(_T("\tERROR - Default constructor creates valid line\n")); numErr++; } else { logMessage(_T("\tOK - Default constructor creates invalid line\n")); } // Get/Set line coordinates double xStart = getRandomDouble(); double yStart = getRandomDouble(); double zStart = getRandomDouble(); double xEnd = getRandomDouble(); double yEnd = getRandomDouble(); double zEnd = getRandomDouble(); ln.begin().x(xStart); ln.begin().y(yStart); ln.begin().z(zStart); ln.end().x(xEnd); ln.end().y(yEnd); ln.end().z(zEnd); if (!ln.isValid() || ln.begin().x() != xStart || ln.begin().y() != yStart || ln.begin().z() != zStart || ln.end().x() != xEnd || ln.end().y() != yEnd || ln.end().z() != zEnd) { logMessage(_T("\tERROR - Get/Set not working\n")); numErr++; } else { logMessage(_T("\tOK - Get/Set working\n")); } // Copy constructor GM_3dLine ln1(ln); if (ln1.isValid() != ln.isValid() || ln1.begin().x() != ln.begin().x() || ln1.begin().y() != ln.begin().y() || ln1.begin().z() != ln.begin().z() || ln1.end().x() != ln.end().x() || ln1.end().y() != ln.end().y() || ln1.end().z() != ln.end().z()) { logMessage(_T("\tERROR - Copy constructor not working\n")); numErr++; } else { logMessage(_T("\tOK - Copy constructor working\n")); } // Constructor (points) GM_3dPoint startPt(getRandomDouble(), getRandomDouble(), getRandomDouble()); GM_3dPoint endPt(getRandomDouble(), getRandomDouble(), getRandomDouble()); GM_3dLine ln2(startPt, endPt); if (!ln2.isValid() || ln2.begin().x() != startPt.x() || ln2.begin().y() != startPt.y() || ln2.begin().z() != startPt.z() || ln2.end().x() != endPt.x() || ln2.end().y() != endPt.y() || ln2.end().z() != endPt.z()) { logMessage(_T("\tERROR - Points constructor not working\n")); numErr++; } else { logMessage(_T("\tOK - Points constructor working\n")); } // Constructor (coordinates) xStart = getRandomDouble(); yStart = getRandomDouble(); zStart = getRandomDouble(); xEnd = getRandomDouble(); yEnd = getRandomDouble(); zEnd = getRandomDouble(); GM_3dLine ln3(xStart, yStart, zStart, xEnd, yEnd, zEnd); if (!ln3.isValid() || ln3.begin().x() != xStart || ln3.begin().y() != yStart || ln3.begin().z() != zStart || ln3.end().x() != xEnd || ln3.end().y() != yEnd || ln3.end().z() != zEnd) { logMessage(_T("\tERROR - Coordinate constructor not working\n")); numErr++; } else { logMessage(_T("\tOK - Coordinate constructor working\n")); } // dx, dy, dz double dx = ln2.dx(); double dy = ln2.dy(); double dz = ln2.dz(); if (dx != ln2.end().x()-ln2.begin().x() || dy != ln2.end().y()-ln2.begin().y() || dz != ln2.end().z()-ln2.begin().z()) { logMessage(_T("\tERROR - dx, dy or dz not working\n")); numErr++; } else { logMessage(_T("\tOK - dx, dy or dz working\n")); } // Dot product double dotProduct = ln2 * ln3; double dxLn2 = ln2.dx(); double dyLn2 = ln2.dy(); double dzLn2 = ln2.dz(); double dxLn3 = ln3.dx(); double dyLn3 = ln3.dy(); double dzLn3 = ln3.dz(); double checkDotProduct = dxLn2*dxLn3 + dyLn2*dyLn3 + dzLn2*dzLn3; if (dotProduct != checkDotProduct) { logMessage(_T("\tERROR - Dot product not working\n")); numErr++; } else { logMessage(_T("\tOK - Dot product working\n")); } // Cross product GM_3dLine crossProdLn = ln2 ^ ln3; double checkCrossProdX = ln2.begin().x() + (dyLn2*dzLn3 - dzLn2*dyLn3); double checkCrossProdY = ln2.begin().y() + (dzLn2*dxLn3 - dxLn2*dzLn3); double checkCrossProdZ = ln2.begin().z() + (dxLn2*dyLn3 - dyLn2*dxLn3); if (!crossProdLn.isValid() || crossProdLn.end().x() != checkCrossProdX || crossProdLn.end().y() != checkCrossProdY || crossProdLn.end().z() != checkCrossProdZ) { logMessage(_T("\tERROR - Cross product not working\n")); numErr++; } else { logMessage(_T("\tOK - Cross product working\n")); } // Center GM_3dPoint ln2Center = ln2.center(); if (!ln2Center.isValid() || ln2Center.x() != ln2.begin().x() + (ln2.end().x()-ln2.begin().x())/2.0 || ln2Center.y() != ln2.begin().y() + (ln2.end().y()-ln2.begin().y())/2.0 || ln2Center.z() != ln2.begin().z() + (ln2.end().z()-ln2.begin().z())/2.0) { logMessage(_T("\tERROR - Center point computation not working\n")); numErr++; } else { logMessage(_T("\tOK - Center point computation working\n")); } // Invert GM_3dLine ln2Copy(ln2); ln2.invert(); if (!ln2Copy.isValid() || ln2Copy.begin().x() != ln2.end().x() || ln2Copy.begin().y() != ln2.end().y() || ln2Copy.begin().z() != ln2.end().z() || ln2Copy.end().x() != ln2.begin().x() || ln2Copy.end().y() != ln2.begin().y() || ln2Copy.end().z() != ln2.begin().z()) { logMessage(_T("\tERROR - Inversion not working\n")); numErr++; } else { logMessage(_T("\tOK - Inversion working\n")); } // Length double checkLen = sqrt(ln2.dx()*ln2.dx() + ln2.dy()*ln2.dy() + ln2.dz()*ln2.dz()); if (ln2.length() != checkLen) { logMessage(_T("\tERROR - Length computation not working\n")); numErr++; } else { logMessage(_T("\tOK - Length computation working\n")); } // Null check GM_3dLine nullLn(0.0, 0.0, 0.0, 0.0, 0.0, 0.0); bool checkNull1 = nullLn.isNull(); nullLn.begin().x(10.0); bool checkNull2 = nullLn.isNull(); if (!nullLn.isValid() || !checkNull1 || checkNull2) { logMessage(_T("\tERROR - Null line check not working\n")); numErr++; } else { logMessage(_T("\tOK - Null line check working\n")); } // Vertical line check double xCoord = getRandomDouble(); double yCoord = getRandomDouble(); GM_3dLine vertLn(xCoord, yCoord, getRandomDouble(), xCoord, yCoord, getRandomDouble()); bool checkVert1 = vertLn.isVertical(); vertLn.begin().x(vertLn.begin().x() + 10.0); bool checkVert2 = vertLn.isVertical(); if (!vertLn.isValid() || !checkVert1 || checkVert2) { logMessage(_T("\tERROR - Vertical line check not working\n")); numErr++; } else { logMessage(_T("\tOK - Vertical line check working\n")); } // Horizontal line check double zCoord = getRandomDouble(); GM_3dLine horLn(getRandomDouble(), getRandomDouble(), zCoord, getRandomDouble(), getRandomDouble(), zCoord); bool checkHor1 = horLn.isHorizontal(); horLn.begin().z(horLn.begin().z() + 10.0); bool checkHor2 = horLn.isHorizontal(); if (!horLn.isValid() || !checkHor1 || checkVert2) { logMessage(_T("\tERROR - Horizontal line check not working\n")); numErr++; } else { logMessage(_T("\tOK - Horizontal line check working\n")); } // Z min/max double minZ = ln2.minZ(); double maxZ = ln2.maxZ(); double checkMin = ln2.begin().z() < ln2.end().z() ? ln2.begin().z() : ln2.end().z(); double checkMax = ln2.begin().z() > ln2.end().z() ? ln2.begin().z() : ln2.end().z(); if (minZ != checkMin || maxZ != checkMax) { logMessage(_T("\tERROR - min/max Z not working\n")); numErr++; } else { logMessage(_T("\tOK - min/max Z working\n")); } // Point on line at Z double sec = getRandom01Double(); double dX = ln2.dx(); double dY = ln2.dy(); double dZ = ln2.dz(); double xCheck = ln2.begin().x() + (sec * dX); double yCheck = ln2.begin().y() + (sec * dY); double zCheck = ln2.begin().z() + (sec * dZ); GM_3dPoint pointAtZ = ln2.pointAtZ(zCheck); if (!pointAtZ.isValid() || fabs(pointAtZ.x()-xCheck) > GM_NULL_TOLERANCE || fabs(pointAtZ.y()-yCheck) > GM_NULL_TOLERANCE) { logMessage(_T("\tERROR - Point on line at Z not working\n")); numErr++; } else { logMessage(_T("\tOK - Point on line at Z working\n")); } // Nomal vector on XY GM_3dVector normalVectorR = ln2.normalXYVector(true); GM_3dVector normalVectorL = ln2.normalXYVector(false); GM_3dVector ln2Dir(ln2); double dotPR = normalVectorR * ln2Dir; double dotPL = normalVectorL * ln2Dir; bool RSide = ln2Dir.isAtLeftOnXY(normalVectorR); bool LSide = ln2Dir.isAtLeftOnXY(normalVectorL); if (!normalVectorR.isValid() || !normalVectorL.isValid() || fabs(dotPR) > GM_NULL_TOLERANCE || fabs(dotPL) > GM_NULL_TOLERANCE || !RSide || LSide) { logMessage(_T("\tERROR - XY normal vector computation not working\n")); numErr++; } else { logMessage(_T("\tOK - XY normal vector computation working\n")); } // Point from section double section = getRandom01Double(); GM_3dPoint sectionPoint = ln2.pointFromSection(section); double ln2Len = ln2.length(); double pointSectionLen = ln2.begin().distFrom(sectionPoint); if (fabs((pointSectionLen / ln2Len) - section) > GM_NULL_TOLERANCE) { logMessage(_T("\tERROR - Point from section not working\n")); numErr++; } else { logMessage(_T("\tOK - Point from section working\n")); } // Section from point double checkSection = ln2.sectionFromPoint(sectionPoint); if (fabs(checkSection - section) > GM_NULL_TOLERANCE) { logMessage(_T("\tERROR - Section from point not working\n")); numErr++; } else { logMessage(_T("\tOK - Section from point working\n")); } // Point distance ln2Dir.normalize(); GM_3dVector ln2NormDir(ln2Dir); section = getRandom01Double(); sectionPoint = ln2.pointFromSection(section); if (fabs(ln2Dir.x()) > GM_NULL_TOLERANCE) { ln2NormDir.x(getRandomDouble()); ln2NormDir.y(getRandomDouble()); ln2NormDir.z(getRandomDouble()); ln2NormDir.normalize(); ln2NormDir.x(-(ln2Dir.y()*ln2NormDir.y() + ln2Dir.z()*ln2NormDir.z()) / ln2Dir.x()); } else if (fabs(ln2Dir.y()) > GM_NULL_TOLERANCE) { ln2NormDir.x(getRandomDouble()); ln2NormDir.y(getRandomDouble()); ln2NormDir.z(getRandomDouble()); ln2NormDir.normalize(); ln2NormDir.y(-(ln2Dir.x()*ln2NormDir.x() + ln2Dir.z()*ln2NormDir.z()) / ln2Dir.y()); } else if (fabs(ln2Dir.z()) > GM_NULL_TOLERANCE) { ln2NormDir.x(getRandomDouble()); ln2NormDir.y(getRandomDouble()); ln2NormDir.z(getRandomDouble()); ln2NormDir.normalize(); ln2NormDir.z(-(ln2Dir.x()*ln2NormDir.x() + ln2Dir.y()*ln2NormDir.y()) / ln2Dir.z()); } else { ln2NormDir.invalidate(); } double dist = 0.0; double checkDist = 0.0; GM_3dPoint pointOnLine; if (ln2NormDir.isValid()) { ln2NormDir.normalize(); double dotProd = ln2NormDir * ln2Dir; dist = fabs(getRandomDouble()); GM_3dPoint externPoint(sectionPoint); externPoint = (GM_3dVector)externPoint + (ln2NormDir * dist); checkDist = ln2.pointDistance(externPoint, pointOnLine); } if (!pointOnLine.isValid() || fabs(dist - checkDist) > GM_NULL_TOLERANCE) { logMessage(_T("\tERROR - Point distance not working\n")); numErr++; } else { logMessage(_T("\tOK - Point distance working\n")); } return numErr; }