Inertia: Global setting for presistant layout

Created on 10 Dec 2019  路  4Comments  路  Source: inertiajs/inertia

Hello,

Long time user, first time issue writer.

In a recent project, I found myself adding the same code to every single page that Inertia was returning. Since I am trying to create the SPA experience, and assume all that use Inertia have the same end goal, I want a persistent layout.

import Layout from "@layouts/Default";

export default {
    props: ["user"],
    layout: Layout
};

Now, this isn't _that bad_ but I am now about 30 pages into my app and feel like this could be a bit of a better experience.

My request is to somehow make the layout a global setting that can be assigned once, and still be able to override this _should_ i need to use a different layout somewhere else in my app.

I will now click "Submit new issue" which really means, "Submit this feature request" in this case and wait for a response.

Thanks,

Yaz.

enhancement vue 2

Most helpful comment

I think you can intercept resolveComponent and change the module layout.

resolveComponent: name => import(@/pages/${name}).then(module => { if (!module.default.layout) { module.default.layout = MainLayout } return module.default })

I think you can even go further and on pages provide a string instead of importing layout on each page. Imagine you have a login page and you want to use different layout then instead of importing Layout in Login page you can just provide layout: 'LayoutName' then your resolveComponent can check if there is a string value then you can just import that from the layouts and use that.

I guess you can also check Nuxt's code to see how they do but I guess they do similar too.

Thanks

All 4 comments

~Hmmm, can't you register the Layout as a global component and use that as a temporary solution? Looks like it would save you at least one import each time you make a new view :)~

Doesn't work, sorry

I think you can intercept resolveComponent and change the module layout.

resolveComponent: name => import(@/pages/${name}).then(module => { if (!module.default.layout) { module.default.layout = MainLayout } return module.default })

I think you can even go further and on pages provide a string instead of importing layout on each page. Imagine you have a login page and you want to use different layout then instead of importing Layout in Login page you can just provide layout: 'LayoutName' then your resolveComponent can check if there is a string value then you can just import that from the layouts and use that.

I guess you can also check Nuxt's code to see how they do but I guess they do similar too.

Thanks

So I spent some time this morning hacking on this, (testing the solution in #212), and I actually think @azal-io's solution here is the right way to go鈥攊nstead of adding a new prop for this in each adapter.

Here's how easy it is to do this in the resolveComponent() callback:

resolveComponent: name => import(`./Pages/${name}`).then(({ default: page }) => {
  page.layout = page.layout === undefined ? Layout : page.layout
  return page
}),

And, what's really cool about this approach is that this method receives the current page name, meaning you can actually conditionally set the default layout based on this. For example:

resolveComponent: name => import(`./Pages/${name}`).then(({ default: page }) => {
  if (!name.startsWith('Public/') && page.layout === undefined) {
    page.layout = Layout
  }
  return page
}),

And, with both of these approaches, because I'm doing an explicit === undefined check, you can still disable this on a per page basis by setting layout: null.

Given how easy this is to do, and actually more powerful because of the name being available, I think I'm going to update the documentation to recommend this approach, and not build this into the adapters as a new prop.

Documentation has been added for this "feature": https://github.com/inertiajs/inertiajs.com/commit/97cc6787488576c891bff02d37f6c95bfa9352f0

Which you can see here: https://inertiajs.com/pages#default-layouts

Was this page helpful?
0 / 5 - 0 ratings

Related issues

mpskovvang picture mpskovvang  路  5Comments

sammagee picture sammagee  路  3Comments

gajosadrian picture gajosadrian  路  5Comments

adriandmitroca picture adriandmitroca  路  5Comments

kufdaw picture kufdaw  路  6Comments