How to add a remove button for nested object fields in Sanity?

9 replies
Last updated: Dec 1, 2025
Hey all! 🙂Is there any way to allow easy deleting an object field inside another object? I have a "IntroText" component that has a "CTA" Button component which is optional. When I want to remove an existing button I have to 1. delete the title and 2. remove the page reference. Is there a way to show a "Remove" button on the "CTA" button that just removes everything belonging to the object?
AI Update

Yes, you can definitely add a "Remove" button to clear out your entire CTA object field at once! The best approach is to create a custom input component that adds a remove button alongside the default object input.

Here's how to implement it using the correct custom input component pattern:

import {ObjectInputProps, set, unset} from 'sanity'
import {Button, Stack} from '@sanity/ui'
import {TrashIcon} from '@sanity/icons'

function CTAInput(props: ObjectInputProps) {
  const {renderDefault, onChange, value} = props
  
  const handleRemove = () => {
    // Use unset() to remove the entire object field
    onChange(unset())
  }
  
  return (
    <Stack space={3}>
      {renderDefault(props)}
      {value && ( // Only show button if CTA exists
        <Button
          text="Remove CTA"
          icon={TrashIcon}
          tone="critical"
          mode="ghost"
          onClick={handleRemove}
        />
      )}
    </Stack>
  )
}

// In your schema definition:
defineField({
  name: 'cta',
  type: 'object',
  title: 'CTA Button',
  fields: [
    {name: 'title', type: 'string'},
    {name: 'page', type: 'reference', to: [{type: 'page'}]}
  ],
  components: {
    input: CTAInput
  }
})

The key here is using onChange(unset()) directly. According to the PatchEvent documentation, when you call onChange with unset(), it creates the appropriate patch to remove the entire field. This is the proper way to handle patches in custom input components.

The renderDefault(props) function renders the standard object input with all your fields (title and page reference), and the button appears below it. When clicked, it removes the entire CTA object in one go, which is exactly what you're looking for!

The conditional {value && ...} ensures the remove button only appears when there's actually a CTA to remove, keeping the UI clean when the field is empty.

This approach works perfectly with Sanity's real-time collaboration system and gives you full control over the button's appearance and placement.

Show original thread
9 replies

Sanity – Build the way you think, not the way your CMS thinks

Sanity is the developer-first content operating system that gives you complete control. Schema-as-code, GROQ queries, and real-time APIs mean no more workarounds or waiting for deployments. Free to start, scale as you grow.

Was this answer helpful?