Content creation
From an information architecture perspective, tutorial content is divided into parts, which are further divided into chapters, each consisting of lessons.
For instance, a Vite tutorial might be structured like this:
This structure is reflected in the directory structure of your TutorialKit project. When you open the project in the code editor and navigate to the src/content/tutorial
directory, you will see a several numbered folders. These represent the parts of your tutorial.
Directorysrc
Directorycontent
Directorytutorial
Directory1-basics
Directory1-introduction/
- …
Directory2-your-first-vite-project/
- …
Directory2-vite-cli/
- …
- meta.md
- config.ts
Directorytemplates/
- …
Navigate into one of these folders to see another folder that represents a chapter. Inside the chapter folder, you will find one or more lesson folders.
You can also omit parts or chapters such that you only have lessons or only lessons and parts. Here are a few examples:
Directorysrc
Directorycontent
Directorytutorial
Directorygetting-started
Directory_files/
- …
Directory_solution/
- …
- content.md
Directoryadding-pages/
- …
- meta.md
- config.ts
Directorytemplates/
- …
Directorysrc
Directorycontent
Directorytutorial
Directoryintroduction/
Directorywhat-is-vite/
Directory_files/
- …
Directory_solution/
- …
- content.md
Directoryinstalling/
- …
Directoryproject-structure/
- …
- meta.md
- config.ts
Directorytemplates/
- …
A lesson content file
Navigate to the src/content/tutorial/1-basics/1-introduction/1-welcome
folder and open the content.md
in your editor. You will see a file structured like this:
This is a Markdown file with a frontmatter block at the top (marked by a single ---
line at the beginning of the file and another ---
line to close the block).
The frontmatter block contains metadata about the lesson, such as the title, description, and other properties that will allow you to configure this specific lesson.
Everything below the frontmatter block is the lesson content itself. You can write your lesson content in Markdown format, using headings, lists, images, and other Markdown features. You can also use the MDX format by changing the file extension from the default .md
to .mdx
.
Try changing the content of the content.md
file and see the changes reflected in the browser.
Adding a lesson
To add a new lesson, create a new folder inside the chapter folder. Name it with a number that is not yet used in the chapter. For example, if the last lesson in the chapter is 1-welcome
, you can name the new lesson folder 2-why-vite
.
The numbers you prefix the lesson folders with are used to order the lessons in the tutorial.
You might notice that the name of the lesson folder is also used in the URL segment of the lesson in the tutorial app. For example, the URL of the lesson 1-welcome
will look something like localhost:4321/1-basics/1-introduction/1-welcome
. You can change that by modifying the slug
property in the lesson’s frontmatter block:
This will change the URL of the lesson to localhost:4321/1-basics/1-introduction/hello-world
.
A lesson code
Beside the content.md
file in a lesson’s directory, you will find two folders:
_files
_solution
The _files
folder contains any code files that are part of the lesson. For example, if the lesson revolves around React components, you might have a Button.jsx
file there. The content of this file will be displayed in the tutorial app’s code editor and will be run in its preview. You can place any number of files in this folder.
The _solution
folder contains the code for the lesson in its solved state. This is the code that the user will see when they click the “Solve” button in the tutorial app. The folder usually contains the same files as the _files
folder, but with the code filled in. It may also include additional files.
Code templates
For the code to run in the preview, it must be an actual, working application, including a dev server and any necessary configuration files. Usually, it’s not practical to include this kind of boilerplate files in a lesson content (and copy it for every further lesson!). Instead, you can use the template
feature of TutorialKit to provide a base project that will be used for all lessons.
To display the code in the preview of a lesson, TutorialKit will use the template project and apply the content of the _files
(or _solution
) folder on top of it.
You can find the default template in the src/templates/default
directory. This is a Vite project which is a great starting point for a vanilla JavaScript app. Note, that when you navigate to that folder and run npm run dev
inside, it will be a fully working Vite project.
You can modify this template to fit your needs, or create a new one from scratch. You can also have multiple templates and switch between them for different parts of your tutorial. To do that, you need to specify the template name in the lesson’s, chapter’s, or part’s front matter block:
This declaration will make TutorialKit use the src/templates/my-advanced-template
directory as the base for the lesson.
If you start having a lot of templates and they all share some files, you can create a shared template that they all extend. This way, you can keep the shared files in one place and avoid duplication. To do that, you need to specify the extends
property in the template’s .tk-config.json
file:
This will make the template inherit all files from the shared-template
directory. You can then override any file in the template by placing a file with the same name in the template’s directory.
Here’s an example of how you can structure your templates:
Markdown and MDX Support
TutorialKit comes with built-in support for both Markdown and MDX, powered by Astro. This means you can leverage all Markdown and MDX features when creating lesson content. To explore the full capabilities, check out Astro’s Markdown support and MDX support documentation for more details.
Callouts
Callouts are visual elements designed to highlight specific information or provide additional context within a document or user interface. They are ideal for drawing attention to important tips, warnings, and other key messages.
You can create callouts using the following types: tip
, info
, warn
, danger
and success
.
To customize the styles of a callout, check out the theming reference.
Code blocks
TutorialKit offers a comprehensive set of code block features powered by Expressive Code. It includes all core features, along with optional plugins like collapsible sections and line numbers. For a full overview, check out the Expressive Code documentation.
Useful Expressive Code Attributes
title
- Sets the title of the code block.frame
- Defines the frame of the code block. Options:"code"
,"terminal"
,"none"
,"auto"
.showLineNumbers
- Displays line numbers. You can combine this withstartLineNumber=#
to begin numbering from a specific line.wrap
- Controls word wrapping. UsepreserveIndent
andpreserveIndent=false
to adjust indentation handling.
Marking Lines
{x}
- Marks specific lines. For example,{6,10-18}
will mark lines 6 and 10 through 18.ins
- Marks inserted lines. Example:ins={6,10-18}
.del
- Marks deleted lines. Example:del={6,10-18}
.{"Label":x}
- Assigns a label to a line or range of lines. Works withmark
,ins
, anddel
. Example:{"Label1":5} del={"Label2":7-8} ins={"Label3":10-12}
. If the label is long, consider placing an empty line in the code for better readability.collapse={X-Y}
- Collapses the specified lines. Example:collapse={1-5,12-14}
.
Marking Text
You can highlight text using strings or regular expressions. For example:
Importing files
In addition to Expressive Code features, you can import files from your code template _files
and _solution
folders using the file or solution shortcodes. These shortcodes insert the content of the specified file directly into your lesson content.
file
shortcode is used to reference files from the lesson_files
or code template folder.solution
shortcode is used to reference files from the lesson_solution
folder.
For example, the following code will insert the content of the box.css
file from the _files
folder: