---
title: "Block Components"
description: "Reference for all included Gutenberg block components"
canonical_url: "https://wpnuxt.com/reference/block-components"
---
# Block Components

> Reference for all included Gutenberg block components

`@wpnuxt/blocks` includes Vue components for common Gutenberg blocks.

## How It Works

The `BlockRenderer` component iterates over `editorBlocks` and renders each block using the appropriate component based on the block's `name` attribute.

```text
core/paragraph  →  CoreParagraph.vue
core/heading    →  CoreHeading.vue
core/image      →  CoreImage.vue
```

Unsupported blocks fall back to `EditorBlock`, which renders the saved HTML.

## Included Components

### CoreParagraph

Renders paragraph blocks with support for anchors, CSS classes, and inline styles.

<table>
<thead>
  <tr>
    <th>
      Attribute
    </th>
    
    <th>
      Type
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        content
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      HTML content
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        anchor
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Element ID for linking
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        className
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Custom CSS classes
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        style
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Inline styles
    </td>
  </tr>
</tbody>
</table>

```vue
<!-- Output -->
<p id="anchor" class="custom-class" style="...">
  Content here
</p>
```

### CoreHeading

Renders heading blocks (h1-h6) based on the `level` attribute.

<table>
<thead>
  <tr>
    <th>
      Attribute
    </th>
    
    <th>
      Type
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        content
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      HTML content
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        level
      </code>
    </td>
    
    <td>
      <code>
        number
      </code>
    </td>
    
    <td>
      Heading level (1-6)
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        anchor
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Element ID for linking
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        className
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Custom CSS classes
    </td>
  </tr>
</tbody>
</table>

```vue
<!-- Output for level 2 -->
<h2 id="anchor" class="custom-class">
  Heading text
</h2>
```

### CoreImage

Renders images using `<NuxtImg>` for optimization. Falls back to rendered HTML if URL is missing.

<table>
<thead>
  <tr>
    <th>
      Attribute
    </th>
    
    <th>
      Type
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        url
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Image URL
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        alt
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Alt text
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        width
      </code>
    </td>
    
    <td>
      <code>
        number
      </code>
    </td>
    
    <td>
      Image width
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        height
      </code>
    </td>
    
    <td>
      <code>
        number
      </code>
    </td>
    
    <td>
      Image height
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        scale
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Object fit mode
    </td>
  </tr>
</tbody>
</table>

```vue
<!-- Output -->
<NuxtImg
  src="/wp-content/uploads/image.jpg"
  alt="Description"
  width="800"
  height="600"
/>
```

<note>

Requires `@nuxt/image` module. Configure `imageDomains` in `wpNuxtBlocks` config.

</note>

### CoreButton

Renders button blocks. Automatically uses `<UButton>` when Nuxt UI is available, otherwise falls back to native elements.

<table>
<thead>
  <tr>
    <th>
      Attribute
    </th>
    
    <th>
      Type
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        text
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Button text
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        url
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Link URL
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        linkTarget
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Target attribute (<code>
        _blank
      </code>
      
      , etc.)
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        rel
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Rel attribute
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        style
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Inline styles
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        fontSize
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Font size preset
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        metadata
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Button variant (solid, outline, soft, etc.)
    </td>
  </tr>
</tbody>
</table>

```vue
<!-- With Nuxt UI -->
<UButton to="/page" variant="solid" size="md">
  Click me
</UButton>

<!-- Without Nuxt UI -->
<a href="/page" class="wp-block-button__link">
  Click me
</a>
```

### CoreButtons

Container for multiple button blocks. Renders inner `CoreButton` components.

```vue
<!-- Output -->
<div class="wp-block-buttons">
  <CoreButton :block="innerBlock" />
  <!-- ... -->
</div>
```

### CoreQuote

Renders blockquote with inner paragraph blocks.

<table>
<thead>
  <tr>
    <th>
      Attribute
    </th>
    
    <th>
      Type
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        innerBlocks
      </code>
    </td>
    
    <td>
      <code>
        array
      </code>
    </td>
    
    <td>
      Nested paragraph blocks
    </td>
  </tr>
</tbody>
</table>

```vue
<!-- Output -->
<blockquote>
  <p class="text-sm text-primary-500">Quote text</p>
</blockquote>
```

### CoreGallery

Renders image galleries with inner image blocks.

### CoreSpacer

Renders vertical and horizontal spacing.

<table>
<thead>
  <tr>
    <th>
      Attribute
    </th>
    
    <th>
      Type
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        spacerHeight
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Spacer height (e.g., <code>
        50px
      </code>
      
      )
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        spacerWidth
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Spacer width (optional)
    </td>
  </tr>
</tbody>
</table>

```vue
<!-- Output -->
<div style="height: 50px; width: 100px" />
```

### CoreDetails

Renders expandable details/summary blocks.

<table>
<thead>
  <tr>
    <th>
      Attribute
    </th>
    
    <th>
      Type
    </th>
    
    <th>
      Description
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        summary
      </code>
    </td>
    
    <td>
      <code>
        string
      </code>
    </td>
    
    <td>
      Summary text (visible)
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        innerBlocks
      </code>
    </td>
    
    <td>
      <code>
        array
      </code>
    </td>
    
    <td>
      Content blocks (hidden until expanded)
    </td>
  </tr>
</tbody>
</table>

```vue
<!-- Output -->
<details>
  <summary>Click to expand</summary>
  <!-- Inner blocks rendered here -->
</details>
```

### EditorBlock (Fallback)

Renders the saved HTML for unsupported blocks.

```vue
<!-- Output -->
<div v-sanitize-html="block.renderedHtml" />
```

## Custom Components

Override any component by creating a file in `components/blocks/`:

```vue [components/blocks/CoreParagraph.vue]
<script setup lang="ts">
import type { CoreParagraph } from '#wpnuxt/blocks'

defineProps<{
  block: CoreParagraph
}>()
</script>

<template>
  <p class="my-custom-paragraph">
    <span v-sanitize-html="block?.attributes?.content" />
  </p>
</template>
```

Your component automatically takes precedence over the default.

## Adding New Block Types

Create a component for any WordPress block:

```vue [components/blocks/CoreCode.vue]
<script setup lang="ts">
defineProps<{
  block: {
    attributes?: {
      content?: string
      language?: string
    }
  }
}>()
</script>

<template>
  <pre><code :class="`language-${block.attributes?.language}`">{{ block.attributes?.content }}</code></pre>
</template>
```

The component name must match the block name pattern:

- `core/code` → `CoreCode.vue`
- `core/list` → `CoreList.vue`
- `acf/custom-block` → `AcfCustomBlock.vue`

## Type Imports

Import block types for TypeScript support:

```ts
import type {
  CoreParagraph,
  CoreHeading,
  CoreImage,
  CoreButton,
  EditorBlock
} from '#wpnuxt/blocks'
```


## Sitemap

See the full [sitemap](https://wpnuxt.com/sitemap.md) for all pages.
