Cabbage Logo
Back to Cabbage Site

Slider position (not value) changes to default when changing bounds

Hello Cabbage Forum,

My apologies if I am repeating an old topic, I did look around for a solution. I have been working with Cabbage for a few months at this point and usually I can figure out or find the answer to my questions but I am finally stumped.

I am trying to change widget bounds for different layout options (i.e. layout1 and layout2), triggered by 2 buttons (“layout_1_button”, “layout_2_button”) without changing the value of the sliders. The value of each slider is unchanged when moved, but the slider looks like it has returned to default value. I have tried setting the value of the widget after moving, but it does not affect the position of the slider. It is good that moving the widget bounds does not change its value, but it would be nice if the position of the slider reflected its true value after the move. Here is an example of what I have:

<Cabbage>
form caption("Untitled") size(1200, 720), guiMode("queue") pluginId("def1")
label bounds(0, 0, 600, 30), channel("layout_1_label"), text("Layout 1"), fontSize(14), fontColour(175, 195, 255), corners(0), colour(50, 70, 150)
button bounds(0, 0, 599, 30), channel("layout_1_button"), text(""), colour:0(90, 90, 140, 0), colour:1(50, 60, 80, 0), latched(0), presetIgnore(1)
label bounds(601, 0, 599, 30), channel("layout_2_label") text("Layout 2"), fontSize(14), fontColour(175, 195, 255), corners(0), colour(50, 70, 90), presetIgnore(1)
button bounds(600, 0, 600, 30), channel("layout_2_button"), text(""), colour:0(90, 90, 140, 0), colour:1(50, 60, 80, 0), latched(0), presetIgnore(1)
hslider bounds(464, 370, 500, 50), channel("dry_signal"), range(0, 1, 1, 1, 0.01), text("'Dry' Signal"), trackerColour(99, 126, 171), outlineColour(0, 0, 0, 50), colour(27, 55, 102), textColour(175, 195, 255)
hslider bounds(466, 450, 500, 50), channel("reverb"), range(0, 1, 0.5, 1, 0.01), text("Reverb"), trackerColour(99, 126, 171), outlineColour(0, 0, 0, 50), colour(27, 55, 102), textColour(175, 195, 255)

</Cabbage>
<CsoundSynthesizer>
<CsOptions>
-n -d
</CsOptions>
<CsInstruments>
ksmps = 100
nchnls = 2
0dbfs = 1

gkLayout init 1

instr SelectLayoutListener
    kLayout1Button, kTrigger1 cabbageGetValue "layout_1_button"
    kLayout2Button, kTrigger2 cabbageGetValue "layout_2_button"
    
    if kLayout1Button + kTrigger1 > 1 then
        gkLayout = 1
    elseif kLayout2Button + kTrigger2 > 1 then
        gkLayout = 2
    endif
    if kLayout1Button + kTrigger1 > 1 || kLayout2Button + kTrigger2 > 1 then
        event("i", "SetLayoutButtonColors", 0, 0, gkLayout)
        event("i", "SetHorizSlidersLayout", 0, 0, gkLayout)
    endif
endin

instr SetLayoutButtonColors
    iLayout = p4
    if iLayout == 1 then
        cabbageSet "layout_1_label", "colour:0", 50, 70, 150
        cabbageSet "layout_2_label", "colour:0", 50, 70, 90
    elseif iLayout == 2 then
        cabbageSet "layout_1_label", "colour:0", 50, 70, 90
        cabbageSet "layout_2_label", "colour:0", 50, 70, 150
    endif
endin

instr SetHorizSlidersLayout
    iLayout = p4
    if iLayout == 1 then
        cabbageSet "dry_signal", "bounds", 464, 370, 500, 50
        cabbageSet "reverb", "bounds", 466, 450, 500, 50
        iDryValue cabbageGetValue "dry_signal"
        iReverbValue cabbageGetValue "reverb"
        print iDryValue
        print iReverbValue
    elseif iLayout == 2 then
        cabbageSet "dry_signal", "bounds", 163, 380, 380, 50
        cabbageSet "reverb", "bounds", 165, 460, 380, 50
        iDryValue cabbageGetValue "dry_signal"
        iReverbValue cabbageGetValue "reverb"
    endif
endin

</CsInstruments>
<CsScore>
i "SelectLayoutListener" 0 1000
</CsScore>
</CsoundSynthesizer>

It looks like hrange sliders are fine, but vsliders are affected.

