Ошибка JavaScript в IE Использование библиотеки прототипов в Rails - PullRequest
0 голосов
/ 02 февраля 2010

Я запускаю приложение Rails и использую прототип. Скрипт ломается в IE, но работает во всех других браузерах. Я признателен за любую помощь в поиске решения этой проблемы.

Вот проблема:
Мои пользователи продают продукты и разновидности продуктов. Доступные варианты зависят от продукта. Например, если речь идет о фруктах, пользователь может выбрать продукт «Яблоко», тогда мне нужно показать ему сорта яблок на выбор, а не все сорта на всем сайте.

Я использую javascript, чтобы ограничить варианты раскрывающихся списков для разновидностей , чтобы они зависели от продукта, впервые выбранного из раскрывающегося списка. Таким образом, если пользователь выбирает продукт «яблоко», то список сортов динамически ограничивается только сортами яблок. Это прекрасно работает во всех браузерах, кроме, конечно, IE.

В IE, когда я выбираю продукт из выпадающего списка, скрипт завершается ошибкой, и появляется сообщение об ошибке «Объект не поддерживает это свойство или метод»

Я полагаю, что проблема и решение объяснены на следующей странице, если вы прокрутите вниз - раздел, помеченный как Native Extensions: http://prototypejs.org/learn/extensions

К сожалению, я не очень хорошо разбираюсь в javascript и не знаю точно, как решить проблему на практике, основываясь на пояснениях на странице прототипа.

Вот этот файл javascript:

var varieties = new Array();
<% for variety in @varieties -%>
  varieties.push (new Array (<%=h variety.product_id %>, "<%=h variety.name %>", <%=h variety.id %>));
<% end -%>


function collectionSelected(e) {
  product_id = e.getValue();
  options = e.next(1).options;
  options.length = 1;
  varieties.each(function(variety) {
    if (variety[0] == product_id) {
      options[options.length] = new Option(variety[1], variety[2]);
    }
  });
}

Любое руководство высоко ценится.

Обновление

Это HTML ...

Пользователи / edit.html.erb

<% javascript 'dynamic_varieties' %>
  <h2>Edit Your Profile</h2>
    <%= render :partial => 'form' %>  

Пользователи / _form.html.erb

<% form_for @user do |f| %>     
  <!-- This dynamically adds a new pair of dropdowns, i.e. product & variety -->
  <p class="addProduct"><%= add_season_link "+ Add another product" %></p> 

  <!-- This is where the product & variety dropdowns are rendered -->
  <div id="seasons">
<%= render :partial => 'season', :collection => @user.seasons %>
  </div>
<% end %>

Пользователи / _season.html.erb

  <div class="season">
<% new_or_existing = season.new_record? ? 'new' : 'existing' %>
<% prefix = "user[#{new_or_existing}_season_attributes][]" %>

<% fields_for prefix, season do |season_form| -%>
  <%= error_messages_for :season, :object => season %>
      <div class="eachMarketDrop">
          <p class="marketDrop">
            <!-- This is the product dropdown that triggers the dependent variety dropdown -->
            <label for = "user_product_id">Product:</label> <%= season_form.collection_select :product_id, Product.find(:all, :order =>'name'), :id, :name, {:prompt => "Select Product"}, {:onchange => "collectionSelected(this);"} %>
            <label for="user_variety_id">Variety:</label>
            <!-- This is the variety dropdown that is dependent on the product dropdown -->
            <% varieties = season.product ? season.product.varieties : Variety.all %>
            <%= season_form.select :variety_id, options_from_collection_for_select(varieties, :id, :name, season.variety_id), :prompt => "This is optional" %>
          </p>
      </div>
<% end -%>

Обновление № 2

Я установил Firebug Lite и подтвердил, что строка, выдающая ошибку в IE:

options = e.next(1).options;

Следующие варианты также выдают ту же ошибку:
options = $ (e) .next (1) .options
options = e.next ('select'). options;

Есть идеи?

Ответы [ 2 ]

0 голосов
/ 04 февраля 2010

Pullmonkey (http://www.pullmonkey.com/) на Rails Forum понял это. Теперь он отлично работает во всех браузерах.

Решение было изменить

{:onchange => "collectionSelected(this);"}   

до

{:onchange => "collectionSelected($(this));"} %>  

Друг объяснил это так:
«это» - смешное слово в JS - оно может означать много вещей. В исходном коде вашему методу collectionSelected передается само событие. С $ (this), метод collectionSelected передается элементу, который вызывает событие. Таким образом, в этом случае e.next () имеет смысл, b / c «e» - это подсказка продукта. В предыдущем случае, когда «e» было событием, e.next () ничего не значит!

0 голосов
/ 02 февраля 2010

У меня такое ощущение, что e.next(1) вызовет проблемы.

Вероятно, лучше четко указывать, что вы хотите, поскольку разные браузеры по-разному думают о том, что будет дальше в DOM в любой момент времени.

Попробуйте e.next('select') возможно?

Было бы проще ответить с помощью HTML.

...