Loading the XML file data

We will first discuss how to simply load an XML file. We will later consider how to add data back into an XML file.

Getting started

For this chapter, I created a new project called Data, and all the necessary files can be found in the Resources folder of this chapter. The project file is also included in the code resource for the chapter, so if you get stuck anywhere, you can refer to it for clarification.

To load an XML file, we first need to have an XML file to work with. For this, I included the GroupList.xml file. Import this file into the project.

The file can be viewed in Xcode. Click on the file to see it in the navigator, as follows:

<Group>
  <Player>
    <Name>Siddharth</Name>
    <Level>1</Level>
  </Player>
  <Player>
    <Name>Alice</Name>
    <Level>2</Level>
  </Player>
  <Player>
    <Name>Steve</Name>
    <Level>3</Level>
  </Player>
</Group>

In the file, we have our group of players that we want to load. There are three players, and for each of the players, we will also include properties such as their name and level. Player Siddharth is level 1, Alice is level 2, and Steve is level 3.

Once you import the XML file, you will next make some changes to the project so that it can be read in the XML file.

For this, we will use GDataXML created by Google to process XML data. You can download it from https://github.com/google/gdata-objectivec-client.

Once it is downloaded, go to the Source/ XMLSupport folder and copy the GDataXMLNode.h and GDataXMLNode.m files to your project. It is better if you create a new group before importing so that the project file is neatly organized.

Next, click on your project in Xcode in Build Settings, select all the items in Header Search Paths under Search Paths, and then add /usr/include/libxml2.

Getting started

Then, in Other Linker Flags, add –lxml2.

Getting started

Also, select the GDataXMLNode.m file and add the –fno-objc-arc compiler flag to it.

How to do it…

In the MainScene.m file, let's create a user struct so that we can create a mutable array to store data in. So, at the top of the class, we will create a struct called Player, as follows:

typedefstruct{

  __unsafe_unretainedNSString* name;
  int level;

}Player; 

In the MainScene.h file, we will create a variable called players of the mutable array type via the following code:

@interface MainScene :CCNode{

  NSMutableArray *players;

}

+(CCScene*) scene;

@end

Next, in the init function, we will initialize the mutable array, as follows:

+(CCScene*) scene{

  return [[self alloc]init];
}

-(id)init{

  if(self = [super init]){


    //** XML

    players = [[NSMutableArrayalloc]init];


  }

  return self;
}

Next, we will create a function that will load the XML file, get data from it, and save it in the mutable array. We will call this function loadXMLGroup and add it as follows:

- (void)loadXMLGroup {

  NSString *filePath = [self XMLdataFilePath:FALSE];
  NSData *xmlData = [[NSMutableDataalloc] initWithContentsOfFile:filePath];
  NSError *error;
  GDataXMLDocument *doc = [[GDataXMLDocumentalloc] initWithData:xmlData
    options:0 error:&error];
  if (doc == nil){

    NSLog(@" **** unable to load xml ****");
  }

  NSLog(@"%@", doc.rootElement);

  NSArray *groupMembers = [doc.rootElementelementsForName:@"Player"];

  for (GDataXMLElement *groupMember in groupMembers) {

    NSString *name;
    int level;

    Player player;

    //** Name
    NSArray *names = [groupMemberelementsForName:@"Name"];
    if (names.count> 0) {
      GDataXMLElement *firstName = (GDataXMLElement *) [names objectAtIndex:0];
      name = firstName.stringValue;

      NSLog(@"Name: %@", name);

      player.name = name;

    } else continue;

    //** Level
    NSArray *levels = [groupMemberelementsForName:@"Level"];
    if (levels.count> 0) {
      GDataXMLElement *firstLevel = (GDataXMLElement *) [levels objectAtIndex:0];
      level = firstLevel.stringValue.intValue;

      NSLog(@"Level: %d", level);

      player.level = level;

    } else continue;


    NSValue *value = [NSValuevalueWithBytes:&player objCType:@encode(Player)];
    [playersaddObject:value];

  }

}

First we will pass in the filename of the XML file that we would like to load, which is a string. Next, we will get the actual data from the file using the NSData property class. This will then be transferred to a variable called doc of the GDataXMLDocument type.

If doc is empty, we will log an error saying that no data was found.

Otherwise, we will store all the values in an NSArray variable called groupMembers.

To cycle through each of the elements of the array, we will use the GDataXMLElement property, and we will use the for loop to go through each of the elements.

Two temporary variables are created to store the name and level. Also, a variable called player is created of the Player type to store in the players' Mutable array.

The name and level member elements are taken and stored in separate NSArrays, respectively.

All the player elements are stored in a separate array called players.

We will also log the names and levels if found in GDataXMLElement.

To actually retrieve the file path for the XML file, we have to create a function as follows. This same function will be used to get a filename to save:

- (NSString *)XMLdataFilePath:(BOOL)forSave {

NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,
  NSUserDomainMask, YES);

NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *documentsPath = [documentsDirectorystringByAppendingPathComponent:@"GroupList.xml"];

if (forSave || [[NSFileManagerdefaultManager] fileExistsAtPath:documentsPath]) {
    returndocumentsPath;

  } else {

    return [[NSBundlemainBundle] pathForResource:@"GroupList" ofType:@"xml"];
  }
}

This file function will check whether a file with the same name already exists. If it exists, then the file path is returned. If not, then a new XML file is created and the path is returned as a string.

Now, in the init function, after where we initialized the players, the Mutable array calls the loadXMLGroup function, as follows:

-(id)init{

  if(self = [super init]){


    //** XML

    players = [[NSMutableArrayalloc]init];

    [selfloadXMLGroup];

  }

  return self;
}

How it works…

All you have to do is run the project now; the XML file will be loaded, and the output will be displayed as follows:

How it works…

As expected, the log prints out the contents of the XML file as it was shown at the beginning.

In the next section, we will discuss how to save data to the XML file.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.191.186.219