Управление коннекторами в презентациях с использованием C++
Коннектор PowerPoint — это специальная линия, которая соединяет два объекта и остаётся привязанной к объектам даже при их перемещении или изменении позиции на слайде.
Коннекторы обычно соединяются с точками соединения (зелёные точки), которые присутствуют на всех объектах по умолчанию. Точки соединения появляются, когда курсор подходит к ним.
Точки регулировки (оранжевые точки), которые существуют только у некоторых коннекторов, используются для изменения положения и формы коннекторов.
Типы коннекторов
В PowerPoint вы можете использовать прямые, сгибные (угловые) и кривые коннекторы.
Aspose.Slides предоставляет следующие коннекторы:
| Коннектор | Image | Количество точек регулировки |
|---|---|---|
ShapeType.Line |
![]() |
0 |
ShapeType.StraightConnector1 |
![]() |
0 |
ShapeType.BentConnector2 |
![]() |
0 |
ShapeType.BentConnector3 |
![]() |
1 |
ShapeType.BentConnector4 |
![]() |
2 |
ShapeType.BentConnector5 |
![]() |
3 |
ShapeType.CurvedConnector2 |
![]() |
0 |
ShapeType.CurvedConnector3 |
![]() |
1 |
ShapeType.CurvedConnector4 |
![]() |
2 |
ShapeType.CurvedConnector5 |
![]() |
3 |
Соединение фигур с помощью коннекторов
- Создайте экземпляр класса Presentation.
- Получите ссылку на слайд по его индексу.
- Добавьте два AutoShape на слайд, используя метод
AddAutoShapeобъектаShapes. - Добавьте коннектор методом
AddConnectorобъектаShapes, указав тип коннектора. - Соедините фигуры с помощью коннектора.
- Вызовите метод
Reroute, чтобы применить кратчайший путь соединения. - Сохраните презентацию.
Этот C++‑код показывает, как добавить коннектор (сгибной) между двумя фигурами (эллипсом и прямоугольником):
// Путь к каталогу документов.
const String outPath = u"../out/ConnectShapesUsingConnectors_out.pptx";
const String templatePath = u"../templates/ConnectorLineAngle.pptx";
// Загружает требуемую презентацию
SharedPtr<Presentation> pres = MakeObject<Presentation>();
// Получает первый слайд
SharedPtr<ISlide> slide = pres->get_Slides()->idx_get(0);
// Получает коллекцию фигур для конкретного слайда
SharedPtr<IShapeCollection> shapes = slide->get_Shapes();
// Добавляет автоконтур «Эллипс»
SharedPtr<IAutoShape> ellipse = slide->get_Shapes()->AddAutoShape(ShapeType::Ellipse, 0, 100, 100, 100);
// Добавляет автоконтур «Прямоугольник»
SharedPtr<IAutoShape> rect = slide->get_Shapes()->AddAutoShape(ShapeType::Rectangle, 100, 300, 100, 100);
// Добавляет фигуру‑коннектор в коллекцию фигур слайда
SharedPtr<IConnector> connector = shapes->AddConnector(ShapeType::BentConnector2, 0, 0, 10, 10);
// Соединяет фигуры при помощи коннектора
connector->set_StartShapeConnectedTo ( ellipse);
connector->set_EndShapeConnectedTo (rect);
// Вызывает Reroute, устанавливающий автоматический кратчайший путь между фигурами
connector->Reroute();
// Сохраняет презентацию
pres->Save(outPath, Aspose::Slides::Export::SaveFormat::Pptx);
NOTE
Методconnector->Reroute перестраивает коннектор и заставляет его принять самый короткий возможный путь между фигурами. Чтобы достичь цели, метод может изменить точки StartShapeConnectionSiteIndex и EndShapeConnectionSiteIndex.
Указание точки соединения
Если нужно, чтобы коннектор связывал две фигуры через конкретные точки на фигурах, укажите предпочитаемые точки соединения следующим образом:
- Создайте экземпляр класса Presentation.
- Получите ссылку на слайд по его индексу.
- Добавьте два AutoShape на слайд, используя метод
AddAutoShapeобъектаShapes. - Добавьте коннектор методом
AddConnectorобъектаShapes, указав тип коннектора. - Соедините фигуры с помощью коннектора.
- Установите предпочтительные точки соединения на фигурах.
- Сохраните презентацию.
Этот C++‑код демонстрирует операцию, в которой указывается предпочтительная точка соединения:
// Путь к каталогу документов.
const String outPath = u"../out/ConnectShapeUsingConnectionSite_out.pptx";
const String templatePath = u"../templates/ConnectorLineAngle.pptx";
// Загружает нужную презентацию
SharedPtr<Presentation> pres = MakeObject<Presentation>();
// Получает первый слайд
SharedPtr<ISlide> slide = pres->get_Slides()->idx_get(0);
// Получает коллекцию фигур для конкретного слайда
SharedPtr<IShapeCollection> shapes = slide->get_Shapes();
// Добавляет автоконтур Эллипс
SharedPtr<IAutoShape> ellipse = slide->get_Shapes()->AddAutoShape(ShapeType::Ellipse, 0, 100, 100, 100);
// Добавляет автоконтур Прямоугольник
SharedPtr<IAutoShape> rect = slide->get_Shapes()->AddAutoShape(ShapeType::Rectangle, 100, 200, 100, 100);
// Добавляет форму‑коннектор в коллекцию фигур слайда
SharedPtr<IConnector> connector = shapes->AddConnector(ShapeType::BentConnector3, 0, 0, 10, 10);
// Соединяет фигуры с помощью коннектора
connector->set_StartShapeConnectedTo(ellipse);
connector->set_EndShapeConnectedTo(rect);
// Устанавливает предпочтительный индекс точки соединения для фигуры Эллипс
int wantedIndex = 6;
// Проверяет, меньше ли предпочтительный индекс максимального количества точек соединения
if (ellipse->get_ConnectionSiteCount() > wantedIndex)
{
// Устанавливает предпочтительную точку соединения для автоконтурa Эллипс
connector->set_StartShapeConnectionSiteIndex ( wantedIndex);
}
// Сохраняет презентацию
pres->Save(outPath, Aspose::Slides::Export::SaveFormat::Pptx);
Регулировка точки коннектора
Вы можете изменять существующий коннектор через его точки регулировки. Только коннекторы с точками регулировки могут быть изменены таким способом. Смотрите таблицу в разделе Типы коннекторов
Простой пример
Рассмотрим случай, когда коннектор между двумя фигурами (A и B) проходит через третью фигуру (C):

