CommitListViewController.m 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128
  1. //
  2. // CommitListViewController.m
  3. // FLEXample
  4. //
  5. // Created by Tanner on 3/11/20.
  6. // Copyright © 2020 Flipboard. All rights reserved.
  7. //
  8. #import "CommitListViewController.h"
  9. #import "FLEXample-Swift.h"
  10. #import <FLEX.h>
  11. @interface CommitListViewController ()
  12. @property (nonatomic) FLEXMutableListSection<Commit *> *commits;
  13. @property (nonatomic, readonly) NSMutableDictionary<NSString *, UIImage *> *avatars;
  14. @end
  15. @implementation CommitListViewController
  16. - (id)init {
  17. // Default style is grouped
  18. return [self initWithStyle:UITableViewStylePlain];
  19. }
  20. - (void)viewDidLoad {
  21. [super viewDidLoad];
  22. _avatars = [NSMutableDictionary new];
  23. self.title = @"FLEX Commit History";
  24. self.showsSearchBar = YES;
  25. self.navigationItem.rightBarButtonItem = [UIBarButtonItem
  26. flex_itemWithTitle:@"FLEX" target:FLEXManager.sharedManager action:@selector(toggleExplorer)
  27. ];
  28. // Load and process commits
  29. NSString *commitsURL = @"https://api.github.com/repos/Flipboard/FLEX/commits";
  30. [self startDataTask:commitsURL completion:^(NSData *data, NSInteger statusCode, NSError *error) {
  31. if (statusCode == 200) {
  32. self.commits.list = [Commit commitsFrom:data];
  33. [self fadeInNewRows];
  34. } else {
  35. [FLEXAlert showAlert:@"Error"
  36. message:error.localizedDescription ?: @(statusCode).stringValue
  37. from:self
  38. ];
  39. }
  40. }];
  41. }
  42. - (void)viewWillAppear:(BOOL)animated {
  43. [super viewWillAppear:animated];
  44. [self disableToolbar];
  45. }
  46. - (NSArray<FLEXTableViewSection *> *)makeSections {
  47. _commits = [FLEXMutableListSection list:@[]
  48. cellConfiguration:^(__kindof UITableViewCell *cell, Commit *commit, NSInteger row) {
  49. cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
  50. cell.textLabel.text = commit.firstLine;
  51. cell.detailTextLabel.text = commit.secondLine;
  52. cell.detailTextLabel.lineBreakMode = NSLineBreakByTruncatingTail;
  53. // cell.textLabel.numberOfLines = 2;
  54. // cell.detailTextLabel.numberOfLines = 3;
  55. UIImage *avi = self.avatars[commit.committer.login];
  56. if (avi) {
  57. cell.imageView.image = avi;
  58. } else {
  59. cell.tag = commit.identifier;
  60. [self loadImage:commit.committer.avatarUrl completion:^(UIImage *image) {
  61. self.avatars[commit.committer.login] = image;
  62. if (cell.tag == commit.identifier) {
  63. cell.imageView.image = image;
  64. } else {
  65. [self.tableView reloadRowsAtIndexPaths:@[
  66. [NSIndexPath indexPathForRow:row inSection:0]
  67. ] withRowAnimation:UITableViewRowAnimationAutomatic];
  68. }
  69. }];
  70. }
  71. } filterMatcher:^BOOL(NSString *filterText, Commit *commit) {
  72. return [commit matchesWithQuery:filterText];
  73. }
  74. ];
  75. self.commits.selectionHandler = ^(__kindof UIViewController *host, Commit *commit) {
  76. [host.navigationController pushViewController:[
  77. FLEXObjectExplorerFactory explorerViewControllerForObject:commit
  78. ] animated:YES];
  79. };
  80. return @[self.commits];
  81. }
  82. // Empty sections are removed by default and we always want this one section
  83. - (NSArray<FLEXTableViewSection *> *)nonemptySections {
  84. return @[_commits];
  85. }
  86. - (void)fadeInNewRows {
  87. NSIndexSet *sections = [NSIndexSet indexSetWithIndex:0];
  88. [self.tableView reloadSections:sections withRowAnimation:UITableViewRowAnimationAutomatic];
  89. }
  90. - (void)loadImage:(NSString *)imageURL completion:(void(^)(UIImage *image))callback {
  91. [self startDataTask:imageURL completion:^(NSData *data, NSInteger statusCode, NSError *error) {
  92. if (statusCode == 200) {
  93. callback([UIImage imageWithData:data]);
  94. }
  95. }];
  96. }
  97. - (void)startDataTask:(NSString *)urlString completion:(void (^)(NSData *data, NSInteger statusCode, NSError *error))completionHandler {
  98. // return;
  99. NSURL *url = [NSURL URLWithString:urlString];
  100. [[NSURLSession.sharedSession dataTaskWithURL:url completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
  101. dispatch_async(dispatch_get_main_queue(), ^{
  102. NSInteger code = [(NSHTTPURLResponse *)response statusCode];
  103. completionHandler(data, code, error);
  104. });
  105. }] resume];
  106. }
  107. @end