Сложный JSON как источник данных NSArray для iOS UITableView - PullRequest
2 голосов
/ 31 августа 2011

Я попробовал почти все перед публикацией (Google, Apple Dev Doc и т. Д.).Надеюсь, я ничего не пропустил до публикации ..

Я уже создал работающий JSON <-> Webservice <-> iPhone.

со следующим кодом:

NSString *responseString = [[[NSString alloc] initWithData:responseData encoding:NSUTF8StringEncoding]autorelease];
NSDictionary *jsonDict = [responseString JSONValue];
NSString *loginResult = [jsonDict valueForKey:@"LoginResult"];

loginResult - имя сотрудника: например, "Henning Wenger"

Соответствующий JSON выглядит следующим образом:

{"LoginResult":"S:00000412"}

Теперь у меня есть более сложная задача, с которой я не могу справиться:

Я получаю следующий JSON от веб-службы:

{"GetTeamPresentStatusResult"[
{"Firstname":"Steffen","Id":"00000456","IsPresent":"true","Lastname":"Polker"},
{"Firstname":"Erich","Id":"00000455","IsPresent":"true","Lastname":"Welter"},     
{"Firstname":"Titus","Id":"00000454","IsPresent":"true","Lastname":"Sommerbeck"},      {"Firstname":"Ruediger","Id":"00000453","IsPresent":"true","Lastname":"Oelmann"},{"Firstname":"Heinz","Id":"00000452","IsPresent":"true","Lastname":"Radelfs"},{"Firstname":"Franz","Id":"00000451","IsPresent":"true","Lastname":"Wippermann"},{"Firstname":"Klaus-Dieter","Id":"00000450","IsPresent":"true","Lastname":"Just"},{"Firstname":"Alan","Id":"00000412","IsPresent":"true","Lastname":"Turing"},{"Firstname":"Konrad","Id":"00000138","IsPresent":"true","Lastname":"Zuse"},{"Firstname":"Marius","Id":"00000112","IsPresent":"true","Lastname":"Sandmann"}]}

Мой код для обработки этого начинается с:

NSDictionary *jsonDict = [responseString JSONValue];
NSArray *teamStatus = [jsonDict objectForKey:@"GetTeamPresentStatusResult"];
[self BuildDataSource: nil :teamStatus];

teamStatus теперь содержит 10 пар ключ / значение.

Вот как я пытался создать источник данных для своей таблицы:

- (void)BuildDataSource: (id) sender: (NSArray*)teamStatusData{

teamStatusMutableArray = [[NSMutableArray alloc]init];
teamStatusDataSection = [[NSArray alloc]initWithArray:teamStatusData];

teamStatusDictSectionOne = [NSDictionary dictionaryWithObject:teamStatusDataSection forKey:@"OrgUnits"];
[teamStatusMutableArray addObject:teamStatusDictSectionOne];

[tblView reloadData];
}

Мне не удается выяснить, каким путем отсюда можно получить данные, как мне это нужно.

Нужны ли мне разные массивы, где один содержит имя / значение, а другой содержитфамилия / значение?Если да, как мне это сделать?

Вот некоторые строки, которые я пробовал до сих пор, но они не помогли:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {

static NSString *CellIdentifier = @"Cell";

UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
    cell = [[[UITableViewCell alloc] initWithFrame:CGRectZero reuseIdentifier:CellIdentifier] autorelease];
}

// Set up the cell...
//First get the dictionary object

NSDictionary *dictionary = [teamStatusMutableArray objectAtIndex:indexPath.section];

NSString *testString = [dictionary valueForKey:@"Firstname"];
NSArray *testarray = [dictionary objectForKey:@"OrgUnits"];

NSString *test = [testarray JSONRepresentation];

test = [test stringByReplacingOccurrencesOfString:@"[" withString:@""];
test = [test stringByReplacingOccurrencesOfString:@"]" withString:@""];

NSDictionary *jsonDict = [test JSONValue];
}

Мне нужно иметь источник данных сИмена сотрудников, которые я могу привязать к таблице.Оттуда я думаю, что смогу проделать свой путь без дополнительной помощи.

