让VueJS和jQuery玩得很好

时间:2017-04-05 20:13:43

标签: javascript jquery twitter-bootstrap vue.js vuejs2

这个问题与Using intl-tel-input and vuejs2 together有关/类似,但仍然没有答案。

VueJS Use prop as data-attribute value有一个解决方案,但有点解释“环境”。

因此,长话短说,我正在动态设置一个新的引导选项卡(标题和URL),然后尝试使用jQuery(重新)绑定某些功能。

在我的Vue方法中添加以下行https://github.com/thecodeassassin/bootstrap-remote-data/blob/master/js/bootstrap-remote-tabs.js#L258将应用该功能,但前提是我触发了两次更改。

与第一个(未答复的)问题相同的问题。

有人可以解释vueJSjQuery之间的工作原理吗?以及如何解决问题,希望无需重写jQuery包。

如果我console.log我的变量只是落后一步。

LE:

我为相关提到的问题准备了一支笔: https://codepen.io/AngelinCalu/pen/LWvwNq

2 个答案:

答案 0 :(得分:12)

让Vue与其他DOM操作工具包很好地配合的方法是完全隔离它们:如果你打算使用jQuery来操作DOM小部件,你也不会在它上面使用Vue(反之亦然)。

A wrapper component充当桥梁,其中Vue可以与组件交互,组件可以使用jQuery(或其他)操纵其内部DOM元素。

<{3}}之外的jQuery选择器是一个糟糕的代码味道。您的validatePhoneNumber使用了一个选择器和一个DOM操作调用,但您正在使用Vue来处理keydown个事件。您需要使用jQuery处理此小部件上的所有内容。不要使用Vue设置其类或phone_number或处理其事件。这些都是DOM操作。正如我所提到的,如果你将它包装在一个组件中,你可以将props传递给组件,你可以使用jQuery来设置class和phone_number。

答案 1 :(得分:2)

我认为其背后的原因是when the keydown event is fired,插件的内部工作方式启动并且不会立即暴露手机值。这导致竞争条件,您在插件本身内部更新电话号码之前过早地检索电话号码值

只需通过收听其他活动即可解决此问题,例如keyupinput

const app = new Vue({
  el: '#app',

  data: {
    phone_number: "",
    validPhone: false
  },


  methods: {
    validatePhoneNumber: function() {
      var phone_element = $('#phone');
      var validPhoneNo = phone_element.intlTelInput("isValidNumber");
      var phoneNo = phone_element.intlTelInput("getNumber");
      console.log(phoneNo + ' -> ' + validPhoneNo); // I am interested in both values
    }
  },


  mounted: function() {
    $('#phone').intlTelInput({
      utilsScript: "js/utils.js",
      initialCountry: "auto",
      geoIpLookup: function(callback) {
        $.get('https://ipinfo.io', function() {}, "jsonp").always(function(resp) {
          var countryCode = (resp && resp.country) ? resp.country : "";
          callback(countryCode);
        });
      },
      preferredCountries: []
    });
  }
});
<link href="https://cdnjs.cloudflare.com/ajax/libs/intl-tel-input/11.0.10/css/intlTelInput.css" rel="stylesheet" />
<link href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/4.0.0-alpha.6/css/bootstrap.min.css" rel="stylesheet" />

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.2.4/vue.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/intl-tel-input/11.0.10/js/utils.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/intl-tel-input/11.0.10/js/intlTelInput.min.js"></script>

<div id="app">
  <div class="row">
    <div class="col-sm-offset-2 col-sm-6">
      <input class="form-control" @input="validatePhoneNumber" :class="{validInput: validPhone }" name="phone" value="" ref="phone_element" :phone_number="phone_number" type="text" id="phone" />
    </div>
  </div>
</div>

我必须承认,这仍然不是理想的解决方案,因为可能仍然存在竞争条件。确保不存在竞争条件的唯一方法是在解析和验证电话号码后等待插件触发自定义回调,您可以在VueJS中的输入元素上侦听。现在我看到该插件只有一个自定义回调国家/地区。