# Crash with ctkRangeWidget

**URL:** <https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299>\
**Category:** Development\
**Tags:** ctk\
**Created:** [December 31, 2020, 2:26pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299 "2020-12-31T14:26:21Z")\
**Posts on this page:** 9\
**Page:** 1

<div class="post-metadata">

**Author:** ![xriobe](https://avatars.discourse-cdn.com/v4/letter/x/59ef9b/32.png) [@xriobe](https://discourse.slicer.org/u/xriobe)\
**Post date:** [December 31, 2020, 2:26pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299/1 "2020-12-31T14:26:21Z")

</div>

Hi,

I have an issue with a wrong behavior of ctkRangeWidget that ends with the crash of Slicer 4.11.20200930 in Debug build (Ubuntu 20).

I think it is probably the same as this bug that has been closed without knowing how to reproduce:

> **[0002467: crash when scrolling through multivolumes - MantisBT](https://mantisarchive.slicer.org/view.php?id=2467)**

In my case it occurs in qMRMLVolumeThresholdWidget when using the sequence player if the frames have data with different scalar range values. At the change of frame, the threshold widget updates and call setRange(double min, double max), ending up in ctkRangeWidget::setRange where the slider and spinbox values are compared in a Q\_ASSERT (ctkRangeWidget.cpp line 380):

Q\_ASSERT(d-\>equal(d-\>Slider-\>maximumValue(), d-\>MaximumSpinBox-\>value()));

What happens is that a few lines above the call to  
d-\>Slider-\>setRange(d-\>MaximumSpinBox-\>minimum(), d-\>MinimumSpinBox-\>maximum());  
doesn’t always update the slider’s values.

As a side question about this line, shoudn’t it rather be d-\>Slider-\>setRange(d-\> **Minimum** SpinBox-\>minimum(), d-\> **Maximum** SpinBox-\>maximum()); ?

The reason why the values are not updated is because there are some rounding calculations with conversions to int during the process. It would be long to describe all here, but in ctkDoubleRangeSlider::setRange, the call to d-\>Slider-\>setRange(d-\>toInt(newMin), d-\>toInt(newMax)); converts the ranges to number of steps.

In an example with previous max range being 1272 and new one 1267, with a step of 10, it results in the same value rounded\_int(1272/10) == rounded\_int(1267/10) == 127, and in the implementation of the previous call to setRange, the “emit rangeChanged” is not done:

void QAbstractSlider::setRange(int min, int max)  
{  
Q\_D(QAbstractSlider);  
int oldMin = d-\>minimum;  
int oldMax = d-\>maximum;  
d-\>minimum = min;  
d-\>maximum = qMax(min, max);  
if (oldMin != d-\>minimum || oldMax != d-\>maximum) {  
sliderChange(SliderRangeChange);  
emit rangeChanged(d-\>minimum, d-\>maximum);  
setValue(d-\>value); // re-bound  
}  
}

At the end, the slider (d-\>Slider-\>maximumValue()) and the spin box (d-\>MinimumSpinBox-\>maximum()) values are not synchronized and we are in the assert situation where 1267 != 1272.

I don’t really know what would be the correct fix for that.

- should the method QAbstractSlider::setRange be overridden in ctkRangeSlider and use more info for the condition check?
- should ctkDoubleRangeSlider or ctkRangeWidget force call ctkRangeSlider::onRangeChanged or ctkRangeSlider::setValues in this situation?
- something else ?

---

<div class="post-metadata">

**Author:** ![lassoan](https://sea2.discourse-cdn.com/flex002/user_avatar/discourse.slicer.org/lassoan/32/13_2.png) [@lassoan](https://discourse.slicer.org/u/lassoan)\
**Post date:** [December 31, 2020, 4:02pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299/2 "2020-12-31T16:02:57Z")

</div>

Thanks for the detailed analysis. Do you think the assert detects an actual error or it can normal that there are transient states during the check fails? We could simply remove this check or convert it to just logging a message if we find that it does not help but rather interferes with debugging.

---

<div class="post-metadata">

**Author:** ![xriobe](https://avatars.discourse-cdn.com/v4/letter/x/59ef9b/32.png) [@xriobe](https://discourse.slicer.org/u/xriobe)\
**Post date:** [December 31, 2020, 4:24pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299/3 "2020-12-31T16:24:34Z")

</div>

At the end of the process of all events and updates, those values for the slider and spin box are out of synchronization, so there is a real error if they have to be. For my case the crash is more annoying than this error, considering that it occurs only for some specific cases where it’s not a problem to have slightly different values so it is a very minor bug, but maybe other people needing exact match will have bigger issues…

Replacing the assert by a log could be a first easy step, better having a “polluted” log than a crash.

I see in different places of these ctk_Range_ classes that sometimes the values are forced set for specific cases, so it could be a possibility if we can detect this rounding side effect, but i’m new to ctk/Slicer so i don’t know the impact of it in other cases, these widgets are pretty complex.

---

<div class="post-metadata">

**Author:** ![xriobe](https://avatars.discourse-cdn.com/v4/letter/x/59ef9b/32.png) [@xriobe](https://discourse.slicer.org/u/xriobe)\
**Post date:** [February 1, 2021, 5:10pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299/4 "2021-02-01T17:10:50Z")

</div>

Hi!  
Is there some decision about this among the core developers of CTK ?  
Or should we simply remove the asserts ?

Regards

---

<div class="post-metadata">

**Author:** ![lassoan](https://sea2.discourse-cdn.com/flex002/user_avatar/discourse.slicer.org/lassoan/32/13_2.png) [@lassoan](https://discourse.slicer.org/u/lassoan)\
**Post date:** [February 1, 2021, 5:13pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299/5 "2021-02-01T17:13:18Z")

</div>

Please submit your proposed changes (e.g., replace plain assert by log assert) as a pull request to commontk/ctk. Thank you.

---

<div class="post-metadata">

**Author:** ![xriobe](https://avatars.discourse-cdn.com/v4/letter/x/59ef9b/32.png) [@xriobe](https://discourse.slicer.org/u/xriobe)\
**Post date:** [February 1, 2021, 6:50pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299/6 "2021-02-01T18:50:54Z")

</div>

Done here: [Replace Q\_ASSERT by qWarning to avoid crash in debug by xriobe · Pull Request #948 · commontk/CTK · GitHub](https://github.com/commontk/CTK/pull/948)  
I used qWarning as seen in other widgets

---

<div class="post-metadata">

**Author:** ![jcfr](https://sea2.discourse-cdn.com/flex002/user_avatar/discourse.slicer.org/jcfr/32/17825_2.png) [@jcfr](https://discourse.slicer.org/u/jcfr)\
**Post date:** [February 1, 2021, 8:07pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299/7 "2021-02-01T20:07:09Z")

</div>

Thanks for submitting the changes, the PR has been integrated.

Could you know submit a PR updating CTK in Slicer ? Consider adding a commit similar to [this one](https://github.com/Slicer/Slicer/commit/3e650d3f8607323003bc5a624961a4c1b4f43291)

---

<div class="post-metadata">

**Author:** ![xriobe](https://avatars.discourse-cdn.com/v4/letter/x/59ef9b/32.png) [@xriobe](https://discourse.slicer.org/u/xriobe)\
**Post date:** [February 1, 2021, 9:20pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299/8 "2021-02-01T21:20:52Z")

</div>

Done: [BUG: Update CTK to fix a crash in ctkRangeWidget::SetRange in Debug mode by xriobe · Pull Request #5422 · Slicer/Slicer · GitHub](https://github.com/Slicer/Slicer/pull/5422)

---

<div class="post-metadata">

**Author:** ![jcfr](https://sea2.discourse-cdn.com/flex002/user_avatar/discourse.slicer.org/jcfr/32/17825_2.png) [@jcfr](https://discourse.slicer.org/u/jcfr)\
**Post date:** [February 1, 2021, 9:30pm UTC](https://discourse.slicer.org/t/crash-with-ctkrangewidget/15299/9 "2021-02-01T21:30:19Z")

</div>

Et voila, changes have been integrated into upstream Slicer  
🙏🚀
