Vue doesn't work correctly with AddThis for sharing links

I am facing an issue with my webpage that uses AddThis for link sharing and Vue for rendering. The problem arises when the page displays a list of links across multiple pages. Sharing works perfectly on the first page, but on the second page, it still shows the links from the first page.

Here is a simple example to recreate this problem:

new Vue({
  el: '#app',
  data: {
    pages: [
      [{
        url: 'http://google.com',
        title: 'Google'
      }],
      [{
        url: 'http://yahoo.com',
        title: 'Yahoo'
      }]
    ],
    currentPage: 0
  },
  computed: {
    items() {
      return this.pages[this.currentPage]
    }
  },
  methods: {
    switchPage() {
      if (this.currentPage === 0) {
        this.currentPage = 1;
      } else {
        this.currentPage = 0;
      }
    }
  }
})
<script src="https://unpkg.com/vue"></script>

<div id="app">
  <div class="sharer" v-for="item in items">
    <div class="addthis_inline_share_toolbox" :data-url="item.url" :data-title="item.title">{{ item.title }}</div>
  </div>
  <button @click="switchPage">Switch pages</button>
</div>

<script src="https://s7.addthis.com/js/300/addthis_widget.js#pubid=ra-57f620a4f185d54b"></script>

When I navigate to the second page, the AddThis functionality does not capture the data-* attributes for sharing Yahoo, while it works fine for Google on the first page.

Note: Due to restrictions on accessing cookies by the sandboxed iframe, the StackOverflow snippet cannot be run here. However, you can find a working version at https://jsfiddle.net/d1az3qb3/3/. Please disable any ad-blockers to allow AddThis to load.

What I have already tried

  • Executing addthis.layers.refresh() after switching pages
  • Running
    addthis.toolbox('.addthis_inline_share_toolbox')

(Tried both directly and within this.$nextTick(() => …))

Question

Is AddThis malfunctioning, is there a compatibility issue with Vue, or is there a solution to make them work together seamlessly?

Answer №1

It seems like there may be a problem with the AddThis feature. One solution could be to display all the links and then use the v-show directive to hide the ones that you are not interested in.

new Vue({
  el: '#app',
  data: {
    pages: [
      {
        url: 'http://google.com',
        title: 'Google',
        id: 1
      },
      {
        url: 'http://yahoo.com',
        title: 'Yahoo',
        id: 2
      }
    ],
    currentPage: 0
  },
  computed: {
    selectedItem() {
      return this.pages[this.currentPage].id
    }
  },
  methods: {
    switchPage() {
      if (this.currentPage === 0) {
        this.currentPage = 1;
      } else {
        this.currentPage = 0;
      }
    }
  }
})
<script src="https://unpkg.com/vue"></script>

<div id="app">
  <div class="sharer" v-for="item in pages">
    <div v-show="item.id === selectedItem" class="addthis_inline_share_toolbox" :data-url="item.url" :data-title="item.title">{{ item.title }}</div>
  </div>
  <button @click="switchPage">Switch pages</button>
</div>

<script src="https://s7.addthis.com/js/300/addthis_widget.js#pubid=ra-57f620a4f185d54b"></script>

Answer №2

After extensive research, I discovered that in order to make it work properly, all AddThis layers need to be destroyed and re-initialized using the SmartLayer API. Here is an example of how to achieve this:

new Vue({
  el: '#app',
  data: {
    pages: [
      [{
        url: 'http://google.com',
        title: 'Google'
      }],
      [{
        url: 'http://yahoo.com',
        title: 'Yahoo'
      }]
    ],
    currentPage: 0
  },
  computed: {
    items() {
      return this.pages[this.currentPage]
    }
  },
  methods: {
    switchPage() {
      if (this.currentPage === 0) {
        this.currentPage = 1;
      } else {
        this.currentPage = 0;
      }

      this.$nextTick(() => {
        // The interesting bit:
        const destroyLayers = layers => layers.destroy();
        destroyLayers.pi = true;  // Necessary for AddThis

        addthis.layers(destroyLayers);
        addthis.layers.refresh();
      });
    }
  }
})
<script src="https://unpkg.com/vue"></script>

<div id="app">
  <div class="sharer" v-for="item in items">
    <div class="addthis_inline_share_toolbox_ctwk" :data-url="item.url" :data-title="item.title">{{ item.title }}</div>
  </div>
  <button @click="switchPage">Switch pages</button>
</div>

<script type="text/javascript" src="//s7.addthis.com/js/300/addthis_widget.js#pubid=ra-57f620a4f185d54b"></script>

If you want to see a fully functional JSFiddle version, check out https://jsfiddle.net/msiemens/82ysztk9/1/

Answer №3

I'm not completely satisfied with the solution that involves refreshing all the addThis elements on the page. For those seeking a more streamlined approach, there is an API available for creating custom addThis buttons which can be found here

One way to implement this is as follows:

<script>
  export default {
    methods: {
      bindAddThis() {
        this.$nextTick(() => {
          window.addthis.share({
            container_selector: ".content--sharing-icons",
            button_selector: ".addthis_share_button"
          });
        });
      }
    },
    afterUpdate() {
      this.bindAddThis();
    },
    mounted() {
      this.bindAddThis();
    }
  };
</script>

Unfortunately, the addThis API does not allow for using an element as a selector so $refs cannot be used.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

The Angular Http Interceptor is failing to trigger a new request after refreshing the token

In my project, I implemented an HTTP interceptor that manages access token refreshing. If a user's access token expires and the request receives a 401 error, this function is designed to handle the situation by refreshing the token and re-executing ...

Struggling with getting Sprite maps to function properly within THREE.js

I'm having some trouble adding a sprite to my scene in the usual way. The image I'm using can be found here: i.imgur.com/kMT4mOH.png var map = THREE.ImageUtils.loadTexture('i.imgur.com/kMT4mOH.png'); var mat = new THREE.SpriteMaterial( ...

Express: Every declaration of 'user' must have the same modifiers

In my application, I am utilizing both express and passport. Within these packages, there is a user attribute within the Request interface. Currently, the express package has a user attribute in the request object, such as req.user, but no additional prope ...

Clicking on the div will redirect the page to one destination, while clicking on the anchor tag will redirect the page to a different destination

I have a div containing an anchor tag, like so: <div onclick="redirect to one location" style="height:200px;width:200px"><a href="http://www.google.com" >text</a></div> The div has dimensions of 200px by 200px and on click, it sho ...

Ruby on Rails is experiencing a malfunction with the Ajax request

In designing a quiz, I wanted to display the questions one by one in a list. When clicking on a question in the list, it should navigate to that specific question's location. However, I encountered an issue where the loader does not stop loading. Her ...

How to Resubmit a Form Using Ajax?

My form utilizes ajax to call the server for user authentication. However, I've encountered an issue where if a user enters the wrong password and then tries to correct it, any subsequent calls do not trigger the on('submit') function, leavi ...

Top recommendation for parsing a single record from a JSON array

Currently I am fetching the result of a REST method (observable) which typically contains only one element. Although my code is functional and displaying the data, I keep getting an ERROR message in the browser console saying TypeError: Cannot read propert ...

The step-by-step guide for replacing the extJs Controller component

I have developed a versatile component that is being utilized across different products. In this case, I have a generic window and window controller which I am customizing to fit our specific product requirements. This is my generic window: Ext.define(&a ...

The Google analytics page tracking feature is experiencing issues within an AngularJS application and is not functioning correctly

My current project focuses on AngularJS, catering to both mobile applications and desktop websites. I have downloaded analytics.js locally and integrated it into my GA tracking code within the index.html file: (function(i,s,o,g,r,a,m){i['GoogleAnalyt ...

React.js encountered an error: Unexpected "<" token

My journey with react.js has just begun. I am currently using Webstorm for development. I have encountered an error that I am struggling to solve. It seems like React is not being recognized even after trying to install various npm react packages. Synta ...

Exploring ng-view navigation in AngularJS

I have come across an SEO issue while working on a static website in AngularJS. Google Webmasters Tools report no crawl errors, but when I attempt to fetch different routes, it consistently returns the same home page result. It seems to be ignoring what ...

Dynamic popup in RShiny interface with the ability to be moved around

I am currently working on a dashboard project and I am looking to implement a dynamic popup feature that can be moved around. I have been able to create a pop-up, but it remains static. I would like the flexibility for users to drag and position the popup ...

What is the best way to arrange an array of objects in JavaScript by numerical order and then alphabetically?

Possible Duplicate: Sorting objects in an array by a field value in JavaScript I'm looking to sort an array of objects both numerically (by id) and alphabetically (by name). However, the current method I'm using is not giving me the desired ...

Utilize the #value template in PrimeVue Dropdown to retrieve country code for setting the default selected flag

In the student edit modal, I have a Dropdown where I need to display a flag for the default country. When using PrimeVue, I can access the country code from a template using #option="slotProps", but not with #value="slotProps". This m ...

Can anyone provide guidance on implementing pagination with Firebase Realtime Database in Vue.js?

Currently, I am working on implementing pagination for my data from the Firebase Realtime Database. Do I need to switch to Firestore instead? Google's documentation provides detailed information on how to implement pagination using Firestore (https:// ...

Tips for dynamically displaying images in both horizontal and vertical orientations

I would like to showcase images in the imageList. Here is what I want: AB CD How can this be achieved? It's not a matter of being even or odd Perhaps the list could look something like this: ABCDE FG I simply want a new row or display:block when ...

The useEffect hook in ReactJs is triggering multiple times

Encountering challenges while developing an Infinite scroll using ReactJs and Intersection observer API. Upon initial application load, the API gets called twice instead of once. This behavior may be due to strict mode, although not confirmed. Additionall ...

The ace.edit function is unable to locate the #javascript-editor div within the mat-tab

Having trouble integrating an ace editor with Angular material Error: ace.edit cannot locate the div #javascript-editor You can view my code on StackBlitz (check console for errors) app.component.html <mat-tab-group> <mat-tab label="Edito ...

Show a variety of pictures using React

Is it possible to repeat an image (e.g. photo.jpg) n times in Reactjs using a provided value for n in props? If yes, how can this be achieved? function Card(props) { for (let i = 0; i < props.rating; i++) { <img className="star" src ...

Transmitting data via AJAX to a sails endpoint

Currently, I am facing an issue with a client-side component that generates a DataURL when a user uploads or takes a picture and then crops it. My goal is to send this DataURL via an AJAX call to a sails endpoint. As per the documentation provided by Sails ...