Personalizza le forme di presentazione in C++

Panoramica

Questo articolo spiega come personalizzare le forme delle presentazioni in Aspose.Slides modificando la geometria della forma tramite punti di modifica e percorsi geometrici. Mostra come utilizzare GeometryPath e IGeometryPath per modificare forme esistenti, eseguire operazioni di modifica di base del percorso, aggiungere o rimuovere punti e applicare la geometria aggiornata a una forma.

Modifica una forma usando i punti di modifica

Considera un quadrato. In PowerPoint, usando edit points, puoi

  • spostare l’angolo del quadrato verso l’interno o l’esterno
  • specificare la curvatura di un angolo o di un punto
  • aggiungere nuovi punti al quadrato
  • manipolare i punti del quadrato, ecc.

In sostanza, puoi eseguire le operazioni descritte su qualsiasi forma. Usando i punti di modifica, puoi modificare una forma o crearne una nuova a partire da una forma esistente.

Suggerimenti per la modifica delle forme

overview_image

Prima di iniziare a modificare le forme di PowerPoint tramite i punti di modifica, potresti voler considerare questi aspetti delle forme:

  • Una forma (o il suo percorso) può essere chiusa o aperta.
  • Quando una forma è chiusa, non ha un punto di inizio o di fine. Quando una forma è aperta, ha un inizio e una fine.
  • Tutte le forme sono composte da almeno 2 punti di ancoraggio collegati tra loro da linee.
  • Una linea è o dritta o curva. I punti di ancoraggio determinano la natura della linea.
  • I punti di ancoraggio esistono come punti d’angolo, punti dritti o punti lisci:
    • Un punto d’angolo è un punto in cui 2 linee dritte si uniscono formando un angolo.
    • Un punto liscio è un punto in cui 2 maniglie esistono su una linea retta e i segmenti della linea si collegano con una curva fluida. In questo caso, tutte le maniglie sono distanziate dal punto di ancoraggio di pari distanza.
    • Un punto dritto è un punto in cui 2 maniglie esistono su una linea retta e i segmenti della linea si collegano con una curva fluida. In questo caso, le maniglie non devono essere distanziate dal punto di ancoraggio di pari distanza.
  • Spostando o modificando i punti di ancoraggio (che cambiano l’angolo delle linee), è possibile alterare l’aspetto di una forma.

Per modificare le forme di PowerPoint tramite i punti di modifica, Aspose.Slides fornisce la classe GeometryPath e l’interfaccia IGeometryPath.

Operazioni di modifica semplici

Questo codice C++ mostra come

Aggiungi una linea alla fine di un percorso

void LineTo(PointF point);
void LineTo(float x, float y);

Aggiungi una linea in una posizione specifica su un percorso:

void LineTo(PointF point, uint32_t index);
void LineTo(float x, float y, uint32_t index);

Aggiungi una curva Bezier cubica alla fine di un percorso:

void CubicBezierTo(PointF point1, PointF point2, PointF point3);
void CubicBezierTo(float x1, float y1, float x2, float y2, float x3, float y3);

Aggiungi una curva Bezier cubica nella posizione specificata su un percorso:

void CubicBezierTo(PointF point1, PointF point2, PointF point3, uint32_t index);
void CubicBezierTo(float x1, float y1, float x2, float y2, float x3, float y3, uint32_t index);

Aggiungi una curva Bezier quadratica alla fine di un percorso:

void QuadraticBezierTo(PointF point1, PointF point2);
void QuadraticBezierTo(float x1, float y1, float x2, float y2);

Aggiungi una curva Bezier quadratica nella posizione specificata su un percorso:

void QuadraticBezierTo(PointF point1, PointF point2, uint32_t index);
void QuadraticBezierTo(float x1, float y1, float x2, float y2, uint32_t index);

Allega un arco dato a un percorso:

void ArcTo(float width, float heigth, float startAngle, float sweepAngle);

Chiudi la figura corrente di un percorso:

void CloseFigure();

Imposta la posizione per il punto successivo:

void MoveTo(PointF point);
void MoveTo(float x, float y);

Rimuovi il segmento di percorso all’indice indicato:

void RemoveAt(int32_t index);

Aggiungi punti personalizzati a una forma

  1. Crea un’istanza della classe GeometryShape e imposta il tipo ShapeType.Rectangle.
  2. Ottieni un’istanza della classe GeometryPath dalla forma.
  3. Aggiungi un nuovo punto tra i due punti superiori del percorso.
  4. Aggiungi un nuovo punto tra i due punti inferiori del percorso.
  5. Applica il percorso alla forma.

Questo codice C++ mostra come aggiungere punti personalizzati a una forma:

SharedPtr<Presentation> pres = System::MakeObject<Presentation>();

SharedPtr<IShapeCollection> shapes = pres->get_Slides()->idx_get(0)->get_Shapes();
SharedPtr<GeometryShape> shape = System::ExplicitCast<GeometryShape>(shapes->AddAutoShape(ShapeType::Rectangle, 100.0f, 100.0f, 200.0f, 100.0f));

