mirror of
https://github.com/jhbruhn/eurorack.git
synced 2025-03-15 02:55:49 +00:00
Create PartData struct for part to store it in flash
This commit is contained in:
parent
abf9769e18
commit
337b9e1e75
7 changed files with 59 additions and 83 deletions
|
@ -21,7 +21,7 @@ Settings settings;
|
||||||
|
|
||||||
Part parts[PART_COUNT];
|
Part parts[PART_COUNT];
|
||||||
Part* part_pointers[PART_COUNT] = { &parts[0], &parts[1], &parts[2], &parts[3] };
|
Part* part_pointers[PART_COUNT] = { &parts[0], &parts[1], &parts[2], &parts[3] };
|
||||||
UI ui(part_pointers);
|
UI ui(part_pointers, &settings);
|
||||||
|
|
||||||
// Default interrupt handlers.
|
// Default interrupt handlers.
|
||||||
extern "C" {
|
extern "C" {
|
||||||
|
|
|
@ -54,42 +54,39 @@ typedef enum : uint8_t {
|
||||||
VOICE_DETAIL_XL = 3
|
VOICE_DETAIL_XL = 3
|
||||||
} PartVoiceDetail_t;
|
} PartVoiceDetail_t;
|
||||||
|
|
||||||
class Part {
|
struct PartData { // Everything defined here will be stored in flash even in power down
|
||||||
public:
|
PartVoiceCount_t part_voice_count = VOICE_COUNT_1;
|
||||||
Part()
|
PartVoiceDetail_t part_voice_detail = VOICE_DETAIL_S;
|
||||||
: part_voice_count(VOICE_COUNT_1)
|
bool midi_filter_channel_enabled = true;
|
||||||
, part_voice_detail(VOICE_DETAIL_S)
|
uint8_t midi_filter_channel = 1;
|
||||||
, midi_filter_channel_enabled(true)
|
uint8_t midi_filter_lowest_note = 0;
|
||||||
, midi_filter_channel(1)
|
uint8_t midi_filter_highest_note = 127;
|
||||||
, midi_filter_lowest_note(0)
|
MIDIInput_t midi_filter_input = MIDI_INPUT_OMNI;
|
||||||
, midi_filter_highest_note(127)
|
MIDIThruMode_t midi_thru_mode = MIDI_THRU_OFF;
|
||||||
, midi_thru_mode(MIDI_THRU_OFF)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < TOTAL_COLUMN_COUNT; i++) {
|
|
||||||
output_type_row_0[i] = BI_OFF;
|
|
||||||
output_type_row_1[i] = UNI_OFF;
|
|
||||||
output_type_row_2[i] = UNI_OFF;
|
|
||||||
output_type_row_3[i] = GATE_OFF;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
void ProcessMidiInput(/* TODO: Inputs */);
|
|
||||||
|
|
||||||
uint8_t RequiredColumns();
|
|
||||||
|
|
||||||
PartVoiceCount_t part_voice_count;
|
|
||||||
PartVoiceDetail_t part_voice_detail;
|
|
||||||
bool midi_filter_channel_enabled;
|
|
||||||
uint8_t midi_filter_channel;
|
|
||||||
uint8_t midi_filter_lowest_note;
|
|
||||||
uint8_t midi_filter_highest_note;
|
|
||||||
MIDIInput_t midi_filter_input;
|
|
||||||
MIDIThruMode_t midi_thru_mode;
|
|
||||||
BiOutputType_t output_type_row_0[TOTAL_COLUMN_COUNT];
|
BiOutputType_t output_type_row_0[TOTAL_COLUMN_COUNT];
|
||||||
UniOutputType_t output_type_row_1[TOTAL_COLUMN_COUNT];
|
UniOutputType_t output_type_row_1[TOTAL_COLUMN_COUNT];
|
||||||
UniOutputType_t output_type_row_2[TOTAL_COLUMN_COUNT];
|
UniOutputType_t output_type_row_2[TOTAL_COLUMN_COUNT];
|
||||||
GateOutputType_t output_type_row_3[TOTAL_COLUMN_COUNT];
|
GateOutputType_t output_type_row_3[TOTAL_COLUMN_COUNT];
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class Part {
|
||||||
|
public:
|
||||||
|
Part()
|
||||||
|
{
|
||||||
|
for (int i = 0; i < TOTAL_COLUMN_COUNT; i++) {
|
||||||
|
data.output_type_row_0[i] = BI_OFF;
|
||||||
|
data.output_type_row_1[i] = UNI_OFF;
|
||||||
|
data.output_type_row_2[i] = UNI_OFF;
|
||||||
|
data.output_type_row_3[i] = GATE_OFF;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void ProcessMidiInput(/* TODO: Inputs */);
|
||||||
|
|
||||||
|
uint8_t RequiredColumns();
|
||||||
|
|
||||||
|
PartData data;
|
||||||
|
};
|
||||||
|
|
||||||
extern Part parts[];
|
extern Part parts[];
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -1,23 +1,11 @@
|
||||||
#include "settings.h"
|
#include "settings.h"
|
||||||
#include "midi2cv/part.h"
|
#include "midi2cv/part.h"
|
||||||
|
|
||||||
Settings::Settings()
|
Settings::Settings() : first_start(false)
|
||||||
{
|
{
|
||||||
persistent_data_.honor = 1;
|
persistent_data_.honor = 1;
|
||||||
|
|
||||||
for (int i = 0; i < PART_COUNT; i++) {
|
first_start = !chunk_storage_.Init(&persistent_data_, &state_);
|
||||||
PartState* part = &state_.part_states[i];
|
|
||||||
|
|
||||||
part->midi_filter_channel = 1;
|
|
||||||
part->midi_filter_channel_enabled = true;
|
|
||||||
part->midi_filter_lowest_note = 0;
|
|
||||||
part->midi_filter_highest_note = 127;
|
|
||||||
part->midi_filter_input = MIDI_INPUT_OMNI;
|
|
||||||
part->part_voice_count = VOICE_COUNT_1;
|
|
||||||
part->part_voice_detail = VOICE_DETAIL_S;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*bool success =*/chunk_storage_.Init(&persistent_data_, &state_);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Settings::SavePersistentData()
|
void Settings::SavePersistentData()
|
||||||
|
|
|
@ -7,23 +7,12 @@
|
||||||
|
|
||||||
struct PersistentData {
|
struct PersistentData {
|
||||||
uint8_t honor;
|
uint8_t honor;
|
||||||
uint8_t padding[15];
|
uint8_t padding[7];
|
||||||
enum { tag = 0x494C4143 }; // CALI
|
enum { tag = 0x494C4143 }; // CALI
|
||||||
};
|
};
|
||||||
|
|
||||||
struct PartState { // 8 bytes, TODO: can these be pointers to the actual values, or can we do some other copying magic?
|
|
||||||
PartVoiceCount_t part_voice_count;
|
|
||||||
PartVoiceDetail_t part_voice_detail;
|
|
||||||
uint8_t midi_filter_channel_enabled;
|
|
||||||
uint8_t midi_filter_channel;
|
|
||||||
uint8_t midi_filter_lowest_note;
|
|
||||||
uint8_t midi_filter_highest_note;
|
|
||||||
MIDIInput_t midi_filter_input;
|
|
||||||
MIDIThruMode_t midi_thru_mode;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct State {
|
struct State {
|
||||||
PartState part_states[PART_COUNT]; // 4 * 8 bytes
|
PartData part_datas[PART_COUNT];
|
||||||
//uint8_t padding[4];
|
//uint8_t padding[4];
|
||||||
enum { tag = 0x54415453 }; // STAT
|
enum { tag = 0x54415453 }; // STAT
|
||||||
};
|
};
|
||||||
|
@ -56,17 +45,22 @@ class Settings {
|
||||||
return &state_;
|
return &state_;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline const PartState& part(int i) const
|
inline const PartData& part(int i) const
|
||||||
{
|
{
|
||||||
return state_.part_states[i];
|
return state_.part_datas[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
inline PartState* mutable_part(int i)
|
inline PartData* mutable_part(int i)
|
||||||
{
|
{
|
||||||
return &state_.part_states[i];
|
return &state_.part_datas[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
inline bool is_first_start() {
|
||||||
|
return this->first_start;
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
bool first_start;
|
||||||
PersistentData persistent_data_;
|
PersistentData persistent_data_;
|
||||||
State state_;
|
State state_;
|
||||||
|
|
||||||
|
@ -79,5 +73,3 @@ class Settings {
|
||||||
|
|
||||||
DISALLOW_COPY_AND_ASSIGN(Settings);
|
DISALLOW_COPY_AND_ASSIGN(Settings);
|
||||||
};
|
};
|
||||||
|
|
||||||
extern Settings settings;
|
|
||||||
|
|
|
@ -14,11 +14,12 @@ using namespace stmlib;
|
||||||
|
|
||||||
const uint32_t kEncoderLongPressTime = 600;
|
const uint32_t kEncoderLongPressTime = 600;
|
||||||
|
|
||||||
UI::UI(Part** part_pointers)
|
UI::UI(Part** part_pointers, Settings* settings)
|
||||||
: main_menu(part_pointers)
|
: main_menu(part_pointers)
|
||||||
, parts(part_pointers)
|
, parts(part_pointers)
|
||||||
{
|
{
|
||||||
this->input_queue.Init();
|
this->input_queue.Init();
|
||||||
|
this->settings = settings;
|
||||||
|
|
||||||
LoadState();
|
LoadState();
|
||||||
}
|
}
|
||||||
|
@ -61,22 +62,17 @@ void UI::Draw()
|
||||||
|
|
||||||
void UI::LoadState()
|
void UI::LoadState()
|
||||||
{
|
{
|
||||||
for (size_t i = 0; i < PART_COUNT; i++) {
|
for(size_t i = 0; i < PART_COUNT; i++)
|
||||||
parts[i]->midi_filter_channel = settings.part(i).midi_filter_channel;
|
this->parts[i]->data = settings->part(i);
|
||||||
parts[i]->midi_filter_channel_enabled = settings.part(i).midi_filter_channel_enabled;
|
|
||||||
parts[i]->midi_filter_lowest_note = settings.part(i).midi_filter_lowest_note;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void UI::SaveState()
|
void UI::SaveState()
|
||||||
{
|
{
|
||||||
for (size_t i = 0; i < PART_COUNT; i++) {
|
for (size_t i = 0; i < PART_COUNT; i++) {
|
||||||
settings.mutable_part(i)->midi_filter_channel = this->parts[i]->midi_filter_channel;
|
*(settings->mutable_part(i)) = this->parts[i]->data;
|
||||||
settings.mutable_part(i)->midi_filter_channel_enabled = this->parts[i]->midi_filter_channel_enabled;
|
|
||||||
settings.mutable_part(i)->midi_filter_lowest_note = this->parts[i]->midi_filter_lowest_note;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
settings.SaveState();
|
settings->SaveState();
|
||||||
}
|
}
|
||||||
|
|
||||||
void UI::Flush()
|
void UI::Flush()
|
||||||
|
|
|
@ -5,12 +5,13 @@
|
||||||
#include "stmlib/ui/event_queue.h"
|
#include "stmlib/ui/event_queue.h"
|
||||||
|
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
|
#include "settings.h"
|
||||||
#include "ui/main_menu.h"
|
#include "ui/main_menu.h"
|
||||||
#include <array>
|
#include <array>
|
||||||
|
|
||||||
class UI {
|
class UI {
|
||||||
public:
|
public:
|
||||||
UI(Part** part_pointers);
|
UI(Part** part_pointers, Settings* settings);
|
||||||
~UI() {}
|
~UI() {}
|
||||||
|
|
||||||
void Poll();
|
void Poll();
|
||||||
|
@ -20,6 +21,8 @@ class UI {
|
||||||
private:
|
private:
|
||||||
stmlib::EventQueue<16> input_queue;
|
stmlib::EventQueue<16> input_queue;
|
||||||
|
|
||||||
|
Settings* settings;
|
||||||
|
|
||||||
bool long_press_event_sent_;
|
bool long_press_event_sent_;
|
||||||
uint32_t start_stop_press_time_;
|
uint32_t start_stop_press_time_;
|
||||||
bool encoder_long_press_event_sent_;
|
bool encoder_long_press_event_sent_;
|
||||||
|
|
|
@ -12,14 +12,14 @@ static const char* kMidiThruStrings[] = { "off", "on", "polychain" };
|
||||||
|
|
||||||
PartMenu::PartMenu(Part* _part)
|
PartMenu::PartMenu(Part* _part)
|
||||||
: part(_part)
|
: part(_part)
|
||||||
, item_voice_count("voice count", (uint8_t*)&_part->part_voice_count, 1, 4, 1)
|
, item_voice_count("voice count", (uint8_t*)&_part->data.part_voice_count, 1, 4, 1)
|
||||||
, item_voice_detail("voice detail", (uint8_t*)&_part->part_voice_detail, kVoiceDetailStrings, 4)
|
, item_voice_detail("voice detail", (uint8_t*)&_part->data.part_voice_detail, kVoiceDetailStrings, 4)
|
||||||
, item_midi_filter_enabled("MIDI filter", &_part->midi_filter_channel_enabled, "on", "off")
|
, item_midi_filter_enabled("MIDI filter", &_part->data.midi_filter_channel_enabled, "on", "off")
|
||||||
, item_midi_channel("MIDI channel", (uint8_t*)&_part->midi_filter_channel, kMidiChannelStrings, 17)
|
, item_midi_channel("MIDI channel", (uint8_t*)&_part->data.midi_filter_channel, kMidiChannelStrings, 17)
|
||||||
, item_midi_input("MIDI input", (uint8_t*)&_part->midi_filter_input, kMidiInputStrings, 3)
|
, item_midi_input("MIDI input", (uint8_t*)&_part->data.midi_filter_input, kMidiInputStrings, 3)
|
||||||
, item_midi_lowest_note("MIDI lowest", (uint8_t*)&_part->midi_filter_lowest_note)
|
, item_midi_lowest_note("MIDI lowest", (uint8_t*)&_part->data.midi_filter_lowest_note)
|
||||||
, item_midi_highest_note("MIDI highest", (uint8_t*)&_part->midi_filter_highest_note)
|
, item_midi_highest_note("MIDI highest", (uint8_t*)&_part->data.midi_filter_highest_note)
|
||||||
, item_midi_thru_mode("MIDI thru", (uint8_t*)&_part->midi_thru_mode, kMidiThruStrings, 3)
|
, item_midi_thru_mode("MIDI thru", (uint8_t*)&_part->data.midi_thru_mode, kMidiThruStrings, 3)
|
||||||
{
|
{
|
||||||
this->menu.add_item(&this->item_voice_count);
|
this->menu.add_item(&this->item_voice_count);
|
||||||
this->menu.add_item(&this->item_voice_detail);
|
this->menu.add_item(&this->item_voice_detail);
|
||||||
|
|
Loading…
Reference in a new issue