In my project I am using an AudioProcessorValueTreeState to store my parameters and chunks as it is described in the tutorial (Tutorial: Saving and loading your plug-in state).
For the creation of preset files I am using state.createXml() which gives me something like <PARAM id="m_uLFOWave_LFO1" value="2.00000000000000000000"/>. For the parameter if I have defined a valueToTextFunction and textToValueFunction that map the 2.f to “SINE” and vice versa.
Now I would like to create an XML instead that uses the texts and not the values. So for the example above I would need to get <PARAM id="m_uLFOWave_LFO1" text="SINE"/>. With this I hope to create preset files that are more robust to changes (so e.g. I could change the internal representation of sine to 3 in future without invalidating the preset files).
Is there an easy and elegant way of creating such an XML from my current ValueTree and retrieving it back later to a tree?
Hi there. Thanks for the answer. I should have mentioned that I am using the component attachments, e.g. AudioProcessorValueTreeState::SliderAttachment, ButtonAttachment and ComboBoxAttachment (in the example with “SINE” above). And I am defining the parameters with AudioProcessorValueTreeState::createAndAddParameter. From what I see all this only allows for float properties and not string. Do I miss something?
The way I understand this, the answer is probably not what you want to hear. I think of the parameters as floats, and the vt allows a sort of alias which is a string.
It seems like what you are trying to do can be done by changing the valueToTextFunction for param = 3. to “SINE”.
But you probably would still need to reorder things a bit as at the point both 2. and 3. have a valueToTextFunction to translate these to “SINE”.
Then again, I may not be understanding what you are asking…
@AnoesisAudio suggested the expected design. it should be well enough.
(the plug-in state isn’t something the user sees most time).
In addition, and information you provide would also help focusing any answer.
You should remember few things:
parameters are shared with the host. they eventually numeric values to the host. modes/stepped (only modern JUCE) or continuous.
They’re exposed to your host, that means the user can automate them. meaning the range/steps for the parameter would make automation data broken if you change your steps/range afterwards.
If you still want to save a different representation you’d simply take your APVTS copy it to a new ValueTree and encode/decode it.
But you would only do that on saving/loading state calls (to keep using the Attachments).
Yes, totally aware of that and this is why I want to keep my parameters as floats and have them managed by the attachments (including the change gestures to notify the host).
This is exactly what I am looking for. Could you be more specific on this one? How do I encode / decode my APVTS so that it contains the string representation of the float parameters? Do I have to code that manually by looping over all the parameters and calling the getText() / getValueForText() methods and create new tree attributes accordingly? Or is there a more elegant way of doing this?
auto copyOfYourAPVTS = params_.getValueTreeCopy();
copyOfYourAPVTS.setProperty(
<identifier_name_for_string_version>,
methodToReturnTxtVal(copyOfYourAPVTSstateToSave.getProperty(<identifier_name_for_numeric_version>)), nullptr);
// optional, delete the numeric property.
copyOfYourAPVTS.removeProperty(<identifier_name_for_numeric_version>, nullptr);
// same flow as with JUCE tutorials...
std::unique_ptr<XmlElement> xml (copyOfYourAPVTS.createXml());
copyXmlToBinary (*xml, destData);