3D Well Log Curves (#2671): Apply white background to curve draw plane.

This commit is contained in:
Gaute Lindkvist 2018-04-16 10:35:56 +02:00
parent 54097b7cc0
commit 5e6613d428
4 changed files with 133 additions and 71 deletions

View File

@ -131,6 +131,7 @@ void Riv3dWellLogCurveGeometryGenerator::createCurveVerticesAndIndices(const std
// Reverse list, since it was filled in the opposite order
std::reverse(interpolatedWellPathPoints.begin(), interpolatedWellPathPoints.end());
std::reverse(interpolatedNormals.begin(), interpolatedNormals.end());
// The result values for the part of the well which is not clipped off, matching interpolatedWellPathPoints size
std::vector<double> resultValuesForInterpolatedPoints(resultValues.end() - interpolatedWellPathPoints.size(),

View File

@ -44,24 +44,24 @@ Riv3dWellLogGridGeometryGenerator::Riv3dWellLogGridGeometryGenerator(RimWellPath
//--------------------------------------------------------------------------------------------------
///
//--------------------------------------------------------------------------------------------------
std::map< Riv3dWellLogGridGeometryGenerator::DrawableId, cvf::ref<cvf::DrawableGeo> >
bool
Riv3dWellLogGridGeometryGenerator::createGrid(const caf::DisplayCoordTransform* displayCoordTransform,
const cvf::BoundingBox& wellPathClipBoundingBox,
double planeAngle,
double planeOffsetFromWellPathCenter,
double planeWidth,
double gridIntervalSize) const
double gridIntervalSize)
{
CVF_ASSERT(gridIntervalSize > 0);
if (!wellPathGeometry() || wellPathGeometry()->m_measuredDepths.empty())
{
return std::map< DrawableId, cvf::ref<cvf::DrawableGeo> >();
return false;
}
if (!wellPathClipBoundingBox.isValid())
{
return std::map< DrawableId, cvf::ref<cvf::DrawableGeo> >();
return false;
}
@ -71,7 +71,7 @@ Riv3dWellLogGridGeometryGenerator::createGrid(const caf::DisplayCoordTransform*
std::vector<cvf::Vec3d> wellPathPoints = wellPathGeometry()->m_wellPathPoints;
if (wellPathPoints.empty())
{
return std::map< DrawableId, cvf::ref<cvf::DrawableGeo> >();
return false;
}
size_t originalWellPathSize = wellPathPoints.size();
@ -85,13 +85,12 @@ Riv3dWellLogGridGeometryGenerator::createGrid(const caf::DisplayCoordTransform*
wellPathPoints, maxZClipHeight, &horizontalLengthAlongWellToClipPoint, &indexToFirstVisibleSegment);
}
if (wellPathPoints.empty())
if (wellPathPoints.size() < (size_t) 2)
{
return std::map< DrawableId, cvf::ref<cvf::DrawableGeo> >();
// Need at least two well path points to create a valid path.
return false;
}
std::map< DrawableId, cvf::ref<cvf::DrawableGeo> > drawables;
// calculateLineSegmentNormals returns normals for the whole well path. Erase the part which is clipped off
std::vector<cvf::Vec3d> wellPathSegmentNormals =
RigWellPathGeometryTools::calculateLineSegmentNormals(wellPathGeometry(), planeAngle);
@ -99,42 +98,73 @@ Riv3dWellLogGridGeometryGenerator::createGrid(const caf::DisplayCoordTransform*
{
std::vector<cvf::Vec3f> vertices;
vertices.reserve(wellPathPoints.size());
vertices.reserve(wellPathPoints.size() * 2);
std::vector<cvf::uint> indices;
indices.reserve(wellPathPoints.size());
cvf::uint indexCounter = 0;
// Line along and close to well
std::vector<cvf::uint> backgroundIndices;
backgroundIndices.reserve(wellPathPoints.size() * 2);
// Vertices are used for both surface and border
for (size_t i = 0; i < wellPathPoints.size(); i++)
{
vertices.push_back(cvf::Vec3f(displayCoordTransform->transformToDisplayCoord(
wellPathPoints[i] + wellPathSegmentNormals[i] * planeOffsetFromWellPathCenter)));
indices.push_back(indexCounter);
indices.push_back(++indexCounter);
}
// Line along and far away from well in reverse order to create a closed surface.
for (int64_t i = (int64_t) wellPathPoints.size()-1; i >= 0; i--)
{
vertices.push_back(cvf::Vec3f(displayCoordTransform->transformToDisplayCoord(
wellPathPoints[i] + wellPathSegmentNormals[i] * (planeOffsetFromWellPathCenter + planeWidth))));
indices.push_back(indexCounter);
indices.push_back(++indexCounter);
backgroundIndices.push_back((cvf::uint) (2 * i));
backgroundIndices.push_back((cvf::uint) (2 * i + 1));
}
indices.pop_back();
indices.push_back(0u); // Close surface
cvf::ref<cvf::PrimitiveSetIndexedUInt> indexedUInt = new cvf::PrimitiveSetIndexedUInt(cvf::PrimitiveType::PT_LINE_LOOP);
cvf::ref<cvf::UIntArray> indexArray = new cvf::UIntArray(indices);
cvf::ref<cvf::DrawableGeo> gridBorderDrawable = new cvf::DrawableGeo();
indexedUInt->setIndices(indexArray.p());
gridBorderDrawable->addPrimitiveSet(indexedUInt.p());
cvf::ref<cvf::Vec3fArray> vertexArray = new cvf::Vec3fArray(vertices);
gridBorderDrawable->setVertexArray(vertexArray.p());
drawables[GridBorder] = gridBorderDrawable;
{
// Background specific
cvf::ref<cvf::PrimitiveSetIndexedUInt> indexedUInt = new cvf::PrimitiveSetIndexedUInt(cvf::PrimitiveType::PT_TRIANGLE_STRIP);
cvf::ref<cvf::UIntArray> indexArray = new cvf::UIntArray(backgroundIndices);
indexedUInt->setIndices(indexArray.p());
m_background = new cvf::DrawableGeo();
m_background->addPrimitiveSet(indexedUInt.p());
m_background->setVertexArray(vertexArray.p());
}
{
std::vector<cvf::uint> borderIndices;
borderIndices.reserve(vertices.size());
int secondLastEvenVertex = (int) vertices.size() - 4;
// Border close to the well. All even indices.
for (size_t i = 0; i <= secondLastEvenVertex; i += 2)
{
borderIndices.push_back((cvf::uint) i);
borderIndices.push_back((cvf::uint) i+2);
}
// Connect to border away from well
borderIndices.push_back((cvf::uint) (vertices.size() - 2));
borderIndices.push_back((cvf::uint) (vertices.size() - 1));
int secondOddVertex = 3;
int lastOddVertex = (int) vertices.size() - 1;
// Border away from from well are odd indices in reverse order to create a closed surface.
for (int i = lastOddVertex; i >= secondOddVertex; i -= 2)
{
borderIndices.push_back((cvf::uint) i);
borderIndices.push_back((cvf::uint) i - 2);
}
// Close border
borderIndices.push_back(1u);
borderIndices.push_back(0u);
cvf::ref<cvf::PrimitiveSetIndexedUInt> indexedUInt = new cvf::PrimitiveSetIndexedUInt(cvf::PrimitiveType::PT_LINES);
cvf::ref<cvf::UIntArray> indexArray = new cvf::UIntArray(borderIndices);
indexedUInt->setIndices(indexArray.p());
m_border = new cvf::DrawableGeo();
m_border->addPrimitiveSet(indexedUInt.p());
m_border->setVertexArray(vertexArray.p());
}
}
{
std::vector<cvf::Vec3d> interpolatedGridPoints;
@ -184,9 +214,24 @@ Riv3dWellLogGridGeometryGenerator::createGrid(const caf::DisplayCoordTransform*
cvf::ref<cvf::Vec3fArray> vertexArray = new cvf::Vec3fArray(vertices);
normalLinesDrawable->setVertexArray(vertexArray.p());
drawables[NormalLines] = normalLinesDrawable;
m_normalLines = normalLinesDrawable;
}
return drawables;
return true;
}
cvf::ref<cvf::DrawableGeo> Riv3dWellLogGridGeometryGenerator::background()
{
return m_background;
}
cvf::ref<cvf::DrawableGeo> Riv3dWellLogGridGeometryGenerator::border()
{
return m_border;
}
cvf::ref<cvf::DrawableGeo> Riv3dWellLogGridGeometryGenerator::normalLines()
{
return m_normalLines;
}
//--------------------------------------------------------------------------------------------------

View File

@ -42,24 +42,24 @@ class RimWellPath;
class Riv3dWellLogGridGeometryGenerator : public cvf::Object
{
public:
enum DrawableId
{
NormalLines = 0,
GridBorder = 1,
GridBackground = 2
};
Riv3dWellLogGridGeometryGenerator(RimWellPath* wellPath);
std::map<DrawableId, cvf::ref<cvf::DrawableGeo> >
createGrid(const caf::DisplayCoordTransform* displayCoordTransform,
const cvf::BoundingBox& wellPathClipBoundingBox,
double planeAngle,
double planeOffsetFromWellPathCenter,
double planeWidth,
double gridIntervalSize) const;
bool createGrid(const caf::DisplayCoordTransform* displayCoordTransform,
const cvf::BoundingBox& wellPathClipBoundingBox,
double planeAngle,
double planeOffsetFromWellPathCenter,
double planeWidth,
double gridIntervalSize);
cvf::ref<cvf::DrawableGeo> background();
cvf::ref<cvf::DrawableGeo> border();
cvf::ref<cvf::DrawableGeo> normalLines();
private:
const RigWellPath* wellPathGeometry() const;
private:
caf::PdmPointer<RimWellPath> m_wellPath;
cvf::ref<cvf::DrawableGeo> m_background;
cvf::ref<cvf::DrawableGeo> m_border;
cvf::ref<cvf::DrawableGeo> m_normalLines;
};

View File

@ -223,31 +223,47 @@ void Riv3dWellLogPlanePartMgr::appendGridToModel(cvf::ModelBasicList*
const Rim3dWellLogCurveCollection* curveCollection = m_wellPath->rim3dWellLogCurveCollection();
Rim3dWellLogCurveCollection::PlanePosition planePosition = curveCollection->planePosition();
caf::SurfaceEffectGenerator surfaceEffectGen(cvf::Color4f(1.0, 1.0, 1.0, 0.5), caf::PO_1);
caf::MeshEffectGenerator gridBorderEffectGen(cvf::Color3f(0.4f, 0.4f, 0.4f));
caf::MeshEffectGenerator normalsEffectGen(cvf::Color3f(0.4f, 0.4f, 0.4f));
normalsEffectGen.setLineStipple(true);
caf::SurfaceEffectGenerator backgroundEffectGen(cvf::Color4f(1.0, 1.0, 1.0, 1.0), caf::PO_2);
caf::MeshEffectGenerator gridBorderEffectGen(cvf::Color3f(0.4f, 0.4f, 0.4f));
caf::MeshEffectGenerator normalsEffectGen(cvf::Color3f(0.4f, 0.4f, 0.4f));
backgroundEffectGen.enableLighting(false);
std::map < Riv3dWellLogGridGeometryGenerator::DrawableId, cvf::ref<cvf::DrawableGeo> > gridDrawables =
m_3dWellLogGridGeometryGenerator->createGrid(displayCoordTransform,
wellPathClipBoundingBox,
planeAngle(drawPlane),
wellPathCenterToPlotStartOffset(planePosition),
planeWidth(),
gridIntervalSize);
bool gridCreated = m_3dWellLogGridGeometryGenerator->createGrid(displayCoordTransform,
wellPathClipBoundingBox,
planeAngle(drawPlane),
wellPathCenterToPlotStartOffset(planePosition),
planeWidth(),
gridIntervalSize);
if (!gridCreated) return;
std::map < Riv3dWellLogGridGeometryGenerator::DrawableId, cvf::ref<cvf::Effect> > effects;
effects[Riv3dWellLogGridGeometryGenerator::GridBackground] = surfaceEffectGen.generateCachedEffect();
effects[Riv3dWellLogGridGeometryGenerator::GridBorder] = gridBorderEffectGen.generateCachedEffect();
effects[Riv3dWellLogGridGeometryGenerator::NormalLines] = normalsEffectGen.generateCachedEffect();
cvf::ref<cvf::Effect> backgroundEffect = backgroundEffectGen.generateCachedEffect();
cvf::ref<cvf::Effect> borderEffect = gridBorderEffectGen.generateCachedEffect();
cvf::ref<cvf::Effect> normalsEffect = normalsEffectGen.generateCachedEffect();
for(std::pair< Riv3dWellLogGridGeometryGenerator::DrawableId, cvf::ref<cvf::DrawableGeo> > item : gridDrawables)
cvf::ref<cvf::DrawableGeo> background = m_3dWellLogGridGeometryGenerator->background();
if (background.notNull())
{
Riv3dWellLogGridGeometryGenerator::DrawableId drawableId = item.first;
cvf::ref<cvf::DrawableGeo> drawable = item.second;
CVF_ASSERT(drawable.notNull());
cvf::ref<cvf::Part> part = createPart(drawable.p(), effects[drawableId].p());
cvf::ref<cvf::Part> part = createPart(background.p(), backgroundEffect.p());
if (part.notNull())
{
model->addPart(part.p());
}
}
cvf::ref<cvf::DrawableGeo> border = m_3dWellLogGridGeometryGenerator->border();
if (border.notNull())
{
cvf::ref<cvf::Part> part = createPart(border.p(), borderEffect.p());
if (part.notNull())
{
model->addPart(part.p());
}
}
cvf::ref<cvf::DrawableGeo> normals = m_3dWellLogGridGeometryGenerator->normalLines();
if (normals.notNull())
{
cvf::ref<cvf::Part> part = createPart(normals.p(), normalsEffect.p());
if (part.notNull())
{
model->addPart(part.p());