29
29
#import " FZAccordionTableView.h"
30
30
#import < objc/runtime.h>
31
31
32
+ #pragma mark -
33
+ #pragma mark - FZAccordionTableViewSection
34
+ #pragma mark -
35
+
36
+ @interface FZAccordionTableViewSection : NSObject
37
+ @property (nonatomic , getter =isOpen) BOOL open;
38
+ @property (nonatomic ) NSInteger numberOfRows;
39
+ @end
40
+
41
+ @implementation FZAccordionTableViewSection
42
+ - (instancetype )initWithNumberOfRows : (NSInteger )numberOfRows {
43
+ if (self = [super init ]) {
44
+ _numberOfRows = numberOfRows;
45
+ }
46
+ return self;
47
+ }
48
+ @end
49
+
32
50
#pragma mark -
33
51
#pragma mark - FZAccordionTableViewHeaderView
34
52
#pragma mark -
@@ -81,8 +99,9 @@ @interface FZAccordionTableView() <UITableViewDataSource, UITableViewDelegate, F
81
99
@property id <UITableViewDelegate, FZAccordionTableViewDelegate> subclassDelegate;
82
100
@property id <UITableViewDataSource> subclassDataSource;
83
101
84
- @property (strong , nonatomic ) NSMutableSet *openedSections;
85
- @property (strong , nonatomic ) NSMutableDictionary *numOfRowsForSection;
102
+ // @property (strong, nonatomic) NSMutableSet *openedSections;
103
+ // @property (strong, nonatomic) NSMutableDictionary *numOfRowsForSection;
104
+ @property (strong , nonatomic ) NSMutableArray <FZAccordionTableViewSection *> *sections; // <FZAccordionTableViewSection *>
86
105
87
106
@end
88
107
@@ -119,8 +138,9 @@ - (id)init {
119
138
}
120
139
121
140
- (void )initializeVars {
122
- _openedSections = [[NSMutableSet alloc ] init ];
123
- _numOfRowsForSection = [NSMutableDictionary dictionary ];
141
+ // _openedSections = [[NSMutableSet alloc] init];
142
+ // _numOfRowsForSection = [NSMutab
143
+ _sections = [NSMutableArray new ];
124
144
_allowMultipleSectionsOpen = NO ;
125
145
_enableAnimationFix = NO ;
126
146
_keepOneSectionOpen = NO ;
@@ -129,24 +149,24 @@ - (void)initializeVars {
129
149
#pragma mark - Helper methods -
130
150
131
151
- (BOOL )isSectionOpen : (NSInteger )section {
132
- return [self .openedSections containsObject: @( section) ];
152
+ return [self .sections[ section] isOpen ];
133
153
}
134
154
135
155
- (BOOL )isAlwaysOpenedSection : (NSInteger )section {
136
156
return [self .sectionsAlwaysOpen containsObject: @(section)];
137
157
}
138
158
139
- - (void )addOpenedSection : (NSInteger )section {
140
- [self .openedSections addObject: @(section) ];
159
+ - (void )addOpenedSection : (NSInteger )section { // KRIS TODO: Rename this to markSectionOpen
160
+ [self .sections[section] setOpen: YES ];
141
161
}
142
162
143
163
- (void )removeOpenedSection : (NSInteger )section {
144
- [self .openedSections removeObject: @(section) ];
164
+ [self .sections[section] setOpen: NO ];
145
165
}
146
166
147
167
- (NSArray *)getIndexPathsForSection : (NSInteger )section {
148
168
149
- NSInteger numOfRows = [self .numOfRowsForSection[@( section)] integerValue ];
169
+ NSInteger numOfRows = [self .sections[ section] numberOfRows ];
150
170
NSMutableArray *indexPaths = [NSMutableArray array ];
151
171
for (int row = 0 ; row < numOfRows; row++) {
152
172
[indexPaths addObject: [NSIndexPath indexPathForRow: row inSection: section]];
@@ -202,27 +222,11 @@ - (void)setDataSource:(id<UITableViewDataSource>)dataSource {
202
222
203
223
- (void )deleteSections : (NSIndexSet *)sections withRowAnimation : (UITableViewRowAnimation)animation {
204
224
205
- // Loop:
206
- // [self headerViewForSection:section];
207
- // stop when its past the possible table view bounds.
208
- // update each of the sections by 1.
209
-
210
-
211
- // You can also utilize: viewForHeaderInSection
212
- // Save the lowest possible section that was called for viewForHeaderInSection???
213
- //
214
- // [sections enumerateIndexesWithOptions:NSEnumerationReverse usingBlock:^(NSUInteger idx, BOOL * _Nonnull stop) {
215
- //
216
- // }];
217
- //
218
- // for (int i = sections.firstIndex; i < self.numberOfSections; i++) {
219
- // FZAccordionTableViewHeaderView *headerView = [self tableView:self viewForHeaderInSection:i];
220
- // headerView.section--;
221
- // }
222
-
223
- [sections enumerateIndexesUsingBlock: ^(NSUInteger index, BOOL * _Nonnull stop) {
224
- self.numOfRowsForSection [@(index)] = nil ;
225
- [self .openedSections removeObject: @(index)];
225
+ [sections enumerateIndexesUsingBlock: ^(NSUInteger section, BOOL * _Nonnull stop) {
226
+ [self .sections removeObjectAtIndex: section];
227
+ // KRIS TODO: If the removed section is one that needs ot be oepned, we need to open the next section.
228
+ // OR Refactor sections open to just be a delegate call "canOpen Section
229
+ // [self.openedSections removeObject:@(section)];
226
230
}];
227
231
[super deleteSections: sections withRowAnimation: animation];
228
232
}
@@ -249,21 +253,21 @@ - (BOOL)respondsToSelector:(SEL)aSelector {
249
253
- (void )setSectionsAlwaysOpen : (NSSet *)alwaysOpenedSections {
250
254
_sectionsAlwaysOpen = alwaysOpenedSections;
251
255
252
- if (_sectionsAlwaysOpen != nil ) {
253
- for (NSNumber *alwaysOpenedSection in _sectionsAlwaysOpen) {
254
- [self addOpenedSection: alwaysOpenedSection.integerValue];
255
- }
256
- }
256
+ // if (_sectionsAlwaysOpen != nil) {
257
+ // for (NSNumber *alwaysOpenedSection in _sectionsAlwaysOpen) {
258
+ // [self addOpenedSection:alwaysOpenedSection.integerValue];
259
+ // }
260
+ // }
257
261
}
258
262
259
263
- (void )setInitialOpenSections : (NSSet *)initialOpenedSections {
260
264
_initialOpenSections = initialOpenedSections;
261
265
262
- if (_initialOpenSections != nil ) {
263
- for (NSNumber *section in _initialOpenSections) {
264
- [self addOpenedSection: section.integerValue];
265
- }
266
- }
266
+ // if (_initialOpenSections != nil) {
267
+ // for (NSNumber *section in _initialOpenSections) {
268
+ // [self addOpenedSection:section.integerValue];
269
+ // }
270
+ // }
267
271
}
268
272
269
273
#pragma mark - FZAccordionTableViewHeaderViewDelegate -
@@ -280,14 +284,20 @@ - (void)tappedHeaderView:(FZAccordionTableViewHeaderView *)sectionHeaderView {
280
284
281
285
// Keep at least one section open
282
286
if (self.keepOneSectionOpen ) {
283
- NSInteger countOfOpenSections = self. openedSections . count ;
287
+ NSInteger countOfOpenSections = 0 ;
284
288
285
- if (self. sectionsAlwaysOpen . count > 0 ) { // Subtract 'sectionsAlwaysOpen' from 'openedSections'
286
- NSMutableSet *openedSectionsCopy = [self .openedSections mutableCopy ];
287
- [openedSectionsCopy minusSet: self .sectionsAlwaysOpen] ;
288
- countOfOpenSections = openedSectionsCopy. count ;
289
+ for ( NSInteger i = 0 ; i < self. numberOfSections ; i++) {
290
+ if ( [self .sections[i] isOpen ]) {
291
+ countOfOpenSections++ ;
292
+ }
289
293
}
290
294
295
+ // if (self.sectionsAlwaysOpen.count > 0) { // Subtract 'sectionsAlwaysOpen' from 'openedSections'
296
+ // NSMutableSet *openedSectionsCopy = [self.openedSections mutableCopy];
297
+ // [openedSectionsCopy minusSet:self.sectionsAlwaysOpen];
298
+ // countOfOpenSections = openedSectionsCopy.count;
299
+ // }
300
+
291
301
if (countOfOpenSections == 1 && [self isSectionOpen: section]) {
292
302
return ;
293
303
}
@@ -323,20 +333,23 @@ - (void)openSection:(NSInteger)section withHeaderView:(FZAccordionTableViewHeade
323
333
324
334
UITableViewRowAnimation insertAnimation = UITableViewRowAnimationTop;
325
335
if (!self.allowMultipleSectionsOpen ) {
326
- for (NSNumber *openSection in self.openedSections ) {
327
- if (openSection.integerValue < section) {
336
+ // If any section is open beneath the one we are trying to open,
337
+ // animate from the bottom
338
+ for (NSInteger i = section-1 ; i >= 0 ; i--) {
339
+ if ([self .sections[i] isOpen ]) {
328
340
insertAnimation = UITableViewRowAnimationBottom;
329
341
}
330
342
}
331
343
}
332
344
333
- if (self.enableAnimationFix ) {
334
- if (self.openedSections .count > 0 &&
335
- (section == self.numOfRowsForSection .count -1 || section == self.numOfRowsForSection .count -2 ) &&
336
- !self.allowsMultipleSelection ) {
337
- insertAnimation = UITableViewRowAnimationFade;
338
- }
339
- }
345
+ // KRIS TODO: Fix
346
+ // if (self.enableAnimationFix) {
347
+ // if (self.openedSections.count > 0 &&
348
+ // (section == self.sections.count-1 || section == self.sections.count-2) &&
349
+ // !self.allowsMultipleSelection) {
350
+ // insertAnimation = UITableViewRowAnimationFade;
351
+ // }
352
+ // }
340
353
341
354
[self addOpenedSection: section];
342
355
[self beginUpdates ];
@@ -368,9 +381,10 @@ - (void)closeSection:(NSInteger)section withHeaderView:(FZAccordionTableViewHead
368
381
- (void )autoCollapseAllSectionsExceptSection : (NSInteger )section {
369
382
// Get all of the sections that we need to close
370
383
NSMutableSet *sectionsToClose = [[NSMutableSet alloc ] init ];
371
- for (NSNumber *openedSection in self.openedSections ) {
372
- if (openedSection.integerValue != section && ![self isAlwaysOpenedSection: openedSection.integerValue]) {
373
- [sectionsToClose addObject: openedSection];
384
+ for (NSInteger i = 0 ; i < self.numberOfSections ; i++) {
385
+ FZAccordionTableViewSection *sectionInfo = self.sections [i];
386
+ if (section != i && sectionInfo.isOpen && ![self isAlwaysOpenedSection: i]) {
387
+ [sectionsToClose addObject: @(i)];
374
388
}
375
389
}
376
390
@@ -387,8 +401,8 @@ - (void)autoCollapseAllSectionsExceptSection:(NSInteger)section {
387
401
closeAnimation = UITableViewRowAnimationBottom;
388
402
}
389
403
if (self.enableAnimationFix ) {
390
- if ((sectionToClose.integerValue == self.numOfRowsForSection .count - 1 ||
391
- sectionToClose.integerValue == self.numOfRowsForSection .count - 2 ) &&
404
+ if ((sectionToClose.integerValue == self.sections .count - 1 ||
405
+ sectionToClose.integerValue == self.sections .count - 2 ) &&
392
406
!self.allowsMultipleSelection ) {
393
407
closeAnimation = UITableViewRowAnimationFade;
394
408
}
@@ -412,14 +426,48 @@ - (void)autoCollapseAllSectionsExceptSection:(NSInteger)section {
412
426
413
427
#pragma mark - <UITableViewDataSource> -
414
428
429
+ - (NSInteger )numberOfSectionsInTableView : (UITableView *)tableView {
430
+
431
+ NSInteger numOfSections = 1 ; // Default value for UITableView is 1
432
+
433
+ if ([self .subclassDataSource respondsToSelector: @selector (numberOfSectionsInTableView: )]) {
434
+ numOfSections = [self .subclassDataSource numberOfSectionsInTableView: tableView];
435
+ }
436
+
437
+ // Initialize an empty array filled with @(0)
438
+ // id sections[numOfSections];
439
+ // memset(sections, (int)[NSNumber numberWithInt:0], numOfSections);
440
+ // self.numberOfRowsInSection = [NSMutableArray arrayWithObjects:sections count:numOfSections];
441
+ // self.numberOfRowsInSection = [NSMutableArray arrayWithCapacity:numOfSections];
442
+ // NSMutableArray *newNumberOfRowsInSection = [NSMutableArray arrayWithCapacity:numOfSections];
443
+
444
+ for (NSInteger i = self.sections .count ; i < numOfSections; i++) {
445
+ FZAccordionTableViewSection *section = [[FZAccordionTableViewSection alloc ] initWithNumberOfRows: 0 ];
446
+ section.open = NO ;
447
+ [self .sections addObject: section];
448
+ // KRIS TO DO: Handle sections always open and initial open sections.
449
+ }
450
+
451
+
452
+ // First time
453
+ // it's less
454
+ // it's more
455
+
456
+
457
+ // we must maintain the correct size, yet also copy in the left-over elements.
458
+
459
+
460
+ return numOfSections;
461
+ }
462
+
415
463
- (NSInteger )tableView : (UITableView *)tableView numberOfRowsInSection : (NSInteger )section {
416
464
417
465
NSInteger numOfRows = 0 ;
418
466
419
467
if ([self .subclassDataSource respondsToSelector: @selector (tableView:numberOfRowsInSection: )]) {
420
468
numOfRows = [self .subclassDataSource tableView: tableView numberOfRowsInSection: section];;
421
469
}
422
- self.numOfRowsForSection [@( section)] = @( numOfRows) ;
470
+ [ self .sections[ section] setNumberOfRows: numOfRows] ;
423
471
424
472
return ([self isSectionOpen: section]) ? numOfRows : 0 ;
425
473
}
0 commit comments