Код:
auto pres = System::MakeObject<Presentation>();
auto slide = pres->get_Slides()->idx_get(0);
auto shapes = slide->get_Shapes();
auto shape = shapes->AddAutoShape(ShapeType::Rectangle, 300.0f, 150.0f, 150.0f, 75.0f);
auto shapeFrom = shapes->AddAutoShape(ShapeType::Rectangle, 500.0f, 400.0f, 100.0f, 50.0f);
auto shapeTo = shapes->AddAutoShape(ShapeType::Rectangle, 100.0f, 100.0f, 70.0f, 30.0f);
auto connector = shapes->AddConnector(ShapeType::BentConnector5, 20.0f, 20.0f, 400.0f, 300.0f);
auto lineFormat = connector->get_LineFormat();
lineFormat->set_EndArrowheadStyle(LineArrowheadStyle::Triangle);
auto lineFillFormat = lineFormat->get_FillFormat();
lineFillFormat->set_FillType(FillType::Solid);
lineFillFormat->get_SolidFillColor()->set_Color(System::Drawing::Color::get_Black());
connector->set_StartShapeConnectedTo(shapeFrom);
connector->set_EndShapeConnectedTo(shapeTo);
connector->set_StartShapeConnectionSiteIndex(2);
Чтобы обойти третью фигуру, можно сместить вертикальную линию коннектора влево:

auto adj2 = connector->get_Adjustments()->idx_get(1);
adj2->set_RawValue(adj2->get_RawValue() + 10000);
Сложные случаи
При более сложных регулировках необходимо учитывать следующее:
- Точка регулировки коннектора тесно связана с формулой, вычисляющей её положение. Поэтому изменение позиции точки может изменить форму коннектора.
- Точки регулировки находятся в строгом порядке в массиве. Они пронумерованы от начальной точки коннектора до конечной.
- Значения точек отражают процент от ширины/высоты фигуры коннектора.
- Фигура ограничена начальной и конечной точками коннектора, умноженными на 1000.
- Первая, вторая и третья точки определяют процент от ширины, процент от высоты и снова процент от ширины соответственно.
- При вычислении координат точек регулировки необходимо учитывать вращение коннектора и его отражение. Примечание: угол вращения для всех коннекторов, показанных в разделе Типы коннекторов, равен 0.
Случай 1
Рассмотрим случай, когда два текстовых фрейма соединены коннектором:

