通过 JSON 层次结构和 objectForKey 使用 AFNetworking 加载图像视图

Posted

技术标签:

【中文标题】通过 JSON 层次结构和 objectForKey 使用 AFNetworking 加载图像视图【英文标题】:Loading imageviews with AFNetworking via JSON hierarchy and objectForKey 【发布时间】:2014-04-17 00:40:29 【问题描述】:

AFNetworking 非常陌生,但经过许多 SO 问题...我得出结论,这是解决我的问题的方法。

我有一个JSON 数据层次结构,动态加载我的 TableViewController 单元格。我所有的文本字符串都在正确加载,但我的URL 中的图像没有进入我的图像视图。

在使用 AFNetworking 库之前,我已经加载了图像,但是当我滚动并返回时,我遇到了一些照片没有保持加载的问题(它们必须再次加载。)

我缺少什么来获取我的图像?

TableViewController.m

-(void)viewDidLoad 
    [super viewDidLoad];

    // Set the side bar button action. When it's tapped, it'll show up the sidebar.
    siderbarButton.target = self.revealViewController;
    siderbarButton.action = @selector(revealToggle:);

    // Set the gesture
    [self.view addGestureRecognizer:self.revealViewController.panGestureRecognizer];

    self.tableView.backgroundColor = [UIColor whiteColor];
    self.parentViewController.view.backgroundColor = [UIColor colorWithRed:1.0 green:1.0 blue:1.0 alpha:1];

    self.navigationItem.titleView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"logo_app_white.png"]];

    NSURL *myURL = [[NSURL alloc]initWithString:@"http://domain.com/json2.php"];
    NSData *myData = [[NSData alloc]initWithContentsOfURL:myURL];
    NSError *error;

    jsonArray = [NSJSONSerialization JSONObjectWithData:myData options:NSJSONReadingMutableContainers error:&error];

    [tableView reloadData]; // if tableView is unidentified make the tableView IBOutlet


- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section

    // Return the number of rows in the section.
    return jsonArray.count;



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


    NeedCardTableViewCell *cell = (NeedCardTableViewCell *) [tableView dequeueReusableCellWithIdentifier:@"needCard"];

    if (cell == nil)
    
        cell = [[NeedCardTableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:@"needCard"];
    

    NSDictionary *needs = jsonArray[indexPath.row]; // get the data dict for the row
    cell.textNeedTitle.text = [needs objectForKey: @"needTitle"];
    cell.textNeedPoster.text = [needs objectForKey: @"needPoster"];
    cell.textNeedDescrip.text = [needs objectForKey: @"needDescrip"];

    AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager];
    [manager GET:@"userImage" parameters:nil success:^(AFHTTPRequestOperation *operation, id responseObject) 
        NSLog(@"JSON: %@", responseObject);
        _imageProfPic.image = responseObject;
     failure:^(AFHTTPRequestOperation *operation, NSError *error) 
        NSLog(@"Error: %@", error);
    ];

    return cell;

【问题讨论】:

【参考方案1】:

您是否尝试过使用AFNetworking+UIImageView 类别?然后您可以调用:

[_imageProfPic setImage:[NSURL URLWithString:@"http://myimageurl.com/imagename.jpg"]];

这将发出一个请求,然后将返回的图像设置为您的 UIImageView 的 UIImage,而无需您执行任何其他操作。您还应该考虑在 AppDelegate 中初始化 NSURLCache:

NSURLCache *cache = [[NSURLCache alloc] initWithMemoryCapacity:4 * 1024 * 1024
                                                  diskCapacity:10 * 1024 * 1024
                                                      diskPath:nil];
[NSURLCache setSharedURLCache:cache];

看看NSHipster's run down on NSURLCache。这将有助于第二次更快地重新加载图像和所有请求。这在处理图像和表格时变得越来越重要。

【讨论】:

如何使用来自 jsonArray 的密钥发出 afnetworking+uiimageview 请求?另外,我假设我只是为此导入 afnetworking+uiimageview.h 文件? 如果您使用的是 AFNetworking,我假设您想发出请求以从应用程序外部(例如从 API)获取数据。在这种情况下,您必须在 setImage 方法中设置所需图像的 URL。例如,放置http://upload.wikimedia.org/wikipedia/commons/7/75/Internet1.jpg 将返回来自***站点的图像并将其设置为 UIImageView 的 UIImage。 @"userImage" 在您的 GET 请求中代表什么?是的,您只需导入类别即可使用它。 @"userImage" 是我的 JSON 文件中的一个键。它被保存到“jsonArray”中,它的值是图像的 URL(取决于请求的用户信息)。我正在使用 objectForKey 从 jsonArray 中调用图像的 URL 以放入我的图像视图“imageProfPic”。我正在使用 AFNetworking 将我的 URL(否则为字符串)制作成可以填充 imageview 的图像。 基本上我的网址总是不同的。因此,当我准备好调用它时,我将 URL 保存在键“userImage”下的“jsonArray”中。【参考方案2】:

使用本教程设法解决这个问题: Networking Made Easy with AFNetworking

我使用了最终的 sn-p 代码来得到我想要的结果:

NSURL *url = [[NSURL alloc] initWithString:[movie objectForKey:@"artworkUrl100"]];
[cell.imageView setImageWithURL:url placeholderImage:[UIImage imageNamed:@"placeholder"]];

我删掉了他的代码的第二行,因为我的PHP/JSON 中已经有一个 if 语句

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


    NeedCardTableViewCell *cell = (NeedCardTableViewCell *) [tableView dequeueReusableCellWithIdentifier:@"needCard"];

    if (cell == nil)
    
        cell = [[NeedCardTableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:@"needCard"];
    

    NSDictionary *needs = jsonArray[indexPath.row]; // get the data dict for the row
    cell.textNeedTitle.text = [needs objectForKey: @"needTitle"];
    cell.textNeedPoster.text = [needs objectForKey: @"needPoster"];
    cell.textNeedDescrip.text = [needs objectForKey: @"needDescrip"];

    NSURL *url = [[NSURL alloc] initWithString:[needs objectForKey:@"userImage"]];
    [cell.imageProfPic setImageWithURL:url];

    return cell;

它就像一个魅力,而且这个教程很有帮助,因为我是 AFNetworking 的新手。

【讨论】:

在您最初的问题中,不清楚您是否通过 @"userImage" 从字典的键中获取 URL,因为声明 [manager GET:@"userImage" 将使用 userImage 作为 URL。很高兴无论哪种方式最终都成功了。

以上是关于通过 JSON 层次结构和 objectForKey 使用 AFNetworking 加载图像视图的主要内容,如果未能解决你的问题,请参考以下文章

对 json 层次结构进行排序

使用 json 对象列表以角度生成层次结构视图

如何实现 D3 层次视图

使用 LINQ 在 JSON 中创建树层次结构

json配置文件,如何在打开json文件时,缩进和分组,显示标签的分组层次结构(注意,各分组可折叠或伸展)

RestKit 0.20:在 JSON 中使用动态扁平化层次结构