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.
kev/Drawer/Module/GeoSigmaDraw/SplineDragPipeline.cpp

124 lines
2.9 KiB
C++

1 month ago
#include "StdAfx.h"
#include "SplineDragPipeline.h"
#include "SigmaDoc.h"
#include <vector>
SplineDragPipeline::SplineDragPipeline(SplineCurveModel& model, SplineDragState& dragState, ISplineDragPipelineContext* pContext)
: m_pModel(&model)
, m_pDragState(&dragState)
, m_pContext(pContext)
{
}
bool SplineDragPipeline::ProcessDragStep(bool isPreview, CPointList* pListForPreview)
{
CCurveEx* pValue = nullptr;
int handleIndex = -1;
if (!GetCurveForDragEdit(isPreview, pValue, handleIndex, pListForPreview))
return false;
std::vector<dfPoint> segmentVec;
if (!GetDraggedSegmentAndAttachContext(segmentVec))
{
if (isPreview && pValue)
delete pValue;
return false;
}
if (!WriteDraggedSegmentToCurve(pValue, segmentVec))
{
if (isPreview && pValue)
delete pValue;
return false;
}
if (!isPreview)
SyncControlPointsAndNotify(handleIndex);
EndDragEdit(pValue, isPreview, pListForPreview);
return true;
}
bool SplineDragPipeline::GetCurveForDragEdit(bool isPreview, CCurveEx*& pValue, int& handleIndex, CPointList* pListForPreview)
{
CCurveEx* pDocCurve = (CCurveEx*)m_pContext->GetDoc()->GetDraw()->GetAtValue(m_pContext->GetPos());
if (isPreview)
{
CCurveEx* pc = new CCurveEx;
*pc = *pDocCurve;
pValue = pc;
}
else
pValue = pDocCurve;
handleIndex = m_pContext->GetHandleIndex();
if (handleIndex < 0 || !m_pModel->IsValid())
{
if (isPreview && pListForPreview)
{
if (pValue)
{
pValue->GetPoint(*pListForPreview);
delete pValue;
}
pValue = nullptr;
}
return false;
}
return true;
}
bool SplineDragPipeline::GetDraggedSegmentAndAttachContext(std::vector<dfPoint>& segmentVec)
{
int handleIndex = m_pContext->GetHandleIndex();
if (handleIndex < 0 || !m_pModel->IsValid())
return false;
m_pModel->UpdateControlPoint(handleIndex, m_pDragState->worldLastPoint.x0, m_pDragState->worldLastPoint.y0);
const auto& renderPts = m_pModel->GetRenderPoints();
if (renderPts.empty())
return false;
m_pDragState->previewPoints.RemoveAll();
segmentVec.clear();
for (const auto& rp : renderPts)
{
m_pDragState->previewPoints.AddTail(rp.point);
segmentVec.push_back(rp.point);
}
return true;
}
bool SplineDragPipeline::WriteDraggedSegmentToCurve(CCurveEx* pValue, const std::vector<dfPoint>& segmentVec)
{
if (segmentVec.empty())
return false;
CPointList fullPointList;
for (const auto& p : segmentVec)
fullPointList.AddTail(p);
if (pValue->nPoint == 4)
pValue->nPoint = 3;
if (!pValue->bAutoLocation)
pValue->bAutoLocation = TRUE;
pValue->SetPoints(fullPointList, pValue->nPoint, pValue->bAutoLocation);
return true;
}
void SplineDragPipeline::SyncControlPointsAndNotify(int handleIndex)
{
(void)handleIndex;
m_pContext->WriteModelToDocCurve();
m_pContext->Invalidate();
}
void SplineDragPipeline::EndDragEdit(CCurveEx* pValue, bool isPreview, CPointList* pList)
{
if (isPreview && pValue && pList)
{
pValue->GetPoint(*pList);
delete pValue;
}
}