How to render a custom component for a document list in Sanity.io
4 replies
Last updated: Oct 16, 2023
D
Hi all. I have a question about editing a document in a new pane from a custom component. I have setup the custom component in the following (simplified) desk structure:
In this view I have a listening query for a set of documents and want to render those as buttons with links to open the target document in a new pane.
I have tried:
•
Documents Pane plugin • The same approach as is done in
Document internationalization plugin I keep getting a warning that the desk structure child was not found, but I cannot (or do not know how to) express a specific document type as a child of the structure, as it can be multiple types. This works:
but only (correctly) for a document of
Does anyone have experience doing this and/or can help with this? Thanks!
S.list() .title('Content') .items([ S.listItem().title('Page tree').child( S.component(CustomComponent).id('CustomComponent').title('Custom component'), ), ...
I have tried:
•
<IntentLink />from
usePaneRouter• The same approach as is done in
Documents Pane plugin • The same approach as is done in
Document internationalization plugin I keep getting a warning that the desk structure child was not found, but I cannot (or do not know how to) express a specific document type as a child of the structure, as it can be multiple types. This works:
S.component(CustomComponent).id('CustomComponent').title('Custom component').child(S.document().schemaType('typeA')),
typeAand not
typeBI want similar behaviour for panes as is done in the
documentList.
Does anyone have experience doing this and/or can help with this? Thanks!
Oct 9, 2023, 6:25 AM
It’ll probably be best if you define your structure and your views separately. First, your
Then, you’d define a
document node resolver to handle your views and return the component there:
listItemstructure would need to look like this:
S.listItem() .title('Page Tree') .child( S.documentList() .title('Page Tree') .filter(`_type in [<your-types>]`) ),
document node resolver to handle your views and return the component there:
return S.document().views([ S.view.form(), S.view.component(CustomComponent).title('Custom Component') ])
Oct 10, 2023, 5:07 PM
D
Thank you for taking the time to answer this! It's unfortunately not exactly what I was looking for. In my case the 'Custom Component' is actually a component to render multiple documents of multiple schema types (a page tree to be more concrete). As I understand it the
Do you have any tips for this?
document.viewscan be a way of adding components on the document level and is rendered like a tab (like the iframe preview plugin), while I want it to replace the behaviour of the default
documentListcomponent. This is what led me to believe I need to add it as a component in the structure.
Do you have any tips for this?
Oct 11, 2023, 6:30 AM
This plugin (which has custom components for list items) is probably the closest to what you’re looking for. However, the Structure Builder API is for rendering lists of documents and a component cannot be a child of a list. If you just want a visual representation of your page tree, it’ll be easier to just create a separate plugin where you’re not bound by those rules.
Oct 12, 2023, 6:00 PM
D
Oh my, this is it! Thank you so much for pointing me to this plugin. The solution I was looking for was the following, if anyone might run into this question as well:
Apparently it is possible to render a custom component for a
S.listItem() .title("Page tree") .child( Object.assign(S.documentList().filter('_type in ["homePage","contentPage"]').title("Page tree").serialize(), { __preserveInstance: true, key: 'pageTree', id: 'pageTree', type: 'component', component: PageTreeView, }), ),
documentListlike this. Internally it will still be a document list and it is handled accordingly, resulting in the expected behaviour of the pane router 👍
Oct 16, 2023, 6:19 AM
Sanity– build remarkable experiences at scale
Sanity is a modern headless CMS that treats content as data to power your digital business. Free to get started, and pay-as-you-go on all plans.