Home >Web Front-end >JS Tutorial >Build a Greeting Card Maker w/ Vue Satori

Build a Greeting Card Maker w/ Vue Satori

Mary-Kate Olsen
Mary-Kate OlsenOriginal
2024-12-20 20:39:20728browse

Build a Greeting Card Maker w/ Vue  Satori

Written by Dubem Izuorah

For the creative developers out there seeking a festive project that leverages your coding skills, let’s build a digital Holiday Greeting Card that you can customize, add your own photo, and instantly download. We’ll be using some cutting-edge web technologies to make this happen, and along the way, you’ll learn about graphics generation, several cool packages, and some neat Vue 3 tricks.

What we are going to be building

Build a Greeting Card Maker w/ Vue  Satori

Screenshot of Holiday Greeting Card Maker interface

By the end of this tutorial, you’ll have:

  • A fully functional web app for creating personalized holiday cards
  • Hands-on experience with Vue 3, Nuxt, and some powerful rendering libraries
  • An understanding of how to dynamically generate graphics in the browser

Project Initialization

We’ll use Nuxt 3 as our framework because it provides a robust, batteries-included setup for Vue applications. Open your terminal and let’s create our project by running the commands below:

npx nuxi init christmas-card-maker 
cd christmas-card-maker
yarn install

Why Nuxt? It gives us a solid foundation with built-in routing, easy module integration, and an overall easy setup. Perfect for our greeting card maker!

Installing Our Toolkit

Now, we’ll add the libraries that will make our card generation magic happen. Run the following commands on your terminal:

yarn add @vue/server-renderer @vueuse/core nuxt satori satori-html
yarn add -D @nuxtjs/tailwindcss

Let me break down why we’re choosing each of these:

  • @vue/server-renderer: Allows us to render Vue components & props as HTML strings - crucial for our SVG generation
  • satori: Converts our HTML and CSS string into beautiful SVG graphics
  • Satori HTML: A helper library for rendering HTML content compatible with Satori
  • @vueuse/core: Provides helpful utilities like local storage, watchDebounce and many more
  • @nuxtjs/tailwindcss: Gives us rapid styling capabilities

Configuring our Project

Let’s update our nuxt.config.ts to set up our development environment:

? nuxt.config.ts

export default defineNuxtConfig({
  ssr: false,
  devtools: { enabled: true },
  modules: ["@nuxtjs/tailwindcss"],
});

We’re disabling server-side rendering for this client-side app and enabling Tailwind CSS module. This gives us a lightweight, responsive setup perfect for our greeting card maker.

Coding our Card Maker

Now that we’re all setup, let’s dive into creating our Holiday Card Maker step-by-step.

Step 1. Implementing the Card Maker Interface

Let’s first focus on creating a simple layout for our card maker. We’ll set up a form with fields for the user to add a name, greeting, and an image upload. We’ll also add a preview area where the card will be displayed.

Here’s what the base layout will look like:

? app.vue

npx nuxi init christmas-card-maker 
cd christmas-card-maker
yarn install

Why do we need this setup?

  1. createSSRApp and renderToString : Render Vue components to HTML strings by virtually mounting the component and its props and rendering out its final output.
  2. useLocalStorage : Save form data locally, so users don’t lose progress if they reload.
  3. watchDebounced : Helps us prevent performance issues by delaying the processing of user inputs until a certain duration after typing has stopped.
  4. satori : Convert HTML to SVG for our graphics.
  5. satori-html : Parse HTML strings into a format satori understands.
  6. The fonts ref uses useLocalStorage to persists the user’s inputs. If you refresh the page, we won’t lose the form input and can continue where we left.
  7. The svg and fonts variables will store the generated card design and loaded font data.

Step 3. Creating the Card Template

Next, let’s create the card template component we imported earlier. This is where the magic happens.

We’ll use the data from the form to personalize the card. In components/ChristmasCard.vue, we’ll design our card’s visual template. Think of this like designing a canvas where users can personalize their greeting.

? components/ChristmasCard.vue

yarn add @vue/server-renderer @vueuse/core nuxt satori satori-html
yarn add -D @nuxtjs/tailwindcss

Breaking it down:

  • We use the onMounted hook, which is auto-imported in Nuxt 3, to load and store the fonts needed for generating the graphics.
  • You can use any .ttf font file. To get the same font I used, “Instrument Sans” font, visit Google Fonts, click “Get Font,” then download the font files. Extract the ZIP file, and copy the .ttf font (e.g., InstrumentSans-Regular.ttf) into the public/fonts folder of your Nuxt project. Reference it as /fonts/InstrumentSans-Regular.ttf in your code.
  • Inside onMounted, we call refreshGraphics to generate the initial SVG graphics once the font has loaded.
  • We use watchDebounced to track changes in the form and update the graphics 500ms after the last update. Note: this is a performance trick.
  • The loadFonts function loads the required fonts all at once using Promise.all instead of sequentially. Another performance trick to note.

Step 5. Generating SVG from Vue Component

Here’s where we tie everything together. We’ll convert the ChristmasCard component into an SVG.

? app.vue

npx nuxi init christmas-card-maker 
cd christmas-card-maker
yarn install

