Encountering a problem with integrating Vue js and making a jquery

Hello there! I'm currently working on fetching data through ajax and utilizing a vue wrapper component. Here's the code snippet I'm using:

  <html>
    <head>
        <title>title</title>
        <meta charset="UTF-8">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <style>
            html, body {
                font: 13px/18px sans-serif;
            }
            select {
                min-width: 300px;
            }
        </style>
    </head>
    <body>
        <div id="el"></div>

        <!-- using string template here to work around HTML <option> placement restriction -->
        <script type="text/x-template" id="demo-template">
            <div>
            <p>Selected: {{ input.selected }}</p>
            <select2 :options="options" v-model="input.selected">
            <option disabled value="0">Select one</option>
            </select2>
            </div>
        </script>

        <script type="text/x-template" id="select2-template">
            <select>
            <slot></slot>
            </select>
        </script>
        <script src="http://themestarz.net/html/craigs/assets/js/jquery-3.3.1.min.js"></script>
        <script src="https://unpkg.com/<a href="/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="c3b5b6a683f1edf6edf2f4">[email protected]</a>/dist/vue.js"></script>
        <script src="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.0/js/select2.min.js"></script>
        <script src="https://unpkg.com/axios/dist/axios.min.js"></script>
        <script>
            Vue.component('select2', {
                props: ['options', 'value'],
                template: '#select2-template',
                mounted: function () {
                    var vm = this;
                    $(this.$el)
                            // init select2
                            .select2({data: this.options})
                            .val(this.value)
                            .trigger('change')
                            // emit event on change.
                            .on('change', function () {
                                vm.$emit('input', this.value)
                            });
                },
                watch: {
                    value: function (value) {
                        // update value
                        $(this.$el)
                                .val(value)
                                .trigger('change')



                    },
                    options: function (options) {
                        // update options
                        $(this.$el).empty().select2({data: options})
                    }
                },
                destroyed: function () {
                    $(this.$el).off().select2('destroy')
                }
            })

            var vm = new Vue({
                el: '#el',
                template: '#demo-template',
                data: {
                    input: {
                        selected: "all"
                    },
                    options: []
                },
                created: function () {
                    this.mymethod();
                },
                methods: {
                    mymethod: function () {
                        var vm = this;


                        $.get("https://api.coindesk.com/v1/bpi/currentprice.json", function (data) {
                            vm.options = [
                                {id: 'all', text: 'All'},
                                {id: 1, text: 'Hello'},
                                {id: 2, text: 'World'},
                                {id: 3, text: 'Bye'}
                            ];

                            vm.input.selected = 2;
                        });
                    }
                }
            });
        </script>
    </body>
</html>

Once the items are loaded into the drop-down, I need to modify the selected item like this:

vm.input.selected = 2;

However, this change is not taking place after the ajax request. If I include the array before the ajax call, it works as expected. But I specifically require the data from an ajax request. To simplify things for better understanding, I have reduced the complexity of the code.

You can also check out the jsfiddle link for this issue. It appears that the problem lies within the vue component implementation.

Answer №1

After conducting a few tests, it appears that the issue arises from changing the select2's value prior to updating its options. Consequently, when attempting to change to option 2, which doesn't exist, the modification fails to take effect.

As mentioned in my earlier comment, rearranging the order of options and value within the component's watch resolves this issue. This is likely because by adjusting the sequence, the options are updated right before the new value is assigned.

To illustrate, refer to the following functional example:

Vue.component('select2', {
  props: ['options', 'value'],
  template: '#select2-template',
  mounted: function() {
    var vm = this;
    $(this.$el)
      // initialize select2
      .select2({
        data: this.options
      })
      .val(this.value)
      .trigger('change')
      // emit event upon change.
      .on('change', function() {
        vm.$emit('input', this.value)
      });
  },
  watch: {
    options: function(options) {
      // update options
      $(this.$el).empty().select2({
        data: options
      })
    },
    value: function(value) {
      // update value
      $(this.$el)
        .val(value)
        .trigger('change')
    }
  },
  destroyed: function() {
    $(this.$el).off().select2('destroy')
  }
})

var vm = new Vue({
  el: '#el',
  template: '#demo-template',
  data: {
    input: {
      selected: "all"
    },
    options: []
  },
  created: function() {
    this.mymethod();
  },
  methods: {
    mymethod: function() {
      var vm = this;
      $.get("https://api.coindesk.com/v1/bpi/currentprice.json", function(data) {
        vm.options = [{
            id: 'all',
            text: 'All'
          },
          {
            id: 1,
            text: 'Hello'
          },
          {
            id: 2,
            text: 'World'
          },
          {
            id: 3,
            text: 'Bye'
          }
        ];
        vm.input.selected = 2;
        //      setTimeout(() =>  { vm.input.selected = 2; }, 0);
      });
    }
  }
});
html,
body {
  font: 13px/18px sans-serif;
}

select {
  min-width: 300px;
}
<script type="text/javascript" src="https://code.jquery.com/jquery-3.3.1.js"></script>
<script type="text/javascript" src="https://unpkg.com/<a href="/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="dbadaebe9be9f5eef5eaec">[email protected]</a>/dist/vue.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.0/js/select2.min.js"></script>
<script type="text/javascript" src="https://unpkg.com/axios/dist/axios.min.js"></script>

<div id="el"></div>

<!-- using string template here to work around HTML <option> placement restriction -->
<script type="text/x-template" id="demo-template">
  <div>
    <p>Selected: {{ input.selected }}</p>
    <select2 :options="options" v-model="input.selected">
      <option disabled value="0">Select one</option>
    </select2>
  </div>