Код:
// Создаёт объект класса презентации, представляющий файл PPTX
auto pres = System::MakeObject<Presentation>();
// Получает первый слайд презентации
auto slide = pres->get_Slides()->idx_get(0);
// Получает фигуры с первого слайда
auto shapes = slide->get_Shapes();
// Добавляет фигуры, которые будут соединены коннектором
auto shapeFrom = shapes->AddAutoShape(ShapeType::Rectangle, 100.0f, 100.0f, 60.0f, 25.0f);
shapeFrom->get_TextFrame()->set_Text(u"From");
auto shapeTo = shapes->AddAutoShape(ShapeType::Rectangle, 500.0f, 100.0f, 60.0f, 25.0f);
shapeTo->get_TextFrame()->set_Text(u"To");
// Добавляет коннектор
auto connector = shapes->AddConnector(ShapeType::BentConnector4, 20.0f, 20.0f, 400.0f, 300.0f);
auto lineFormat = connector->get_LineFormat();
// Указывает направление коннектора
lineFormat->set_EndArrowheadStyle(LineArrowheadStyle::Triangle);
// Задает толщину линии коннектора
lineFormat->set_Width(3);
// Указывает цвет коннектора
auto lineFillFormat = lineFormat->get_FillFormat();
lineFillFormat->set_FillType(Aspose::Slides::FillType::Solid);
lineFillFormat->get_SolidFillColor()->set_Color(System::Drawing::Color::get_Crimson());
// Связывает фигуры с помощью коннектора
connector->set_StartShapeConnectedTo(shapeFrom);
connector->set_StartShapeConnectionSiteIndex(3);
connector->set_EndShapeConnectedTo(shapeTo);
connector->set_EndShapeConnectionSiteIndex(2);
// Получает точки регулировки коннектора
auto adjustments = connector->get_Adjustments();
auto adjValue_0 = adjustments->idx_get(0);
auto adjValue_1 = adjustments->idx_get(1);
Регулировка
Мы можем изменить значения точек регулировки коннектора, увеличив соответствующие проценты ширины и высоты на 20 % и 200 % соответственно:
// Изменяет значения точек регулировки
adjValue_0->set_RawValue(adjValue_0->get_RawValue() + 20000);
adjValue_1->set_RawValue(adjValue_1->get_RawValue() + 200000);
Результат:

Чтобы задать модель, позволяющую определить координаты и форму отдельных частей коннектора, создадим фигуру, соответствующую горизонтальному компоненту коннектора в точке connector.Adjustments[0]:
// Нарисовать вертикальный компонент коннектора
float x = connector->get_X() + connector->get_Width() * adjValue_0->get_RawValue() / 100000;
float y = connector->get_Y();
float height = connector->get_Height() * adjValue_1->get_RawValue() / 100000;
shapes->AddAutoShape(ShapeType::Rectangle, x, y, 0.0f, height);
Результат:

Случай 2
В Случае 1 мы продемонстрировали простую операцию регулировки коннектора на основе базовых принципов. В обычных ситуациях необходимо учитывать вращение коннектора и его отображение (которые задаются свойствами connector.Rotation, connector.Frame.FlipH и connector.Frame.FlipV). Сейчас покажем процесс.
Сначала добавим новый текстовый фрейм (To 1) на слайд (для соединения) и создадим новый (зелёный) коннектор, соединяющий его с уже созданными объектами.
// Создаёт новый объект привязки
auto shapeTo_1 = shapes->AddAutoShape(ShapeType::Rectangle, 100.0f, 400.0f, 60.0f, 25.0f);
shapeTo_1->get_TextFrame()->set_Text(u"To 1");
// Создаёт новый коннектор
connector = shapes->AddConnector(ShapeType::BentConnector4, 20.0f, 20.0f, 400.0f, 300.0f);
lineFormat->set_EndArrowheadStyle(LineArrowheadStyle::Triangle);
lineFormat->set_Width(3);
lineFillFormat->set_FillType(Aspose::Slides::FillType::Solid);
lineFillFormat->get_SolidFillColor()->set_Color(System::Drawing::Color::get_MediumAquamarine());
// Соединяет объекты с помощью только что созданного коннектора
connector->set_StartShapeConnectedTo(shapeFrom);
connector->set_StartShapeConnectionSiteIndex(2);
connector->set_EndShapeConnectedTo(shapeTo_1);
connector->set_EndShapeConnectionSiteIndex(3);
// Получает точки регулировки коннектора
adjValue_0 = adjustments->idx_get(0);
adjValue_1 = adjustments->idx_get(1);
// Изменяет значения точек регулировки
adjValue_0->set_RawValue(adjValue_0->get_RawValue() + 20000);
adjValue_1->set_RawValue(adjValue_1->get_RawValue() + 200000);
Результат:

