render method

  1. @override
void render(
  1. Buffer buffer,
  2. Rect area
)
override

Renders the widget onto the provided buffer within the specified area.

Implementation

@override
void render(Buffer buffer, Rect area) {
  _updateFlatNodes();
  adjustScroll(area.height);

  final activeSelectedStyle = focused
      ? selectedStyle
      : Style(
          foreground: selectedStyle.foreground,
          background: CharmColors.char,
          modifiers: selectedStyle.modifiers,
        );

  for (var i = 0; i < area.height; i++) {
    final nodeIdx = _scrollOffset + i;
    if (nodeIdx >= _flatNodes.length) break;

    final flat = _flatNodes[nodeIdx];
    final isSelected = nodeIdx == _selectedIndex;

    var x = 0;

    // 1. Ancestor guide lines
    for (var depthIdx = 0; depthIdx < flat.depth - 1; depthIdx++) {
      if (x >= area.width) break;
      final isLast = flat.ancestorIsLast[depthIdx];
      final part = isLast ? '   ' : '│  ';
      buffer.writeString(
        area.x + x,
        area.y + i,
        part,
        isSelected ? activeSelectedStyle : lineStyle,
      );
      x += 3;
    }

    // 2. Active node guide line
    if (flat.depth > 0 && x < area.width) {
      final isLast = flat.ancestorIsLast.last;
      final part = isLast ? '└── ' : '├── ';
      buffer.writeString(
        area.x + x,
        area.y + i,
        part,
        isSelected ? activeSelectedStyle : lineStyle,
      );
      x += 4;
    }

    // 3. Expander indicator
    if (x < area.width) {
      final indicator = flat.node.isLeaf
          ? '  '
          : (flat.node.isExpanded ? '▼ ' : '▶ ');
      buffer.writeString(
        area.x + x,
        area.y + i,
        indicator,
        isSelected ? activeSelectedStyle : lineStyle,
      );
      x += 2;
    }

    // 4. Label
    final remainingWidth = area.width - x;
    if (remainingWidth > 0) {
      final labelChars = flat.node.label.characters;
      final labelText = labelChars.length > remainingWidth
          ? labelChars.take(remainingWidth).toString()
          : labelChars.toString() +
                (' ' * (remainingWidth - labelChars.length));
      buffer.writeString(
        area.x + x,
        area.y + i,
        labelText,
        isSelected ? activeSelectedStyle : unselectedStyle,
      );
    }
  }
}