Enclosing a router-link tag in a button in vuejs

Buttonvue.jsVue Router

Button Problem Overview


Can I wrap or enclose a router-link tag in a button tag?

When I press the button, I want it to route me to the desired page.

Button Solutions


Solution 1 - Button

You can use tag prop.

<router-link to="/foo" tag="button">foo</router-link>

Please use v-slot if you use 3.0+ (thanks to Romain and Jeff)

Solution 2 - Button

While the answers on here are all good, none seem to be the simplest solution. After some quick research, it seems that the real easiest way to make a button use vue-router is with the router.push call. This can be used within a .vue template like this:

<button @click="$router.push('about')">Click to Navigate</button>

Super simple and clean. I hope someone else finds this useful!

Source: https://router.vuejs.org/guide/essentials/navigation.html

Solution 3 - Button

@choasia's answer is correct.

Alternatively, you could wrap a button tag in a router-link tag like so:

<router-link :to="{name: 'myRoute'}">
  <button id="myButton" class="foo bar">Go!</button>
</router-link>

This is not so clean because your button will be inside a link element (<a>). However, the advantage is that you have a full control on your button, which may be necessary if you work with a front-end framework like Bootstrap.

I have never used this technique on buttons, to be honest. But I did this on divs quite often...

Solution 4 - Button

Thanks to Wes Winder's answer, and extending it to include route params:

<button @click="$router.push({name: 'about-something', params: { id: 'abc123' },})">Click to Navigate</button>

And reiterating the source which Wes provided: https://router.vuejs.org/guide/essentials/navigation.html

Solution 5 - Button

Official Answer as of 2022

Use the slots api Documentation Here

Example using the slots api
<router-link
  to="/about"
  v-slot="{href, route, navigate}"
  >
    <button :href="href" @click="navigate" class='whatever-you-want'>
      {{ route.name }}
    </button>
</router-link>

If you think this is unintuitive/verbose, please complain over here

Why are the other answers problematic?
  • @choasia's answer (using the tag prop) is deprecated and doesn't allow for props to be passed to the component

  • @Badacadabra's answer causes problems with CSS especially if the button is from a library (ex: adding a margin, or positioning)

Solution 6 - Button

Now days (VueJS >= 2.x) you would do:

<router-link tag="button" class="myClass" id="button" :to="place.to.go">Go!</router-link>

Solution 7 - Button

> Routing methods using method as well routing

  1. Router link > > <router-link to="/login">Login </router-link>

  2. When click on button that type call another route.

>

<script>
export default {
    name:'auth',
    data() {
        return {}
    },
    methods: {
        onLogIn() {
            this.$router.replace('/dashboard');
        }
    }
}

Solution 8 - Button

I'm working on Vue CLI 2 and this one has worked for me!

<router-link to="/about-creator">
<button>About Creator</button>
</router-link>

Solution 9 - Button

    // literal string path
router.push('home')

// object
router.push({ path: 'home' })

// named route
router.push({ name: 'user', params: { userId: '123' } })

// with query, resulting in /register?plan=private
router.push({ path: 'register', query: { plan: 'private' } })

Solution 10 - Button

Using the v-btn component you can simply:

<v-btn onclick="location.href='https://www.Google.com'" type="button" class="mb-4">Google</v-btn>

Solution 11 - Button

Sadly no, there is currently no way to do this properly.

I say properly because there obviously are several solutions that were already proposed to this question. The problem is: they seem to work but really they are not correct.

Here is why:

  1. It is invalid to put any actionable element inside of another in html (there's plenty of invalid html out there and it has not caught fire yet, am I right?).

  2. Most of the solutions I've seen here don't provide any navigation accessibility (nor link features such as "open link in new tab").

  3. The one that does (by Jeff Hykin) has a couple of draw backs too:

    • It fails to observe point 1)
    • In his snippet, @click="navigate" is not necessary because <router-link> is really an <a>, which will trigger a navigation by itself and href is totally useless to a <button>.
    • EDIT: Answer by Badacadabra is a bit better, but still point 1)

Assuming what you want is to reuse a properly styled button component to be used as a valid accessible link.

The real solution and you won't like it (I don't), is to create a component for the button, create another for the link and put whatever can be reused in yet another file (a base actionable component for example).

If the button comes from a library, well, another example that libraries never really solve every problem for you.

Solution 12 - Button

An example using bootstrap-vue and creating a link with the id inside a table row:

<b-table :fields="fields" :items="items">
    <template v-slot:cell(action)="data">
        <router-link :to="`/rounds/${data.item.id}`" v-slot="{ href, route, navigate}">
            <b-button :href="href" @click="navigate" color="primary" style="text">{{ data.item.id }}</b-button>
        </router-link>
    </template>
</b-table>

Where fields and items are the columns names and the table content, respectively.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionKushagra AgarwalView Question on Stackoverflow
Solution 1 - ButtonchoasiaView Answer on Stackoverflow
Solution 2 - ButtonWes WinderView Answer on Stackoverflow
Solution 3 - ButtonBadacadabraView Answer on Stackoverflow
Solution 4 - ButtonJoe WhoView Answer on Stackoverflow
Solution 5 - ButtonJeff HykinView Answer on Stackoverflow
Solution 6 - ButtonAnugaView Answer on Stackoverflow
Solution 7 - ButtonKaushik shrimaliView Answer on Stackoverflow
Solution 8 - ButtonAasshey TriveddiView Answer on Stackoverflow
Solution 9 - ButtonMuhammad WaqasView Answer on Stackoverflow
Solution 10 - ButtonSolvelView Answer on Stackoverflow
Solution 11 - ButtonRomain VincentView Answer on Stackoverflow
Solution 12 - ButtonPedro HenriqueView Answer on Stackoverflow