VTK  9.7.20260913
vtkCellArray.h
Go to the documentation of this file.
1// SPDX-FileCopyrightText: Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
2// SPDX-License-Identifier: BSD-3-Clause
242
243#ifndef vtkCellArray_h
244#define vtkCellArray_h
245
246#include "vtkAbstractCellArray.h"
247#include "vtkCommonDataModelModule.h" // For export macro
248#include "vtkWrappingHints.h" // For VTK_MARSHALMANUAL
249
250#include "vtkAOSDataArrayTemplate.h" // Needed for inline methods
251#include "vtkAffineArray.h" // Needed for inline methods
252#include "vtkCell.h" // Needed for inline methods
253#include "vtkDataArrayAccessor.h" // Needed for inline methods
254#include "vtkDataArrayRange.h" // Needed for inline methods
255#include "vtkFeatures.h" // for VTK_USE_MEMKIND
256#include "vtkSmartPointer.h" // For vtkSmartPointer
257#include "vtkTypeInt32Array.h" // Needed for inline methods
258#include "vtkTypeInt64Array.h" // Needed for inline methods
259#include "vtkTypeList.h" // Needed for ArrayList definition
260
261#include <cassert> // Needed for assert
262#include <initializer_list> // Needed for API
263#include <type_traits> // Needed for std::is_same
264#include <utility> // Needed for std::forward
265
286#define VTK_CELL_ARRAY_V2
287
288VTK_ABI_NAMESPACE_BEGIN
290class vtkIdTypeArray;
291
292class VTKCOMMONDATAMODEL_EXPORT VTK_MARSHALMANUAL vtkCellArray : public vtkAbstractCellArray
293{
294public:
299
301
305 static vtkCellArray* New();
307 void PrintSelf(ostream& os, vtkIndent indent) override;
308 void PrintDebug(ostream& os);
310
320 bool AllocateEstimate(vtkIdType numCells, vtkIdType maxCellSize)
321 {
322 return this->AllocateExact(numCells, numCells * maxCellSize);
323 }
324
334 bool AllocateExact(vtkIdType numCells, vtkIdType connectivitySize);
335
346 {
347 return this->AllocateExact(other->GetNumberOfCells(), other->GetNumberOfConnectivityIds());
348 }
349
359 bool ResizeExact(vtkIdType numCells, vtkIdType connectivitySize);
360
364 void Initialize() override;
365
369 void Reset();
370
376 void Squeeze();
377
388 bool IsValid();
389
393 vtkIdType GetNumberOfCells() const override { return this->Offsets->GetNumberOfValues() - 1; }
394
399 vtkIdType GetNumberOfOffsets() const override { return this->Offsets->GetNumberOfValues(); }
400
405 {
406 return static_cast<vtkIdType>(this->Offsets->GetComponent(cellId, 0));
407 }
408
412 void SetOffset(vtkIdType cellId, vtkIdType offset)
413 {
414 this->Offsets->SetComponent(cellId, 0, static_cast<double>(offset));
415 }
416
421 {
422 return this->Connectivity->GetNumberOfValues();
423 }
424
431
433
446 void SetData(AOSArray32*, AOSArray32* connectivity);
447 void SetData(AOSArray64*, AOSArray64* connectivity);
448 void SetData(AffineArray32*, AOSArray32* connectivity);
449 void SetData(AffineArray64*, AOSArray64* connectivity);
451
466 bool SetData(vtkDataArray* offsets, vtkDataArray* connectivity);
467
485 bool SetData(vtkIdType cellSize, vtkDataArray* connectivity);
486
495
499 StorageTypes GetStorageType() const noexcept { return this->StorageType; }
500
504 bool IsStorage64Bit() const { return this->StorageType == StorageTypes::Int64; }
505
509 bool IsStorage32Bit() const { return this->StorageType == StorageTypes::Int32; }
510
515
520
525 {
526 return this->IsStorageFixedSize32Bit() || this->IsStorageFixedSize64Bit();
527 }
528
532 bool IsStorageGeneric() const { return this->StorageType == StorageTypes::Generic; }
533
540 bool IsStorageShareable() const override
541 {
542 switch (this->StorageType)
543 {
546 return std::is_same_v<vtkTypeInt32, vtkIdType>;
549 return std::is_same_v<vtkTypeInt64, vtkIdType>;
551 default:
552 return false;
553 }
554 }
555
557
571
573
587 {
588 switch (type)
589 {
591 return this->CanConvertTo32BitStorage();
593 return this->CanConvertTo64BitStorage();
599 default:
600 return true;
601 }
602 }
603
604
606
628 {
629 switch (type)
630 {
632 return this->ConvertTo32BitStorage();
634 return this->ConvertTo64BitStorage();
636 return this->ConvertToFixedSize32BitStorage();
638 return this->ConvertToFixedSize64BitStorage();
640 default:
641 return true;
642 }
643 }
644
645
647
666 bool EnsureStorageForCellSize(vtkIdType cellSize);
667
672 vtkDataArray* GetOffsetsArray() const { return this->Offsets; }
683
684
686
700
701
710 vtkIdType IsHomogeneous() const override;
711
721 void InitTraversal();
722
737 int GetNextCell(vtkIdType& npts, vtkIdType const*& pts) VTK_SIZEHINT(pts, npts);
738
749 int GetNextCell(vtkIdList* pts);
750
761 inline void GetCellAtId(vtkIdType cellId, vtkIdType& cellSize, vtkIdType const*& cellPoints,
762 vtkIdList* ptIds) VTK_SIZEHINT(cellPoints, cellSize)
763 VTK_EXPECTS(0 <= cellId && cellId < GetNumberOfCells()) override;
764
770 inline void GetCellAtId(vtkIdType cellId, vtkIdList* pts)
771 VTK_EXPECTS(0 <= cellId && cellId < GetNumberOfCells()) override;
772
780 inline void GetCellAtId(vtkIdType cellId, vtkIdType& cellSize, vtkIdType* cellPoints)
781 VTK_SIZEHINT(cellPoints, cellSize)
782 VTK_EXPECTS(0 <= cellId && cellId < GetNumberOfCells()) override;
783
787 vtkIdType GetCellPointAtId(vtkIdType cellId, vtkIdType cellPointIndex) const
788 VTK_EXPECTS(0 <= cellId && cellId < GetNumberOfCells())
789 VTK_EXPECTS(0 <= cellPointIndex && cellPointIndex < this->GetCellSize(cellId));
790
794 vtkIdType GetCellSize(vtkIdType cellId) const override;
795
799 inline vtkIdType InsertNextCell(vtkCell* cell);
800
805 inline vtkIdType InsertNextCell(vtkIdType npts, const vtkIdType* pts) VTK_SIZEHINT(pts, npts);
806
812
820 vtkIdType InsertNextCell(const std::initializer_list<vtkIdType>& cell)
821 {
822 return this->InsertNextCell(static_cast<vtkIdType>(cell.size()), cell.begin());
823 }
824
831 inline vtkIdType InsertNextCell(int npts);
832
837 void InsertCellPoint(vtkIdType id);
838
843 void UpdateCellCount(int npts);
844
846
855
859 void ReverseCellAtId(vtkIdType cellId) VTK_EXPECTS(0 <= cellId && cellId < GetNumberOfCells());
860
862
870 void ReplaceCellAtId(vtkIdType cellId, vtkIdType cellSize, const vtkIdType* cellPoints)
871 VTK_EXPECTS(0 <= cellId && cellId < GetNumberOfCells()) VTK_SIZEHINT(cellPoints, cellSize);
873
881 void ReplaceCellPointAtId(vtkIdType cellId, vtkIdType cellPointIndex, vtkIdType newPointId);
882
890 void ReplaceCellAtId(vtkIdType cellId, const std::initializer_list<vtkIdType>& cell)
891 {
892 this->ReplaceCellAtId(cellId, static_cast<vtkIdType>(cell.size()), cell.begin());
893 }
894
899 int GetMaxCellSize() override;
900
904 void DeepCopy(vtkAbstractCellArray* ca) override;
905
910
914 void Append(vtkCellArray* src, vtkIdType pointOffset = 0);
915
927
929
943 bool ImportLegacyFormat(const vtkIdType* data, vtkIdType len) VTK_SIZEHINT(data, len);
945
947
960 bool AppendLegacyFormat(vtkIdTypeArray* data, vtkIdType ptOffset = 0);
961 bool AppendLegacyFormat(const vtkIdType* data, vtkIdType len, vtkIdType ptOffset = 0)
962 VTK_SIZEHINT(data, len);
964
973 unsigned long GetActualMemorySize() const;
974
975 // The following code is used to support
976
977 // The wrappers get understandably confused by some of the template code below
978#ifndef __VTK_WRAP__
979 /*
980 * Utilities class that every dispatch functor used with Dispatch() must inherit
981 * or optionally use its static methods.
982 */
984 {
985 template <class ArrayT>
987
988 template <class OffsetsT>
989 vtkIdType GetNumberOfCells(OffsetsT* offsets)
990 {
991 return offsets->GetNumberOfValues() - 1;
992 }
993
994 template <class ArrayT>
995 static decltype(vtk::DataArrayValueRange<1, vtkIdType>(std::declval<ArrayT>())) GetRange(
996 ArrayT* array)
997 {
999 }
1000
1001 template <class OffsetsT>
1002 static vtkIdType GetBeginOffset(OffsetsT* offsets, vtkIdType cellId)
1003 {
1004 return static_cast<vtkIdType>(GetRange(offsets)[cellId]);
1005 }
1006
1007 template <class OffsetsT>
1008 static vtkIdType GetEndOffset(OffsetsT* offsets, vtkIdType cellId)
1009 {
1010 return static_cast<vtkIdType>(GetRange(offsets)[cellId + 1]);
1011 }
1012
1013 template <class OffsetsT>
1014 static vtkIdType GetCellSize(OffsetsT* offsets, vtkIdType cellId)
1015 {
1016 auto offsetsRange = GetRange(offsets);
1017 return static_cast<vtkIdType>(offsetsRange[cellId + 1] - offsetsRange[cellId]);
1018 }
1019
1020 template <class OffsetsT, class ConnectivityT>
1021 static decltype(vtk::DataArrayValueRange<1, vtkIdType>(std::declval<ConnectivityT>()))
1022 GetCellRange(OffsetsT* offsets, ConnectivityT* conn, vtkIdType cellId)
1023 {
1024 auto offsetsRange = GetRange(offsets);
1026 conn, offsetsRange[cellId], offsetsRange[cellId + 1]);
1027 }
1028 };
1029
1030private: // Helpers that allow Dispatch to return a value:
1031 // All storage types must agree on the returned type; the 32-bit AOS
1032 // instantiation is used to deduce it.
1033 template <typename Functor, typename... Args>
1034 using GetDispatchReturnType = decltype(std::declval<Functor>()(
1035 std::declval<AOSArray32*>(), std::declval<AOSArray32*>(), std::declval<Args>()...));
1036
1037 template <typename Functor, typename... Args>
1038 struct DispatchReturnsVoid : std::is_same<GetDispatchReturnType<Functor, Args...>, void>
1039 {
1040 };
1041
1042public:
1044
1112 template <typename Functor, typename... Args,
1113 typename = typename std::enable_if<DispatchReturnsVoid<Functor, Args...>::value>::type>
1114 void Dispatch(Functor&& functor, Args&&... args)
1115 {
1116 switch (this->StorageType)
1117 {
1119 functor(static_cast<AOSArray32*>(this->Offsets.Get()),
1120 static_cast<AOSArray32*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1121 break;
1123 functor(static_cast<AOSArray64*>(this->Offsets.Get()),
1124 static_cast<AOSArray64*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1125 break;
1127 functor(static_cast<AffineArray32*>(this->Offsets.Get()),
1128 static_cast<AOSArray32*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1129 break;
1131 functor(static_cast<AffineArray64*>(this->Offsets.Get()),
1132 static_cast<AOSArray64*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1133 break;
1135 default:
1136 functor(this->Offsets.Get(), this->Connectivity.Get(), std::forward<Args>(args)...);
1137 break;
1138 }
1139 }
1140 template <typename Functor, typename... Args,
1141 typename = typename std::enable_if<DispatchReturnsVoid<Functor, Args...>::value>::type>
1142 void Dispatch(Functor&& functor, Args&&... args) const
1143 {
1144 switch (this->StorageType)
1145 {
1147 functor(static_cast<AOSArray32*>(this->Offsets.Get()),
1148 static_cast<AOSArray32*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1149 break;
1151 functor(static_cast<AOSArray64*>(this->Offsets.Get()),
1152 static_cast<AOSArray64*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1153 break;
1155 functor(static_cast<AffineArray32*>(this->Offsets.Get()),
1156 static_cast<AOSArray32*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1157 break;
1159 functor(static_cast<AffineArray64*>(this->Offsets.Get()),
1160 static_cast<AOSArray64*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1161 break;
1163 default:
1164 functor(this->Offsets.Get(), this->Connectivity.Get(), std::forward<Args>(args)...);
1165 break;
1166 }
1167 }
1168 template <typename Functor, typename... Args,
1169 typename = typename std::enable_if<!DispatchReturnsVoid<Functor, Args...>::value>::type>
1170 GetDispatchReturnType<Functor, Args...> Dispatch(Functor&& functor, Args&&... args)
1171 {
1172 switch (this->StorageType)
1173 {
1175 return functor(static_cast<AOSArray32*>(this->Offsets.Get()),
1176 static_cast<AOSArray32*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1178 return functor(static_cast<AOSArray64*>(this->Offsets.Get()),
1179 static_cast<AOSArray64*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1181 return functor(static_cast<AffineArray32*>(this->Offsets.Get()),
1182 static_cast<AOSArray32*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1184 return functor(static_cast<AffineArray64*>(this->Offsets.Get()),
1185 static_cast<AOSArray64*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1187 default:
1188 return functor(this->Offsets.Get(), this->Connectivity.Get(), std::forward<Args>(args)...);
1189 }
1190 }
1191 template <typename Functor, typename... Args,
1192 typename = typename std::enable_if<!DispatchReturnsVoid<Functor, Args...>::value>::type>
1193 GetDispatchReturnType<Functor, Args...> Dispatch(Functor&& functor, Args&&... args) const
1194 {
1195 switch (this->StorageType)
1196 {
1198 return functor(static_cast<AOSArray32*>(this->Offsets.Get()),
1199 static_cast<AOSArray32*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1201 return functor(static_cast<AOSArray64*>(this->Offsets.Get()),
1202 static_cast<AOSArray64*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1204 return functor(static_cast<AffineArray32*>(this->Offsets.Get()),
1205 static_cast<AOSArray32*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1207 return functor(static_cast<AffineArray64*>(this->Offsets.Get()),
1208 static_cast<AOSArray64*>(this->Connectivity.Get()), std::forward<Args>(args)...);
1210 default:
1211 return functor(this->Offsets.Get(), this->Connectivity.Get(), std::forward<Args>(args)...);
1212 }
1213 }
1214
1215
1216 // Holds connectivity and offset arrays of the given ArrayType.
1217 template <typename ArrayT>
1219 "Use Dispatch with a struct that inherits from DispatchUtilities ") VisitState
1220 {
1221 using ArrayType = ArrayT;
1222 using ValueType = typename ArrayType::ValueType;
1223 using CellRangeType = decltype(vtk::DataArrayValueRange<1>(std::declval<ArrayType>()));
1224
1225 // We can't just use is_same here, since binary compatible representations
1226 // (e.g. int and long) are distinct types. Instead, ensure that ValueType
1227 // is a signed integer the same size as vtkIdType.
1228 // If this value is true, ValueType pointers may be safely converted to
1229 // vtkIdType pointers via reinterpret cast.
1230 static constexpr bool ValueTypeIsSameAsIdType = std::is_integral<ValueType>::value &&
1231 std::is_signed<ValueType>::value && (sizeof(ValueType) == sizeof(vtkIdType));
1232
1233 ArrayType* GetOffsets() { return this->Offsets; }
1234 const ArrayType* GetOffsets() const { return this->Offsets; }
1235
1237 const ArrayType* GetConnectivity() const { return this->Connectivity; }
1238
1239 vtkIdType GetNumberOfCells() const { return this->Offsets->GetNumberOfValues() - 1; }
1240
1242 {
1243 return static_cast<vtkIdType>(this->Offsets->GetValue(cellId));
1244 }
1245
1247 {
1248 return static_cast<vtkIdType>(this->Offsets->GetValue(cellId + 1));
1249 }
1250
1252 {
1253 return this->GetEndOffset(cellId) - this->GetBeginOffset(cellId);
1254 }
1255
1257 {
1259 this->GetConnectivity(), this->GetBeginOffset(cellId), this->GetEndOffset(cellId));
1260 }
1261
1262 friend class vtkCellArray;
1263
1264 protected:
1266 {
1269 this->Offsets->InsertNextValue(0);
1271 {
1272 this->IsInMemkind = true;
1273 }
1274 }
1275 ~VisitState() = default;
1276 void* operator new(size_t nSize)
1277 {
1278 void* r;
1279#ifdef VTK_USE_MEMKIND
1281#else
1282 r = malloc(nSize);
1283#endif
1284 return r;
1285 }
1286 void operator delete(void* p)
1287 {
1288#ifdef VTK_USE_MEMKIND
1289 VisitState* a = static_cast<VisitState*>(p);
1290 if (a->IsInMemkind)
1291 {
1293 }
1294 else
1295 {
1296 free(p);
1297 }
1298#else
1299 free(p);
1300#endif
1301 }
1302
1305
1306 private:
1307 VisitState(const VisitState&) = delete;
1308 VisitState& operator=(const VisitState&) = delete;
1309 bool IsInMemkind = false;
1310 };
1311#endif // __VTK_WRAP__
1312
1314
1322
1324
1325protected:
1327 ~vtkCellArray() override;
1328
1333
1335
1336private:
1337 vtkCellArray(const vtkCellArray&) = delete;
1338 void operator=(const vtkCellArray&) = delete;
1339};
1340
1341VTK_ABI_NAMESPACE_END
1342
1344{
1345VTK_ABI_NAMESPACE_BEGIN
1346
1348{
1349 // Insert full cell, returns the id of the inserted cell
1350 template <class OffsetsT, class ConnectivityT>
1352 OffsetsT* offsets, ConnectivityT* conn, const vtkIdType npts, const vtkIdType pts[])
1353 {
1354 using ValueType = GetAPIType<OffsetsT>;
1355 using OffsetsAccessorType = vtkDataArrayAccessor<OffsetsT>;
1356 using ConnectivityAccessorType = vtkDataArrayAccessor<ConnectivityT>;
1357 OffsetsAccessorType offsetsAccesor(offsets);
1358 ConnectivityAccessorType connAccesor(conn);
1359
1360 const vtkIdType cellId = offsets->GetNumberOfValues() - 1;
1361
1362 offsetsAccesor.InsertNext(static_cast<ValueType>(conn->GetNumberOfValues() + npts));
1363
1364 for (vtkIdType i = 0; i < npts; ++i)
1365 {
1366 connAccesor.InsertNext(static_cast<ValueType>(pts[i]));
1367 }
1368
1369 return cellId;
1370 }
1371
1372 // Just update offset table (for incremental API), returns the id of the inserted cell
1373 template <class OffsetsT, class ConnectivityT>
1374 vtkIdType operator()(OffsetsT* offsets, ConnectivityT* conn, const vtkIdType npts)
1375 {
1376 using ValueType = GetAPIType<OffsetsT>;
1377 using AccessorType = vtkDataArrayAccessor<OffsetsT>;
1378 AccessorType offsetsAccesor(offsets);
1379
1380 const vtkIdType cellId = offsets->GetNumberOfValues() - 1;
1381
1382 offsetsAccesor.InsertNext(static_cast<ValueType>(conn->GetNumberOfValues() + npts));
1383
1384 return cellId;
1385 }
1386};
1387
1388// for incremental API:
1390{
1391 template <class OffsetsT, class ConnectivityT>
1392 void operator()(OffsetsT* offsets, ConnectivityT* vtkNotUsed(conn), const vtkIdType npts)
1393 {
1394 using ValueType = GetAPIType<OffsetsT>;
1395
1396 auto offsetsRange = GetRange(offsets);
1397 const ValueType cellBegin = offsetsRange[offsets->GetMaxId() - 1];
1398 offsetsRange[offsets->GetMaxId()] = static_cast<ValueType>(cellBegin + npts);
1399 }
1400};
1401
1403{
1404 template <class OffsetsT, class ConnectivityT>
1405 vtkIdType operator()(OffsetsT* offsets, ConnectivityT* vtkNotUsed(conn), vtkIdType cellId)
1406 {
1407 return GetCellSize(offsets, cellId);
1408 }
1409};
1410
1412{
1413 template <class OffsetsT, class ConnectivityT>
1414 void operator()(OffsetsT* offsets, ConnectivityT* conn, const vtkIdType cellId, vtkIdList* ids)
1415 {
1416 auto offsetsRange = GetRange(offsets);
1417 const auto& beginOffset = offsetsRange[cellId];
1418 const auto& endOffset = offsetsRange[cellId + 1];
1419 const vtkIdType cellSize = static_cast<vtkIdType>(endOffset - beginOffset);
1420 const auto cellConnectivity = GetRange(conn).begin() + beginOffset;
1421
1422 // ValueType differs from vtkIdType, so we have to copy into a temporary buffer:
1423 ids->SetNumberOfIds(cellSize);
1424 vtkIdType* idPtr = ids->GetPointer(0);
1425 for (vtkIdType i = 0; i < cellSize; ++i)
1426 {
1427 idPtr[i] = static_cast<vtkIdType>(cellConnectivity[i]);
1428 }
1429 }
1430
1431 // Fills the caller's buffer and returns the cell size.
1432 template <class OffsetsT, class ConnectivityT>
1434 OffsetsT* offsets, ConnectivityT* conn, const vtkIdType cellId, vtkIdType* cellPoints)
1435 {
1436 auto offsetsRange = GetRange(offsets);
1437 const auto& beginOffset = offsetsRange[cellId];
1438 const auto& endOffset = offsetsRange[cellId + 1];
1439 const vtkIdType cellSize = static_cast<vtkIdType>(endOffset - beginOffset);
1440 const auto cellConnectivity = GetRange(conn).begin() + beginOffset;
1441
1442 // ValueType differs from vtkIdType, so we have to copy into a temporary buffer:
1443 for (vtkIdType i = 0; i < cellSize; ++i)
1444 {
1445 cellPoints[i] = static_cast<vtkIdType>(cellConnectivity[i]);
1446 }
1447
1448 return cellSize;
1449 }
1450
1451 // SFINAE helper to check if a Functors's connectivity array's memory can be used as a vtkIdType*.
1452 template <typename ConnectivityT>
1454 {
1455 static constexpr bool value =
1456 std::is_base_of_v<vtkAOSDataArrayTemplate<vtkIdType>, ConnectivityT>;
1457 };
1458
1459 // Points cellPoints at the cell's connectivity and returns the cell size.
1460 template <class OffsetsT, class ConnectivityT>
1461 std::enable_if_t<CanShareConnPtr<ConnectivityT>::value, vtkIdType> operator()(OffsetsT* offsets,
1462 ConnectivityT* conn, const vtkIdType cellId, vtkIdType const*& cellPoints,
1463 vtkIdList* vtkNotUsed(temp))
1464 {
1465 auto offsetsRange = GetRange(offsets);
1466 const auto& beginOffset = offsetsRange[cellId];
1467 const auto& endOffset = offsetsRange[cellId + 1];
1468 // This is safe, see CanShareConnPtr helper above.
1469 cellPoints = conn->GetPointer(beginOffset);
1470 return static_cast<vtkIdType>(endOffset - beginOffset);
1471 }
1472
1473 template <class OffsetsT, class ConnectivityT>
1474 std::enable_if_t<!CanShareConnPtr<ConnectivityT>::value, vtkIdType> operator()(OffsetsT* offsets,
1475 ConnectivityT* conn, const vtkIdType cellId, vtkIdType const*& cellPoints, vtkIdList* temp)
1476 {
1477 auto offsetsRange = GetRange(offsets);
1478 const auto& beginOffset = offsetsRange[cellId];
1479 const auto& endOffset = offsetsRange[cellId + 1];
1480 const vtkIdType cellSize = static_cast<vtkIdType>(endOffset - beginOffset);
1481 const auto cellConnectivity = GetRange(conn).begin() + beginOffset;
1482
1483 temp->SetNumberOfIds(cellSize);
1484 vtkIdType* tempPtr = temp->GetPointer(0);
1485 for (vtkIdType i = 0; i < cellSize; ++i)
1486 {
1487 tempPtr[i] = static_cast<vtkIdType>(cellConnectivity[i]);
1488 }
1489
1490 cellPoints = tempPtr;
1491 return cellSize;
1492 }
1493};
1494
1496{
1497 template <class OffsetsT, class ConnectivityT>
1499 OffsetsT* offsets, ConnectivityT* conn, vtkIdType cellId, vtkIdType cellPointIndex)
1500 {
1501 return static_cast<vtkIdType>(GetRange(conn)[GetBeginOffset(offsets, cellId) + cellPointIndex]);
1502 }
1503};
1504
1506{
1507 template <class OffsetsT, class ConnectivityT>
1508 void operator()(OffsetsT* offsets, ConnectivityT* conn)
1509 {
1510 using ValueType = GetAPIType<OffsetsT>;
1511 using AccessorType = vtkDataArrayAccessor<OffsetsT>;
1512 offsets->Reset();
1513 conn->Reset();
1514 AccessorType accessor(offsets);
1515 ValueType firstOffset = 0;
1516 accessor.InsertNext(firstOffset);
1517 }
1518};
1519
1521{
1522 template <class OffsetsT, class ConnectivityT>
1523 void operator()(OffsetsT* vtkNotUsed(offsets), ConnectivityT* conn, vtkIdType id)
1524 {
1525 using ValueType = GetAPIType<ConnectivityT>;
1526 using AccessorType = vtkDataArrayAccessor<ConnectivityT>;
1527 AccessorType accessor(conn);
1528 accessor.InsertNext(static_cast<ValueType>(id));
1529 }
1530};
1531
1532VTK_ABI_NAMESPACE_END
1533} // end namespace vtkCellArray_detail
1534
1535VTK_ABI_NAMESPACE_BEGIN
1536//----------------------------------------------------------------------------
1538{
1539 this->TraversalCellId = 0;
1540}
1541
1542//----------------------------------------------------------------------------
1543inline int vtkCellArray::GetNextCell(vtkIdType& npts, vtkIdType const*& pts) VTK_SIZEHINT(pts, npts)
1544{
1545 if (this->TraversalCellId < this->GetNumberOfCells())
1546 {
1547 this->GetCellAtId(this->TraversalCellId, npts, pts);
1548 ++this->TraversalCellId;
1549 return 1;
1550 }
1551
1552 npts = 0;
1553 pts = nullptr;
1554 return 0;
1555}
1556
1557//----------------------------------------------------------------------------
1559{
1561 {
1562 this->GetCellAtId(this->TraversalCellId, pts);
1563 ++this->TraversalCellId;
1564 return 1;
1565 }
1566
1567 pts->Reset();
1568 return 0;
1569}
1570//----------------------------------------------------------------------------
1572{
1573 return this->Dispatch(vtkCellArray_detail::GetCellSizeImpl{}, cellId);
1574}
1575
1576//----------------------------------------------------------------------------
1577void vtkCellArray::GetCellAtId(vtkIdType cellId, vtkIdType& cellSize, vtkIdType const*& cellPoints,
1578 vtkIdList* ptIds) VTK_SIZEHINT(cellPoints, cellSize)
1579{
1580 cellSize = this->Dispatch(vtkCellArray_detail::GetCellAtIdImpl{}, cellId, cellPoints, ptIds);
1581}
1582
1583//----------------------------------------------------------------------------
1585{
1586 this->Dispatch(vtkCellArray_detail::GetCellAtIdImpl{}, cellId, pts);
1587}
1588
1589//----------------------------------------------------------------------------
1590void vtkCellArray::GetCellAtId(vtkIdType cellId, vtkIdType& cellSize, vtkIdType* cellPoints)
1591{
1592 cellSize = this->Dispatch(vtkCellArray_detail::GetCellAtIdImpl{}, cellId, cellPoints);
1593}
1594
1595//----------------------------------------------------------------------------
1597{
1598 return this->Dispatch(vtkCellArray_detail::CellPointAtIdImpl{}, cellId, cellPointIndex);
1599}
1600
1601//----------------------------------------------------------------------------
1603{
1604 switch (this->StorageType)
1605 {
1607 if (this->GetOffsetsAffineArray32()->GetBackend()->Slope != cellSize)
1608 {
1609 return this->ConvertTo32BitStorage();
1610 }
1611 return true;
1613 if (this->GetOffsetsAffineArray64()->GetBackend()->Slope != cellSize)
1614 {
1615 return this->ConvertTo64BitStorage();
1616 }
1617 return true;
1618 case Int64:
1619 case Int32:
1620 case Generic:
1621 default:
1622 return true;
1623 }
1624}
1625
1626//----------------------------------------------------------------------------
1628 VTK_SIZEHINT(pts, npts)
1629{
1630 this->EnsureStorageForCellSize(npts);
1631 return this->Dispatch(vtkCellArray_detail::InsertNextCellImpl{}, npts, pts);
1632}
1633
1634//----------------------------------------------------------------------------
1636{
1637 this->EnsureStorageForCellSize(npts);
1638 return this->Dispatch(vtkCellArray_detail::InsertNextCellImpl{}, static_cast<vtkIdType>(npts));
1639}
1640
1641//----------------------------------------------------------------------------
1646
1647//----------------------------------------------------------------------------
1649{
1650 this->EnsureStorageForCellSize(npts);
1652}
1653
1654//----------------------------------------------------------------------------
1656{
1657 return this->InsertNextCell(pts->GetNumberOfIds(), pts->GetPointer(0));
1658}
1659
1660//----------------------------------------------------------------------------
1662{
1663 vtkIdList* pts = cell->GetPointIds();
1664 return this->InsertNextCell(pts->GetNumberOfIds(), pts->GetPointer(0));
1665}
1666
1667//----------------------------------------------------------------------------
1669{
1671}
1672
1673VTK_ABI_NAMESPACE_END
1674#endif // vtkCellArray.h
Array-Of-Structs implementation of vtkGenericDataArray.
virtual vtkIdType GetNumberOfCells() const =0
Get the number of cells in the array.
void GetCellAtId(vtkIdType cellId, vtkIdType &cellSize, vtkIdType const *&cellPoints)
Return the point ids for the cell at cellId.
A utility array for wrapping affine functions in implicit arrays.
static vtkAffineArray< ValueType > * FastDownCast(vtkAbstractArray *source)
Encapsulate traversal logic for vtkCellArray.
bool AppendLegacyFormat(vtkIdTypeArray *data, vtkIdType ptOffset=0)
Append an array of data with the legacy vtkCellArray layout, e.g.:
vtkIdType GetCellSize(vtkIdType cellId) const override
Return the size of the cell at cellId.
vtkDataArray * GetOffsetsArray() const
Return the array used to store cell offsets.
int GetNextCell(vtkIdType &npts, vtkIdType const *&pts)
GetDispatchReturnType< Functor, Args... > Dispatch(Functor &&functor, Args &&... args) const
void UseFixedSizeDefaultStorage(vtkIdType cellSize)
Initialize internal data structures to use 32- or 64-bit storage.
vtkIdType GetOffset(vtkIdType cellId) override
Get the offset (into the connectivity) for a specified cell id.
void UseDefaultStorage()
Initialize internal data structures to use 32- or 64-bit storage.
bool AllocateCopy(vtkCellArray *other)
Pre-allocate memory in internal data structures to match the used size of the input vtkCellArray.
static void SetDefaultStorageIs64Bit(bool val)
Control the default internal storage size.
void DeepCopy(vtkAbstractCellArray *ca) override
Perform a deep copy (no reference counting) of the given cell array.
bool IsValid()
Check that internal storage is consistent and in a valid state.
friend class vtkCellArrayIterator
bool SetData(vtkIdType cellSize, vtkDataArray *connectivity)
Sets the internal arrays to the supported connectivity array with an offsets array automatically gene...
void ShallowCopy(vtkAbstractCellArray *ca) override
Shallow copy ca into this cell array.
vtkIdType GetNumberOfOffsets() const override
Get the number of elements in the offsets array.
bool CanConvertToFixedSize64BitStorage() const
Check if the existing data can safely be converted to use 32- or 64- bit storage.
vtkIdType GetTraversalCellId()
Get/Set the current cellId for traversal.
void SetData(AOSArray64 *, AOSArray64 *connectivity)
Set the internal data arrays to the supplied offsets and connectivity arrays.
vtkIdType GetNumberOfCells() const override
Get the number of cells in the array.
void Reset()
Reuse list.
vtkAOSDataArrayTemplate< vtkTypeInt32 > AOSArray32
bool CanConvertToFixedSizeDefaultStorage() const
Check if the existing data can safely be converted to use 32- or 64- bit storage.
vtkIdType GetNumberOfConnectivityIds() const override
Get the size of the connectivity array that stores the point ids.
vtkAOSDataArrayTemplate< vtkTypeInt64 > AOSArray64
bool CanConvertToStorageType(StorageTypes type) const
Check if the existing data can safely be converted to use 32- or 64- bit storage.
void SetData(AffineArray32 *, AOSArray32 *connectivity)
Set the internal data arrays to the supplied offsets and connectivity arrays.
bool ConvertToFixedSize64BitStorage()
Convert internal data structures to use 32- or 64-bit storage.
vtkAffineArray< vtkTypeInt64 > AffineArray64
bool AllocateExact(vtkIdType numCells, vtkIdType connectivitySize)
Pre-allocate memory in internal data structures.
bool ResizeExact(vtkIdType numCells, vtkIdType connectivitySize)
ResizeExact() resizes the internal structures to hold numCells total cell offsets and connectivitySiz...
AOSArray64 * GetOffsetsAOSArray64() const
Ensure that a cell of size cellSize can be safely inserted or appended.
bool AllocateEstimate(vtkIdType numCells, vtkIdType maxCellSize)
Pre-allocate memory in internal data structures.
bool ImportLegacyFormat(const vtkIdType *data, vtkIdType len)
Import an array of data with the legacy vtkCellArray layout, e.g.:
vtkIdType TraversalCellId
void UseFixedSize64BitStorage(vtkIdType cellSize)
Initialize internal data structures to use 32- or 64-bit storage.
void InitTraversal()
bool IsStorageShareable() const override
bool IsStorageGeneric() const
void Dispatch(Functor &&functor, Args &&... args) const
void Use64BitStorage()
Initialize internal data structures to use 32- or 64-bit storage.
vtkSmartPointer< vtkDataArray > Offsets
vtkDataArray * GetConnectivityArray() const
Return the array used to store the point ids that define the cells' connectivity.
bool ConvertToDefaultStorage()
Convert internal data structures to use 32- or 64-bit storage.
bool CanConvertToDefaultStorage() const
Check if the existing data can safely be converted to use 32- or 64- bit storage.
GetDispatchReturnType< Functor, Args... > Dispatch(Functor &&functor, Args &&... args)
static bool DefaultStorageIs64Bit
bool CanConvertTo32BitStorage() const
Check if the existing data can safely be converted to use 32- or 64- bit storage.
void GetCellAtId(vtkIdType cellId, vtkIdType &cellSize, vtkIdType const *&cellPoints, vtkIdList *ptIds) override
Return the point ids for the cell at cellId.
void SetData(AffineArray64 *, AOSArray64 *connectivity)
Set the internal data arrays to the supplied offsets and connectivity arrays.
void InsertCellPoint(vtkIdType id)
Used in conjunction with InsertNextCell(npts) to add another point to the list of cells.
unsigned long GetActualMemorySize() const
Return the memory in kibibytes (1024 bytes) consumed by this cell array.
~vtkCellArray() override
vtkCellArrayIterator * NewIterator()
NewIterator returns a new instance of vtkCellArrayIterator that is initialized to point at the first ...
void ReplaceCellAtId(vtkIdType cellId, vtkIdList *list)
Replaces the point ids for the specified cell with the supplied list.
void UseFixedSize32BitStorage(vtkIdType cellSize)
Initialize internal data structures to use 32- or 64-bit storage.
void ReverseCellAtId(vtkIdType cellId)
Reverses the order of the point ids for the specified cell.
bool IsStorage32Bit() const
bool SetData(vtkDataArray *offsets, vtkDataArray *connectivity)
Set the internal data arrays to the supplied offsets and connectivity arrays.
void Initialize() override
Free any memory and reset to an empty state.
void Squeeze()
Reclaim any extra memory while preserving data.
vtkSmartPointer< vtkDataArray > Connectivity
bool IsStorageFixedSize32Bit() const
bool ConvertTo32BitStorage()
Convert internal data structures to use 32- or 64-bit storage.
AffineArray64 * GetOffsetsAffineArray64() const
Ensure that a cell of size cellSize can be safely inserted or appended.
bool ImportLegacyFormat(vtkIdTypeArray *data)
Import an array of data with the legacy vtkCellArray layout, e.g.:
bool ConvertToFixedSizeDefaultStorage()
Convert internal data structures to use 32- or 64-bit storage.
void SetData(AOSArray32 *, AOSArray32 *connectivity)
Set the internal data arrays to the supplied offsets and connectivity arrays.
bool ConvertToStorageType(StorageTypes type)
Convert internal data structures to use 32- or 64-bit storage.
AffineArray32 * GetOffsetsAffineArray32() const
Ensure that a cell of size cellSize can be safely inserted or appended.
void SetOffset(vtkIdType cellId, vtkIdType offset)
Set the offset (into the connectivity) for a specified cell id.
bool ConvertToSmallestStorage()
Convert internal data structures to use 32- or 64-bit storage.
bool AppendLegacyFormat(const vtkIdType *data, vtkIdType len, vtkIdType ptOffset=0)
Append an array of data with the legacy vtkCellArray layout, e.g.:
void ExportLegacyFormat(vtkIdTypeArray *data)
Fill data with the old-style vtkCellArray data layout, e.g.
bool ConvertTo64BitStorage()
Convert internal data structures to use 32- or 64-bit storage.
void Dispatch(Functor &&functor, Args &&... args)
bool ConvertToFixedSize32BitStorage()
Convert internal data structures to use 32- or 64-bit storage.
vtkAffineArray< vtkTypeInt32 > AffineArray32
void Use32BitStorage()
Initialize internal data structures to use 32- or 64-bit storage.
vtkIdType GetCellPointAtId(vtkIdType cellId, vtkIdType cellPointIndex) const
Return the point id at cellPointIndex for the cell at cellId.
void SetTraversalCellId(vtkIdType cellId)
Get/Set the current cellId for traversal.
bool IsStorageFixedSize64Bit() const
static bool GetDefaultStorageIs64Bit()
Control the default internal storage size.
StorageTypes StorageType
int GetMaxCellSize() override
Returns the size of the largest cell.
vtkIdType InsertNextCell(vtkCell *cell)
Insert a cell object.
AOSArray32 * GetOffsetsAOSArray32() const
Ensure that a cell of size cellSize can be safely inserted or appended.
void PrintSelf(ostream &os, vtkIndent indent) override
Standard methods for instantiation, type information, and printing.
void PrintDebug(ostream &os)
Standard methods for instantiation, type information, and printing.
vtkIdType IsHomogeneous() const override
Check if all cells have the same number of vertices.
bool EnsureStorageForCellSize(vtkIdType cellSize)
Ensure that a cell of size cellSize can be safely inserted or appended.
void UpdateCellCount(int npts)
Used in conjunction with InsertNextCell(int npts) and InsertCellPoint() to update the number of point...
bool IsStorageFixedSize() const
static vtkCellArray * New()
Standard methods for instantiation, type information, and printing.
StorageTypes GetStorageType() const noexcept
void ReplaceCellPointAtId(vtkIdType cellId, vtkIdType cellPointIndex, vtkIdType newPointId)
Replaces the pointId at cellPointIndex of a cell with newPointId.
bool CanConvertToFixedSize32BitStorage() const
Check if the existing data can safely be converted to use 32- or 64- bit storage.
AOSArray32 * GetConnectivityAOSArray32() const
Return the array used to store the point ids that define the cells' connectivity.
void Append(vtkCellArray *src, vtkIdType pointOffset=0)
Append cells from src into this.
bool IsStorage64Bit() const
void ReplaceCellAtId(vtkIdType cellId, vtkIdType cellSize, const vtkIdType *cellPoints)
Replaces the point ids for the specified cell with the supplied list.
AOSArray64 * GetConnectivityAOSArray64() const
Return the array used to store the point ids that define the cells' connectivity.
bool CanConvertTo64BitStorage() const
Check if the existing data can safely be converted to use 32- or 64- bit storage.
abstract class to specify cell behavior
Definition vtkCell.h:130
vtkIdList * GetPointIds()
Return the list of point ids defining the cell.
Definition vtkCell.h:223
static vtkDataArray * FastDownCast(vtkAbstractArray *source)
Perform a fast, safe cast from a vtkAbstractArray to a vtkDataArray.
list of point or cell ids
Definition vtkIdList.h:135
void SetNumberOfIds(vtkIdType number)
Specify the number of ids for this object to hold.
vtkIdType GetNumberOfIds() const noexcept
Return the number of id's in the list.
Definition vtkIdList.h:185
void Reset()
Reset to an empty state but retain previously allocated memory.
Definition vtkIdList.h:295
vtkIdType * GetPointer(vtkIdType i)
Get a pointer to a particular data index.
Definition vtkIdList.h:259
dynamic, self-adjusting array of vtkIdType
a simple class to control print indentation
Definition vtkIndent.h:108
static vtkMallocingFunction GetCurrentMallocFunction()
static vtkFreeingFunction GetAlternateFreeFunction()
static bool GetUsingMemkind()
A global state flag that controls whether vtkObjects are constructed in the usual way (the default) o...
Hold a reference to a vtkObjectBase instance.
static vtkSmartPointer< T > New()
Create an instance of a VTK object.
typename detail::GetAPITypeImpl< ArrayType, ForceValueTypeForVtkDataArray >::APIType GetAPIType
VTK_ITER_INLINE auto DataArrayValueRange(const ArrayTypePtr &array, ValueIdType start=-1, ValueIdType end=-1) -> typename detail::SelectValueRange< ArrayTypePtr, TupleSize, ForceValueTypeForVtkDataArray >::type
Generate an stl and for-range compatible range of flat AOS iterators from a vtkDataArray.
vtkIdType GetNumberOfCells(OffsetsT *offsets)
static vtkIdType GetCellSize(OffsetsT *offsets, vtkIdType cellId)
static vtkIdType GetEndOffset(OffsetsT *offsets, vtkIdType cellId)
static decltype(vtk::DataArrayValueRange< 1, vtkIdType >(std::declval< ConnectivityT >())) GetCellRange(OffsetsT *offsets, ConnectivityT *conn, vtkIdType cellId)
static vtkIdType GetBeginOffset(OffsetsT *offsets, vtkIdType cellId)
static decltype(vtk::DataArrayValueRange< 1, vtkIdType >(std::declval< ArrayT >())) GetRange(ArrayT *array)
vtk::GetAPIType< ArrayT, vtkIdType > GetAPIType
vtkIdType GetNumberOfCells() const
CellRangeType GetCellRange(vtkIdType cellId)
vtkIdType GetEndOffset(vtkIdType cellId) const
vtkSmartPointer< ArrayType > Offsets
vtkSmartPointer< ArrayType > Connectivity
static constexpr bool ValueTypeIsSameAsIdType
const ArrayType * GetOffsets() const
decltype(vtk::DataArrayValueRange< 1 >(std::declval< ArrayType >())) CellRangeType
vtkIdType GetBeginOffset(vtkIdType cellId) const
vtkIdType GetCellSize(vtkIdType cellId) const
const ArrayType * GetConnectivity() const
typename ArrayType::ValueType ValueType
ArrayType * GetConnectivity()
vtkIdType operator()(OffsetsT *offsets, ConnectivityT *conn, vtkIdType cellId, vtkIdType cellPointIndex)
void operator()(OffsetsT *offsets, ConnectivityT *conn, const vtkIdType cellId, vtkIdList *ids)
std::enable_if_t<!CanShareConnPtr< ConnectivityT >::value, vtkIdType > operator()(OffsetsT *offsets, ConnectivityT *conn, const vtkIdType cellId, vtkIdType const *&cellPoints, vtkIdList *temp)
std::enable_if_t< CanShareConnPtr< ConnectivityT >::value, vtkIdType > operator()(OffsetsT *offsets, ConnectivityT *conn, const vtkIdType cellId, vtkIdType const *&cellPoints, vtkIdList *temp)
vtkIdType operator()(OffsetsT *offsets, ConnectivityT *conn, const vtkIdType cellId, vtkIdType *cellPoints)
vtkIdType operator()(OffsetsT *offsets, ConnectivityT *conn, vtkIdType cellId)
void operator()(OffsetsT *offsets, ConnectivityT *conn, vtkIdType id)
vtkIdType operator()(OffsetsT *offsets, ConnectivityT *conn, const vtkIdType npts, const vtkIdType pts[])
vtkIdType operator()(OffsetsT *offsets, ConnectivityT *conn, const vtkIdType npts)
void operator()(OffsetsT *offsets, ConnectivityT *conn)
void operator()(OffsetsT *offsets, ConnectivityT *conn, const vtkIdType npts)
Efficient templated access to vtkDataArray.
#define vtkDataArray
STL-compatible iterable ranges that provide access to vtkDataArray elements.
#define VTK_DEPRECATED_IN_9_8_0(reason)
int vtkIdType
Definition vtkType.h:363
#define VTK_SIZEHINT(...)
#define VTK_EXPECTS(x)
#define VTK_MARSHALMANUAL
#define VTK_NEWINSTANCE