Iterate through a UDataTable and Cast to a Struct

I´m using this as an example to iterate through a custom DataTable. The structure is the following:

structure.PNG

The Combat Actions are a C++ class which inherites from UObject. What I am trying to do is Iterate through the DataTable, cast each row to an Struct, representing this DataTable structure and store it in a TMap. The cast always fails and returns a NULL.

Struct:



USTRUCT(BlueprintType)
struct FComboTableRow : public FTableRowBase
{
    GENERATED_BODY()

    FComboTableRow();

    /** String of buttons for this combo **/
    UPROPERTY(EditAnywhere, BlueprintReadWrite)
        FString m_sCombo;
    /** CombatAction of the last input of the combo **/
    UPROPERTY(EditAnywhere, BlueprintReadWrite)
        TSubclassOf<class UCombatAction> m_combatAction;
};


Code:

I have tried to Iterate and Cast in these two ways (in the first one I get the row names correctly):



//First way
    UDataTable* pDataTable = LoadObject<UDataTable>(NULL, UTF8_TO_TCHAR("DataTable'/Game/Blueprints/DataTables/Tables/ComboDataTable.ComboDataTable'"));
    FString ContextString;
    TArray<FName> RowNames;
    RowNames = pDataTable->GetRowNames();
    for (auto& name : RowNames)
    {
        FComboTableRow* pRow = pDataTable->FindRow<FComboTableRow>(name, ContextString);
        if (pRow)
        {
            m_hashTCombatAction.Add(pRow->m_sCombo, pRow->m_combatAction.GetDefaultObject());
        }
    }


//Second way
for (auto it : pDataTable->GetRowMap())
    {
        FString rowName = (it.Key).ToString();
        FComboTableRow* pRow = (FComboTableRow*)it.Value;
        m_hashTCombatAction.Add(pRow->m_sCombo, pRow->m_combatAction.GetDefaultObject());
    }


Any ideas? Thanks in advance

I am still stuck with this problem. Any help?
Thank you :slight_smile:

You can simply copy what UDataTable::FindRow does. As a bonus you get type-safety then too. For what you’re doing however, it seems pretty odd to use a data table. Perhaps a UDataAsset with a TArray<FMyStruct> instead? Seems pointless to copy data arund like that.

If you still want to use a data table:



// Type-Safety
check(LoadedTable->GetRowStruct()->IsChildOf(FMyStruct::StaticStruct()));

for (const TPair<FName, uint8*>& RowItr: LoadedTable->GetRowMap())
{
    const FMyStruct* MyData = reinterpret_cast<const FMyStruct*>(RowItr.Value);
}


2 Likes

In my case DataStructFormat from the blueprint and FStruct from c++ have diff property order . issue was able to cast some of inital properties but all properties.

I think it’s right. You have to check(in mind at very first) if your datatable "FComboTableRow " is really fix the struct?

// Type-Safety
check(LoadedTable->GetRowStruct()->IsChildOf(FMyStruct::StaticStruct()));

if you struct is “string,UCombatAction(),string”; a more string property may cause NULL(cant cast())

I struggled on that make it more flexible using DataSet,DataRow(Common) in C# or Java language…