# Customize posts' contents with your own styles

**URL:** https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738
**Category:** Developer Guides
**Tags:** css
**Created:** [March 10, 2023, 6:18pm UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738 "2023-03-10T18:18:34Z")
**Posts on this page:** 9
**Page:** 1

<div class="post-metadata">

### Author: ![Discourse](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/discourse/32/148734_2.png) [@Discourse](https://meta.discourse.org/u/Discourse)
#### Post date: [March 10, 2023, 6:18pm UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/1 "2023-03-10T18:18:34Z")

</div>

## Requirements

ℹ To be able to use these tips and tricks, you need to be an administrator of either a self-hosted Discourse instance or a [Discourse-hosted plan](https://discourse.org/pricing) higher than **Basic**.

## Introduction

Discourse supports several methods to format and customize a post’s contents. You can find the list here:

> [@Formatting posts using markdown, BBCode, and HTML](https://meta.discourse.org/t/supported-formatting-in-posts-markdown-bbcode-and-html/239348):
>
> bookmark This reference guide details all the formatting options available in Discourse posts, including markdown, BBCode, and HTML. It specifies what is supported and provides resources where you can see examples. person_raising_hand Required user level: All users Understanding supported formatting in posts While plain text is sufficient for most replies, Discourse allows users to enhance the formatting of their posts by using markdown, BBCode, and HTML. This guide explains what types …

But sometimes, you’ll want something more specific, for example, a link that looks like a button.

![Green button](https://global.discourse-cdn.com/meta/original/4X/4/1/4/414cf12fcfd6158231bea2e5ffb2bd662ebb86e1.png)

This is the kind of modification we’ll learn here.

## The logic

I’ll briefly explain the logic behind but you can go to the next step and jump into a practical example 🙂

Discourse allows any HTML attribute starting with `data-` in a post’s content.  
Those are the attributes we’ll target with CSS to customize our content.

I’ll call them **`data-` attributes** in this tutorial 🙂

One way to create elements with these attributes is a BBcode-like tag: `[wrap]`, to which we’ll add a value of our choice. Here we choose “button” (that could be anything else, even the name of your dog 🐕):

```md
[wrap=button]some text[/wrap]

```

This will output an HTML element having the following attribute: `data-wrap="button"`.

## First example: a pink background

Let’s start with a practical example. We’ll create text with a pink background.

### As a _block_ element

In your post, on an empty line, write:

```md
[wrap=pink]pink text[/wrap]

```

 ![block wrap](https://global.discourse-cdn.com/meta/original/4X/6/c/7/6c779dd085666fa6409e8941648233ff7f4e9e49.png)

It will create a `div` element having the attribute `data-wrap="pink"`.

Then, add the following CSS to your theme.  
Go to Admin panel → Customize → Themes → your theme → Edit CSS/HTML → CSS.

Put the following CSS code inside:

```css
[data-wrap="pink"] {
  background: pink;
}

```

Then click the Save button.

 ![wrap css](https://global.discourse-cdn.com/meta/original/4X/5/4/b/54b861aa679ec30f83f8c9051b0dc530e392e411.png)

Go back to your post, and see the result:

 ![image](https://global.discourse-cdn.com/meta/original/4X/a/f/c/afc2be9fe14f21f95deac9df817c1ee3417b3747.png)

Yes, it is already beautiful 🌸

You’ll notice that the background covers the whole post width. Because our wrap is the only element on its line, it outputs a **block** element.  
You can learn more about the difference between **blocks** and **inline** HTML elements here: [HTML Block and Inline Elements](https://www.w3schools.com/html/html_blocks.asp).

If you want your pink background on multiple lines (still as a **block** ), you’ll need both your `[wrap]` tags having no other content or text on the same line:

```md
[wrap=pink]
pink text
pink text
pink text
pink text
[/wrap]

```

This will look like this:

 ![image](https://global.discourse-cdn.com/meta/original/4X/0/e/d/0ed260dede79fe6e9e1860c7c9dcf1212f631f89.png)

### As an _inline_ element

Now, let’s add some text before the `[wrap]`, or after, or both 😄. For example:

`Here is some [wrap=pink]pink text[/wrap] and it's awesome ✨`

Here’s the result:

 ![image](https://global.discourse-cdn.com/meta/original/4X/3/5/4/354a425de56e886206acd1a317cc73f4762b00f5.png)

If text or other elements are on the same line as one of your `[wrap]` tags, it will output an **inline** element.

## Second example: a link with a button’s appearance.

Fiddling with the `[wrap]` tag can sometimes lead to unwanted results for various reasons, one being that it can be a block or an inline element depending on the context.  
So, we’ll describe two different methods that achieve the same result, but you’ll be able to pick the one that suits you the most ✌

### An inline button link with `[wrap]`

The syntax to create a link using markdown is: `[some text](https://some-link.etc)`.  
To customize the text and make it appear like a button, we’ll insert the wrap inside the square brackets. Here’s an example:

```md
This [[wrap=button]nice link[/wrap]](https://discourse.org/) is a blue button 🐳 !

```

We won’t comment on what this code outputs. You know that because you wrote `[wrap=button]`, you’ll have to target `[data-wrap="button"]` in your CSS.

So, let’s go, let’s add some fancy CSS to make it pretty! ✨

```css
[data-wrap="button"] {
  display: inline-block;
  padding: 0.5em 1em;
  background: DodgerBlue;
  color: White;
}

```

We won’t detail the CSS rules here. There are many CSS resources on the Internet, so if you want to do more specific modifications, you’ll have to learn about it first. 🙂

The result 🪄 :

 ![Blue button](https://global.discourse-cdn.com/meta/original/4X/9/8/c/98cf478030c1554c7a69af817447e714e1d0a59a.png)

That looks good, right?

### An inline button link with regular HTML content

Since Discourse accepts HTML code, we can decide not to use the `[wrap]` tags and use HTML with a `data-` attribute. In this example, we’ll use the regular Markdown syntax for the link and surround it with `<span>` tags.  
ℹ We can’t directly use a link `<a>` tag because it’s an exception and won’t allow any `data-` attribute.

Write:

```md
This <span data-button>[link](https://discourse.org/)</span> is a green button 🐸 !

```

It will output a link **inside** a `<span>` tag having a `data-button` attribute, which means the CSS will be a bit more complicated. We will have to target both `data-button` and the link:

```css
[data-button] {
  display: inline-block;
  padding: 0.5em 1em;
  background: ForestGreen;
  a {
    color: White;
  }
}

```

And here’s the result!

 ![image](https://global.discourse-cdn.com/meta/original/4X/e/c/5/ec583ad632d6c3f434878b961d6a4db50ae3c32a.png)

## To go further

### A customized list using `[wrap]`

`[wrap]` tags and `data-` attributes can be used in many contexts and you can customize more advanced content. The limit is mostly your CSS knowledge (and HTML to a lesser extent).

I’ll give a single example without explanation by customizing a list in which each element will be prepended with a cat emoji:

Text:

```md
[wrap=cat]

- Felix
- Garfield
- Nat's cat
  [/wrap]

```

CSS:

```css
[data-wrap="cat"] ul {
  list-style: none;
  li:before {
    content: "🐈";
    margin-right: 0.25em;
  }
}

```

Result:

 ![Cat list](https://global.discourse-cdn.com/meta/original/4X/f/1/8/f187dfd6d6836479e21b9c4d59166898041e5907.png)

### Using your own theme’s colors variables

If you allow users to use different themes or colors, your modifications may not look good for each one, especially if they have choices between light and dark color schemes.

A good practice is using Discourse’s color variables instead of “hardcoded” colors such as `red`, `#FF0000` or `rgb(255,0,0)`.

Here’s an example in which the button’s background color will use the primary color of the current palette, and the text will use the secondary color:

Text:

```md
This [[wrap=button]nice link[/wrap]](https://discourse.org/) is a button 🌈 !

```

CSS:

```css
[data-wrap="button"] {
  display: inline-block;
  padding: 0.5em 1em;
  background: var(--primary);
  color: var(--secondary);
}

```

Here’s how it will look for a user using the Solarized Light color scheme:

 ![Solarized Light button](https://global.discourse-cdn.com/meta/original/4X/4/1/5/415bd342059b531d99dff0c4ffc00fb91473ef09.png)

And if they use the Solarized Dark color scheme:

 ![Solarized Dark button](https://global.discourse-cdn.com/meta/original/4X/a/1/2/a122701c5a9e8a192999ade95480147beb58e9dd.png)

## Conclusion

You now have the basics to create custom elements using the `[wrap]` element and the `data-` attributes.

To make more advanced customizations, learning CSS is primordial. You’ll find many tutorials on the Internet.

The following Discourse’s guide can also be of some help: [Making custom CSS changes on your site](https://meta.discourse.org/t/make-css-changes-on-your-site/168101).  
Using the developer’s tools of your Internet Browser will also easily show you the list of your Discourse’s color variables and what each looks like:

 ![image](https://global.discourse-cdn.com/meta/original/4X/1/2/6/126406cffede13212873283ecd1d80085751f936.png)

* * *

🖐 Feel free to suggest any modification for this guide!

* * *

This document is version controlled - suggest changes [on github](https://github.com/discourse/discourse/blob/main/docs/developer-guides/docs/05-themes-components/33-post-content-styles.md).

---

<div class="post-metadata">

### Author: ![merefield](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/merefield/32/176214_2.png) [@merefield](https://meta.discourse.org/u/merefield)
#### Post date: [March 10, 2023, 6:34pm UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/2 "2023-03-10T18:34:21Z")

</div>

Thank you @Canapin

A good example of a Theme Component using some of these concepts is this one:

> [@Discourse Coloured Text](https://meta.discourse.org/t/discourse-coloured-text/218111):
>
> “BBCode-lite” without the need to install a plugin … Adds a simple control (palette icon) to the Composer to facilitate colouring of the foreground and background of text Select a word or text Hit the palette control It will be wrapped like so: [wrap=color color=# bgcolor=#]word[/wrap] Replace the #s with html-compatible colour names, e.g. “red”, “grey” … experiment.biohazard NB Same caveats apply as to BBCode: can be used to hide text. Credits Uses @j.jaffeux’s [Generic bbcode…](https://meta.discourse.org/t/generic-bbcode-wrapper-for-theme-components/123516)

---

<div class="post-metadata">

### Author: ![UnitedFreedom](https://avatars.discourse-cdn.com/v4/letter/u/ac91a4/32.png) [@UnitedFreedom](https://meta.discourse.org/u/UnitedFreedom)
#### Post date: [March 10, 2023, 6:46pm UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/3 "2023-03-10T18:46:17Z")

</div>

Nice work!

Im curious to see what other creative solutions users come up with using the data attribute.

* * *

Is there any advantage of using HTML `<span data-button>` over BBCode `[wrap="button"]` ?

---

<div class="post-metadata">

### Author: ![Canapin](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/canapin/32/119591_2.png) [@Canapin](https://meta.discourse.org/u/Canapin)
#### Post date: [March 10, 2023, 6:54pm UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/4 "2023-03-10T18:54:35Z")

</div>

> [@UnitedFreedom](#):
>
> Is there any advantage of using HTML `<span data-button>` over BBCode `[wrap="button"]` ?

Without having thought about it too much, I’d say using a `<span>` allows you to put an **inline** element as the only content on a single line.

Using a `[wrap]` on a single line without any other content next to it will automatically output a **block** element. The text inside will also be wrapped with paragraph `<p>` tags.

Other than that, it’s probably a matter of taste. I also didn’t mention that a `[wrap]` and an HTML element can have multiple `-data` attributes as I don’t think it’s very useful for most purposes.

---

<div class="post-metadata">

### Author: ![UnitedFreedom](https://avatars.discourse-cdn.com/v4/letter/u/ac91a4/32.png) [@UnitedFreedom](https://meta.discourse.org/u/UnitedFreedom)
#### Post date: [March 10, 2023, 7:09pm UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/5 "2023-03-10T19:09:48Z")

</div>

# How to add Bootstrap “Cards” in your Posts/Topics

…some might say this is crazy, to complicated, or overboard but I love it 😃

 ![image](https://global.discourse-cdn.com/meta/original/4X/2/9/7/2975b72251138d2944c21c77aa7f96a4426d0489.png)

- Added some colours to better see the nesting of the BBCode.

# **STOP!**** Don’t use my code**

Instead, use the improved code posted by @Canapin [CLICK HERE](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/6)

#### BBCode to include in Topic/Post

```plaintext
[wrap="card"]
[wrap="card-header"] **Card Header** [/wrap]
[wrap="card-body"]
[wrap="card-title"] **Card Title** [/wrap]
[wrap="card-text"]Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text[/wrap]
[/wrap]
[/wrap]

```

#### CSS Code to add to theme.

```plaintext
// Bootstrap Card Box
[data-wrap="card"] {
    position: relative;
    display: flex;
    flex-direction: column;
    min-width: 0;
    word-wrap: break-word;
    background-color: #fff;
    background-clip: border-box;
    border: 1px solid rgba(0,0,0,.125);
    border-radius: 0.25rem;
}

// Bootstrap Card Header
[data-wrap="card-header"] {
    padding: 0.5rem 1rem;
    margin-bottom: 0;
    border-bottom: 1px solid rgba(0,0,0,.125);
    background: #007bff;
    color: #fff;
    border-radius: 5px 5px 0px 0px;
    
}

// Bootstrap Card Body
[data-wrap="card-body"] {
    flex: 1 1 auto;
    padding: 1rem 1rem;
}

// Bootstrap Card Title
[data-wrap="card-title"] {
    margin-bottom: 0.5rem;
}

// Bootstrap Card Text
[data-wrap="card-text"] {
    margin-top: 0;
    margin-bottom: 1rem;
}

```

---

<div class="post-metadata">

### Author: ![Canapin](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/canapin/32/119591_2.png) [@Canapin](https://meta.discourse.org/u/Canapin)
#### Post date: [March 10, 2023, 11:44pm UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/6 "2023-03-10T23:44:02Z")

</div>

> [@UnitedFreedom](#):
>
> to complicated

Of course, it depends on what you intend to put in it, but to achieve the same exact visual as your example, you can optimize your code a lot:

```plaintext
[wrap="card-header"] **Card Header** [/wrap]
[wrap="card-body"]
**Card Title**

Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text, Card Text
[/wrap]

```

```css
[data-wrap="card-header"] {
    padding: 0.5em 1em;
    border: 1px solid rgba(0,0,0,.125);
    border-bottom: 0;
    background: #007bff;
    color: #fff;
    border-radius: 5px 5px 0 0;
}

[data-wrap="card-body"] {
    padding: 1em;    
    border: 1px solid rgba(0,0,0,.125);
    border-radius: 0 0 5px 5px;
}

```

 ![Bootstrap card](https://global.discourse-cdn.com/meta/original/4X/a/d/8/ad8b69805b98122c37b7f9035d03ea9fe1c7abc3.png)

---

<div class="post-metadata">

### Author: ![UnitedFreedom](https://avatars.discourse-cdn.com/v4/letter/u/ac91a4/32.png) [@UnitedFreedom](https://meta.discourse.org/u/UnitedFreedom)
#### Post date: [March 10, 2023, 11:55pm UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/7 "2023-03-10T23:55:41Z")

</div>

Ahhh! Thats so much better! Thank you so much for making the improvements! \<3

---

<div class="post-metadata">

### Author: ![Andy\_Clifton](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/andy_clifton/32/244459_2.png) [@Andy\_Clifton](https://meta.discourse.org/u/Andy_Clifton)
#### Post date: [March 17, 2023, 10:12am UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/8 "2023-03-17T10:12:32Z")

</div>

Nice! When is the markdown in the `[wrap]...[/wrap]` element processed, or is there a trick to getting it to render before it’s included in the wrap?

For example, I’ve tried formatting some text in the element as **bold** or _italic_, and it doesn’t render like that - I just see `_text_` or ` **text** ` on the page in my browser, once I save it ☹

---

<div class="post-metadata">

### Author: ![Canapin](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/canapin/32/119591_2.png) [@Canapin](https://meta.discourse.org/u/Canapin)
#### Post date: [March 17, 2023, 10:28am UTC](https://meta.discourse.org/t/customize-posts-contents-with-your-own-styles/257738/9 "2023-03-17T10:28:54Z")

</div>

It indeed seems formatting (whether it’s HTML, Markdow or BBcode) won’t work in `[wrap]` if it’s an inline element (if there’s other content on the same line):

 ![image](https://global.discourse-cdn.com/meta/original/4X/e/7/1/e71e01b58306cb0fcfac259c005cec29561f3004.png)

You’ll need to create a `<span>` for this.
