Creating a full viewport component

You can create a Frontastic component that takes up the full viewport of a browser (also known as full-bleed). Let's look at an example of how to do this.

Below is an example of a hero Frontastic component. The image can either be the full width of the grid or the full width of the viewport.

Full width of grid (12-column layout element)

Full width of viewport (full-bleed)

1 layout element example1 layout element example

Full bleed image exampleFull bleed image example

Let's build a simplified example:

As always, we start with the schema. We'll create a text field and a toggle so users of the Frontastic studioFrontastic studio - The interface you use to manage, build, and edit all areas of your project and commerce sites. Previously known as `backstage`. can turn our full-bleed image feature on and off.

{
    "tasticType": "frontastic/examples/hero",
     "name": "Hero",
     "icon": "image",
     "category": "content",
     "schema": [
        {
            "name": "Content",
            "fields": [
                {
                    "label": "Image",
                    "field": "image",
                    "type": "media"
                },
                {
                    "label": "Full-bleed?",
                    "field": "isFullBleed",
                    "type": "boolean",
                    "required": true,
                    "default": true
                },
                {
                    "label": "Aspect ratio",
                    "field": "aspect",
                    "type": "enum",
                    "default": "16/9",
                    "values": [
                        {
                            "value": "original",
                            "name": "Original"
                        },
                        {
                            "value": "16/9",
                            "name": "16:9"
                        },
                        {
                            "value": "4/3",
                            "name": "4:3"
                        },
                        {
                            "value": "21/9",
                            "name": "21:9"
                        }
                    ]
                }
            ]
        }
     ]
}

Upload this schema to the Frontastic studio.

Next, we need to create our index.tsx file to receive the information from the schema.

import React from 'react'

import Hero from 'components/Hero'

const HeroTastic = ({ data }) => {
    return <Hero {...data} />
}

export default HeroTastic;

Then, we create a wrapper component and add it to our layout folder. This simple React Component makes sure its contents (the children) fill up the whole horizontal viewport space. To accomplish this, we use a little CSS trick.

import React from 'react'

export default function FullPageWidthWrapper ({ children, className = '' }) {
    return (
        <div
            className={className}
            style={{
                width: '100vw',
                position: 'relative',
                left: '50%',
                right: '50%',
                marginLeft: '-50vw',
                marginRight: '-50vw',
            }}
            >
            {children}
        </div>
    )
}

We can now use the wrapper to wrap the contents of our component if the users of the Frontastic studioFrontastic studio - The interface you use to manage, build, and edit all areas of your project and commerce sites. Previously known as `backstage`. choose to do so using the toggle. We do this in the index.tsx of the component.

import React from 'react'
import Image from 'frontastic/lib/image';

import FullPageWidthWrapper from '../Layout/FullPageWidthWrapper'

const Hero = ({ image, aspect, isFullBleed }) => {
    const aspectClass = {
        'original': '',
        '16/9': 'pb-16/9',
        '4/3': 'pb-4/3',
        '21/9': 'pb-21/9',
    }

    const calculateAspectStyle = (aspect, img) => {
        if (aspect === 'original' && img) {
            return { paddingBottom: '${(img.media.height / img.media.width) * 100}%'}
        }
        return {}
    }

    const content = (
        <div className={'relative ${aspectClass[aspect]}'} style={{...calculateAspectStyle(aspect, image)}}>
            <Image media={image} className={'w-${isFullBleed ? 'full' : 'auto'} absolute'} alt="Logo" />
        </div>
    )
   
    if (isFullBleed) {
        return <FullPageWidthWrapper>{content}</FullPageWidthWrapper>
    }

    return content
}

export default Hero

And that's it. When this component is added to a page version in the Frontastic studioFrontastic studio - The interface you use to manage, build, and edit all areas of your project and commerce sites. Previously known as `backstage`., you can now select the image and if it's full-bleed or not:

❗️

If you add another Frontastic componentFrontastic component - A customizable building block that's used together with other components to create a commerce site. Known as `tastic` for short in code. to the same layout elementlayout element - What needs to be added to a page before a Frontastic component can be added or a component group. Previously known as `cell`., it could cause your layout to break. Either keep it in a separate layout elementlayout element - What needs to be added to a page before a Frontastic component can be added or a component group. Previously known as `cell`. or update your CSS to stop this from happening.


Did this page help you?