Let me explain:

  • We first use the renderToHTML utility function to convert the ChristmasCard.vue component imported earlier into HTML string
  • Then we are using the html function imported from satori-html earlier to convert the HTML string into a markup format acceptable by the satori package
  • Finally, we call satori, passing in the markup, width and height configuration as well as the fonts that we loaded earlier in the onMounted hook
  • The resulting svg string is stored in the svg.value ref, which we used in the app.vue template section to display the svg on the viewport. See in the template section

Step 6. Utility Functions

Let’s wrap up everything we’ve been working on by adding some essential utility functions for our code and template features.

Adding Image Upload Support

We’re adding functionality to handle image uploads. This will ensure that users can select an image, check if it’s within the size limit (100KB), and display it.

Paste this below the refreshGraphics code:

? app.vue

yarn add @vue/server-renderer @vueuse/core nuxt satori satori-html
yarn add -D @nuxtjs/tailwindcss

Why check file size? We’re limiting the file size to ensure smooth performance. Anything larger could slow things down, so 100KB is a safe upper limit.

Converting Vue component to HTML string

Next, we’ll render the Vue component as an HTML string. This allows us to use Vue for server-side rendering, email templates, or static site generation. In this case, it’s for generating a greeting card template. Let’s add this as well to our code.

npx nuxi init christmas-card-maker 
cd christmas-card-maker
yarn install

Explanation:

  • createSSRApp : This function is used to create a server-side rendered (SSR) Vue application instance, which can be rendered to an HTML string.
  • renderToString : This renders the Vue component (GreetingCard) to an HTML string, passing any props needed by the component.

Downloading the Card as a JPEG

Finally, let’s add code that will enable us to download our card as a JPEG.

? app.vue

yarn add @vue/server-renderer @vueuse/core nuxt satori satori-html
yarn add -D @nuxtjs/tailwindcss

Why does this work? By using HTML Canvas API, we can draw the SVG onto the canvas and convert it into a JPEG for easy downloading. It’s a quick and efficient way to generate image files from vector graphics.

Step 7. Styling

To ensure the SVG element is displayed correctly within the container, we need to apply some CSS styling. Since the generated SVG has a fixed size of 1080px by 1080px, but the parent container is smaller, we need to scale the SVG to fit inside the container without distortion.

? app.vue

export default defineNuxtConfig({
  ssr: false,
  devtools: { enabled: true },
  modules: ["@nuxtjs/tailwindcss"],
});

This CSS rule ensures that the SVG element inside the .banner-here div is resized to fill the available space while maintaining its aspect ratio.

Build a Greeting Card Maker w/ Vue  Satori

By now, your project should look something like this screenshot. Let’s run it to see the real magic!

Running our code

To see our app in action, run the command below and open http://localhost:3000 on your browser.

For reference, here is the Github repo for this tutorial.

<template>
  <div>



<p><strong>So what’s happening here?</strong></p>

<ol>
<li>
<strong>Card Preview:</strong> The  with v-html="svg" is where our card will appear as an SVG once it’s generated.
</li>
<li><strong>Form Fields:</strong></li>


<ul>
<li>Two text fields: name and greeting. These will dynamically update the card when the user types.</li>
<li>File input: Allows users to upload an image.</li>
</ul>

<ol>
<li>
<strong>File Restrictions:</strong> The small tag below the file input informs users about allowed file size and formats. Large images can slow down rendering, so we’re capping the size at 100KB.</li>
<li>
<strong>Download Button:</strong> This triggers the downloadSvgAsJpeg function, which saves the card as a JPEG image.</li>
</ol>

<h3>
  
  
  Step 2. Setting up Dependencies
</h3>

<p>Now let’s set up the logic and install the packages needed to power our Holiday Card Maker. Let’s import a few packages that will make things easier for us.</p>

<p>? <strong>app.vue</strong><br>
</p>

<pre class="brush:php;toolbar:false">...
</template>

<script setup lang="ts">
import { createSSRApp } from "vue";
import { renderToString } from "@vue/server-renderer";
import { useLocalStorage, watchDebounced } from "@vueuse/core";
import satori from "satori";
import { html } from "satori-html";
import ChristmasCard from "./components/ChristmasCard.vue";
const form = useLocalStorage("app-form", {
  name: "",
  greeting: "Merry Christmas",
  photo: null,
});
const svg = ref("");
const fonts = ref([]);
...
</script>

Build a Greeting Card Maker w/ Vue  Satori

You should see something resembling the interface in the GIF above. You can edit the details, add an image, and download your image. Congrats! You now have your own personal Holiday Card maker.

Wrapping Up

You’ve just built a personalized greeting card maker! ? But don’t stop here. Experiment with different designs, add more customization options, or even create cards for other occasions.

Some ideas to expand your project:

  • Add more background themes
  • Include text color/font selection
  • Create templates for birthdays, anniversaries

Want to do more on the client side? Discover how to render 3d objects in the browser by reading this article.

Originally published at https://www.vuemastery.com on December 19, 2024.


The above is the detailed content of Build a Greeting Card Maker w/ Vue Satori. For more information, please follow other related articles on the PHP Chinese website!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn