# SafeDownCast and subclassing vtkPolyData in Python

**URL:** https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912
**Category:** Support
**Created:** [June 2, 2021, 10:36am UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912 "2021-06-02T10:36:34Z")
**Posts on this page:** 11
**Page:** 1

<div class="post-metadata">

### Author: ![bistek](https://discourse.vtk.org/user_avatar/discourse.vtk.org/bistek/32/2344_2.png) [@bistek](https://discourse.vtk.org/u/bistek)
#### Post date: [June 2, 2021, 10:36am UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/1 "2021-06-02T10:36:34Z")

</div>

Hello, I have defined a subclass of `vtkPolyData` in my Python project. It works well and I am able to use standard `vtkXMLPolyDataWriter` to save it to disk. However, when reloading the objects from file, I would like to cast the `vtkPolyData` that I get from the `vtkXMLPolyDataReader` to my subclass. I figured out it would be as simple as:

```
my_object = MyClass() # MyClass is derived from vtkPolyData

pd_reader = vtk.vtkXMLPolyDataReader()
pd_reader.SetFileName(<my_file_name>)
pd_reader.Update()

my_object.SafeDownCast(pd_reader.GetOutput())
my_object.Modified()

```

But I always get an empty `my_object` (and I have checked: the output from `pd_reader` is a proper `vtkPolyData` object).

Could somebody help?

Thanks very much!

---

<div class="post-metadata">

### Author: ![ben.boeckel](https://discourse.vtk.org/letter_avatar_proxy/v4/letter/b/ea5d25/32.png) [@ben.boeckel](https://discourse.vtk.org/u/ben.boeckel)
#### Post date: [June 2, 2021, 11:09am UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/2 "2021-06-02T11:09:12Z")

</div>

The reader doesn’t know how to create an instance of your derived class, so it won’t be an instance. `SafeDownCast` is analogous to `dynamic_cast`, so if it isn’t an instance of your class, it will return `None`. You’ll need a method on your class to take another `vtkPolyData` and add your class’ bits around it.

---

<div class="post-metadata">

### Author: ![bistek](https://discourse.vtk.org/user_avatar/discourse.vtk.org/bistek/32/2344_2.png) [@bistek](https://discourse.vtk.org/u/bistek)
#### Post date: [June 2, 2021, 2:52pm UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/3 "2021-06-02T14:52:16Z")

</div>

Hello, I was assuming that the following post was correct.

“ A downcast is a cast from a base class to a class derived from the base class. A downcast is only safe if the object addressed at runtime is actually addressing a derived class object.”

[https://vtk.org/pipermail/vtkusers/2011-September/069645.html](https://vtk.org/pipermail/vtkusers/2011-September/069645.html)

MyClass() is derived from vtkPolyData(), so it should have satisfied the condition above. But either I am not understanding, or the post cited above is incorrect.

In any case, could you suggest an example showing how to “ add my class’ bits around a polydata“? I thought that this is the actual purpose of casting (but probably I’m wrong), and I am a bit confused since MyClass() simply adds methods to vtkPolyData(), so in principle a MyClass() instance is just a vtkPolyData() with more methods that are “revealed” dynamically when called, but for instance the data arrays etc are exactly the same.

Thanks very much!

---

<div class="post-metadata">

### Author: ![bistek](https://discourse.vtk.org/user_avatar/discourse.vtk.org/bistek/32/2344_2.png) [@bistek](https://discourse.vtk.org/u/bistek)
#### Post date: [June 2, 2021, 4:16pm UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/4 "2021-06-02T16:16:31Z")

</div>

I have also tried `dynamic_cast`, but it raises an error in Python.

---

<div class="post-metadata">

### Author: ![Yohann\_Bearzi](https://discourse.vtk.org/user_avatar/discourse.vtk.org/yohann_bearzi/32/671_2.png) [@Yohann\_Bearzi](https://discourse.vtk.org/u/Yohann_Bearzi)
#### Post date: [June 2, 2021, 4:39pm UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/5 "2021-06-02T16:39:32Z")

</div>

As @ben.boeckel said, the xml poly data reader produces an output of static type `vtkPolyData`, so you cannot downcast this to your new type. The only way I see for you is to create a filter that shallow copies a `vtkPolyData` into your custom type.

Note that your custom type can only be produced by filters that inherit from `vtkPassInputTypeAlgorithm`. Any filter inheriting from `vtkPolyDataAlgorithm` will produce a `vtkPolyData` for the same reason the xml poly data reader produces a `vtkPolyData`.

Shallow-copying is pretty cheap, so it should be a good enough solution in your case.

---

<div class="post-metadata">

### Author: ![dgobbi](https://discourse.vtk.org/user_avatar/discourse.vtk.org/dgobbi/32/18_2.png) [@dgobbi](https://discourse.vtk.org/u/dgobbi)
#### Post date: [June 2, 2021, 4:39pm UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/6 "2021-06-02T16:39:33Z")

</div>

> [@](#):
>
> MyClass() is derived from vtkPolyData(), so it should have satisfied the condition above

A downcast only changes the type of the _pointer_, it cannot change the type of the _object_. That is why they say that a downcast is only safe when the pointer is “addressing a derived class object.” This is a subtle distinction, but a very important one!

The reader returns a pointer of type `vtkPolyData*`, and this pointer holds the address of a vtkPolyData object. That is the important thing: the object provided by the reader does not belong to your subclass, therefore you cannot downcast it. The only possible way to convert the object is by creating a new object that belongs to your class, and then copying the data.

```python
my_object = MyClass()
my_object.ShallowCopy(pd_reader.GetOutput())
# my_object.DeepCopy(pd_reader.GetOutput()) # do this if ShallowCopy() doesn't work

```

---

<div class="post-metadata">

### Author: ![bistek](https://discourse.vtk.org/user_avatar/discourse.vtk.org/bistek/32/2344_2.png) [@bistek](https://discourse.vtk.org/u/bistek)
#### Post date: [June 2, 2021, 5:00pm UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/7 "2021-06-02T17:00:16Z")

</div>

Dear @dgobbi and @Yohann_Bearzi, thanks very much for the explanation and the solution! It works!

I add here the complete solution for whoever might be interested.

```
my_object = MyClass() # derived from vtkPolyData()
pd_reader = vtk.vtkXMLPolyDataReader()
pd_reader.SetFileName("my_file_name")
pd_reader.Update()
my_object.ShallowCopy(pd_reader.GetOutput())
my_object.Modified()

```

Thanks to everybody!

---

<div class="post-metadata">

### Author: ![Yohann\_Bearzi](https://discourse.vtk.org/user_avatar/discourse.vtk.org/yohann_bearzi/32/671_2.png) [@Yohann\_Bearzi](https://discourse.vtk.org/u/Yohann_Bearzi)
#### Post date: [June 2, 2021, 5:22pm UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/8 "2021-06-02T17:22:15Z")

</div>

> `vtk_object.Modified()`

Ideally, `Modified()` should be called inside `ShallowCopy`, if you actually change internal buffers.

---

<div class="post-metadata">

### Author: ![bistek](https://discourse.vtk.org/user_avatar/discourse.vtk.org/bistek/32/2344_2.png) [@bistek](https://discourse.vtk.org/u/bistek)
#### Post date: [June 3, 2021, 7:57am UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/9 "2021-06-03T07:57:15Z")

</div>

@Yohann_Bearzi, I guess I made an error, now corrected, in copy/pasting my code above. The instance of `My_Class()` returned at the end must be `my_object` created in the first line. Please see if it makes sense for you now.

---

<div class="post-metadata">

### Author: ![Yohann\_Bearzi](https://discourse.vtk.org/user_avatar/discourse.vtk.org/yohann_bearzi/32/671_2.png) [@Yohann\_Bearzi](https://discourse.vtk.org/u/Yohann_Bearzi)
#### Post date: [June 3, 2021, 12:10pm UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/10 "2021-06-03T12:10:36Z")

</div>

Actually, you don’t need to call `Modified` at all. It is already being called when you call `ShallowCopy` in the class hierarchy. We usually try to make `Modified` almost invisible to the user by calling it directly inside classes methods when an internal attribute is changed, because managing it “by hand” is error prone (people are very likely to forget to call it). So you usually don’t need to call `Modified`, unless you have good reasons to do so, inside a class you wrote yourself. `vtkSetMacro` automatically calls `Modified`.

---

<div class="post-metadata">

### Author: ![bistek](https://discourse.vtk.org/user_avatar/discourse.vtk.org/bistek/32/2344_2.png) [@bistek](https://discourse.vtk.org/u/bistek)
#### Post date: [June 4, 2021, 10:48am UTC](https://discourse.vtk.org/t/safedowncast-and-subclassing-vtkpolydata-in-python/5912/11 "2021-06-04T10:48:52Z")

</div>

Perfect, thanks!