<Cabbage>
form caption("Untitled") size(1200, 720), guiMode("queue") pluginId("def1")
label bounds(0, 0, 600, 30), channel("layout_1_label"), text("Layout 1"), fontSize(14), fontColour(175, 195, 255), corners(0), colour(50, 70, 150)
button bounds(0, 0, 599, 30), channel("layout_1_button"), text(""), colour:0(90, 90, 140, 0), colour:1(50, 60, 80, 0), latched(0), presetIgnore(1)
label bounds(601, 0, 599, 30), channel("layout_2_label") text("Layout 2"), fontSize(14), fontColour(175, 195, 255), corners(0), colour(50, 70, 90), presetIgnore(1)
button bounds(600, 0, 600, 30), channel("layout_2_button"), text(""), colour:0(90, 90, 140, 0), colour:1(50, 60, 80, 0), latched(0), presetIgnore(1)
hrange bounds(466, 130, 500, 50), channel("min_duration", "max_duration"), range(0.25, 5, 0.25:1.5, 1, 0.001), text("Soundbyte Length (0.25s - 5s)"), trackerColour(99, 126, 171), textColour(175, 195, 255), colour(27, 55, 102) colour:0(27, 55, 102)
vslider bounds(996, 230, 150, 445), channel("volume"), range(0, 1, 0.75, 1, 0.01), text("Volume"), trackerColour(99, 126, 171), colour(27, 55, 102), textColour(175, 195, 255)
</Cabbage>
<CsoundSynthesizer>
<CsOptions>
-n -d
</CsOptions>
<CsInstruments>
ksmps = 100
nchnls = 2
0dbfs = 1

gkLayout init 1


instr SelectLayoutListener
    kLayout1Button, kTrigger1 cabbageGetValue "layout_1_button"
    kLayout2Button, kTrigger2 cabbageGetValue "layout_2_button"
    
    if kLayout1Button + kTrigger1 > 1 then
        gkLayout = 1
    elseif kLayout2Button + kTrigger2 > 1 then
        gkLayout = 2
    endif
    if kLayout1Button + kTrigger1 > 1 || kLayout2Button + kTrigger2 > 1 then
        event("i", "SetLayoutButtonColors", 0, 0, gkLayout)
        event("i", "SetSlidersLayout", 0, 0, gkLayout)
    endif
endin

instr SetLayoutButtonColors
    iLayout = p4
    if iLayout == 1 then
        cabbageSet "layout_1_label", "colour:0", 50, 70, 150
        cabbageSet "layout_2_label", "colour:0", 50, 70, 90
    elseif iLayout == 2 then
        cabbageSet "layout_1_label", "colour:0", 50, 70, 90
        cabbageSet "layout_2_label", "colour:0", 50, 70, 150
    endif
endin

instr SetSlidersLayout
    iLayout = p4
    if iLayout == 1 then
        cabbageSet "min_duration", "bounds", 466, 130, 500, 50
        cabbageSet "volume", "bounds", 996, 230, 150, 445
        iMinDuration cabbageGetValue "min_duration"
        iVolume cabbageGetValue "volume"
        print iMinDuration, iVolume
    elseif iLayout == 2 then
        cabbageSet "min_duration", "bounds", 165, 620, 410, 50
        cabbageSet "volume", "bounds", 1070, 230, 110, 445
        iMinDuration cabbageGetValue "min_duration"
        iVolume  cabbageGetValue "volume"
        print iMinDuration, iVolume
    endif
endin

</CsInstruments>
<CsScore>
i "SelectLayoutListener" 0 1000
</CsScore>
</CsoundSynthesizer>

Thanks @Yardbird78, this looks like a bug. I’ll take a look now and see if I can sort it.

[edit] This is fixed now. you can grab the latest dev build when it’s finished building :slight_smile:

Fantastic, Rory, thanks so much! I appreciate your speed on this!

I might be missing something obvious, but it seems like there is no Windows installer in the zip file?

Thanks for your help!

I’m just fixing that as we speak…

[edit] new build triggered, it should have a Windows installer when it’s finished :+1:

1 Like

So it looks like the code I presented does exactly what I was hoping after your fix! (That’s good!) But also for some reason my project doesn’t work anymore (less good lol). So I found that if I create the slider widgets with cabbageCreate then when I change the widget’s bounds it seems to change both the appearance and the value of the slider back to default (before it was just changing the appearance). BTW hrange still behaves they way I like. I wonder if it might be possible to have the value and the appearance reflect the same value before and after changing the bounds (like hrange), even when the widgets were created using cabbageCreate?

I’m not 100% sure if this is the reason my project broke, but was using cabbageCreate a lot.

My misbehaving code:

<Cabbage>
form caption("Untitled") size(1200, 720), guiMode("queue") pluginId("def1")
label bounds(0, 0, 600, 30), channel("layout_1_label"), text("Layout 1"), fontSize(14), fontColour(175, 195, 255), corners(0), colour(50, 70, 150)
button bounds(0, 0, 599, 30), channel("layout_1_button"), text(""), colour:0(90, 90, 140, 0), colour:1(50, 60, 80, 0), latched(0), presetIgnore(1)
label bounds(601, 0, 599, 30), channel("layout_2_label") text("Layout 2"), fontSize(14), fontColour(175, 195, 255), corners(0), colour(50, 70, 90), presetIgnore(1)
button bounds(600, 0, 600, 30), channel("layout_2_button"), text(""), colour:0(90, 90, 140, 0), colour:1(50, 60, 80, 0), latched(0), presetIgnore(1)
</Cabbage>
<CsoundSynthesizer>
<CsOptions>
-n -d
</CsOptions>
<CsInstruments>
ksmps = 100
nchnls = 2
0dbfs = 1