</script>

<script type="text/x-template" id="select2-template">
  <select>
    <slot></slot>
  </select>
</script>

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

Utilizing multiple AJAX requests to a single PHP script

Despite searching through other topics, I couldn't find a solution to my issue. I have two ajax calls that both target the same page. One is meant to delete language selection and the other is meant to delete education experience. Oddly enough, the l ...

Is there a way to include a lockfile in a docker container as an optional step?

I am attempting to create a docker image that can optionally incorporate a yarn or npm lockfile during the build process. I want to include it explicitly, but also ensure that the build does not fail if the lockfile is missing. The goal is to respect dete ...

How come my AJAX request is only saving the last set of values in a continuous loop?

function saveangebotdetailfunc(url, GewerkFertig1, AngebotnrFertig1, PreisFertig1, WerkvertragID1, DatumFertig1) { $.ajax({ type: 'POST', url: url, data: { csrfmiddlewaretoken: &ap ...

Using PHP functions in an AJAX request

I am currently attempting to execute a php loop upon clicking a radio button. I understand that ajax is necessary for this task, but as a beginner in ajax, I am struggling to achieve the desired result. Presently, I am unable to click the radio button at a ...

Retrieves MySQL SQL findings and converts them into a JSON structure

I'm in the process of integrating Typeahead.js into my website. The Typeahead.js plugin will retrieve data from a remote page that returns JSON, similar to: http://example.org/search?q=%QUERY Here's the PHP code I've written for my site: ...

What is the best way to ensure that this JavaScript code functions properly when dealing with business operating hours

Using this javascript code allows me to check if a business is open based on its operating hours. It's effective for times like 17:00-23:00, but how can I modify it to work for hours past midnight, such as 0:30 or 1:00 in the morning? var d = new D ...

The second pop-up modal fails to appear

I have successfully implemented 2 modal windows with the help of bootstrap. The first modal is used for adding a user to the database, and the second one is meant for editing an existing user. While the first modal works perfectly fine, the editing modal d ...

Is it possible to switch the hamburger menu button to an X icon upon clicking in Vue 3 with the help of PrimeVue?

When the Menubar component is used, the hamburger menu automatically appears when resizing the browser window. However, I want to change the icon from pi-bars to pi-times when that button is clicked. Is there a way to achieve this? I am uncertain of how t ...

Enhance your MongoDB with the power of JQuery and ExpressJS combined with the magic

I've successfully implemented a delete function using type: 'DELETE', and now I'm attempting to create an UPDATE function. However, I'm unsure if I'm approaching this correctly. Here's the code I've written so far: ...

Responsive div that reacts to scrolling

I am looking for a div that can dynamically change its position as I scroll up or down the page. For example, it could start 30px from the top but then move to 100px as I scroll down further. This div will be located on the right-hand side of my page, clo ...

Decipher the communications sent by the server

I have been working on a hybrid application using vuejs and ruby on rails, and I am trying to figure out how to translate the error messages that are generated by the server. While I have managed to translate the titles easily with a method, I am strugglin ...

Retrieve information from a sensor within an Express server and display it on the user interface

Looking for suggestions on resolving a challenge: I have a Node.js module that retrieves data from a sensor, and I am interested in incorporating a UI element to showcase the sensor data (either in real-time or pseudo-realtime). Is there a way to establ ...

Show a variety of randomly selected pictures from various sources using the command image/next

I'm in the process of building a basic news aggregation website using Next.js. I’ve run into an issue where I need to include specific domains in my next.config file for the Image component to work properly. The problem is, the URLs for the images o ...

PHP code not redirecting page properly

I have successfully transferred values from one page to another using ajax's POST request method. However, I want to set a condition where if someone tries to access the URL directly, they should be redirected to a different page. The issue is that th ...

Comparison between Static Array, MySQL with PHP, and XML file for updating data using AJAX

I am tasked with managing five elements, each of which has 5 distinct colors. My goal is to retrieve pictures that match these specific colors. For example: Boot [Color1,Color2,Color3,Color5] Shoes [Color1,Color2,Color3,Color5] The first element present ...

Utilize client-side script in nodejs to share module functionalities

I created a function within the user controller module to verify if a user is logged in on the site: exports.isLoggedIn = function(req, res, next) { if (req.user) { return true; } else { return false; } }; I'm unsure of h ...

Can two controllers be used for the main-app and sub-app with the same URL using angular ui-route?

I have implemented two controllers, 'BaseController' and 'SubController', for my main application and sub-application. Both controllers are configured to point to an empty URL. Below is the configuration for the main application:- ang ...

The absence of defined exports in TypeScript has presented a challenge, despite attempting various improvement methods

I've exhausted all available resources on the web regarding the TypeScript export issues, but none seem to resolve the problem. Watching a tutorial on YouTube, the presenter faced no such obstacles as I am encountering now. After updating the tsconf ...

Tips on Enhancing a Fetch Query in Laravel with the Help of Ajax

I am encountering difficulty fetching a list of cities with over 40,000 entries. The main issue is the lack of optimization as my browser becomes unresponsive while loading the city data. Within my Laravel Controller, the code snippet below showcases how I ...

Is it possible to use AJAX to change the class name of a Font Awesome icon?

I am considering updating the icon after deleting a row. Should I initially include the font awesome icon once in the blade, then remove the class name and add it back with ajax? blade: <div id="status-{{ $country->id }}"> <div id ...