# How JJCollectionViewRoundFlowLayout Handles Empty Cells: Delegate and Property Configuration

> Learn how JJCollectionViewRoundFlowLayout handles empty cells. Configure delegate methods or properties like isCanCalculateWhenRowEmpty for custom behavior and avoid background issues.

- Repository: [Kingjiajie_Go/jjcollectionviewroundflowlayout](https://github.com/kingjiajie/jjcollectionviewroundflowlayout)
- Tags: how-to-guide
- Published: 2026-03-05

---

**JJCollectionViewRoundFlowLayout skips round background decoration for empty sections by default, but provides granular control through the delegate method `collectionView:layout:isCanCalculateWhenRowEmptyWithSection:` or the Boolean property `isCanCalculateWhenRowEmpty`.**

JJCollectionViewRoundFlowLayout is an open-source iOS library that adds rounded background decoration to UICollectionView sections. When sections contain no cells, the layout must decide whether to render the background decoration anyway. According to the kingjiajie/jjcollectionviewroundflowlayout repository, the library implements a two-tiered decision system in `prepareLayout` that checks a delegate method first, then falls back to a configuration property.

## The Two-Step Empty Section Detection Mechanism

The layout determines whether to draw a round background for a section containing zero items through a prioritized two-step mechanism. This design allows developers to override behavior globally via properties or dynamically via delegate callbacks.

### Step 1: Delegate Method Control

If the layout’s delegate implements the optional protocol method, the layout delegates the decision entirely to this method:

```objc
- (BOOL)collectionView:(UICollectionView *)collectionView
                layout:(UICollectionViewLayout *)collectionViewLayout
isCanCalculateWhenRowEmptyWithSection:(NSInteger)section;

```

When the delegate returns **`NO`**, the section is **skipped** and no decoration view is created. Returning **`YES`** forces the layout to treat the empty section like a normal one, computing a background view based on any existing header or footer.

### Step 2: Property Fallback

If the delegate does **not** implement the method, the layout falls back to the Boolean property `isCanCalculateWhenRowEmpty`. When this property is **`NO`** (the default), empty sections are skipped. Setting the property to **`YES`** forces background calculation for all empty sections globally.

## Implementation Details in prepareLayout

The relevant logic lives in `prepareLayout` within `JJCollectionViewRoundFlowLayout.m`. The layout iterates through sections and applies the two-step check before creating decoration attributes.

The detection and skipping logic appears around lines 998-1005:

```objc
if (numberOfItems > 0) {
    // normal case – obtain first item frame …
} else if ([delegate respondsToSelector:@selector(collectionView:layout:isCanCalculateWhenRowEmptyWithSection:)]) {
    // delegate decides whether to calculate the background for an empty section
    if (![delegate collectionView:self.collectionView
                            layout:self
        isCanCalculateWhenRowEmptyWithSection:section]) {
        continue;   // skip this section
    }
} else if (!self.isCanCalculateWhenRowEmpty) {
    // no delegate, fall back to the property flag
    continue;       // skip this section
}

```

When the `continue` statement executes, the layout **does not** create a `JJCollectionViewRoundLayoutAttributes` object for that section, preventing any decoration view from entering the collection view hierarchy.

If the section passes the empty-section check, the layout proceeds to compute `sectionFrame`, optionally merging header and footer frames, applying `borderEdgeInsets`, and finally appending a decoration attribute:

```objc
JJCollectionViewRoundLayoutAttributes *attr =
    [JJCollectionViewRoundLayoutAttributes layoutAttributesForDecorationViewOfKind:JJCollectionViewRoundSection
                                                                     withIndexPath:[NSIndexPath indexPathForRow:0 inSection:section]];
attr.frame = sectionFrame;
attr.zIndex = -1;
// … configure config model, touch-animation, etc.
[self.decorationViewAttrs addObject:attr];

```

## Configuration Outcomes Matrix

The interaction between the delegate method and the fallback property produces four distinct behaviors:

| Delegate Implementation | Return Value / Property State | Result for Empty Sections |
|-------------------------|------------------------------|---------------------------|
| **Implements method** | Returns `NO` | Section is **ignored**; no background drawn. |
| **Implements method** | Returns `YES` | Section is **processed**; background drawn based on header/footer or default frame. |
| **Does not implement** | `isCanCalculateWhenRowEmpty = NO` (default) | Section is **ignored**. |
| **Does not implement** | `isCanCalculateWhenRowEmpty = YES` | Section is **processed**; background drawn. |

## Practical Code Examples

### Enabling Background for Empty Sections via Property

To globally allow background decoration for all empty sections without implementing delegate methods:

```objc
JJCollectionViewRoundFlowLayout *layout = [[JJCollectionViewRoundFlowLayout alloc] init];
layout.isCanCalculateWhenRowEmpty = YES;   // treat empty sections like normal ones
collectionView.collectionViewLayout = layout;

```

### Controlling Empty Section Handling with Delegate

For dynamic, per-section control, implement the delegate protocol:

```objc
@interface MyViewController () <JJCollectionViewDelegateRoundFlowLayout>
@end

@implementation MyViewController

- (BOOL)collectionView:(UICollectionView *)collectionView
               layout:(UICollectionViewLayout *)layout
isCanCalculateWhenRowEmptyWithSection:(NSInteger)section {
    // Only draw backgrounds for even-indexed sections when they are empty
    return (section % 2 == 0);
}

@end

```

### Full Setup with Headers and Footers

When empty sections contain headers or footers, ensure the layout calculates their frames to determine the background bounds:

```objc
JJCollectionViewRoundFlowLayout *layout = [[JJCollectionViewRoundFlowLayout alloc] init];
layout.isCanCalculateWhenRowEmpty = YES;               // allow empty sections
layout.isCalculateHeader = YES;                        // honour header view
layout.isCalculateFooter = YES;                        // honour footer view
layout.delegate = self;                                 // optional delegate for fine-grained control
collectionView.collectionViewLayout = layout;

```

## Summary

- **JJCollectionViewRoundFlowLayout** skips decoration for empty sections by default to avoid rendering unnecessary backgrounds.
- **Delegate priority**: Implement `collectionView:layout:isCanCalculateWhenRowEmptyWithSection:` to dynamically control empty section rendering per section.
- **Property fallback**: Set `isCanCalculateWhenRowEmpty` to `YES` for global enablement when no delegate method exists.
- **Implementation location**: The logic resides in `prepareLayout` inside `JJCollectionViewRoundFlowLayout.m`, specifically around lines 998-1005.
- **Header/Footer support**: When empty sections are processed, the layout still calculates backgrounds based on existing header and footer frames.

## Frequently Asked Questions

### What happens to the round background when a section has no cells?

By default, **no background is drawn**. The layout checks if the section contains zero items and skips creating the decoration view unless explicitly permitted via the delegate method `collectionView:layout:isCanCalculateWhenRowEmptyWithSection:` or the `isCanCalculateWhenRowEmpty` property set to `YES`.

### Can I show a background for empty sections that contain only a header or footer?

Yes. When `isCanCalculateWhenRowEmpty` is enabled or the delegate permits the section, the layout calculates the `sectionFrame` by incorporating header and footer frames (if `isCalculateHeader` and `isCalculateFooter` are enabled). This ensures the round background surrounds the header or footer even when no cells exist.

### Where is the empty section detection logic implemented?

The detection logic is implemented in the `prepareLayout` method of `JJCollectionViewRoundFlowLayout.m`, specifically around lines 998-1005. This code block checks `numberOfItems`, queries the delegate if implemented, or falls back to the `isCanCalculateWhenRowEmpty` property before deciding whether to `continue` (skip) or proceed with decoration attribute creation.

### Should I use the delegate method or the property for controlling empty sections?

Use the **delegate method** `collectionView:layout:isCanCalculateWhenRowEmptyWithSection:` when you need **per-section control** (for example, only showing backgrounds for specific empty sections). Use the **property** `isCanCalculateWhenRowEmpty` when you want a **global setting** that applies to all empty sections uniformly without implementing delegate methods.