Merge pull request #138 from jfkriz/feature/avatar-component-override-default-placeholder

Avatar - Allow placeholder override, and handle image errors
This commit is contained in:
Ilya Artamonov
2023-06-04 12:40:04 +03:00
committed by GitHub
3 changed files with 68 additions and 5 deletions

View File

@@ -1,5 +1,6 @@
<script setup>
import AvatarExample from './avatar/examples/AvatarExample.vue'
import AvatarAlternativePlaceholderExample from './avatar/examples/AvatarAlternativePlaceholderExample.vue'
import AvatarBorderedExample from './avatar/examples/AvatarBorderedExample.vue'
import AvatarDotIndicatorExample from './avatar/examples/AvatarDotIndicatorExample.vue'
import AvatarSizeExample from './avatar/examples/AvatarSizeExample.vue'
@@ -185,3 +186,33 @@ import { Avatar } from 'flowbite-vue'
</div>
</template>
```
## Alternative Placeholder Icon
Use this example if you'd like to specify a different placeholder icon. Specify a `#placeholder` template slot to override the default placeholder icon. This has no effect if using initials.
<AvatarAlternativePlaceholderExample />
```vue
<template>
<div class="vp-raw flex">
<Avatar class="mr-2.5">
<template #placeholder>
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor" class="w-12 h-12">
<path stroke-linecap="round" stroke-linejoin="round" d="M17.982 18.725A7.488 7.488 0 0012 15.75a7.488 7.488 0 00-5.982 2.975m11.963 0a9 9 0 10-11.963 0m11.963 0A8.966 8.966 0 0112 21a8.966 8.966 0 01-5.982-2.275M15 9.75a3 3 0 11-6 0 3 3 0 016 0z" />
</svg>
</template>
</Avatar>
<Avatar rounded>
<template #placeholder>
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor" class="w-12 h-12">
<path stroke-linecap="round" stroke-linejoin="round" d="M17.982 18.725A7.488 7.488 0 0012 15.75a7.488 7.488 0 00-5.982 2.975m11.963 0a9 9 0 10-11.963 0m11.963 0A8.966 8.966 0 0112 21a8.966 8.966 0 01-5.982-2.275M15 9.75a3 3 0 11-6 0 3 3 0 016 0z" />
</svg>
</template>
</Avatar>
</div>
</template>
<script setup>
import { Avatar } from 'flowbite-vue'
</script>
```

View File

@@ -0,0 +1,21 @@
<template>
<div class="vp-raw flex">
<Avatar class="mr-2.5">
<template #placeholder>
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor" class="w-12 h-12">
<path stroke-linecap="round" stroke-linejoin="round" d="M17.982 18.725A7.488 7.488 0 0012 15.75a7.488 7.488 0 00-5.982 2.975m11.963 0a9 9 0 10-11.963 0m11.963 0A8.966 8.966 0 0112 21a8.966 8.966 0 01-5.982-2.275M15 9.75a3 3 0 11-6 0 3 3 0 016 0z" />
</svg>
</template>
</Avatar>
<Avatar rounded>
<template #placeholder>
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor" class="w-12 h-12">
<path stroke-linecap="round" stroke-linejoin="round" d="M17.982 18.725A7.488 7.488 0 0012 15.75a7.488 7.488 0 00-5.982 2.975m11.963 0a9 9 0 10-11.963 0m11.963 0A8.966 8.966 0 0112 21a8.966 8.966 0 01-5.982-2.275M15 9.75a3 3 0 11-6 0 3 3 0 016 0z" />
</svg>
</template>
</Avatar>
</div>
</template>
<script setup>
import { Avatar } from '../../../../src/index'
</script>

View File

@@ -1,21 +1,32 @@
<template>
<div class="relative">
<div v-if="!img" :class="avatarPlaceholderWrapperClasses">
<svg v-if="!initials" :class="avatarPlaceholderClasses" fill="currentColor" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg">
<img v-if="img && !imageError" :class="avatarClasses" :src="img" :alt="alt" @error="setImageError">
<div v-else :class="avatarPlaceholderWrapperClasses">
<svg v-if="!initials && !hasPlaceholder" :class="avatarPlaceholderClasses" fill="currentColor" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" d="M10 9a3 3 0 100-6 3 3 0 000 6zm-7 9a7 7 0 1114 0H3z" clip-rule="evenodd"></path>
</svg>
<div v-if="!initials && hasPlaceholder" :class="avatarPlaceholderClasses">
<slot name="placeholder" />
</div>
<div v-else :class="avatarPlaceholderInitialsClasses">{{ initials }}</div>
<span v-if="status" :class="avatarDotClasses" :data-pos="statusPosition"></span>
</div>
<img v-else :class="avatarClasses" :src="img" :alt="alt">
<span v-if="status" :class="avatarDotClasses" :data-pos="statusPosition"></span>
</div>
</template>
<script lang="ts" setup>
import { toRefs } from 'vue'
import { computed, ref, toRefs, useSlots } from 'vue'
import type { PropType } from 'vue'
import type { AvatarSize, AvatarStatus, AvatarStatusPosition } from './types'
import { useAvatarClasses } from '@/components/Avatar/composables/useAvatarClasses'
const imageError = ref(false)
function setImageError() {
imageError.value = true
}
const slots = useSlots()
const hasPlaceholder = computed(() => slots.placeholder)
const props = defineProps({
alt: {
type: String,