Kosmesis
Components

Hover Card

A hover-activated preview card, wrapping Morphos's PreviewCard primitive.

Installation

npx kosmesis add hover-card
pnpm dlx kosmesis add hover-card
yarn dlx kosmesis add hover-card
bunx kosmesis add hover-card

Install the following dependencies:

npm install @morphos/overlays
pnpm add @morphos/overlays
yarn add @morphos/overlays
bun add @morphos/overlays

Copy and paste the following code into your project.

hover-card.tsx
import { StatelessComponent } from "@praxisjs/core";import { Component } from "@praxisjs/decorators";import { PreviewCard, PreviewCardContent as MorphosPreviewCardContent, PreviewCardTrigger, type PreviewCardContentProps as MorphosPreviewCardContentProps, type PreviewCardProps, type PreviewCardTriggerProps  } from "@morphos/overlays";import { cn } from "@/lib/utils";/** * shadcn/ui's `HoverCard`/`HoverCardTrigger` map to Morphos's `PreviewCard`/`PreviewCardTrigger`, * re-exported directly and renamed — the root is always instantiated directly * (`@State() card = new HoverCard()`), never mounted via JSX, so wrapping it would break * `.isOpen`/`.openCard()`/`.closeCard()`. */export { PreviewCard as HoverCard, PreviewCardTrigger as HoverCardTrigger };export type { PreviewCardProps as HoverCardProps, PreviewCardTriggerProps as HoverCardTriggerProps };export type HoverCardContentProps = MorphosPreviewCardContentProps;@Component()export class HoverCardContent extends StatelessComponent<HoverCardContentProps> {  render() {    const { class: cls, ...rest } = this.props;    return (      <MorphosPreviewCardContent        class={cn(          "z-50 w-64 rounded-md border bg-popover p-4 text-popover-foreground shadow-md outline-none",          "data-open:animate-in data-open:fade-in-0 data-open:zoom-in-95",          cls,        )}        {...rest}      />    );  }}

Install the following dependencies:

npm install @morphos/overlays @praxisjs/css
pnpm add @morphos/overlays @praxisjs/css
yarn add @morphos/overlays @praxisjs/css
bun add @morphos/overlays @praxisjs/css

Copy and paste the following code into your project.

hover-card.tsx
import { StatelessComponent } from "@praxisjs/core";import { cx, keyframes, Stylesheet, Styled, tokenVars } from "@praxisjs/css";import { Component } from "@praxisjs/decorators";import { PreviewCard, PreviewCardContent as MorphosPreviewCardContent, PreviewCardTrigger, type PreviewCardContentProps as MorphosPreviewCardContentProps, type PreviewCardProps, type PreviewCardTriggerProps  } from "@morphos/overlays";import { KosmesisTokens } from "@/lib/kosmesis-theme";const t = tokenVars(KosmesisTokens);const popIn = keyframes("kosmesis-pop-in", {  from: { opacity: "0", transform: "scale(0.95)" },  to: { opacity: "1", transform: "scale(1)" },});class HoverCardStyles extends Stylesheet {  $content = this.css({    zIndex: 50,    width: "16rem",    borderRadius: `calc(${t.radius} - 2px)`,    border: `1px solid ${t.border}`,    backgroundColor: t.popover,    padding: "1rem",    color: t.popoverForeground,    boxShadow: "0 4px 6px -1px rgb(0 0 0 / 0.1)",    outline: "none",  }).on("&[data-open]", { animation: `${popIn} 100ms ease-out` });}/** * shadcn/ui's `HoverCard`/`HoverCardTrigger` map to Morphos's `PreviewCard`/`PreviewCardTrigger`, * re-exported directly and renamed — the root is always instantiated directly * (`@State() card = new HoverCard()`), never mounted via JSX, so wrapping it would break * `.isOpen`/`.openCard()`/`.closeCard()`. */export { PreviewCard as HoverCard, PreviewCardTrigger as HoverCardTrigger };export type { PreviewCardProps as HoverCardProps, PreviewCardTriggerProps as HoverCardTriggerProps };export type HoverCardContentProps = MorphosPreviewCardContentProps;@Component()export class HoverCardContent extends StatelessComponent<HoverCardContentProps> {  @Styled(HoverCardStyles) $s!: HoverCardStyles;  render() {    const { class: cls, ...rest } = this.props;    return <MorphosPreviewCardContent class={cx(this.$s.$content, cls)} {...rest} />;  }}

Examples

Usage

import { HoverCard, HoverCardContent, HoverCardTrigger } from "@/components/ui/hover-card";

@Component()
class UserMention extends StatefulComponent {
  @State() card = new HoverCard();

  render() {
    return (
      <>
        <HoverCardTrigger card={this.card} class="font-medium underline">@praxisjs</HoverCardTrigger>
        <HoverCardContent card={this.card}>
          <p class="font-semibold">PraxisJS</p>
          <p class="text-sm text-muted-foreground">Signal-driven frontend framework.</p>
        </HoverCardContent>
      </>
    );
  }
}

HoverCard/HoverCardTrigger are Morphos's PreviewCard/PreviewCardTrigger, re-exported and renamed.

On this page