Alex
Alex

Reputation: 11

How to correctly access xml attributes using pugixml?

I'm new to xml, and using the pugixml documentation I haven't been able to read a node attribute to the console. The core of the issue is that I don't understand how the node accessing structure works and I haven't been able to figure it out using my code.

The code provided is a lightly modified line from the actual pugixml manual, so I'm not sure why it isn't working.

XML FILE LOADED

<?xml version="1.0" encoding="utf-8"?>
<settings description="settings root description">
  <!--settings for the options menu-->
  <options description="game options">
    <resolution description="resolution in 16:9 ratio">6</resolution>
    <volume description="volume setting">0</volume>
  </options>
</settings>

C++ CODE TRYING TO USE XML FILE

//set up and load settings xml doc
pugi::xml_document settingsXML;
pugi::xml_parse_result settingsResult = settingsXML.load_file("SFMLVania/include/Settings.xml");

std::cout << "Root description: " << settingsXML.root().attribute("description").as_string();

I'm expecting to see: "Root description: settings root description" in the console.

Instead, I'm getting: "Root description: "

SECOND ATTEMPT -- to try and just get any data and find out where I am in the tree:

std::cout << "Second attempt: " << settingsXML.first_attribute().as_string();

All I got from the second attempt was the console spitting out: "Second attempt: "

Upvotes: 0

Views: 1750

Answers (2)

Chip Brommer
Chip Brommer

Reputation: 168

For anyone that comes across this, you can prevent this error by adding a minimal parse check after the assigning of settingsResult like this:

pugi::xml_document settingsXML;
pugi::xml_parse_result settingsResult = settingsXML.load_file("SFMLVania/include/Settings.xml");

// Catch parsing error
if (!settingsResult )
{
    std::cout << "ERROR: " << settingsResult.description() << '\n';
    return -1;
}

This will catch a bad parse and log the error to the console.

Upvotes: 1

Alex
Alex

Reputation: 11

It turns out, my load path didn't exist, I had forgotten to use ../ to go up a directory and out of the Debug folder where the .exe was stored. I figured this out by testing the load result that could be passed as a bool.

if (settingsResult)
    {
        std::cout << "returned true\n";
    }
    else
        std::cout << "returned false\n";
    if (!settingsResult)
    {
        std::cout << "also returned false\n";
    }

I included some redundant returns in case the bool value didn't function as expected.

The result showed that there was no file loaded (it returned false), and when I reexamined my file structure and added the ../ as a test to the file path, it returned true.

Upvotes: 1

Related Questions