SharedPtr<IGeometryPath> geometryPath = shape->GetGeometryPaths()->idx_get(0);

geometryPath->LineTo(100.0f, 50.0f, 1);
geometryPath->LineTo(100.0f, 50.0f, 4);
shape->SetGeometryPath(geometryPath);

example1_image

Rimuovi punti da una forma

  1. Crea un’istanza della classe GeometryShape e imposta il tipo ShapeType.Heart.
  2. Ottieni un’istanza della classe GeometryPath dalla forma.
  3. Rimuovi il segmento del percorso.
  4. Applica il percorso alla forma.

Questo codice C++ mostra come rimuovere punti da una forma:

SharedPtr<Presentation> pres = System::MakeObject<Presentation>();

SharedPtr<IShapeCollection> shapes = pres->get_Slides()->idx_get(0)->get_Shapes();
SharedPtr<GeometryShape> shape = System::ExplicitCast<GeometryShape>(shapes->AddAutoShape(ShapeType::Heart, 100.0f, 100.0f, 300.0f, 300.0f));

SharedPtr<IGeometryPath> path = shape->GetGeometryPaths()->idx_get(0);
path->RemoveAt(2);
shape->SetGeometryPath(path);

example2_image

Crea una forma personalizzata

  1. Calcola i punti per la forma.
  2. Crea un’istanza della classe GeometryPath.
  3. Riempie il percorso con i punti.
  4. Crea un’istanza della classe GeometryShape.
  5. Applica il percorso alla forma.

Questo codice C++ mostra come creare una forma personalizzata:

SharedPtr<List<PointF>> points = System::MakeObject<List<PointF>>();

float R = 100.0f, r = 50.0f;
int32_t step = 72;

for (int32_t angle = -90; angle < 270; angle += step)
{
    double radians = angle * (Math::PI / 180.f);
    double x = outerRadius * Math::Cos(radians);
    double y = outerRadius * Math::Sin(radians);
    points->Add(PointF((float)x + outerRadius, (float)y + outerRadius));

    radians = Math::PI * (angle + step / 2) / 180.0;
    x = innerRadiusr * Math::Cos(radians);
    y = innerRadiusr * Math::Sin(radians);
    points->Add(PointF((float)x + outerRadius, (float)y + outerRadius));
}

SharedPtr<GeometryPath> starPath = System::MakeObject<GeometryPath>();
starPath->MoveTo(points->idx_get(0));

for (int32_t i = 1; i < points->get_Count(); i++)
{
    starPath->LineTo(points->idx_get(i));
}

starPath->CloseFigure();

SharedPtr<Presentation> pres = System::MakeObject<Presentation>();

SharedPtr<IShapeCollection> shapes = pres->get_Slides()->idx_get(0)->get_Shapes();
SharedPtr<GeometryShape> shape = System::ExplicitCast<GeometryShape>(shapes->AddAutoShape(ShapeType::Rectangle, 100.0f, 100.0f, R * 2, R * 2));

shape->SetGeometryPath(starPath);

example3_image

Crea una forma composita personalizzata

  1. Crea un’istanza della classe GeometryShape.
  2. Crea una prima istanza della classe GeometryPath.
  3. Crea una seconda istanza della classe GeometryPath.
  4. Applica i percorsi alla forma.

Questo codice C++ mostra come creare una forma composita personalizzata:

SharedPtr<Presentation> pres = System::MakeObject<Presentation>();

SharedPtr<IShapeCollection> shapes = pres->get_Slides()->idx_get(0)->get_Shapes();
SharedPtr<GeometryShape> shape = System::ExplicitCast<GeometryShape>(shapes->AddAutoShape(ShapeType::Rectangle, 100.0f, 100.0f, 200.0f, 100.0f));

SharedPtr<IGeometryPath> geometryPath0 = System::MakeObject<GeometryPath>();
geometryPath0->MoveTo(0.0f, 0.0f);
geometryPath0->LineTo(shape->get_Width(), 0.0f);
geometryPath0->LineTo(shape->get_Width(), shape->get_Height() / 3);
geometryPath0->LineTo(0.0f, shape->get_Height() / 3);
geometryPath0->CloseFigure();

SharedPtr<IGeometryPath> geometryPath1 = System::MakeObject<GeometryPath>();
geometryPath1->MoveTo(0.0f, shape->get_Height() / 3 * 2);
geometryPath1->LineTo(shape->get_Width(), shape->get_Height() / 3 * 2);
geometryPath1->LineTo(shape->get_Width(), shape->get_Height());
geometryPath1->LineTo(0.0f, shape->get_Height());
geometryPath1->CloseFigure();

shape->SetGeometryPaths(System::MakeArray<SharedPtr<IGeometryPath>>({ geometryPath0, geometryPath1 }));

example4_image

Crea una forma personalizzata con angoli curvi

