29 using Integer::Integer;
31 void readCurrentValue()
override { this->setValue(soundEditor.currentSound->unisonDetune); }
33 void writeCurrentValue()
override {
34 int32_t current_value = this->getValue();
37 if (currentUIMode == UI_MODE_HOLDING_AFFECT_ENTIRE_IN_SOUND_EDITOR && soundEditor.editingKitRow()) {
39 Kit* kit = getCurrentKit();
41 for (
Drum* thisDrum = kit->firstDrum; thisDrum !=
nullptr; thisDrum = thisDrum->next) {
42 if (thisDrum->type == DrumType::SOUND) {
43 auto* soundDrum =
static_cast<SoundDrum*
>(thisDrum);
45 char modelStackMemoryForSoundDrum[MODEL_STACK_MAX_SIZE];
47 getModelStackFromSoundDrum(modelStackMemoryForSoundDrum, soundDrum)->addSoundFlags();
49 soundDrum->setUnisonDetune(current_value, modelStackForSoundDrum);
55 char modelStackMemory[MODEL_STACK_MAX_SIZE];
58 soundEditor.currentSound->setUnisonDetune(current_value, modelStack);
61 [[nodiscard]] int32_t getMaxValue()
const override {
return kMaxUnisonDetune; }
63 void renderInHorizontalMenu(int32_t startX, int32_t width, int32_t startY, int32_t height)
override {
64 oled_canvas::Canvas& image = OLED::main;
66 const float t = getValue() / 50.0f;
68 for (
int i = 0; i < 3; ++i) {
69 constexpr int32_t lineSpacing = 5;
70 constexpr int32_t maxYOffset = 4;
72 const int32_t y = startY + 3 + i * lineSpacing;
73 const int32_t x0 = startX + 7;
74 const int32_t x1 = startX + width - 7;
78 const int32_t offset =
static_cast<int32_t
>(maxYOffset * t * 0.30f);
79 image.drawLine(x0, y, x1, y + offset);
83 const int32_t offset =
static_cast<int32_t
>(maxYOffset * t * 0.5f);
84 image.drawLine(x0, y - offset, x1, y + offset);
86 if (t > 0.7 && t < 1) {
87 image.clearPixel(x0, y - offset);
88 image.clearPixel(x1, y + offset);
89 image.drawPixel(x0, y - offset - 1);
90 image.drawPixel(x1, y + offset + 1);
95 int32_t offset = y -
static_cast<int32_t
>(maxYOffset * t * 0.8f);
96 if (t > 0 && offset == y) {
100 image.drawLine(x0, offset, x1 - 8, y);
101 image.drawHorizontalLine(y, x1 - 8, x1);