@softize/opus 12.2.0 → 12.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -7,6 +7,12 @@ Depois de qualquer bump, rode os gates (`typecheck` · `test` · `opus check` ·
7
7
  `opus copy --check` · `base copy check` · `manifest:check`) — eles apontam o que a
8
8
  mudança cobra do seu código.
9
9
 
10
+ ## 12.2.1 — 2026-08-23
11
+
12
+ O cabeçalho de `Page` passa a alinhar `actions` à base do bloco formado por título e descrição.
13
+ Assim, os botões permanecem junto ao fim do contexto quando a página apresenta uma linha
14
+ explicativa. Múltiplas ações conservam o espaçamento entre si. A API pública não muda.
15
+
10
16
  ## 12.2.0 — 2026-08-23
11
17
 
12
18
  A escala de arredondamento ganha uma base mais presente sem transformar todo componente em uma
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@softize/opus",
3
- "version": "12.2.0",
3
+ "version": "12.2.1",
4
4
  "description": "End-to-end action protocol for TypeScript. Single package with subpath exports (core + adapters).",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -3,7 +3,8 @@
3
3
  *
4
4
  * Padroniza o que toda página repete: <main> + container de largura CHEIA (o caso
5
5
  * comum do back-office; quem quiser estreito passa `className="max-w-5xl"`) + header
6
- * (título, descrição e a ação à direita — em geral o botão de criar). O conteúdo é
6
+ * (título, descrição e ações à direita, alinhadas ao fim desse bloco — em geral o botão
7
+ * de criar). O conteúdo é
7
8
  * children, sem nada imposto. Presentacional (sem contrato) de propósito: uma página
8
9
  * agrega N fontes; o que é action-driven mora dentro (ActionList, listas query-backed).
9
10
  */
@@ -17,7 +18,7 @@ export interface PageProps {
17
18
  count?: number
18
19
  /** Linha de contexto sob o título. */
19
20
  description?: ReactNode
20
- /** Ação à direita do header em geral o botão de criar. */
21
+ /** Ações à direita do header, alinhadas ao fim do bloco de contexto. */
21
22
  actions?: ReactNode
22
23
  /** Classes do container. Default: largura cheia; `max-w-5xl` estreita e centra. */
23
24
  className?: string
@@ -28,16 +29,22 @@ export function Page({ title, count, description, actions, className, children }
28
29
  return (
29
30
  <main data-slot="page" className="min-w-0 flex-1">
30
31
  <div className={cn('mx-auto px-8 py-8', className)}>
31
- {/* As ações alinham com o TÍTULO; a descrição vem abaixo, em linha própria. */}
32
+ {/* As ações acompanham o fim do contexto, mesmo quando uma descrição sob o título. */}
32
33
  <div data-slot="page-header" className="mb-6">
33
- <div className={cn(actions !== undefined && 'flex items-center justify-between gap-4')}>
34
- <h1 className="flex items-baseline gap-2 text-2xl font-semibold tracking-tight">
35
- {title}
36
- {count !== undefined && <span className="font-mono text-base text-muted-foreground/60">{count}</span>}
37
- </h1>
38
- {actions}
34
+ <div className={cn(actions !== undefined && 'flex items-end justify-between gap-4')}>
35
+ <div data-slot="page-heading" className="min-w-0">
36
+ <h1 className="flex items-baseline gap-2 text-2xl font-semibold tracking-tight">
37
+ {title}
38
+ {count !== undefined && <span className="font-mono text-base text-muted-foreground/60">{count}</span>}
39
+ </h1>
40
+ {description !== undefined && <p className="mt-1 text-sm text-muted-foreground">{description}</p>}
41
+ </div>
42
+ {actions !== undefined && (
43
+ <div data-slot="page-actions" className="flex shrink-0 items-center gap-4">
44
+ {actions}
45
+ </div>
46
+ )}
39
47
  </div>
40
- {description !== undefined && <p className="mt-1 text-sm text-muted-foreground">{description}</p>}
41
48
  </div>
42
49
  {children}
43
50
  </div>
@@ -1,6 +1,10 @@
1
1
  ## Esqueleto de página
2
2
 
3
- O que toda página do back-office repete, num pattern só: `<main>` + container de largura cheia (o caso comum; `className="max-w-5xl"` estreita e centra) + header com título, descrição e a ação à direita. O conteúdo é children, sem nada imposto. Presentacional de propósito — uma página agrega N fontes; o que é action-driven (listas, forms) mora dentro.
3
+ Use `Page` para manter título, contexto, ações e conteúdo no mesmo ritmo visual nas telas do
4
+ back-office. As ações ficam à direita e acompanham a base do conjunto formado pelo título e pela
5
+ descrição. O componente ocupa a largura disponível; passe `className="max-w-5xl"` quando a tela
6
+ pedir conteúdo mais estreito e centralizado. A área abaixo do cabeçalho permanece livre para
7
+ tabelas, cards ou outras composições.
4
8
 
5
9
  ```tsx preview col
6
10
  render(
@@ -8,6 +12,7 @@ render(
8
12
  <Page
9
13
  title="Workspaces"
10
14
  count={3}
15
+ description="Ambientes compartilhados pela equipe."
11
16
  actions={
12
17
  <Button>
13
18
  <Plus /> Novo workspace
@@ -29,6 +34,6 @@ render(
29
34
  | `title` | `string` | | O h1 da página. |
30
35
  | `count` | `number` | | Total de itens ao lado do título (mono, esmaecido). |
31
36
  | `description` | `ReactNode` | | Linha de contexto sob o título (ex.: "N no total · X ativos"). |
32
- | `actions` | `ReactNode` | | Ação à direita do header em geral o botão de criar. |
37
+ | `actions` | `ReactNode` | | Ações à direita do cabeçalho, alinhadas à base do título e da descrição. |
33
38
  | `className` | `string` | largura cheia | Classes do container (`max-w-5xl` estreita e centra). |
34
39
  | `children` | `ReactNode` | | O conteúdo — espaçamento e diagramação são seus. |