You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为jQuery插件实现可配置选项功能的技术求助

解决jQuery货币转换插件配置不生效的问题

问题根源

你的代码里存在几个关键问题导致配置无法生效:

  • 插件初始化方式错误,直接修改defaults的调用写法不对
  • 硬编码覆盖了配置值(比如手动写死了values数组)
  • 插件方法仅合并了配置但没有将合并后的配置应用到实际逻辑中
  • 存在语法错误(比如MutationObserver部分的注释写法破坏了代码结构)

修复后的完整代码

$(document).ready(function() {
  // 定义插件方法,处理配置合并并应用
  $.fn.tsCurrOptions = function(options) {
    // 合并默认配置与用户配置,并更新全局defaults
    $.fn.tsCurrOptions.defaults = $.extend({}, $.fn.tsCurrOptions.defaults, options);
    // 初始化插件逻辑
    initCurrencyConverter();
  };

  // 默认配置
  $.fn.tsCurrOptions.defaults = {
    AvailableCurrencies: ["GBP", "USD", "EUR", "AUD"],
    BaseCurrency: "GBP",
    DecimalPrecision: 2
  };

  // 核心初始化逻辑
  function initCurrencyConverter() {
    const settings = $.fn.tsCurrOptions.defaults;
    const valuesCurr = settings.AvailableCurrencies;
    const baseCurr = settings.BaseCurrency;
    const deciP = settings.DecimalPrecision;

    // 添加转换容器
    $(".product-price").after('<div class="ts-currency-converter"></div>');

    // 创建货币选择下拉框
    const select = $('<select>').prop('id', 'currency').prop('name', 'currency');
    $(valuesCurr).each(function() {
      select.append($("<option>").prop('value', this).text(this.charAt(0).toUpperCase() + this.slice(1)));
    });

    const label = $("<label>").prop('for', 'currency').text("");
    const br = $("<br>");
    $('.header-display-desktop').before(label).before(select).before(br);

    let resultCurr;

    // 设置货币转换基础
    fx.base = baseCurr;
    fx.settings = { from: fx.base };

    // 初始化本地存储
    const currencylocalStorage = localStorage.getItem('Currency');
    if (!currencylocalStorage) {
      localStorage.Currency = fx.base;
    }

    // 获取汇率数据
    $.getJSON('https://api.exchangerate-api.com/v4/latest/USD', function(data) {
      if (typeof fx !== "undefined" && fx.rates) {
        fx.rates = data.rates;
        fx.base = data.base;
      } else {
        window.fxSetup = { rates: data.rates, base: data.base };
      }

      // 提取纯文本方法
      $.fn.justtext = function() {
        return $(this).clone().children().remove().end().text();
      };

      // 价格更新逻辑
      $.fn.hentryGrid = function() {
        const localCurr = localStorage.getItem('Currency');
        $('.hentry').each(function() {
          const self = $(this);
          const hasSale = $(this).find('.product-price').children().length > 0;

          if (hasSale) {
            const saleOriginalPrice = self.find('.original-price').text().replace(/[^\d.]/g, '');
            const salePrice = $(this).find('.product-price').justtext().replace(/[^\d.]/g, '');
            
            const saleupdateCurr = fx.convert(salePrice, { to: localCurr });
            const saleTsUpdateCurr = accounting.formatMoney(saleupdateCurr, "", deciP, ",", ".");
            
            const saleOrigina1updateCurr = fx.convert(saleOriginalPrice, { to: localCurr });
            const saleOrigina1TsUpdateCurr = accounting.formatMoney(saleOrigina1updateCurr, "", deciP, ",", ".");
            
            self.find(".ts-currency-converter").html(`
              <div class="ts-price">
                <span class="ts-orignal-price">${localCurr} ${saleOrigina1TsUpdateCurr}</span>
                <span class="ts-sale-price">${localCurr} ${saleTsUpdateCurr}</span>
              </div>
            `);
          } else {
            const myTextSub = self.find('.product-price').text();
            const priceTxt = myTextSub.replace(/[^a-z]/gi, '');
            const localamount = myTextSub.replace(/[^\d.]/g, '');
            
            const localupdateCurr = fx.convert(localamount, { to: localCurr });
            const formattedPrice = accounting.formatMoney(localupdateCurr, "", deciP, ",", ".");
            
            self.find(".ts-currency-converter").html(`
              <div class="ts-price">${priceTxt} ${localCurr} ${formattedPrice}</div>
            `);
          }
        });
      };

      // 页面加载时更新价格
      const localCurr = localStorage.getItem('Currency');
      $("select#currency").val(localCurr);
      $.fn.hentryGrid();

      // 切换货币时更新
      $('#currency').on('change', function() {
        resultCurr = this.value;
        localStorage.Currency = resultCurr;
        $.fn.hentryGrid();
      });

      // 变体更新监听
      $('.variant-select-wrapper').on('data-attribute-changed', function() {
        const data = $('#contains-data').data('text');
        alert('Data changed to: ' + data);
      });

      // MutationObserver监听变体变化
      const targetNode = document.querySelector('.variant-select-wrapper');
      const config = { attributes: true, childList: true, subtree: true };
      const callback = (mutationList) => {
        for (const mutation of mutationList) {
          if (mutation.type === 'attributes') {
            $.fn.hentryGrid();
          }
        }
      };
      const observer = new MutationObserver(callback);
      observer.observe(targetNode, config);
    });
  }

  // 正确调用插件,传入用户自定义配置
  $.fn.tsCurrOptions({
    AvailableCurrencies: ["GBP", "USD", "EUR", "AUD", "CAD"],
    BaseCurrency: "EUR",
    DecimalPrecision: 5
  });
});

关键修改说明

  1. 重构插件结构:将核心逻辑封装到initCurrencyConverter函数中,插件方法合并配置后自动调用初始化逻辑
  2. 修正配置应用:所有逻辑中使用合并后的settings变量,不再直接取defaults或硬编码值
  3. 修复初始化方式:用$.fn.tsCurrOptions({...})替代错误的$.fn.tsCurrOptions.defaults({...})调用
  4. 修复语法错误:修正MutationObserver部分的注释写法,避免破坏代码结构
  5. 优化模板字符串:用ES6模板字符串替代拼接,减少语法错误
  6. 统一精度配置:之前代码里有一处硬写的2,现在全部改用配置的deciP变量

内容的提问来源于stack exchange,提问作者Muhammad Waqas

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.10 06:30:51