Я из мира .NET (C #), и, возможно, это меня слишком смущает.

Спасибо вам большое..

Henning

Если вам нужна дополнительная информация, пожалуйста, спросите!

Подробности для SPtail:

Вот файл .h:

#import <UIKit/UIKit.h>
#import "RootViewController.h"
#import "EmployeeDetails.h"

@interface OrgUnitAA:NSObject {
NSString *FirstName;
NSString *Id;
NSString *IsPresent;
NSString *LastName;
}

@property (nonatomic, retain) NSString *FirstName;
@property (nonatomic, retain) NSString *Id;
@property (nonatomic, retain) NSString *IsPresent;
@property (nonatomic, retain) NSString *LastName;

@end

@interface TeamStatusView : UIViewController {

UITableView *tblView;
NSMutableArray *teamStatusMutableArray;
NSArray *teamStatusDataSection;
NSDictionary *teamStatusDictSectionOne;
UIViewController *EmployeeDetails;
UIViewController *RootViewController;
NSMutableData *responseData;
}

@property (nonatomic, retain) IBOutlet UITableView *tblView;
@property (nonatomic, retain) NSArray *teamStatusMutableArray;
@property (nonatomic, retain) NSMutableArray *dummyMutableArrayTimeQuota;
@property (nonatomic, retain) NSArray *teamStatusDataSection;
@property (nonatomic, retain) NSDictionary *teamStatusDictSectionOne;
@property (nonatomic, retain) IBOutlet UIViewController *RootViewController;
@property (nonatomic, retain) IBOutlet UIViewController *EmployeeDetails;

- (void)GetTeamStatus: id;
- (void)BuildDataSource: id: (NSArray*)teamStatusData;
@end

Ответы [ 3 ]

1 голос
/ 01 сентября 2011

Я нашел решение.

Вот как я получаю данные:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {

static NSString *CellIdentifier = @"Cell";

UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
    cell = [[[UITableViewCell alloc] initWithFrame:CGRectZero reuseIdentifier:CellIdentifier] autorelease];
}

// Set up the cell...

NSDictionary *dictionary = [teamStatusMutableArray objectAtIndex:indexPath.section];
NSArray *teamStatus = [dictionary objectForKey:@"OrgUnits"];

NSEnumerator *e = [teamStatus objectEnumerator];
id object;

int i = 0;
while (object = [e  nextObject]) {

    if(i == indexPath.row)
    {
        NSString *firstname = [object valueForKey:@"Firstname"];
        NSString *lastname = [object valueForKey:@"Lastname"];
        NSString *fullname = [NSString stringWithFormat:@"%@%@%@", lastname, @", ", firstname];
        cell.textLabel.text = fullname;

        bool isPresent = [object valueForKey:@"IsPresent"];

        if(isPresent == true)
        {
            cell.imageView.image = [UIImage imageNamed:@"GreenBall.png"];
        }
        else
        {
            cell.imageView.image = [UIImage imageNamed:@"RedBall.png"];
        }

        break;
    }
    i++;
}

[aiActivity stopAnimating];
self.aiActivity.hidden = true;

return cell;

}

1 голос
/ 31 августа 2011

Эй, массив, возвращаемый веб-сервисом, содержит словари, что очевидно.

Вместо того, чтобы использовать разные массивы для каждого свойства, вы можете создать класс, который расширяет NSObject и конвертирует каждый словарь, так что у вас будут объекты внутри массива вместо словарей. В этом случае:

@interface OrgUnit:NSObject {
     NSString *FirstName;
     NSNumber *Id;
     bool IsPresent;
     NSString *LastName;
}
//And all the properties here

После этого вы можете конвертировать словари в объекты, используя

OrgUnit *unit = [[OrgUnit alloc] init];
[unit setValuesForKeysWithDictionary:dictionary];

PS: имена переменных в объекте должны совпадать с именами ключей в словаре

0 голосов
/ 31 августа 2011

Может быть просто опечатка.

Измените это:

teamStatusDictSectionOne = [NSDictionary dictionaryWithObject:teamStatusDataSection forKey:@"OrgUnits"];

На это:

teamStatusDictSectionOne = [NSDictionary dictionaryWithObjects:teamStatusDataSection forKey:@"OrgUnits"];

Изменение является -dictionaryWithObjects.Множественное число.Obj-C довольно привередлив в этом.

Кроме того, вы ссылаетесь на indexPath.section при создании отдельных ячеек.Я думаю, что вы должны ссылаться на строку для ячейки.Строка должна соответствовать вашему индексу массива.

NSInteger row = [indexPath row];
NSDictionary *dictionary = [teamStatusMutableArray objectAtIndex:row];
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...