pythag0ras_
pythag0ras_

Reputation: 162

How do I create a navbar for a single-page-app in Vue?

I'm working on a single-page app in Vuejs and I'm wondering how I create a navbar that shows/hides different sections of the app based on what I click. I have the navbar laid out, I just need to figure out how to make it show/hide components. I tried to make the navbar component modify an array that tells my app which components to display, but it can't access the array. What should I do instead?

Upvotes: 1

Views: 4441

Answers (2)

MinorFourChord
MinorFourChord

Reputation: 280

Here is an example of a recent project I made with vue-router. The syntax maybe a little off in the first snippet as I'm used to creating and writing in vue CLI, but you insert the tag in App.vue in the main tag, setup your router page and your router config component.

I would recommend setting up a vue cli create app.

In terminal - vue create hello-world (add vue-router in create steps prompt), vue add vuetify after if you like!

<!DOCTYPE html>
<html>
<head>
  <link href="https://fonts.googleapis.com/css?family=Roboto:100,300,400,500,700,900" rel="stylesheet">
  <link href="https://cdn.jsdelivr.net/npm/@mdi/[email protected]/css/materialdesignicons.min.css" rel="stylesheet">
  <link href="https://cdn.jsdelivr.net/npm/[email protected]/dist/vuetify.min.css" rel="stylesheet">
  <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no, minimal-ui">
</head>
<body>
  <div id="app">
    <v-app>
      <v-main>
        <TopToolbar class="topTool"></TopToolbar>
          <v-main>
            <router-view></router-view>
          </v-main>
        <BottomNav class="bottomN"></BottomNav>
      </v-main>
    </v-app>
  </div>

  <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.js"></script>
  <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vuetify.js"></script>
  <script>
  import BottomNav from 'path';
    new Vue({
      el: '#app',
      vuetify: new Vuetify(),
      components: {TopToolbar, BottomNav},
      data: () => ({
      
      }),
    })
  </script>
</body>
</html>

<template>
  <v-bottom-navigation
    scroll-threshold="800"
    absolute
    color="primary"
    light
    grow
    background-color="primary"
    height="56"
  >
    <v-btn value="scan" :to="{ name: 'Scan'}">
      <span v-if="this.$route.name != 'Scan'" style="color: #fff">Scan</span>
      <v-icon v-if="this.$route.name != 'Scan'" size="24" color="#fff">mdi-barcode-scan</v-icon>
      <v-icon v-else size="24" color="primary">mdi-barcode-scan</v-icon>
    </v-btn>

    <v-btn value="create" :to="{ path: '/'}">
      <span v-if="this.$route.name != 'Create'" style="color: #fff">Create</span>
      <v-icon v-if="this.$route.name != 'Create'" size="24" color="#fff">mdi-barcode</v-icon>
      <v-icon v-else size="24" color="primary">mdi-barcode</v-icon>
    </v-btn>

    <v-btn value="print" :to="{ name: 'Print'}">
      <span v-if="this.$route.name != 'Print'" style="color: #fff">Print</span>
      <v-icon v-if="this.$route.name != 'Print'" size="24" color="#fff">mdi-printer</v-icon>
      <v-icon v-else size="24" color="primary">mdi-printer</v-icon>
    </v-btn>
  </v-bottom-navigation>
</template>

<script lang="ts">
import { Component, Vue } from 'vue-property-decorator';

@Component({})
export default class BottomNav extends Vue {}
</script>

<style scoped>

</style>

import Vue from 'vue';
import VueRouter from 'vue-router';

Vue.use(VueRouter);

const routes = [
  {
    path: '/scan',
    name: 'Scan',
    component: () => import('../views/Scan.vue'),
  },
  {
    path: '/',
    name: 'Create',
    component: () => import('../views/Create.vue'),
  },
  {
    path: '/print',
    name: 'Print',
    component: () => import('../views/Print.vue'),
  }
];

const router = new VueRouter({
  mode: 'history',
  base: process.env.BASE_URL,
  routes,
});

export default router;

Upvotes: 1

MinorFourChord
MinorFourChord

Reputation: 280

If you're not using Vue-Router, this may be what you're looking for.

Vue-Router would be preferable in most Vue SPAs though.

<!DOCTYPE html>
<html>
<head>
  <link href="https://fonts.googleapis.com/css?family=Roboto:100,300,400,500,700,900" rel="stylesheet">
  <link href="https://cdn.jsdelivr.net/npm/@mdi/[email protected]/css/materialdesignicons.min.css" rel="stylesheet">
  <link href="https://cdn.jsdelivr.net/npm/[email protected]/dist/vuetify.min.css" rel="stylesheet">
  <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no, minimal-ui">
</head>
<body>
  <div id="app">
    <v-app>
      <v-main>
        <template>
  <div>
    
    <v-tabs
      v-model="tab"
      background-color="blue accent-4"
      class="elevation-2"
      dark
      :centered="centered"
      :grow="grow"
      :vertical="vertical"
      :right="right"
      :prev-icon="prevIcon ? 'mdi-arrow-left-bold-box-outline' : undefined"
      :next-icon="nextIcon ? 'mdi-arrow-right-bold-box-outline' : undefined"
      :icons-and-text="icons"
    >
      <v-tabs-slider></v-tabs-slider>

      <v-tab
        v-for="i in tabs"
        :key="i"
        :href="`#tab-${i}`"
      >
        Tab {{ i }}
      </v-tab>

      <v-tab-item
        v-for="i in tabs"
        :key="i"
        :value="'tab-' + i"
      >
        <v-card
          flat
          tile
        >
          <v-card-text>{{ text }}</v-card-text>
        </v-card>
      </v-tab-item>
    </v-tabs>
  </div>
</template>
      </v-main>
    </v-app>
  </div>

  <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.js"></script>
  <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vuetify.js"></script>
  <script>
    new Vue({
      el: '#app',
      vuetify: new Vuetify(),
      data: () => ({
      tab: null,
        text: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.',
        icons: false,
        centered: false,
        grow: false,
        vertical: false,
        prevIcon: false,
        nextIcon: false,
        right: false,
        tabs: 3,
    }),
    })
  </script>
</body>
</html>

Upvotes: 3

Related Questions