OpenShot Audio Library | OpenShotAudio  0.6.0
juce_ValueTreePropertyWithDefault.h
1 /*
2  ==============================================================================
3 
4  This file is part of the JUCE library.
5  Copyright (c) 2022 - Raw Material Software Limited
6 
7  JUCE is an open source library subject to commercial or open-source
8  licensing.
9 
10  By using JUCE, you agree to the terms of both the JUCE 7 End-User License
11  Agreement and JUCE Privacy Policy.
12 
13  End User License Agreement: www.juce.com/juce-7-licence
14  Privacy Policy: www.juce.com/juce-privacy-policy
15 
16  Or: You may also use this code under the terms of the GPL v3 (see
17  www.gnu.org/licenses).
18 
19  JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER
20  EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE
21  DISCLAIMED.
22 
23  ==============================================================================
24 */
25 
26 namespace juce
27 {
28 
29 //==============================================================================
39 {
40 public:
41  //==============================================================================
47 
53  const Identifier& propertyID,
54  UndoManager* um)
55  {
56  referTo (tree, propertyID, um);
57  }
58 
64  const Identifier& propertyID,
65  UndoManager* um,
66  var defaultToUse)
67  {
68  referTo (tree, propertyID, um, defaultToUse);
69  }
70 
80  const Identifier& propertyID,
81  UndoManager* um,
82  var defaultToUse,
83  StringRef arrayDelimiter)
84  {
85  referTo (tree, propertyID, um, defaultToUse, arrayDelimiter);
86  }
87 
90  {
91  referToWithDefault (other.targetTree,
92  other.targetProperty,
93  other.undoManager,
94  other.defaultValue,
95  other.delimiter);
96  }
97 
100  {
101  defaultValue.removeListener (this);
102  }
103 
104  //==============================================================================
109  var get() const noexcept
110  {
111  if (isUsingDefault())
112  return defaultValue;
113 
114  if (delimiter.isNotEmpty())
115  return delimitedStringToVarArray (targetTree[targetProperty].toString(), delimiter);
116 
117  return targetTree[targetProperty];
118  }
119 
121  Value getPropertyAsValue() { return targetTree.getPropertyAsValue (targetProperty, undoManager); }
122 
124  var getDefault() const { return defaultValue; }
125 
127  void setDefault (const var& newDefault) { defaultValue = newDefault; }
128 
130  bool isUsingDefault() const { return ! targetTree.hasProperty (targetProperty); }
131 
133  void resetToDefault() noexcept { targetTree.removeProperty (targetProperty, nullptr); }
134 
140  std::function<void()> onDefaultChange;
141 
142  //==============================================================================
147  ValueTreePropertyWithDefault& operator= (const var& newValue)
148  {
149  setValue (newValue, undoManager);
150  return *this;
151  }
152 
157  void setValue (const var& newValue, UndoManager* undoManagerToUse)
158  {
159  if (auto* array = newValue.getArray())
160  targetTree.setProperty (targetProperty, varArrayToDelimitedString (*array, delimiter), undoManagerToUse);
161  else
162  targetTree.setProperty (targetProperty, newValue, undoManagerToUse);
163  }
164 
165  //==============================================================================
171  void referTo (ValueTree tree,
172  const Identifier& property,
173  UndoManager* um)
174  {
175  referToWithDefault (tree,
176  property,
177  um,
178  Value (new SynchronousValueSource (var())),
179  {});
180  }
181 
187  void referTo (ValueTree tree,
188  const Identifier& property,
189  UndoManager* um,
190  var defaultVal)
191  {
192  referToWithDefault (tree,
193  property,
194  um,
195  Value (new SynchronousValueSource (defaultVal)),
196  {});
197  }
198 
204  void referTo (ValueTree tree,
205  const Identifier& property,
206  UndoManager* um,
207  var defaultVal,
208  StringRef arrayDelimiter)
209  {
210  referToWithDefault (tree,
211  property,
212  um,
213  Value (new SynchronousValueSource (defaultVal)),
214  arrayDelimiter);
215  }
216 
217  //==============================================================================
219  ValueTree& getValueTree() noexcept { return targetTree; }
220 
222  Identifier& getPropertyID() noexcept { return targetProperty; }
223 
225  UndoManager* getUndoManager() noexcept { return undoManager; }
226 
227  //==============================================================================
229  {
230  referToWithDefault (other.targetTree,
231  other.targetProperty,
232  other.undoManager,
233  other.defaultValue,
234  other.delimiter);
235 
236  return *this;
237  }
238 
239 private:
240  //==============================================================================
241  class SynchronousValueSource : public Value::ValueSource
242  {
243  public:
244  explicit SynchronousValueSource (const var& initialValue)
245  : value (initialValue)
246  {
247  }
248 
249  var getValue() const override
250  {
251  return value;
252  }
253 
254  void setValue (const var& newValue) override
255  {
256  if (! newValue.equalsWithSameType (value))
257  {
258  value = newValue;
259  sendChangeMessage (true);
260  }
261  }
262 
263  private:
264  var value;
265 
266  JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (SynchronousValueSource)
267  };
268 
269  //==============================================================================
270  static String varArrayToDelimitedString (const Array<var>& input, StringRef delim)
271  {
272  // if you are trying to control a var that is an array then you need to
273  // set a delimiter string that will be used when writing to XML!
274  jassert (delim.isNotEmpty());
275 
276  StringArray elements;
277 
278  for (auto& v : input)
279  elements.add (v.toString());
280 
281  return elements.joinIntoString (delim);
282  }
283 
284  static Array<var> delimitedStringToVarArray (StringRef input, StringRef delim)
285  {
286  Array<var> arr;
287 
288  for (auto t : StringArray::fromTokens (input, delim, {}))
289  arr.add (t);
290 
291  return arr;
292  }
293 
294  void valueChanged (Value&) override
295  {
296  NullCheckedInvocation::invoke (onDefaultChange);
297  }
298 
299  void referToWithDefault (ValueTree v,
300  const Identifier& i,
301  UndoManager* um,
302  const Value& defaultVal,
303  StringRef del)
304  {
305  targetTree = v;
306  targetProperty = i;
307  undoManager = um;
308  defaultValue.referTo (defaultVal);
309  delimiter = del;
310 
311  defaultValue.addListener (this);
312  }
313 
314  //==============================================================================
315  ValueTree targetTree;
316  Identifier targetProperty;
317  UndoManager* undoManager = nullptr;
318  Value defaultValue;
319  String delimiter;
320 
321  //==============================================================================
322  JUCE_LEAK_DETECTOR (ValueTreePropertyWithDefault)
323 };
324 
325 //==============================================================================
326 #ifndef DOXYGEN
327 using ValueWithDefault [[deprecated ("This class has been renamed to better describe what is does. "
328  "This declaration is here for backwards compatibility and new "
329  "code should use the new class name.")]]
330  = ValueTreePropertyWithDefault;
331 #endif
332 
333 } // namespace juce
static StringArray fromTokens(StringRef stringToTokenise, bool preserveQuotedStrings)
ValueTreePropertyWithDefault(ValueTree &tree, const Identifier &propertyID, UndoManager *um, var defaultToUse, StringRef arrayDelimiter)
void referTo(ValueTree tree, const Identifier &property, UndoManager *um, var defaultVal, StringRef arrayDelimiter)
void setValue(const var &newValue, UndoManager *undoManagerToUse)
void referTo(ValueTree tree, const Identifier &property, UndoManager *um, var defaultVal)
ValueTreePropertyWithDefault(const ValueTreePropertyWithDefault &other)
ValueTreePropertyWithDefault(ValueTree &tree, const Identifier &propertyID, UndoManager *um, var defaultToUse)
ValueTreePropertyWithDefault(ValueTree &tree, const Identifier &propertyID, UndoManager *um)
void referTo(ValueTree tree, const Identifier &property, UndoManager *um)
Array< var > * getArray() const noexcept