2014-12-07 19:09:38 -05:00
// Copyright 1998-2015 Epic Games, Inc. All Rights Reserved.
2014-10-01 18:20:53 -04:00
# include "SerializationPrivatePCH.h"
# include "JsonStructDeserializerBackend.h"
/* Internal helpers
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
namespace JsonStructDeserializerBackend
{
2014-10-24 12:05:53 -04:00
/**
* Clears the value of the given property .
*
* @ param Property The property to clear .
* @ param Outer The property that contains the property to be cleared , if any .
* @ param Data A pointer to the memory holding the property ' s data .
* @ param ArrayIndex The index of the element to clear ( if the property is an array ) .
* @ return true on success , false otherwise .
* @ see SetPropertyValue
*/
bool ClearPropertyValue ( UProperty * Property , UProperty * Outer , void * Data , int32 ArrayIndex )
2014-10-01 18:20:53 -04:00
{
UArrayProperty * ArrayProperty = Cast < UArrayProperty > ( Outer ) ;
if ( ArrayProperty ! = nullptr )
{
2014-10-24 12:05:53 -04:00
if ( ArrayProperty - > Inner ! = Property )
{
return false ;
}
2014-10-01 18:20:53 -04:00
FScriptArrayHelper ArrayHelper ( ArrayProperty , ArrayProperty - > template ContainerPtrToValuePtr < void > ( Data ) ) ;
ArrayIndex = ArrayHelper . AddValue ( ) ;
}
Property - > ClearValue_InContainer ( Data , ArrayIndex ) ;
2014-10-24 12:05:53 -04:00
return true ;
2014-10-01 18:20:53 -04:00
}
2014-10-24 12:05:53 -04:00
/**
* Sets the value of the given property .
*
* @ param Property The property to set .
* @ param Outer The property that contains the property to be set , if any .
* @ param Data A pointer to the memory holding the property ' s data .
* @ param ArrayIndex The index of the element to set ( if the property is an array ) .
* @ return true on success , false otherwise .
* @ see ClearPropertyValue
*/
2014-10-01 18:20:53 -04:00
template < typename UPropertyType , typename PropertyType >
2014-10-24 12:05:53 -04:00
bool SetPropertyValue ( UProperty * Property , UProperty * Outer , void * Data , int32 ArrayIndex , const PropertyType & Value )
2014-10-01 18:20:53 -04:00
{
PropertyType * ValuePtr = nullptr ;
UArrayProperty * ArrayProperty = Cast < UArrayProperty > ( Outer ) ;
if ( ArrayProperty ! = nullptr )
{
2014-10-24 12:05:53 -04:00
if ( ArrayProperty - > Inner ! = Property )
{
return false ;
}
2014-10-01 18:20:53 -04:00
FScriptArrayHelper ArrayHelper ( ArrayProperty , ArrayProperty - > template ContainerPtrToValuePtr < void > ( Data ) ) ;
int32 Index = ArrayHelper . AddValue ( ) ;
ValuePtr = ( PropertyType * ) ArrayHelper . GetRawPtr ( Index ) ;
}
else
{
UPropertyType * TypedProperty = Cast < UPropertyType > ( Property ) ;
2014-10-24 12:05:53 -04:00
if ( TypedProperty = = nullptr )
{
return false ;
}
2014-10-01 18:20:53 -04:00
ValuePtr = TypedProperty - > template ContainerPtrToValuePtr < PropertyType > ( Data , ArrayIndex ) ;
}
2014-10-24 12:05:53 -04:00
if ( ValuePtr = = nullptr )
{
return false ;
}
2014-10-01 18:20:53 -04:00
* ValuePtr = Value ;
2014-10-24 12:05:53 -04:00
return true ;
2014-10-01 18:20:53 -04:00
}
}
/* IStructDeserializerBackend interface
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2014-10-24 12:05:53 -04:00
const FString & FJsonStructDeserializerBackend : : GetCurrentPropertyName ( ) const
2014-10-01 18:20:53 -04:00
{
return JsonReader - > GetIdentifier ( ) ;
}
2014-10-24 12:05:53 -04:00
FString FJsonStructDeserializerBackend : : GetDebugString ( ) const
2014-10-01 18:20:53 -04:00
{
return FString : : Printf ( TEXT ( " Line: %u, Ch: %u " ) , JsonReader - > GetLineNumber ( ) , JsonReader - > GetCharacterNumber ( ) ) ;
}
2014-10-24 12:05:53 -04:00
const FString & FJsonStructDeserializerBackend : : GetLastErrorMessage ( ) const
2014-10-01 18:20:53 -04:00
{
return JsonReader - > GetErrorMessage ( ) ;
}
bool FJsonStructDeserializerBackend : : GetNextToken ( EStructDeserializerBackendTokens & OutToken )
{
if ( ! JsonReader - > ReadNext ( LastNotation ) )
{
return false ;
}
switch ( LastNotation )
{
case EJsonNotation : : ArrayEnd :
OutToken = EStructDeserializerBackendTokens : : ArrayEnd ;
break ;
case EJsonNotation : : ArrayStart :
OutToken = EStructDeserializerBackendTokens : : ArrayStart ;
break ;
case EJsonNotation : : Boolean :
case EJsonNotation : : Null :
case EJsonNotation : : Number :
case EJsonNotation : : String :
{
OutToken = EStructDeserializerBackendTokens : : Property ;
}
break ;
case EJsonNotation : : Error :
OutToken = EStructDeserializerBackendTokens : : Error ;
break ;
case EJsonNotation : : ObjectEnd :
OutToken = EStructDeserializerBackendTokens : : StructureEnd ;
break ;
case EJsonNotation : : ObjectStart :
OutToken = EStructDeserializerBackendTokens : : StructureStart ;
break ;
default :
OutToken = EStructDeserializerBackendTokens : : None ;
}
return true ;
}
bool FJsonStructDeserializerBackend : : ReadProperty ( UProperty * Property , UProperty * Outer , void * Data , int32 ArrayIndex )
{
using namespace JsonStructDeserializerBackend ;
switch ( LastNotation )
{
// boolean values
case EJsonNotation : : Boolean :
{
bool BoolValue = JsonReader - > GetValueAsBoolean ( ) ;
if ( Property - > GetClass ( ) = = UBoolProperty : : StaticClass ( ) )
{
2014-10-24 12:05:53 -04:00
return SetPropertyValue < UBoolProperty , bool > ( Property , Outer , Data , ArrayIndex , BoolValue ) ;
2014-10-01 18:20:53 -04:00
}
2014-10-24 12:05:53 -04:00
UE_LOG ( LogSerialization , Verbose , TEXT ( " Boolean field %s with value '%s' is not supported in UProperty type %s (%s) " ) , * Property - > GetFName ( ) . ToString ( ) , BoolValue ? * ( GTrue . ToString ( ) ) : * ( GFalse . ToString ( ) ) , * Property - > GetClass ( ) - > GetName ( ) , * GetDebugString ( ) ) ;
return false ;
2014-10-01 18:20:53 -04:00
}
break ;
// numeric values
case EJsonNotation : : Number :
{
2014-10-28 19:44:18 -04:00
double NumericValue = JsonReader - > GetValueAsNumber ( ) ;
2014-10-01 18:20:53 -04:00
if ( Property - > GetClass ( ) = = UByteProperty : : StaticClass ( ) )
{
2014-10-24 12:05:53 -04:00
return SetPropertyValue < UByteProperty , int8 > ( Property , Outer , Data , ArrayIndex , ( int8 ) NumericValue ) ;
2014-10-01 18:20:53 -04:00
}
2014-10-24 12:05:53 -04:00
if ( Property - > GetClass ( ) = = UDoubleProperty : : StaticClass ( ) )
{
return SetPropertyValue < UDoubleProperty , double > ( Property , Outer , Data , ArrayIndex , NumericValue ) ;
2014-10-01 18:20:53 -04:00
}
2014-10-24 12:05:53 -04:00
if ( Property - > GetClass ( ) = = UFloatProperty : : StaticClass ( ) )
{
return SetPropertyValue < UFloatProperty , float > ( Property , Outer , Data , ArrayIndex , NumericValue ) ;
}
if ( Property - > GetClass ( ) = = UIntProperty : : StaticClass ( ) )
{
return SetPropertyValue < UIntProperty , int32 > ( Property , Outer , Data , ArrayIndex , ( int32 ) NumericValue ) ;
}
if ( Property - > GetClass ( ) = = UUInt32Property : : StaticClass ( ) )
{
return SetPropertyValue < UUInt32Property , uint32 > ( Property , Outer , Data , ArrayIndex , ( uint32 ) NumericValue ) ;
}
if ( Property - > GetClass ( ) = = UInt16Property : : StaticClass ( ) )
{
return SetPropertyValue < UInt16Property , int16 > ( Property , Outer , Data , ArrayIndex , ( int16 ) NumericValue ) ;
}
if ( Property - > GetClass ( ) = = UUInt16Property : : StaticClass ( ) )
{
return SetPropertyValue < UUInt16Property , uint16 > ( Property , Outer , Data , ArrayIndex , ( uint16 ) NumericValue ) ;
}
if ( Property - > GetClass ( ) = = UInt64Property : : StaticClass ( ) )
{
return SetPropertyValue < UInt64Property , int64 > ( Property , Outer , Data , ArrayIndex , ( int64 ) NumericValue ) ;
}
if ( Property - > GetClass ( ) = = UUInt64Property : : StaticClass ( ) )
{
return SetPropertyValue < UUInt64Property , uint64 > ( Property , Outer , Data , ArrayIndex , ( uint64 ) NumericValue ) ;
}
if ( Property - > GetClass ( ) = = UInt8Property : : StaticClass ( ) )
{
return SetPropertyValue < UInt8Property , int8 > ( Property , Outer , Data , ArrayIndex , ( int8 ) NumericValue ) ;
}
UE_LOG ( LogSerialization , Verbose , TEXT ( " Numeric field %s with value '%f' is not supported in UProperty type %s (%s) " ) , * Property - > GetFName ( ) . ToString ( ) , NumericValue , * Property - > GetClass ( ) - > GetName ( ) , * GetDebugString ( ) ) ;
return false ;
2014-10-01 18:20:53 -04:00
}
break ;
// null values
case EJsonNotation : : Null :
2014-10-24 12:05:53 -04:00
return ClearPropertyValue ( Property , Outer , Data , ArrayIndex ) ;
2014-10-01 18:20:53 -04:00
// strings, names & enumerations
case EJsonNotation : : String :
{
const FString & StringValue = JsonReader - > GetValueAsString ( ) ;
if ( Property - > GetClass ( ) = = UStrProperty : : StaticClass ( ) )
{
2014-10-24 12:05:53 -04:00
return SetPropertyValue < UStrProperty , FString > ( Property , Outer , Data , ArrayIndex , StringValue ) ;
2014-10-01 18:20:53 -04:00
}
2014-10-24 12:05:53 -04:00
if ( Property - > GetClass ( ) = = UNameProperty : : StaticClass ( ) )
2014-10-01 18:20:53 -04:00
{
2014-10-24 12:05:53 -04:00
return SetPropertyValue < UNameProperty , FName > ( Property , Outer , Data , ArrayIndex , * StringValue ) ;
2014-10-01 18:20:53 -04:00
}
2014-10-24 12:05:53 -04:00
if ( Property - > GetClass ( ) = = UByteProperty : : StaticClass ( ) )
2014-10-01 18:20:53 -04:00
{
UByteProperty * ByteProperty = Cast < UByteProperty > ( Property ) ;
int32 Index = ByteProperty - > Enum - > FindEnumIndex ( * StringValue ) ;
2014-10-24 12:05:53 -04:00
if ( Index = = INDEX_NONE )
2014-10-01 18:20:53 -04:00
{
2014-10-24 12:05:53 -04:00
return false ;
2014-10-01 18:20:53 -04:00
}
2014-10-24 12:05:53 -04:00
return SetPropertyValue < UByteProperty , uint8 > ( Property , Outer , Data , ArrayIndex , ( uint8 ) Index ) ;
2014-10-01 18:20:53 -04:00
}
2014-10-24 12:05:53 -04:00
if ( Property - > GetClass ( ) = = UClassProperty : : StaticClass ( ) )
{
return SetPropertyValue < UClassProperty , UClass * > ( Property , Outer , Data , ArrayIndex , LoadObject < UClass > ( NULL , * StringValue , NULL , LOAD_NoWarn ) ) ;
}
UE_LOG ( LogSerialization , Verbose , TEXT ( " String field %s with value '%s' is not supported in UProperty type %s (%s) " ) , * Property - > GetFName ( ) . ToString ( ) , * StringValue , * Property - > GetClass ( ) - > GetName ( ) , * GetDebugString ( ) ) ;
return false ;
2014-10-01 18:20:53 -04:00
}
break ;
}
return true ;
}
2014-10-24 12:05:53 -04:00
void FJsonStructDeserializerBackend : : SkipArray ( )
2014-10-01 18:20:53 -04:00
{
JsonReader - > SkipArray ( ) ;
}
2014-10-24 12:05:53 -04:00
void FJsonStructDeserializerBackend : : SkipStructure ( )
2014-10-01 18:20:53 -04:00
{
JsonReader - > SkipObject ( ) ;
}