Display image in Vue

User
How to display image from assets folder in vue js
Assistant
In Vue.js, to display an image from the `assets` folder, you need to use the `@` alias or `require()` because images in `src/assets/` are processed by Webpack (or Vite) and need to be referenced correctly.

### ✅ Option 1: Using `@` alias (Recommended in Single File Components)

<template>
  <img :src="require('@/assets/images/my-image.jpg')" alt="My Image" />
</template>

Or, if you're using Vite:

<template>
  <img src="@/assets/images/my-image.jpg" alt="My Image" />
</template>

But in Vite, this might need to be dynamic using `import`:

<script setup>
import myImage from '@/assets/images/my-image.jpg';
</script>

<template>
  <img :src="myImage" alt="My Image" />
</template>

### ✅ Option 2: In “ using `import`

<script>
import myImage from '@/assets/images/my-image.jpg';

export default {
  data() {
    return {
      myImage
    };
  }
};
</script>

<template>
  <img :src="myImage" alt="My Image" />
</template>

### ✅ Folder Structure Example

src/
├── assets/
│   └── images/
│       └── my-image.jpg
├── components/
│   └── MyComponent.vue

Let me know if you're using Vue 2 or 3, and whether it's with Vite, Webpack, or Laravel Mix, so I can tailor the solution even more precisely.

User
in vue 3
Assistant
Great! Since you're using **Vue 3**, here’s the best way to display an image from the `assets` folder depending on your build tool:

### ✅ If you're using **Vite** (common in Vue 3 projects)

Use `import` in “ or regular “:

#### ✅ Example with “:

<script setup>
import myImage from '@/assets/images/my-image.jpg';
</script>

<template>
  <img :src="myImage" alt="My Image" />
</template>

### ✅ If you're using **Vue CLI with Webpack**

You can use `require()` or `import`:

<template>
  <img :src="require('@/assets/images/my-image.jpg')" alt="My Image" />
</template>

Or with `import`:

<script>
import myImage from '@/assets/images/my-image.jpg';

export default {
  data() {
    return {
      myImage
    };
  }
};
</script>

<template>
  <img :src="myImage" alt="My Image" />
</template>

### 🧠 Bonus: Static Image (rarely recommended)

You can also hardcode the path if the image is in `public/` instead of `src/assets/`:

<img src="/images/my-image.jpg" alt="Static Image" />

But this skips asset optimization, so prefer `import` when working with `src/assets`.

Let me know if you're using Vite, Vue CLI, or Laravel Mix—I'll tailor it exactly to your setup.

User
The server is configured with a public base URL of /frontend/ – did you mean to visit /frontend/images/review1.png instead?
Assistant
Ah, that message is from **Vite** or the browser telling you your image URL doesn't match the public base path you've set.

Since your server is configured with a base URL of `/frontend/`, **Vite prepends `/frontend/` to all assets during build**.

### ✅ Solution (Using `import` so Vite handles it properly)

Use `import` for image assets in `.vue` files — this way, Vite knows how to resolve the path even with a custom `base` URL like `/frontend/`.

#### Example (Vue 3 + Vite):

<script setup>
import reviewImage from '@/assets/images/review1.png';
</script>

<template>
  <img :src="reviewImage" alt="Review" />
</template>

This will compile to the correct path: `/frontend/assets/review1-[hash].png`

### ❌ Avoid this (hardcoded paths):

<img src="/images/review1.png" alt="Wrong path" />

That will look for `/images/review1.png`, but your base is `/frontend/`, so it fails.

### ✅ Alternative (if using `public/` folder)

If you really want to hardcode the image path, place the image in the `public/images/` folder and use:

<img src="/frontend/images/review1.png" alt="Review" />

But this skips Vite optimizations (like caching, hashing, etc.).

Let me know which option you're going with or if you want help refactoring!

User
Failed to resolve import "@/assets/images/review1.png" from "src/views/PortfolioPage.vue". Does the file exist?
Assistant
That error means Vite can't find the image at the specified path. Let's troubleshoot it step-by-step:

### ✅ 1. **Check the File Structure**

Make sure the file actually exists at this location:

src/
├── assets/
│   └── images/
│       └── review1.png
└── views/
    └── PortfolioPage.vue

> ✅ Is `review1.png` in `src/assets/images/`?

### ✅ 2. **Check the Import Syntax**

If using **Vue 3 with Vite**, use this in `PortfolioPage.vue`:

<script setup>
import reviewImage from '@/assets/images/review1.png';
</script>

<template>
  <img :src="reviewImage" alt="Review" />
</template>

> The `@` alias should point to `src/`. If it doesn’t work…

### 🔁 3. **Try Using Relative Path Instead (Quick Test)**

Sometimes alias misconfigurations can mess up imports. Try a **relative path**:

<script setup>
import reviewImage from '../assets/images/review1.png';
</script>

Or, if you're in `src/views/PortfolioPage.vue`, and the image is in `src/assets/images`, then `../assets/images/review1.png` is correct.

