-
-
Notifications
You must be signed in to change notification settings - Fork 85
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Feature: Waveform loop lock #293
Changes from 13 commits
8dee117
0b74c59
8147e84
88d40c2
ca7a173
86e0347
85ef194
6c8e205
96f49cd
460a504
1b6dc94
7317e1d
2db7410
981ddb5
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -51,6 +51,9 @@ extern "C" { | |
|
||
const uint8_t zeroes[] = {0, 0, 0, 0, 0, 0, 0, 0}; | ||
|
||
int loopLength = 0; | ||
bool loopLocked = false; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. these would probably benefit from being members of |
||
|
||
SampleMarkerEditor sampleMarkerEditor{}; | ||
|
||
SampleMarkerEditor::SampleMarkerEditor() { | ||
|
@@ -142,10 +145,28 @@ void SampleMarkerEditor::writeValue(uint32_t value, MarkerType markerTypeNow) { | |
getCurrentSampleHolder()->startPos = value; | ||
} | ||
else if (markerTypeNow == MarkerType::LOOP_START) { | ||
getCurrentMultisampleRange()->sampleHolder.loopStartPos = value; | ||
if (loopLocked) { | ||
int intendedLoopEndPos = value + loopLength; | ||
if (intendedLoopEndPos <= getCurrentSampleHolder()->endPos) { | ||
getCurrentMultisampleRange()->sampleHolder.loopStartPos = value; | ||
getCurrentMultisampleRange()->sampleHolder.loopEndPos = intendedLoopEndPos; | ||
} | ||
} | ||
else { | ||
getCurrentMultisampleRange()->sampleHolder.loopStartPos = value; | ||
} | ||
} | ||
else if (markerTypeNow == MarkerType::LOOP_END) { | ||
getCurrentMultisampleRange()->sampleHolder.loopEndPos = value; | ||
if (loopLocked) { | ||
int intendedLoopStartPos = value - loopLength; | ||
if (intendedLoopStartPos >= getCurrentSampleHolder()->startPos) { | ||
getCurrentMultisampleRange()->sampleHolder.loopEndPos = value; | ||
getCurrentMultisampleRange()->sampleHolder.loopStartPos = intendedLoopStartPos; | ||
} | ||
} | ||
else { | ||
getCurrentMultisampleRange()->sampleHolder.loopEndPos = value; | ||
} | ||
} | ||
else if (markerTypeNow == MarkerType::END) { | ||
getCurrentSampleHolder()->endPos = value; | ||
|
@@ -426,6 +447,21 @@ ActionResult SampleMarkerEditor::padAction(int32_t x, int32_t y, int32_t on) { | |
|
||
goto ensureNotPastSampleLength; | ||
} | ||
else if (markerHeld == MarkerType::LOOP_START && markerPressed == MarkerType::LOOP_END) { | ||
if (loopLocked == false) { | ||
loopLocked = true; | ||
int loopStart = getCurrentMultisampleRange()->sampleHolder.loopStartPos; | ||
int loopEnd = getCurrentMultisampleRange()->sampleHolder.loopEndPos; | ||
loopLength = loopEnd - loopStart; | ||
numericDriver.displayPopup("LOCK"); | ||
} | ||
else { | ||
loopLocked = false; | ||
loopLength = 0; | ||
numericDriver.displayPopup("FREE"); | ||
} | ||
return ActionResult::DEALT_WITH; | ||
} | ||
|
||
// Or if a loop point and they pressed the end marker, remove the loop point | ||
else if (markerHeld == MarkerType::LOOP_START) { | ||
|
@@ -623,6 +659,39 @@ static const uint32_t zoomUIModes[] = {UI_MODE_HOLDING_HORIZONTAL_ENCODER_BUTTON | |
|
||
ActionResult SampleMarkerEditor::horizontalEncoderAction(int32_t offset) { | ||
|
||
if (loopLocked && Buttons::isShiftButtonPressed()) { | ||
if (offset > 0) { // turn clockwise | ||
int end = getCurrentSampleHolder()->endPos; | ||
int loopEnd = getCurrentMultisampleRange()->sampleHolder.loopEndPos; | ||
|
||
if (loopEnd + loopLength < end) { | ||
loopLength = loopLength * 2; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. is this right? This reads like it's doubling/halfing the loop length when you turn the knob instead of incrementing it which is not how I read the conversation There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yes, it's right. I did think we might be at different viewpoints here. The intention is that you'll set a loop length related to the tempo of the sample or track then doubling or halving the loop length will keep it rhythmically intact. Being able to arbitrarily adjust the loop length with SHIFT+TURN<> is fine but I'd still want a want to exactly double or half it. It's a magic way to find cool and unusual looping sections within samples. Maybe SHIFT+PUSH+TURN<> for doubling/halving? Then use SHIFT+TURN<> for continuous change. |
||
numericDriver.displayPopup(HAVE_OLED ? "Loop doubled" : "DOUB"); | ||
} | ||
else { | ||
numericDriver.displayPopup(HAVE_OLED ? "Loop too long" : "CANT"); | ||
return ActionResult::DEALT_WITH; | ||
} | ||
} | ||
else { // turn anti-clockwise | ||
if (loopLength > 2) { | ||
loopLength = loopLength / 2; | ||
numericDriver.displayPopup(HAVE_OLED ? "Loop halved" : "HALF"); | ||
} | ||
else { | ||
numericDriver.displayPopup(HAVE_OLED ? "Loop too short" : "CANT"); | ||
return ActionResult::DEALT_WITH; | ||
} | ||
} | ||
|
||
int loopStart = getCurrentMultisampleRange()->sampleHolder.loopStartPos; | ||
int newLoopEnd = loopStart + loopLength; | ||
writeValue(newLoopEnd, MarkerType::LOOP_END); | ||
uiNeedsRendering(this, 0xFFFFFFFF, 0); | ||
|
||
return ActionResult::DEALT_WITH; | ||
} | ||
|
||
// We're quite likely going to need to read the SD card to do either scrolling or zooming | ||
if (sdRoutineLock) { | ||
return ActionResult::REMIND_ME_OUTSIDE_CARD_ROUTINE; | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it should be shift+turn to edit loop length, shift+press to double. It feels weird having this little control over length if the loop is longer than a few samples
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
See my response above about doubling/halving.