Questo codice C++ mostra come creare una forma personalizzata con angoli curvi (verso l’interno);

float shapeX = 20.f;
float shapeY = 20.f;
float shapeWidth = 300.f;
float shapeHeight = 200.f;

float leftTopSize = 50.f;
float rightTopSize = 20.f;
float rightBottomSize = 40.f;
float leftBottomSize = 10.f;

auto presentation = System::MakeObject<Presentation>();

auto childShape = presentation->get_Slides()->idx_get(0)->get_Shapes()->AddAutoShape(ShapeType::Custom, shapeX, shapeY, shapeWidth, shapeHeight);

auto geometryPath = System::MakeObject<GeometryPath>();

PointF point1(leftTopSize, 0.0f);
PointF point2(shapeWidth - rightTopSize, 0.0f);
PointF point3(shapeWidth, shapeHeight - rightBottomSize);
PointF point4(leftBottomSize, shapeHeight);
PointF point5(0.0f, leftTopSize);

geometryPath->MoveTo(point1);
geometryPath->LineTo(point2);
geometryPath->ArcTo(rightTopSize, rightTopSize, 180.0f, -90.0f);
geometryPath->LineTo(point3);
geometryPath->ArcTo(rightBottomSize, rightBottomSize, -90.0f, -90.0f);
geometryPath->LineTo(point4);
geometryPath->ArcTo(leftBottomSize, leftBottomSize, 0.0f, -90.0f);
geometryPath->LineTo(point5);
geometryPath->ArcTo(leftTopSize, leftTopSize, 90.0f, -90.0f);

geometryPath->CloseFigure();

childShape->SetGeometryPath(geometryPath);

presentation->Save(u"output.pptx", SaveFormat::Pptx);

Scopri se la geometria di una forma è chiusa

Una forma chiusa è definita come quella i cui lati si collegano tutti, formando un unico contorno senza interruzioni. Tale forma può essere una figura geometrica semplice o un contorno personalizzato complesso. L’esempio di codice seguente mostra come verificare se la geometria di una forma è chiusa:

bool IsGeometryClosed(SharedPtr<IGeometryShape> geometryShape)
{
    bool isClosed = false;

    for (auto&& geometryPath : geometryShape->GetGeometryPaths())
    {
        auto dataLength = geometryPath->get_PathData()->get_Length();
        if (dataLength == 0)
            continue;

        auto lastSegment = geometryPath->get_PathData()[dataLength - 1];
        isClosed = lastSegment->get_PathCommand() == PathCommandType::Close;

        if (!isClosed)
            return false;
    }

    return isClosed;
}

Converti GeometryPath in GraphicsPath

  1. Crea un’istanza della classe GeometryShape.
  2. Crea un’istanza della classe GraphicsPath del namespace System.Drawing.Drawing2D.
  3. Converti l’istanza di GraphicsPath nell’istanza di GeometryPath usando ShapeUtil.
  4. Applica i percorsi alla forma.

Questo codice C++—un’implementazione dei passaggi sopra—dimostra il processo di conversione da GeometryPath a GraphicsPath:

SharedPtr<Presentation> pres = System::MakeObject<Presentation>();

SharedPtr<IShapeCollection> shapes = pres->get_Slides()->idx_get(0)->get_Shapes();
SharedPtr<GeometryShape> shape = System::ExplicitCast<GeometryShape>(shapes->AddAutoShape(ShapeType::Rectangle, 100.0f, 100.0f, 300.0f, 100.0f));

SharedPtr<IGeometryPath> originalPath = shape->GetGeometryPaths()->idx_get(0);
originalPath->set_FillMode(PathFillModeType::None);

SharedPtr<Drawing2D::GraphicsPath> graphicsPath = System::MakeObject<Drawing2D::GraphicsPath>();
graphicsPath->AddString(u"Text in shape", System::MakeObject<FontFamily>(u"Arial"), 1, 40.0f, PointF(10.0f, 10.0f), StringFormat::get_GenericDefault());

SharedPtr<IGeometryPath> textPath = ShapeUtil::GraphicsPathToGeometryPath(graphicsPath);
textPath->set_FillMode(PathFillModeType::Normal);

shape->SetGeometryPaths(System::MakeArray<SharedPtr<IGeometryPath>>({ originalPath, textPath }));

example5_image

FAQ

Cosa accadrà al riempimento e al contorno dopo aver sostituito la geometria?

Lo stile rimane associato alla forma; cambia solo il contorno. Il riempimento e il contorno vengono applicati automaticamente alla nuova geometria.

Come ruoto correttamente una forma personalizzata insieme alla sua geometria?

Usa la proprietà di rotation della forma; la geometria ruota con la forma perché è vincolata al sistema di coordinate della forma stessa.

Posso convertire una forma personalizzata in un’immagine per “bloccare” il risultato?

Sì. Esporta l’slide o la shape desiderata in un formato raster; questo semplifica ulteriori lavori con geometrie complesse.