### ✅ 4. **Ensure the Alias `@` is Configured (Vite only)**

In `vite.config.js`, you should have something like:

import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import path from 'path'

export default defineConfig({
  plugins: [vue()],
  resolve: {
    alias: {
      '@': path.resolve(__dirname, 'src')
    }
  },
  base: '/frontend/', // important if you're deploying to /frontend/
})

> Restart the dev server after making changes to `vite.config.js`.

Let me know:

– The actual location of `review1.png`
– The exact path of `PortfolioPage.vue`
– If you're using Vite, Vue CLI, or something else

I’ll give you the precise import path that works for your setup.

User
import { fileURLToPath, URL } from 'node:url'

import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import vueJsx from '@vitejs/plugin-vue-jsx'
import vueDevTools from 'vite-plugin-vue-devtools'

// https://vite.dev/config/
export default defineConfig({
base: '/frontend/',
plugins: [
vue(),
vueJsx(),
vueDevTools(),
],
resolve: {
alias: {
'@': fileURLToPath(new URL('./src', import.meta.url))
},
},
server: {
host: 'localhost',
port: 5173,
strictPort: true,
origin: 'http://localhost:5173',
watch: {
ignored: ['**/node_modules/**', '**/vendor/**'],
usePolling: true,
},

},
})

Assistant
Thanks for sharing your `vite.config.js` — everything looks good, including your alias config:

alias: {
  '@': fileURLToPath(new URL('./src', import.meta.url))
}

That means `@/assets/images/review1.png` **should work**, assuming the file actually exists.

### ✅ Let's Double-Check Everything

#### 1. **File Exists**
Make sure the image is here:

src/
└── assets/
    └── images/
        └── review1.png ✅

Make sure there's **no typo** in the filename (`review1.PNG` vs `review1.png` — case matters!).

#### 2. **Correct Import in Vue File**

In `src/views/PortfolioPage.vue`:

<script setup>
import reviewImage from '@/assets/images/review1.png';
</script>

<template>
  <img :src="reviewImage" alt="Review Image" />
</template>

This **must be in “ or “**, not in the template as a raw string.

#### 3. **Restart the Dev Server**

Vite sometimes caches aggressively. After fixing file paths:

npm run dev
# or
yarn dev

Make sure to **stop and restart** the server.

#### 4. **Still Not Working? Try a Relative Path as a Quick Test**

In `PortfolioPage.vue`, try:

<script setup>
import reviewImage from '../assets/images/review1.png';
</script>

If that works, it means something’s still wrong with the `@` alias, though your config looks correct.

Want to be extra sure? Run:

ls src/assets/images/

And verify that `review1.png` is listed.

Let me know if you'd like to try the `public/` folder method as a fallback or want help debugging further.

User
image are not responsinve in vutify
Assistant
If you're using Vuetify's “ and your images are not responsive (not scaling properly), it's likely due to either missing styling or incorrect usage of the `cover` prop. Let’s go step-by-step to make the images responsive:

### ✅ 1. **Make Sure Images Are Imported Properly**

If you are importing images in your “:

<script setup>
import review1 from '@/assets/images/review1.png'
import review2 from '@/assets/images/review2.png'
import review3 from '@/assets/images/review3.png'
import review4 from '@/assets/images/review4.png'
import review5 from '@/assets/images/review5.png'
</script>

### ✅ 2. **Ensure Proper Use of `v-carousel-item` with Vuetify 3**

<template>
  <v-carousel
    height="400"
    hide-delimiter-background
    show-arrows="hover"
  >
    <v-carousel-item
      v-for="(image, i) in images"
      :key="i"
      :src="image"
      cover
    />
  </v-carousel>
</template>

<script setup>
import review1 from '@/assets/images/review1.png'
import review2 from '@/assets/images/review2.png'
import review3 from '@/assets/images/review3.png'
import review4 from '@/assets/images/review4.png'
import review5 from '@/assets/images/review5.png'

const images = [review1, review2, review3, review4, review5]
</script>

### ✅ 3. **Optional: Override with Custom CSS (if needed)**

Sometimes the image may need a little extra help, especially in custom layouts:

.v-carousel-item > .v-img {
  object-fit: cover;
  width: 100%;
  height: 100%;
}

You can put this in your component’s “ or in global styles if needed.

### ✅ 4. **Use `cover` Properly**

You already have `cover` — which is correct. It tells Vuetify's `v-img` component (used internally in `v-carousel-item`) to scale the image while preserving its aspect ratio and filling the container.

### ✅ 5. **Set the Carousel Height**

Make sure you give the carousel a height, like:

<v-carousel height="400"> ... </v-carousel>

Without a defined height, it might collapse or appear broken.

Let me know if you're using Vuetify 2 or 3 (this solution assumes Vuetify 3), and if the images are still not scaling properly, I can help you with more specific CSS.

Leave a Comment

Your email address will not be published. Required fields are marked *