Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.

lukeboy_2002's avatar

Short body for index

Hi,

I have a blog with a body. Now I want to display a part of the body, Shortbody, on the index page. I tried a lot of given answers on the Internet but it doesn't work.

In my index.vue I would like too change {{ post.body }} to for example {{ post.shortbody }}.

my index.vue

<template>
    <AppLayout title="Posts">
        <template #hero>
            <img
                alt="TripleB"
                class="h-40 w-full overflow-hidden object-cover md:h-56 lg:h-72"
                src="/assets/blog.jpg"
            />
            <div
                class="absolute inset-0 bg-black bg-opacity-10 dark:bg-opacity-40"
            ></div>
            <div
                class="absolute inset-0 flex flex-col items-center justify-center"
            >
                <h1 class="text-4xl font-bold text-white">TBV-TripleB Blog</h1>
            </div>
        </template>
        <Article
            v-for="post in posts.data"
            :key="post.id"
            class="mb-4 p-4 last-of-type:mb-0"
        >
            <div class="flex space-x-4">
                <div class="hidden sm:flex sm:w-1/4 sm:justify-center">
                    <img
                        :src="post.image"
                        alt="{{ post.title }}"
                        class="max-h-44"
                    />
                </div>
                <div class="w-full sm:w-3/4">
                    <div class="flex items-center justify-between">
                        <div class="flex space-x-2 text-xs text-gray-500">
                            <VideoCameraIcon class="mr-2 size-4" />
                            Tutorial
                        </div>
                        <div>time ago</div>
                    </div>
                    <div>
                        <div
                            class="mb-2 text-2xl font-bold tracking-tight text-gray-900 transition duration-150 ease-in-out hover:text-orange-500 focus:text-orange-500 focus:outline-none dark:text-white dark:hover:text-orange-500 dark:focus:text-orange-500"
                        >
                            {{ post.title }}
                        </div>
                        <p
                            class="mb-5 whitespace-pre-wrap font-light text-gray-700 dark:text-gray-50"
                        >
                            {{ post.body }}
                        </p>
                    </div>
                    <div class="flex space-x-2 text-xs text-gray-500">
                        <UserIcon class="size-4" />
                        {{ post.user.username }}
                    </div>
                </div>
            </div>
        </Article>
        <Paginate :meta="posts.meta" />
        <template #side> To be Continued</template>
    </AppLayout>
</template>

<script setup>
import AppLayout from "@/Layouts/AppLayout.vue";
import Article from "@/Components/Article.vue";
import Paginate from "@/Components/Paginate.vue";

import { VideoCameraIcon } from "@heroicons/vue/24/outline";
import { UserIcon } from "@heroicons/vue/24/solid";

defineProps(["posts"]);
</script>
0 likes
2 replies
LaryAI's avatar
LaryAI
AI
Best Answer
Level 58

To display a shortened version of the blog post body (shortbody) on your index page, you can create a computed property or a method in your Vue component to generate this shortened text. Here’s a step-by-step solution:

  1. Create a method to generate the short body text: This method will take the full body text and return a truncated version of it.

  2. Update your template to use this new method: Replace {{ post.body }} with {{ getShortBody(post.body) }}.

Here’s how you can implement this:

Step 1: Create the getShortBody Method

In your <script setup> section, add a method to truncate the body text. For example, you can limit the text to the first 100 characters followed by an ellipsis (...).

<script setup>
import AppLayout from "@/Layouts/AppLayout.vue";
import Article from "@/Components/Article.vue";
import Paginate from "@/Components/Paginate.vue";

import { VideoCameraIcon } from "@heroicons/vue/24/outline";
import { UserIcon } from "@heroicons/vue/24/solid";

defineProps(["posts"]);

const getShortBody = (body) => {
    const maxLength = 100; // You can adjust the length as needed
    if (body.length <= maxLength) {
        return body;
    }
    return body.substring(0, maxLength) + '...';
};
</script>

Step 2: Update the Template

Replace {{ post.body }} with {{ getShortBody(post.body) }} in your template.

<template>
    <AppLayout title="Posts">
        <template #hero>
            <img
                alt="TripleB"
                class="h-40 w-full overflow-hidden object-cover md:h-56 lg:h-72"
                src="/assets/blog.jpg"
            />
            <div
                class="absolute inset-0 bg-black bg-opacity-10 dark:bg-opacity-40"
            ></div>
            <div
                class="absolute inset-0 flex flex-col items-center justify-center"
            >
                <h1 class="text-4xl font-bold text-white">TBV-TripleB Blog</h1>
            </div>
        </template>
        <Article
            v-for="post in posts.data"
            :key="post.id"
            class="mb-4 p-4 last-of-type:mb-0"
        >
            <div class="flex space-x-4">
                <div class="hidden sm:flex sm:w-1/4 sm:justify-center">
                    <img
                        :src="post.image"
                        alt="{{ post.title }}"
                        class="max-h-44"
                    />
                </div>
                <div class="w-full sm:w-3/4">
                    <div class="flex items-center justify-between">
                        <div class="flex space-x-2 text-xs text-gray-500">
                            <VideoCameraIcon class="mr-2 size-4" />
                            Tutorial
                        </div>
                        <div>time ago</div>
                    </div>
                    <div>
                        <div
                            class="mb-2 text-2xl font-bold tracking-tight text-gray-900 transition duration-150 ease-in-out hover:text-orange-500 focus:text-orange-500 focus:outline-none dark:text-white dark:hover:text-orange-500 dark:focus:text-orange-500"
                        >
                            {{ post.title }}
                        </div>
                        <p
                            class="mb-5 whitespace-pre-wrap font-light text-gray-700 dark:text-gray-50"
                        >
                            {{ getShortBody(post.body) }}
                        </p>
                    </div>
                    <div class="flex space-x-2 text-xs text-gray-500">
                        <UserIcon class="size-4" />
                        {{ post.user.username }}
                    </div>
                </div>
            </div>
        </Article>
        <Paginate :meta="posts.meta" />
        <template #side> To be Continued</template>
    </AppLayout>
</template>

This solution will display a shortened version of the blog post body on your index page. Adjust the maxLength variable in the getShortBody method to control the length of the truncated text.

chiefguru's avatar

Hi @lukeboy_2002

We present the first 400 characters of our blog posts as the summary, but because our blogs are HTML formatted we have to strip out all of the HTML tags. If we do not hell breaks loose.

<p>{!! mb_strimwidth(strip_tags($post->post_body_output()), 0, 400, " ...")  !!}</p>

Please or to participate in this conversation.