laurenashpole / vue-inner-image-zoom

https://laurenashpole.github.io/vue-inner-image-zoom
140 stars 16 forks source link

Can't handle image loading error #48

Open madiyetov opened 2 years ago

madiyetov commented 2 years ago

I am trying to show fallback image when image fails to load. Currently I can't do it, because an error event of img does not bubble, therefore it's not possible to somehow react to that event.

I guess we can:

  1. either bubble it with <img @error="(e) => $emit('error', e)" />l
  2. or implement fallback feature in the component itself.

@laurenashpole wdyt? Maybe there are other approaches.

laurenashpole commented 2 years ago

@madiyetov I think in the next update to the component, I'm going to switch to allowing an imgAttributes prop which should allow for easier load and error event handling. I'll let you know when that goes out.

HossinAmin commented 7 months ago

@madiyetov I have been using this package and found a way around it. I created a component with a hidden image element and listened to the events of the hidden image element to affect the inner-image-zoom components.

See the following code:

<template>
  <div>
    <img
      v-show="false"
      :src="src"
      :alt="alt"
      @load="onLoaded"
      @error="onError"
    />

    <inner-image-zoom
      v-if="!loading && !error"
      class="h-full w-full"
      :src="src"
      :zoomSrc="src"
      :zoomType="zoomType"
    />

    <CommonSkeletonLoader v-else-if="loading && !error" class="h-full w-full" />

    <img
      v-else-if="!loading && error"
      class="h-full w-full"
      src="~/assets/images/no-photo.png"
      :alt="alt"
    />
  </div>
</template>

<script setup lang="ts">
import "vue-inner-image-zoom/lib/vue-inner-image-zoom.css";
// @ts-ignore
import InnerImageZoom from "vue-inner-image-zoom"; // This libirary doesn't have types

const props = defineProps({
  src: {
    type: String,
  },
  zoomType: {
    type: String,
    default: "hover",
  },
  alt: {
    type: String,
  },
});

const error = ref(false);
const loading = ref(true);

const onLoaded = () => {
  error.value = false;
  loading.value = false;
};

const onError = () => {
  error.value = true;
  loading.value = false;
};
</script>