fix: profile banner fallback
This commit is contained in:
parent
4cbcaeb3f2
commit
664284ce95
1 changed files with 93 additions and 63 deletions
|
|
@ -3,12 +3,12 @@ import { ref } from 'vue';
|
||||||
|
|
||||||
defineProps<{
|
defineProps<{
|
||||||
icon?: string;
|
icon?: string;
|
||||||
|
fallbackCover?: string;
|
||||||
color?: string;
|
color?: string;
|
||||||
img?: string | null;
|
img?: string | null;
|
||||||
bgColor?: string;
|
bgColor?: string;
|
||||||
title?: string;
|
title?: string;
|
||||||
caption?: string;
|
caption?: string;
|
||||||
cover?: string | null;
|
|
||||||
|
|
||||||
hideFade?: boolean;
|
hideFade?: boolean;
|
||||||
active?: boolean;
|
active?: boolean;
|
||||||
|
|
@ -22,49 +22,75 @@ defineEmits<{
|
||||||
(e: 'edit'): void;
|
(e: 'edit'): void;
|
||||||
}>();
|
}>();
|
||||||
|
|
||||||
|
const coverUrl = defineModel<string>('coverUrl', {
|
||||||
|
required: false,
|
||||||
|
default: '',
|
||||||
|
});
|
||||||
|
|
||||||
const showOverlay = ref(false);
|
const showOverlay = ref(false);
|
||||||
</script>
|
</script>
|
||||||
<template>
|
<template>
|
||||||
<div
|
<q-img
|
||||||
|
fit="cover"
|
||||||
class="cover rounded bordered relative-position"
|
class="cover rounded bordered relative-position"
|
||||||
:style="`background-image: linear-gradient(
|
position="0 0"
|
||||||
|
:src="coverUrl || fallbackCover || 'blank-cover.png'"
|
||||||
|
@error="coverUrl = ''"
|
||||||
|
>
|
||||||
|
<nav
|
||||||
|
class="full-width full-height"
|
||||||
|
:style="`background-image: linear-gradient(
|
||||||
90deg, ${
|
90deg, ${
|
||||||
$q.dark.isActive
|
$q.dark.isActive
|
||||||
? `hsla(var(--gray-10-hsl) / ${hideFade ? '0' : '1'}) 10%,hsla(var(--gray-10-hsl) / 0) 100%`
|
? `hsla(var(--gray-10-hsl) / ${hideFade ? '0' : '1'}) 10%,hsla(var(--gray-10-hsl) / 0) 100%`
|
||||||
: `rgba(255, 255, 255, ${hideFade ? '0' : '1'}) 10%,rgba(255, 255, 255, 0) 100%`
|
: `rgba(255, 255, 255, ${hideFade ? '0' : '1'}) 10%,rgba(255, 255, 255, 0) 100%`
|
||||||
}
|
}
|
||||||
),
|
)`"
|
||||||
url(${cover || 'blank-cover.png'});`"
|
>
|
||||||
>
|
<!-- profile -->
|
||||||
<!-- profile -->
|
<div class="flex items-center full-height q-pl-lg" style="z-index: 999">
|
||||||
<div class="absolute-top flex items-center full-height q-pl-lg">
|
|
||||||
<div
|
|
||||||
class="surface-1"
|
|
||||||
style="
|
|
||||||
border-radius: 50%;
|
|
||||||
border: 4px solid var(--surface-1);
|
|
||||||
overflow: hidden;
|
|
||||||
"
|
|
||||||
>
|
|
||||||
<div
|
<div
|
||||||
class="avatar__status"
|
class="surface-1"
|
||||||
style="z-index: 2"
|
style="
|
||||||
:style="`${active ? 'background-color: hsla(var(--positive-bg) / 1)' : 'background-color: hsla(var(--text-mute) / 1)'}`"
|
border-radius: 50%;
|
||||||
></div>
|
border: 4px solid var(--surface-1);
|
||||||
<q-avatar
|
overflow: hidden;
|
||||||
size="6rem"
|
"
|
||||||
font-size="3rem"
|
|
||||||
class="cursor-pointer"
|
|
||||||
style="z-index: 1"
|
|
||||||
:style="`background-color: ${img ? 'white' : bgColor || 'var(--brand-1)'}; color: ${color || 'white'}`"
|
|
||||||
@mouseover="showOverlay = true"
|
|
||||||
@mouseleave="showOverlay = false"
|
|
||||||
@click.stop="$emit('view')"
|
|
||||||
>
|
>
|
||||||
<q-img v-if="img" :src="img" :ratio="1" />
|
<div
|
||||||
<q-icon v-if="!img" :name="icon || 'mdi-account'" />
|
class="avatar__status"
|
||||||
|
style="z-index: 2"
|
||||||
|
:style="`${active ? 'background-color: hsla(var(--positive-bg) / 1)' : 'background-color: hsla(var(--text-mute) / 1)'}`"
|
||||||
|
></div>
|
||||||
|
<q-avatar
|
||||||
|
size="6rem"
|
||||||
|
font-size="3rem"
|
||||||
|
class="cursor-pointer relative-position"
|
||||||
|
style="z-index: 1"
|
||||||
|
:style="{
|
||||||
|
'background-color': `${bgColor || 'var(--brand-1)'}`,
|
||||||
|
color: `${color || 'white'}`,
|
||||||
|
}"
|
||||||
|
@mouseover="showOverlay = true"
|
||||||
|
@mouseleave="showOverlay = false"
|
||||||
|
@click.stop="$emit('view')"
|
||||||
|
>
|
||||||
|
<q-img v-if="img" :src="img" :ratio="1">
|
||||||
|
<template #error>
|
||||||
|
<div
|
||||||
|
class="full-width full-height flex items-center justify-center"
|
||||||
|
style="background-color: transparent"
|
||||||
|
:style="{
|
||||||
|
color: `${color || 'white'}`,
|
||||||
|
}"
|
||||||
|
>
|
||||||
|
<q-icon :name="icon || 'mdi-account'" />
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
</q-img>
|
||||||
|
<q-icon v-else :name="icon || 'mdi-account'" />
|
||||||
|
|
||||||
<Transition name="slide-fade">
|
<!-- <Transition name="slide-fade"> -->
|
||||||
<div
|
<div
|
||||||
v-if="showOverlay && !readonly"
|
v-if="showOverlay && !readonly"
|
||||||
class="absolute-bottom text-caption flex items-center justify-center upload-overlay"
|
class="absolute-bottom text-caption flex items-center justify-center upload-overlay"
|
||||||
|
|
@ -73,37 +99,38 @@ const showOverlay = ref(false);
|
||||||
>
|
>
|
||||||
{{ $t('editImage') }}
|
{{ $t('editImage') }}
|
||||||
</div>
|
</div>
|
||||||
</Transition>
|
<!-- </Transition> -->
|
||||||
</q-avatar>
|
</q-avatar>
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<!-- text -->
|
|
||||||
<div
|
|
||||||
class="absolute-bottom relative-position justify-between row text-cover"
|
|
||||||
:class="{ dark: $q.dark.isActive }"
|
|
||||||
>
|
|
||||||
<div class="column">
|
|
||||||
<span class="text-bold q-pt-xs text-body1">{{ title }}</span>
|
|
||||||
<span class="app-text-muted">{{ caption }}</span>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<!-- icon -->
|
|
||||||
<div class="row items-center q-pr-lg">
|
|
||||||
<div class="q-gutter-x-sm">
|
|
||||||
<q-btn
|
|
||||||
v-for="(item, n) in menu"
|
|
||||||
:key="n"
|
|
||||||
flat
|
|
||||||
size="sm"
|
|
||||||
class="q-pa-xs rounded"
|
|
||||||
:icon="item.icon"
|
|
||||||
:style="`background-color: ${item.bgColor}; color: ${item.color}`"
|
|
||||||
/>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
|
||||||
</div>
|
<!-- text -->
|
||||||
|
<div
|
||||||
|
class="absolute-bottom relative-position justify-between row text-cover"
|
||||||
|
:class="{ dark: $q.dark.isActive }"
|
||||||
|
>
|
||||||
|
<div class="column">
|
||||||
|
<span class="text-bold q-pt-xs text-body1">{{ title }}</span>
|
||||||
|
<span class="app-text-muted">{{ caption }}</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- icon -->
|
||||||
|
<div class="row items-center q-pr-lg" style="z-index: 999">
|
||||||
|
<div class="q-gutter-x-sm">
|
||||||
|
<q-btn
|
||||||
|
v-for="(item, n) in menu"
|
||||||
|
:key="n"
|
||||||
|
flat
|
||||||
|
size="sm"
|
||||||
|
class="q-pa-xs rounded"
|
||||||
|
:icon="item.icon"
|
||||||
|
:style="`background-color: ${item.bgColor}; color: ${item.color}`"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</nav>
|
||||||
|
</q-img>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<style lang="scss">
|
<style lang="scss">
|
||||||
|
|
@ -149,8 +176,7 @@ const showOverlay = ref(false);
|
||||||
|
|
||||||
.upload-overlay {
|
.upload-overlay {
|
||||||
top: 3.5rem;
|
top: 3.5rem;
|
||||||
background-color: hsla(var(--gray-10-hsl) / 0.2);
|
background-color: hsla(var(--gray-10-hsl) / 0.5);
|
||||||
backdrop-filter: blur(8px);
|
|
||||||
color: white;
|
color: white;
|
||||||
|
|
||||||
&.dark {
|
&.dark {
|
||||||
|
|
@ -170,4 +196,8 @@ const showOverlay = ref(false);
|
||||||
.slide-fade-leave-to {
|
.slide-fade-leave-to {
|
||||||
opacity: 0;
|
opacity: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.q-img__content > nav {
|
||||||
|
pointer-events: all;
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue