Skip to content

Instantly share code, notes, and snippets.

@AllanJeremy
Created December 23, 2021 11:52
Show Gist options
  • Save AllanJeremy/17ce34dfc4266792a333e06d1f775858 to your computer and use it in GitHub Desktop.
Save AllanJeremy/17ce34dfc4266792a333e06d1f775858 to your computer and use it in GitHub Desktop.
Quasar 2.x Vue 3 Nav drawer component (accepts children) - Remove injections to use in any project
<template>
<q-drawer v-model="leftDrawerIsOpen" show-if-above>
<q-scroll-area
class="flex column justify-between"
style="
height: calc(100% - 150px);
margin-top: 150px;
border-right: 1px solid #ddd;
"
content-style="display:flex; flex-direction:column;justify-content:space-between;"
>
<VerticalNavItems :navItems="navItems" />
<div>
<q-separator></q-separator>
<q-item to="#!">
<q-item-section avatar>
<q-icon name="logout" color="red"></q-icon>
</q-item-section>
<q-item-section class="text-red">
<div class="text-weight-bold">Logout</div>
<small class="text-blue-grey-6">
Log out of your {{ PRODUCT_NAME }} account
</small>
</q-item-section>
</q-item>
</div>
</q-scroll-area>
<q-img
class="absolute-top"
src="https://cdn.quasar.dev/img/material.png"
style="height: 150px"
>
<div class="absolute-bottom bg-transparent">
<q-avatar size="56px" class="q-mb-sm">
<img src="https://cdn.quasar.dev/img/boy-avatar.png" />
</q-avatar>
<div class="text-weight-bold">
{{ user?.firstName }}{{ user?.lastName ? ` ${user.lastName}` : '' }}
</div>
<div>{{ user?.email || 'Loading...' }}</div>
</div>
</q-img>
</q-drawer>
</template>
<script lang="ts">
import { defineComponent, inject } from 'vue';
//* Types
import { AppUser } from 'src/types';
//* Components
import VerticalNavItems from './_partials/VerticalNavItems.vue';
export default defineComponent({
name: 'NavDrawer',
components: { VerticalNavItems },
props: {
navItems: {
type: Array,
required: true,
},
},
setup() {
const user = inject<AppUser>('user');
return { user };
},
});
</script>
<style scoped></style>
<template>
<q-list class="q-my-sm">
<template v-for="(navItem, index) in navItems" :key="`nav-${index}`">
<template v-if="navItem.children?.length">
<div class="text-weight-light q-px-md q-pt-sm q-my-none text-dark">
{{ navItem.title }}
</div>
<VerticalNavItems :nav-items="navItem.children" />
</template>
<q-item v-else :to="navItem.to">
<q-item-section v-if="navItem.icon" avatar>
<q-icon :name="navItem.icon" color="#ccc"></q-icon>
</q-item-section>
<q-item-section>
<span class="text-weight-bold text-blue-grey-10">{{
navItem.title
}}</span>
<small v-if="navItem.description" class="text-blue-grey-4">{{
navItem.description
}}</small>
</q-item-section>
</q-item>
<q-separator v-if="index < navItems.length - 1"></q-separator>
</template>
</q-list>
</template>
<script lang="ts">
import { defineComponent } from 'vue';
export default defineComponent({
name: 'VerticalNavItems',
props: {
//
navItems: {
type: Array,
required: true,
},
},
setup() {
//
return {};
},
});
</script>
<style scoped></style>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment