build method

  1. @override
View? build()
override

Builds this component's renderable output.

App code can return a node, another component, text, or an iterable of renderable values. The renderer normalizes the value internally.

Implementation

@override
View build() {
  if (slides.isEmpty) {
    return Container(
      className: _className,
      props: _props,
      style: _style,
      dartStyle: _dartStyle,
      children: const [],
    );
  }

  return Container(
    className: _className,
    props: {..._props, 'role': 'region', 'aria-roledescription': 'carousel'},
    style: _style,
    dartStyle: DartStyle(
      position: Position.relative,
      width: '100%',
      height: height,
      overflow: Overflow.hidden,
      radius: '24px',
      background: '#0f172a',
    ).merge(_dartStyle),
    children: [
      // Slides Stack Container with crossfade animation
      Container(
        dartStyle: const DartStyle(
          position: Position.absolute,
          width: '100%',
          height: '100%',
          left: '0px',
          top: '0px',
        ),
        children: [
          for (int i = 0; i < slides.length; i++)
            Container(
              dartStyle: DartStyle(
                position: Position.absolute,
                width: '100%',
                height: '100%',
                left: '0px',
                top: '0px',
                opacity: _currentIndex == i ? 1.0 : 0.0,
              ),
              style: {
                'pointer-events': _currentIndex == i ? 'auto' : 'none',
                'transition':
                    'opacity ${transitionDuration.inMilliseconds}ms ease-in-out',
              },
              children: [slides[i]],
            ),
        ],
      ),

      // Left Navigation Arrow Button
      Button(
        variant: ButtonVariant.ghost,
        onPressed: (_) => prevSlide(),
        dartStyle: const DartStyle(
          position: Position.absolute,
          left: '16px',
          top: '50%',
          transform: 'translateY(-50%)',
          width: '40px',
          height: '40px',
          radius: '20px',
          background: 'rgba(255, 255, 255, 0.25)',
          color: Colors.white,
          display: Display.flex,
          alignItems: AlignItems.center,
          justifyContent: JustifyContent.center,
          padding: EdgeInsets.all(0),
        ),
        style: const {
          'hover': {'background': 'rgba(255, 255, 255, 0.4)'},
          'z-index': '10',
        },
        child: Icon(Icons.chevronLeft, size: 24),
      ),

      // Right Navigation Arrow Button
      Button(
        variant: ButtonVariant.ghost,
        onPressed: (_) => nextSlide(),
        dartStyle: const DartStyle(
          position: Position.absolute,
          right: '16px',
          top: '50%',
          transform: 'translateY(-50%)',
          width: '40px',
          height: '40px',
          radius: '20px',
          background: 'rgba(255, 255, 255, 0.25)',
          color: Colors.white,
          display: Display.flex,
          alignItems: AlignItems.center,
          justifyContent: JustifyContent.center,
          padding: EdgeInsets.all(0),
        ),
        style: const {
          'hover': {'background': 'rgba(255, 255, 255, 0.4)'},
          'z-index': '10',
        },
        child: Icon(Icons.chevronRight, size: 24),
      ),

      // Dots Pagination Indicators
      Row(
        dartStyle: const DartStyle(
          position: Position.absolute,
          bottom: '16px',
          left: '50%',
          transform: 'translateX(-50%)',
          gap: '8px',
          alignItems: AlignItems.center,
        ),
        style: const {'z-index': '10'},
        children: [
          for (int i = 0; i < slides.length; i++)
            Button(
              variant: ButtonVariant.ghost,
              onPressed: (_) => selectSlide(i),
              dartStyle: DartStyle(
                width: '8px',
                height: '8px',
                radius: '4px',
                background: _currentIndex == i
                    ? '#ffffff'
                    : 'rgba(255, 255, 255, 0.4)',
                padding: EdgeInsets.all(0),
              ),
            ),
        ],
      ),
    ],
  );
}