Затем создадим фигуру, соответствующую горизонтальному компоненту коннектора, проходящего через новую точку регулировки connector.Adjustments[0]. Используем значения из данных коннектора connector.Rotation, connector.Frame.FlipH и connector.Frame.FlipV и применим известную формулу преобразования координат при вращении вокруг точки x₀:
X = (x — x0) * cos(alpha) — (y — y0) * sin(alpha) + x0;
Y = (x — x0) * sin(alpha) + (y — y0) * cos(alpha) + y0;
В нашем случае угол вращения объекта составляет 90 градусов, а коннектор отображается вертикально, поэтому соответствующий код выглядит так:
Результат:

Мы продемонстрировали расчёты, связанные с простыми и сложными точками регулировки (точки с углами вращения). Полученные знания позволяют создать собственную модель (или написать код) для получения объекта GraphicsPath или даже установки значений точек регулировки коннектора на основе конкретных координат слайда.
Определение угла линии коннектора
- Создайте экземпляр класса Presentation.
- Получите ссылку на слайд по его индексу.
- Доступ к фигуре линии коннектора.
- Используйте ширину, высоту, высоту и ширину рамки фигуры для вычисления угла.
Этот C++‑код демонстрирует операцию, в которой вычисляется угол линии коннектора:
void ConnectorLineAngle()
{
// Путь к каталогу документов.
const String outPath = u"../out/ConnectorLineAngle_out.pptx";
const String templatePath = u"../templates/ConnectorLineAngle.pptx";
// Загружает требуемую презентацию
SharedPtr<Presentation> pres = MakeObject<Presentation>(templatePath);
// Получает первый слайд
SharedPtr<ISlide> slide = pres->get_Slides()->idx_get(0);
for (int i = 0; i < slide->get_Shapes()->get_Count(); i++)
{
double dir = 0.0;
// Получает коллекцию фигур со слайдов
System::SharedPtr<IShape> shape = slide->get_Shapes()->idx_get(i);
if (System::ObjectExt::Is<AutoShape>(shape))
{
SharedPtr<AutoShape> aShape = ExplicitCast<Aspose::Slides::AutoShape>(shape);
if (aShape->get_ShapeType() == ShapeType::Line)
{
// dir = getDirection(aShape->get_Width(), aShape->get_Height(), Convert::ToBoolean(aShape->get_Frame()->get_FlipH()), Convert::ToBoolean(aShape->get_Frame()->get_FlipV()));
dir = getDirection(aShape->get_Width(), aShape->get_Height(), aShape->get_Frame()->get_FlipH(), aShape->get_Frame()->get_FlipV());
}
}
else if (System::ObjectExt::Is<Connector>(shape))
{
SharedPtr<Connector> aShape = ExplicitCast<Aspose::Slides::Connector>(shape);
// dir = getDirection(aShape->get_Width(), aShape->get_Height(), Convert::ToBoolean(aShape->get_Frame()->get_FlipH()), Convert::ToBoolean(aShape->get_Frame()->get_FlipV()));
dir = getDirection(aShape->get_Width(), aShape->get_Height(), aShape->get_Frame()->get_FlipH(),aShape->get_Frame()->get_FlipV());
}
Console::WriteLine(dir);
}
}
//double ConnectorLineAngle::getDirection(float w, float h, NullableBool flipH, NullableBool flipV)
double getDirection(float w, float h, Aspose::Slides::NullableBool flipH, Aspose::Slides::NullableBool flipV)
{
float endLineX = w;
if (flipH == NullableBool::True)
endLineX= endLineX * -1;
else
endLineX=endLineX * 1;
//float endLineX = w * (flipH ? -1 : 1);
float endLineY = h;
if (flipV == NullableBool::True)
endLineY = endLineY * -1;
else
endLineY = endLineY * 1;
// float endLineY = h * (flipV ? -1 : 1);
float endYAxisX = 0;
float endYAxisY = h;
double angle = (Math::Atan2(endYAxisY, endYAxisX) - Math::Atan2(endLineY, endLineX));
if (angle < 0) angle += 2 * Math::PI;
return angle * 180.0 / Math::PI;
}
FAQ
Как определить, можно ли «приклеить» коннектор к конкретной фигуре?
Проверьте, предоставляет ли фигура connection sites. Если их нет или количество равно нулю, прикрепление недоступно; в этом случае используйте свободные концы и позиционируйте их вручную. Рекомендуется проверять количество сайтов перед привязкой.
Что происходит с коннектором, если я удаляю одну из связанных фигур?
Его концы будут отсоединены; коннектор останется на слайде как обычная линия со свободным началом/концом. Вы можете удалить его или переназначить соединения и, при необходимости, reroute.
Сохраняются ли привязки коннектора при копировании слайда в другую презентацию?
Как правило, да, при условии, что связанные фигуры также копируются. Если слайд вставляется в другой файл без связанных фигур, концы становятся свободными, и их потребуется заново привязать.









