Разрезает объекты слоя заданным контуром.
Visual Basic:
Function SplitByPolygon(polygon As Contour, Options As Long) As Long
polygon - контур, пересекаемый со слоем.
Options - параметр, определяющий, какие объекты слоя участвуют в операции:
0 - все объкеты слоя.
1 - только объекты мишени (TargetSelection).
2 - только выделенные объекты (Selection).
- Объекты, имеющие область пересечения с контуром, разделяются на два объекта, один из которых совпадает с областью пересечения, второй содержит оставшуюся часть. Один из образованных объектов наследует ID разрезаемого объекта. Второй объект получает новый уникальный ID.
- Объекты, целиком попавшие в контур или не имеющие пересечения с контуром, остаются без изменения.
Метод возвращает 0 в любом случае - и когда объекты разрезаны, и когда контур их не задел, поэтому судить о результате нужно по самим объектам.
При разрезе одна часть объекта остается под прежним ключом, а другая получает новый ID: объектов в слое становится на один больше на каждый разрезанный объект, наибольший ID растет. Контур, не задевший объектов, ничего не меняет.
Линейные объекты метод тоже режет: части линии снаружи контура остаются за прежним ключом - объект становится многочастным, и PolyLine показывает только первую часть, - а часть внутри контура получает новый ключ.
С объектом, который контур накрыл целиком, поведение не всегда такое, как сказано в примечании выше: обычно объект остается нетронутым, но бывает, что он пропадает из слоя - объектов становится меньше, а прежний ключ перестает существовать. Такие объекты надежнее отсекать заранее, например методом IntersectByContour с критерием 1.
Пример добавляет в слой свой квадрат за краем данных, разрезает его контуром пополам и убирает за собой.
Visual Basic:
Sub Layer_SplitByPolygon 'Берем активный слой карты Set L = Zulu.ActiveMapDoc.Layers.Active Set R = L.GetBoundsRectangle nBefore = L.GetLargestID X0 = R.Xmax + 500 Y0 = R.Ymin 'Свой квадрат 200x200 за краем данных слоя Set C = CreateObject("ZuluLib.Contour") C.AddPoint X0, Y0 C.AddPoint X0 + 200, Y0 C.AddPoint X0 + 200, Y0 + 200 C.AddPoint X0, Y0 + 200 Key = L.AddContour(C, CreateObject("ZuluLib.ElemStyle"), -1, -1) S = "Площадь была: " & L.Elements.Item(Key).Area & ", объектов: " & L.ElementKeys.Count 'Режем его контуром, накрывающим половину Set C2 = CreateObject("ZuluLib.Contour") C2.AddPoint X0 + 100, Y0 - 50 C2.AddPoint X0 + 300, Y0 - 50 C2.AddPoint X0 + 300, Y0 + 250 C2.AddPoint X0 + 100, Y0 + 250 L.SplitByPolygon C2, 0 S = S & vbCrLf & "стала: " & L.Elements.Item(Key).Area & ", объектов: " & L.ElementKeys.Count 'Убираем за собой все, что добавили Set Keys = L.ElementKeys For i = Keys.Count To 1 Step -1 If Keys.Item(i) > nBefore Then L.DeleteElement Keys.Item(i) Next MsgBox S End SubPython:
import zulu def Macro_Layer_SplitByPolygon(): # Берем активный слой карты L = zulu.App.ActiveMapDoc.Layers.Active R = L.GetBoundsRectangle() n_before = L.GetLargestID() x0 = R.Xmax + 500 y0 = R.Ymin # Свой квадрат 200x200 за краем данных слоя c = zulu.Contour() c.AddPoint(x0, y0) c.AddPoint(x0 + 200, y0) c.AddPoint(x0 + 200, y0 + 200) c.AddPoint(x0, y0 + 200) key = L.AddContour(c, zulu.ElemStyle(), -1, -1) print("Площадь была:", L.Elements.Item(key).Area, ", объектов:", L.ElementKeys.Count) # Режем его контуром, накрывающим половину c2 = zulu.Contour() c2.AddPoint(x0 + 100, y0 - 50) c2.AddPoint(x0 + 300, y0 - 50) c2.AddPoint(x0 + 300, y0 + 250) c2.AddPoint(x0 + 100, y0 + 250) L.SplitByPolygon(c2, 0) print("стала:", L.Elements.Item(key).Area, ", объектов:", L.ElementKeys.Count) # Убираем за собой все, что добавили keys = L.ElementKeys for i in range(keys.Count, 0, -1): if keys.Item(i) > n_before: L.DeleteElement(keys.Item(i))