gkLayout init 1

instr CreateSliders
    cabbageCreate("hrange", "bounds(466, 130, 500, 50), channel(\"min_duration\", \"max_duration\"), range(0.25, 5, 0.25:1.5, 1, 0.001), text(\"Soundbyte Length (0.25s - 5s)\"), trackerColour(99, 126, 171), textColour(175, 195, 255), colour(27, 55, 102) colour:0(27, 55, 102)")
    cabbageCreate("vslider", "bounds(996, 230, 150, 445), channel(\"volume\"), range(0, 1, 0.75, 1, 0.01), text(\"Volume\"), trackerColour(99, 126, 171), colour(27, 55, 102), textColour(175, 195, 255)")
    cabbageCreate("hslider", "bounds(466, 450, 500, 50), channel(\"reverb\"), range(0, 1, 0.5, 1, 0.01), text(\"Reverb\"), trackerColour(99, 126, 171), outlineColour(0, 0, 0, 50), colour(27, 55, 102), textColour(175, 195, 255)")
endin

instr SelectLayoutListener
    kLayout1Button, kTrigger1 cabbageGetValue "layout_1_button"
    kLayout2Button, kTrigger2 cabbageGetValue "layout_2_button"
    
    if kLayout1Button + kTrigger1 > 1 then
        gkLayout = 1
    elseif kLayout2Button + kTrigger2 > 1 then
        gkLayout = 2
    endif
    if kLayout1Button + kTrigger1 > 1 || kLayout2Button + kTrigger2 > 1 then
        event("i", "SetLayoutButtonColors", 0, 0, gkLayout)
        event("i", "SetSlidersLayout", 0, 0, gkLayout)
    endif
endin

instr SetLayoutButtonColors
    iLayout = p4
    if iLayout == 1 then
        cabbageSet "layout_1_label", "colour:0", 50, 70, 150
        cabbageSet "layout_2_label", "colour:0", 50, 70, 90
    elseif iLayout == 2 then
        cabbageSet "layout_1_label", "colour:0", 50, 70, 90
        cabbageSet "layout_2_label", "colour:0", 50, 70, 150
    endif
endin

instr SetSlidersLayout
    iLayout = p4
    if iLayout == 1 then
        cabbageSet "min_duration", "bounds", 466, 130, 500, 50
        cabbageSet "volume", "bounds", 996, 230, 150, 445
        cabbageSet "reverb", "bounds", 466, 450, 500, 50
        iMinDuration cabbageGetValue "min_duration"
        iVolume cabbageGetValue "volume"
        iReverb cabbageGetValue "reverb"
        print iMinDuration, iVolume, iReverb
    elseif iLayout == 2 then
        cabbageSet "min_duration", "bounds", 165, 620, 410, 50
        cabbageSet "volume", "bounds", 1070, 230, 110, 445
        cabbageSet "reverb", "bounds", 165, 460, 380, 50
        iMinDuration cabbageGetValue "min_duration"
        iVolume  cabbageGetValue "volume"
        iReverb cabbageGetValue "reverb"
        print iMinDuration, iVolume, iReverb
    endif
endin

</CsInstruments>
<CsScore>
i "CreateSliders" 0 0
i "SelectLayoutListener" 0 1000
</CsScore>
</CsoundSynthesizer>

That’s odd, I will take a look. I can’t think why cabbageCreate would cause things to break again.

It works if you use {{ }} to encapsulate the string:

cabbageCreate("hrange",  {{ bounds(466, 130, 500, 50), channel("min_duration", "max_duration"), range(0.25, 5, 0.25:1.5, 1, 0.001), text("Soundbyte Length (0.25s - 5s)"), trackerColour(99, 126, 171), textColour(175, 195, 255), colour(27, 55, 102) colour:0(27, 55, 102) }})
cabbageCreate("vslider", {{ bounds(996, 230, 150, 445), channel("volume"), range(0, 1, 0.75, 1, 0.01), text("Volume"), trackerColour(99, 126, 171), colour(27, 55, 102), textColour(175, 195, 255) }})
cabbageCreate("hslider", {{ bounds(466, 450, 500, 50), channel("reverb"), range(0, 1, 0.5, 1, 0.01), text("Reverb"), trackerColour(99, 126, 171), outlineColour(0, 0, 0, 50), colour(27, 55, 102), textColour(175, 195, 255) }})

It appears that the channels are somehow not registered in your code. I don’t know why, but until I figure it out, at least you have a work around.