mirror of
https://github.com/juce-framework/JUCE.git
synced 2026-01-22 01:34:21 +00:00
JSON: Added the ability to limit the number of decimal places when serialising floating point numbers
This commit is contained in:
parent
cb8f9b389c
commit
5b6e482a0d
6 changed files with 54 additions and 16 deletions
|
|
@ -1,6 +1,34 @@
|
|||
JUCE breaking changes
|
||||
=====================
|
||||
|
||||
Develop Branch
|
||||
=============
|
||||
|
||||
Change
|
||||
------
|
||||
The writeAsJSON virtual method of the DynamicObject class requires an
|
||||
additional parameter, maximumDecimalPlaces, to specify the maximum precision of
|
||||
floating point numbers.
|
||||
|
||||
Possible Issues
|
||||
---------------
|
||||
Classes which inherit from DynamicObject and override this method will need to
|
||||
update their method signature.
|
||||
|
||||
Workaround
|
||||
----------
|
||||
Your custom DynamicObject class can choose to ignore the additional parameter
|
||||
if you don't wish to support this behaviour.
|
||||
|
||||
Rationale
|
||||
---------
|
||||
When serialising the results of calculations to JSON the rounding of floating
|
||||
point numbers can result in numbers with 17 significant figures where only a
|
||||
few are required. This change to DynamicObject is required to support
|
||||
truncating those numbers.
|
||||
|
||||
|
||||
|
||||
Version 5.1.0
|
||||
=============
|
||||
|
||||
|
|
|
|||
|
|
@ -91,7 +91,7 @@ DynamicObject::Ptr DynamicObject::clone()
|
|||
return d;
|
||||
}
|
||||
|
||||
void DynamicObject::writeAsJSON (OutputStream& out, const int indentLevel, const bool allOnOneLine)
|
||||
void DynamicObject::writeAsJSON (OutputStream& out, const int indentLevel, const bool allOnOneLine, int maximumDecimalPlaces)
|
||||
{
|
||||
out << '{';
|
||||
if (! allOnOneLine)
|
||||
|
|
@ -107,7 +107,7 @@ void DynamicObject::writeAsJSON (OutputStream& out, const int indentLevel, const
|
|||
out << '"';
|
||||
JSONFormatter::writeString (out, properties.getName (i));
|
||||
out << "\": ";
|
||||
JSONFormatter::write (out, properties.getValueAt (i), indentLevel + JSONFormatter::indentSize, allOnOneLine);
|
||||
JSONFormatter::write (out, properties.getValueAt (i), indentLevel + JSONFormatter::indentSize, allOnOneLine, maximumDecimalPlaces);
|
||||
|
||||
if (i < numValues - 1)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -113,14 +113,14 @@ public:
|
|||
never need to call it directly, but it's virtual so that custom object types
|
||||
can stringify themselves appropriately.
|
||||
*/
|
||||
virtual void writeAsJSON (OutputStream&, int indentLevel, bool allOnOneLine);
|
||||
virtual void writeAsJSON (OutputStream&, int indentLevel, bool allOnOneLine, int maximumDecimalPlaces);
|
||||
|
||||
private:
|
||||
//==============================================================================
|
||||
NamedValueSet properties;
|
||||
|
||||
#if JUCE_CATCH_DEPRECATED_CODE_MISUSE
|
||||
// These methods have been deprecated - use var::invoke instead
|
||||
// This method has been deprecated - use var::invoke instead
|
||||
virtual void invokeMethod (const Identifier&, const var*, int) {}
|
||||
#endif
|
||||
|
||||
|
|
|
|||
|
|
@ -323,7 +323,8 @@ class JSONFormatter
|
|||
{
|
||||
public:
|
||||
static void write (OutputStream& out, const var& v,
|
||||
const int indentLevel, const bool allOnOneLine)
|
||||
const int indentLevel, const bool allOnOneLine,
|
||||
int maximumDecimalPlaces)
|
||||
{
|
||||
if (v.isString())
|
||||
{
|
||||
|
|
@ -343,14 +344,18 @@ public:
|
|||
{
|
||||
out << (static_cast<bool> (v) ? "true" : "false");
|
||||
}
|
||||
else if (v.isDouble())
|
||||
{
|
||||
out << String (static_cast<double> (v), maximumDecimalPlaces);
|
||||
}
|
||||
else if (v.isArray())
|
||||
{
|
||||
writeArray (out, *v.getArray(), indentLevel, allOnOneLine);
|
||||
writeArray (out, *v.getArray(), indentLevel, allOnOneLine, maximumDecimalPlaces);
|
||||
}
|
||||
else if (v.isObject())
|
||||
{
|
||||
if (DynamicObject* object = v.getDynamicObject())
|
||||
object->writeAsJSON (out, indentLevel, allOnOneLine);
|
||||
object->writeAsJSON (out, indentLevel, allOnOneLine, maximumDecimalPlaces);
|
||||
else
|
||||
jassertfalse; // Only DynamicObjects can be converted to JSON!
|
||||
}
|
||||
|
|
@ -420,7 +425,8 @@ public:
|
|||
}
|
||||
|
||||
static void writeArray (OutputStream& out, const Array<var>& array,
|
||||
const int indentLevel, const bool allOnOneLine)
|
||||
const int indentLevel, const bool allOnOneLine,
|
||||
int maximumDecimalPlaces)
|
||||
{
|
||||
out << '[';
|
||||
|
||||
|
|
@ -434,7 +440,7 @@ public:
|
|||
if (! allOnOneLine)
|
||||
writeSpaces (out, indentLevel + indentSize);
|
||||
|
||||
write (out, array.getReference(i), indentLevel + indentSize, allOnOneLine);
|
||||
write (out, array.getReference(i), indentLevel + indentSize, allOnOneLine, maximumDecimalPlaces);
|
||||
|
||||
if (i < array.size() - 1)
|
||||
{
|
||||
|
|
@ -493,16 +499,16 @@ Result JSON::parse (const String& text, var& result)
|
|||
return JSONParser::parseObjectOrArray (text.getCharPointer(), result);
|
||||
}
|
||||
|
||||
String JSON::toString (const var& data, const bool allOnOneLine)
|
||||
String JSON::toString (const var& data, const bool allOnOneLine, int maximumDecimalPlaces)
|
||||
{
|
||||
MemoryOutputStream mo (1024);
|
||||
JSONFormatter::write (mo, data, 0, allOnOneLine);
|
||||
JSONFormatter::write (mo, data, 0, allOnOneLine, maximumDecimalPlaces);
|
||||
return mo.toUTF8();
|
||||
}
|
||||
|
||||
void JSON::writeToStream (OutputStream& output, const var& data, const bool allOnOneLine)
|
||||
void JSON::writeToStream (OutputStream& output, const var& data, const bool allOnOneLine, int maximumDecimalPlaces)
|
||||
{
|
||||
JSONFormatter::write (output, data, 0, allOnOneLine);
|
||||
JSONFormatter::write (output, data, 0, allOnOneLine, maximumDecimalPlaces);
|
||||
}
|
||||
|
||||
String JSON::escapeString (StringRef s)
|
||||
|
|
|
|||
|
|
@ -90,10 +90,12 @@ public:
|
|||
/** Returns a string which contains a JSON-formatted representation of the var object.
|
||||
If allOnOneLine is true, the result will be compacted into a single line of text
|
||||
with no carriage-returns. If false, it will be laid-out in a more human-readable format.
|
||||
The maximumDecimalPlaces parameter determines the precision of floating point numbers.
|
||||
@see writeToStream
|
||||
*/
|
||||
static String toString (const var& objectToFormat,
|
||||
bool allOnOneLine = false);
|
||||
bool allOnOneLine = false,
|
||||
int maximumDecimalPlaces = 20);
|
||||
|
||||
/** Parses a string that was created with the toString() method.
|
||||
This is slightly different to the parse() methods because they will reject primitive
|
||||
|
|
@ -105,11 +107,13 @@ public:
|
|||
/** Writes a JSON-formatted representation of the var object to the given stream.
|
||||
If allOnOneLine is true, the result will be compacted into a single line of text
|
||||
with no carriage-returns. If false, it will be laid-out in a more human-readable format.
|
||||
The maximumDecimalPlaces parameter determines the precision of floating point numbers.
|
||||
@see toString
|
||||
*/
|
||||
static void writeToStream (OutputStream& output,
|
||||
const var& objectToFormat,
|
||||
bool allOnOneLine = false);
|
||||
bool allOnOneLine = false,
|
||||
int maximumDecimalPlaces = 20);
|
||||
|
||||
/** Returns a version of a string with any extended characters escaped. */
|
||||
static String escapeString (StringRef);
|
||||
|
|
|
|||
|
|
@ -827,7 +827,7 @@ struct JavascriptEngine::RootObject : public DynamicObject
|
|||
|
||||
DynamicObject::Ptr clone() override { return new FunctionObject (*this); }
|
||||
|
||||
void writeAsJSON (OutputStream& out, int /*indentLevel*/, bool /*allOnOneLine*/) override
|
||||
void writeAsJSON (OutputStream& out, int /*indentLevel*/, bool /*allOnOneLine*/, int /*maximumDecimalPlaces*/) override
|
||||
{
|
||||
out << "function " << functionCode;
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue