Namespace: Beep.Skia.Controls — Inherits: MaterialControl → SkiaComponent

Overview

The Card control is a Material Design 3.0 surface container that groups related content and actions into a single elevated panel. Cards are rendered entirely with SkiaSharp and provide three distinct layout areas: a header for titles and subtitles, a body for arbitrary content, and a footer for action buttons. The card's surface responds to the active Material theme, rendering the correct background color, elevation shadow, and corner shape automatically.

Cards are the primary container primitive in Beep.Skia's UI system. They are used for property editors, tool palettes, detail panels, and any grouped information display. Nested SkiaComponent children are laid out inside the body area using the configured layout engine.

Properties

PropertyTypeDescription
Title string Header title text. Rendered in TitleLarge typography. Set to null to hide the header entirely.
Subtitle string Optional subtitle rendered below the title in BodyMedium typography and muted color.
Content SkiaComponent The root component rendered in the card body area. Can be any SkiaComponent or a container with multiple children.
Elevation int Material Design elevation level (0–5). Controls the shadow cast by the card. Default is 1. Set to 0 for flat cards.
CornerRadius float Radius of the card's rounded corners. Default is 12f (MD3 medium rounding).
HasShadow bool Enables or disables the elevation shadow. Default is true. Disable when the card is on a same-color surface.
IsOutlined bool When true, renders an Outline-colored border instead of (or in addition to) an elevation shadow. Default is false.
HeaderPadding float Internal padding for the header area. Default is 16f.
BodyPadding float Internal padding for the body area. Default is 16f.
FooterPadding float Internal padding for the footer area. Default is 8f.
HeaderHeight float Fixed height of the header area. If 0 (default), the header auto-sizes to fit its content.
FooterHeight float Fixed height of the footer area. If 0 (default), the footer auto-sizes to fit its content.
ShowHeader bool Controls header visibility. When false (and no Title is set), the header area collapses to zero height.
ShowFooter bool Controls footer visibility. When false, the footer area collapses to zero height.

Layout Areas

The Card control divides its surface into three vertical zones, drawn top-to-bottom:

AreaPositionContent
Header Top of the card, below the rounded top corners Renders the Title and Subtitle using theme typography. Optional leading icon can be set. A separator line is drawn between the header and body.
Body Between the header and footer The main content area. The Content component is drawn here using its own DrawContent method. Its coordinate space is relative to the body's top-left corner.
Footer Bottom of the card, above the rounded bottom corners Optional action area. Typically contains Button components arranged horizontally (right-aligned by default). A separator line is drawn between the body and footer.
Image Top of the card, above the header Optional hero image. An SKBitmap rendered full-width with a 16:9 aspect ratio. The image clips to the card's corner radius.

Note

The header, body, and footer are rendered as separate clip regions. Content in the body area cannot overflow into the header or footer zones. Use a ScrollContainer as the Content component to handle overflow.

Code Example

Basic Card with Title and Content

var contentLabel = new Label
{
    Text = "This is the card body content.\nIt can contain any SkiaComponent.",
    X = 0,
    Y = 0,
    Width = 300,
    Height = 80
};
contentLabel.Initialize();

var card = new Card
{
    Title = "Settings",
    Subtitle = "Configure your preferences",
    X = 50,
    Y = 50,
    Width = 350,
    Height = 200,
    Elevation = 2,
    CornerRadius = 12f,
    HasShadow = true,
    Content = contentLabel
};

card.Initialize();
drawingManager.AddComponent(card);
drawingManager.RequestRedraw();

Card with Header Image and Footer Actions

var heroBitmap = SKBitmap.Decode("path/to/image.png");

var closeButton = new Button
{
    Text = "Close",
    ButtonStyle = ButtonStyle.Text,
    X = 0, Y = 0,
    Width = 80, Height = 36
};
closeButton.Initialize();

var saveButton = new Button
{
    Text = "Save",
    ButtonStyle = ButtonStyle.Filled,
    X = 90, Y = 0,
    Width = 80, Height = 36
};
saveButton.Initialize();

var footerContainer = new Container
{
    X = 0, Y = 0,
    Width = 350, Height = 44,
    Children = new List { closeButton, saveButton }
};

var bodyText = new Label
{
    Text = "Project configuration saved successfully.",
    X = 0, Y = 0,
    Width = 300, Height = 60
};
bodyText.Initialize();

var card = new Card
{
    Title = "Project Status",
    Image = heroBitmap,
    Content = bodyText,
    Footer = footerContainer,
    ShowFooter = true,
    X = 50, Y = 50,
    Width = 350,
    Elevation = 3
};

card.Initialize();
drawingManager.AddComponent(card);

Outlined Card (No Shadow)

var card = new Card
{
    Title = "Quick Actions",
    IsOutlined = true,
    HasShadow = false,
    Elevation = 0,
    CornerRadius = 8f,
    X = 450,
    Y = 50,
    Width = 300,
    Height = 160
};

card.Initialize();
drawingManager.AddComponent(card);