Components
Actions
A row of small icon action buttons under an AI response. Purely presentational — no Morphos equivalent.
Installation
npx kosmesis add actionspnpm dlx kosmesis add actionsyarn dlx kosmesis add actionsbunx kosmesis add actionsCopy and paste the following code into your project.
import { StatelessComponent } from "@praxisjs/core";import { Component } from "@praxisjs/decorators";import type { Children } from "@praxisjs/shared";import { cn } from "@/lib/utils";export interface ActionsProps { class?: string; children?: Children;}@Component()export class Actions extends StatelessComponent<ActionsProps> { render() { const { class: cls, children } = this.props; return ( <div data-slot="actions" role="toolbar" class={cn("flex items-center gap-1", cls)}> {children} </div> ); }}export interface ActionProps { label: string; onClick?: () => void; class?: string; children?: Children;}@Component()export class Action extends StatelessComponent<ActionProps> { render() { const { label, onClick, class: cls, children } = this.props; return ( <button type="button" aria-label={label} title={label} class={cn( "flex size-7 items-center justify-center rounded-md text-muted-foreground hover:bg-accent hover:text-accent-foreground", cls, )} onClick={onClick} > {children} </button> ); }}Install the following dependencies:
npm install @praxisjs/csspnpm add @praxisjs/cssyarn add @praxisjs/cssbun add @praxisjs/cssCopy and paste the following code into your project.
import { StatelessComponent } from "@praxisjs/core";import { cx, Stylesheet, Styled, tokenVars } from "@praxisjs/css";import { Component } from "@praxisjs/decorators";import type { Children } from "@praxisjs/shared";import { KosmesisTokens } from "@/lib/kosmesis-theme";const t = tokenVars(KosmesisTokens);class ActionsStyles extends Stylesheet { $root = this.css({ display: "flex", alignItems: "center", gap: "0.25rem" }); $button = this.css({ display: "flex", height: "1.75rem", width: "1.75rem", alignItems: "center", justifyContent: "center", borderRadius: "0.375rem", color: t.mutedForeground, cursor: "pointer", }).on("&:hover", { backgroundColor: t.accent, color: t.accentForeground });}export interface ActionsProps { class?: string; children?: Children;}@Component()export class Actions extends StatelessComponent<ActionsProps> { @Styled(ActionsStyles) $s!: ActionsStyles; render() { const { class: cls, children } = this.props; return ( <div data-slot="actions" role="toolbar" class={cx(this.$s.$root, cls)}> {children} </div> ); }}export interface ActionProps { label: string; onClick?: () => void; class?: string; children?: Children;}@Component()export class Action extends StatelessComponent<ActionProps> { @Styled(ActionsStyles) $s!: ActionsStyles; render() { const { label, onClick, class: cls, children } = this.props; return ( <button type="button" aria-label={label} title={label} class={cx(this.$s.$button, cls)} onClick={onClick}> {children} </button> ); }}Examples
About
Purely presentational — no Morphos equivalent. Actions is the row container; each Action
is a plain icon button (copy, regenerate, share, ...). Pairs well with Message's actions slot.
Usage
import { Icon } from "@morphos/icons";
import { Action, Actions } from "@/components/ui/actions";
<Actions>
<Action label="Copy" onClick={copyText}><Icon name="Copy" size={16} /></Action>
<Action label="Regenerate" onClick={regenerate}><Icon name="RotateCw" size={16} /></Action>
</Actions>Props
Action
| Prop | Type | Default |
|---|---|---|
label | string | — |
onClick | () => void | — |
class | string | — |
Actions accepts class and children only.