IE отправляет внутренний HTML при нажатии на элемент кнопки - PullRequest
8 голосов
/ 18 декабря 2008

У меня на странице есть следующий html (упрощенно).

<button type="submit" name="action" value="ButtonA">Click Here</button>

В Firefox он представляет «ButtonA» как значение для значения формы «action». Тем не менее, в IE7, он отправляет «Нажмите здесь». Есть ли способ решить эту проблему? Я не хочу использовать входные теги, потому что мне нужно иметь возможность настраивать текст, не затрагивая значения, возвращаемые обратно в форму (локализация). По сути, я хочу иметь возможность иметь несколько кнопок с одинаковым именем и, в зависимости от их значения, выполнять разные действия при отправке. Легко ли заставить IE действовать правильно в этом случае?

[MORE]

Может быть, я должен быть более ясным, но я не могу использовать

<input type="submit" name="Action" value="ButtonA">

потому что мне нужно иметь возможность изменять текст, отображаемый для правил локализации, без влияния на фактическое значение кнопки, отправляемой вместе с формой.

[MORE]

Для уточнения, в основном, я хочу, чтобы кнопка могла произносить «Сохранить» или «Sauver» в зависимости от языка, но не иметь значения, переданного на сервер, для изменения. Я также хочу иметь несколько кнопок с одинаковым именем и, в зависимости от значения, делать что-то, а не в зависимости от имени кнопки, и проверять, есть ли значение для этой кнопки. Код уже написан с этой точки зрения, и я просто хочу иметь возможность изменять отображаемый текст в значениях без существующего кода обработки на стороне сервера.

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

Ответы [ 12 ]

3 голосов
/ 18 декабря 2008

Одним из решений является использование Javascript и скрытого поля

   <input type="hidden" name="actionparam" value="DoNothing">
   <input type="button" onclick="OnSubmitForm('ActionA')" Value="Click Here for A" />
   <input type="button" onclick="OnSubmitForm('ActionB')" Value="Click Here for B" />


   function OnSubmitForm(actionname) {
    var f = document.frm;
    f.actionparam.value = actionname;
    f.submit();
 }

Это также работает как скрытая CATPCHA, и вы можете добавить некоторую проверку клиента в функцию javascript

Edit:

Поскольку вы говорите, что хотите перейти на браузеры, не поддерживающие JavaScript, вы можете использовать эту версию, которая разрешает только одно действие по умолчанию людям, не имеющим JavaScript

Дополнительные кнопки отключены в HTML, но затем снова включены с помощью JavaScript.
Протестированный код:

<html>
<head>
    <script type="text/javascript">
    <!--
    function OnSubmitForm(actionname) {
            var f = document.frm;
            f.actionparam.value = actionname;
            f.submit();
    }
    //-->
    </SCRIPT>
</head>
<body>
   <noscript>
        <div style="background-color: yellow; margin: 20px;" >
            You are using a limited version of the site because you don't have Javascript enabled
        </div>
    </noscript>


   <h1>form</h1>
    <form name="frm" method="post">
    <input type="hidden" name="actionparam" value="DefaultAction" />
    <button name="defaultbutton" type="submit">default action</button>
    <button name="extrabutton1" disabled onclick="OnSubmitForm('ExtraAction1')">Extra action 1</button>
    <button name="extrabutton2" disabled onclick="OnSubmitForm('ExtraAction2')">Extra action 2</button>
    </form>


   <h1>Results</h1>
   <h2>forms collection</h2>
   <ol>
   <%
   For x = 1 To Request.Form.count()
      Response.Write("<li>" + Request.Form.key(x) + "=" + Request.Form.item(x) + "</li>")
   Next
   %>
   </ol>


    <script type="text/javascript">
    <!--
    document.frm.extrabutton1.disabled = false;
    document.frm.extrabutton2.disabled = false;
    //-->
    </SCRIPT>

</body>
</html>
2 голосов
/ 17 июня 2009

Просто пришлось иметь дело с замечательной реализацией IE6 элементов button. Это решение опирается на Javascript, но некоторые могут найти его полезным.

Это особенно раздражает при использовании AbstractWizardController в среде Spring, поскольку элемент button является идеальным решением для кнопок «Далее», «Назад» и «Готово» мастера, но не работает в IE6.

Итак, я написал небольшое исправление на основе jQuery (хотя его довольно просто преобразовать, чтобы вам не приходилось использовать библиотеку jQuery).

$(function(){
if((window.XMLHttpRequest == undefined) && (ActiveXObject != undefined)) {
    $('button').click( function(event) {
        var rx = /\bvalue ?= ?(".*?"|'.*?')/i;
        var matches = $(this)[0].outerHTML.match( rx );
        if( matches != null )
            $(this).attr( 'value', matches[1].substring( 1, matches[1].length - 1 ) );
        $('button').not( $(this) ).attr('disabled','disabled');
    });
}
}); 

Это добавит событие onclick ко всем элементам кнопки. Когда кнопка нажата, она будет захватывать внешний HTML кнопки, например ::

<button name="playerId" value="34">Walter Payton</button>

и разобрать атрибут значения. Кажется, для получения значения нужно много усилий, но я обнаружил, что getAttributeNode('value').value вернул innerHTML, а не указанный атрибут значения, так что это не очень помогло. Затем мы устанавливаем субматч регулярного выражения в качестве значения кнопки. Он должен совпадать, если вы используете двойные или одинарные кавычки в качестве разделителей, но вам нужно использовать некоторую форму разделителя .

Результатом этого является то, что вместо публикации "Уолтер Пэйтон" вместо этого будет фактически опубликовано "34". Недостатком является то, что внешний вид кнопки на странице также изменится на «34» непосредственно перед отправкой формы.

Наконец, скрипт найдет все элементы кнопки, кроме одного, по которому щелкнули, и установит их атрибут disabled для отключения. Это гарантирует, что они не включены в POST, и вы не получите ложных срабатываний.

2 голосов
/ 20 декабря 2008

Обычный обходной путь, чтобы заставить его работать с вводом-отправкой, состоит в том, чтобы преобразовать значение в несколько атрибутов 'name', например ::

<input type="submit" name="submit.buttonA" value="Sausage" />
<input type="submit" name="submit.buttonB" value="Mash" />

Слой формы, который я лично использую, автоматически преобразует его так, как если бы был нажат элемент управления «submit» со значением «buttonA» или «buttonB», но в большинстве сред его легко сделать вручную.

1 голос
/ 19 декабря 2008

Ссылка , которую вы указали в вопросе , объясняет, что IE6 отправляет все кнопки при каждой отправке формы, поэтому ваше приложение не будет работать с IE6 независимо от того, какой обходной путь вы используете. Я проверил это и убедился, что IE6 действительно делает это. Это означает, что без Javascript тег , но я не могу рекомендовать, поскольку ссылки всегда являются запросами GET, а запросы GET никогда не должны иметь побочных эффектов, таких как изменение данных.

<div style="float:left">
  <form name="shoppingCart" action="#c" method="GET">
    <input type="hidden" name="item1" value="hat">
    <input type="text" name="item1quantity" value="1"> Hat, red<br>
    <input type="hidden" name="item2" value="scarf">
    <input type="text" name="item2quantity" value="1"> Scarf, red<br>
    <button type="submit" name="button" value="purchase">Buy now!</button>
  </form>  
</div>
<div style="float:right">
  <form name="remove" action="#a" method="GET">
    <input type="hidden" name="item" value="item1">
    <button type="submit" name="button" value="delete1">Remove this item</button>
  </form>
  <form name="remove" action="#b" method="GET">
    <input type="hidden" name="item" value="item2">
    <button type="submit" name="button" value="delete2">Remove this item</button>
  </form>
</div>

Недостатком использования нескольких форм является то, что вы ограничены в том, что вы можете передавать; если пользователь изменит количество в вышеуказанной форме, эта информация не будет отправлена, когда пользователь нажмет кнопку «удалить». Но вы могли бы рассмотреть эту изящную деградацию для пользователей, не являющихся JS, и использовать JS для синхронизации данных в основной форме со скрытыми формами.

1 голос
/ 19 декабря 2008

Хорошие новости: Microsoft исправила это в IE8 (только в стандартном режиме)

Плохие новости: он все еще в бета-версии

Это исправление jQuery работает нормально, или вы можете взломать свой собственный JS для обработки IE.

Что касается тех, кто предлагает ввод поверх кнопки, то это хорошо, но если вам нужна графика или другие стили на вашей кнопке, то кнопка - единственный путь.

1 голос
/ 18 декабря 2008

Я думаю, что вы должны пересмотреть всю эту концепцию. У меня такое чувство, что твой сценарий выглядит примерно так:

  • Пользователь нажимает Сохранить или Отменить
  • На стороне сервера, вы проверяете значение "Сохранить" или "Отмена"
  • Вы выполняете действия, основанные на этом

В действительности не должно иметь значения значение кнопки «Сохранить». В PHP, например, вы можете просто проверить значение a в элементе Save. Независимо от значения «Сохранить» или «Sauver», вы можете выполнять функцию сохранения.

Я прошу прощения, если я далеко от базы здесь. Дайте мне знать, если мои предположения верны.

1 голос
/ 18 декабря 2008

Как упоминает Эдуардо, JavaScript звучит как ваш лучший вариант. Однако вам нужно как-то учитывать тот факт, что если у пользователя отключен JavaScript, вы не получите соответствующее значение.

0 голосов
/ 13 февраля 2012

Простой обходной путь без использования JavaScript:

<button type="submit" name="action" value="ButtonA" onclick="this.value='ButtonA'">Click Here</button>
0 голосов
/ 03 сентября 2009

Проверьте этот ie-button-fix проект, который использует поведение IE (т.е. javascript) для аккуратного решения проблемы.

0 голосов
/ 19 декабря 2008

Я не знаю ни одного способа заставить его работать в IE7 (или IE6) без необходимости JavaScript (или странных мультиформных конструкций).

Разве это не доступно как-то локализованному для серверной части? Скажем, текст поступает из базы данных или это просто встроено в локальные шаблоны или около того? Вы должны быть в состоянии получить локализованную версию этикетки как при печати, так и при проверке формы на внутреннем сервере, не так ли (насколько вы предпочитаете просто использовать неизменное значение, как вы действительно сможете делаем)

Всегда есть решение JavaScript ...

Следующее является скорее проверкой концепции, которая потребует некоторой настройки, чем готовый однострочный jQuery, но он должен работать без необходимости изменения какого-либо HTML:

<!doctype html>
<html>

<head>

<title>Fix Buttons in IE6</title>

<script type="text/javascript">
function fixButtons() {
    var btns = document.getElementsByTagName('button');

    for (var i = 0; i < btns.length; i++) {
        btns[i].onclick = fixValue;
    }
}

function fixValue() {
    var btns = document.getElementsByTagName('button');

    for (var j = 0; j < btns.length; j++) {
        if (this == btns[j]) {
            this.value = this.getAttributeNode('value').value;
        }
        else {
            btns[j].parentNode.removeChild(btns[j--]);
        }
    }
}
</script>

</head>

<body onload="fixButtons()">

<form action="" method="get">
    <button type="submit" name="action1" value="value1">Do Action 1</button>
    <button type="submit" name="action2" value="value2">Do Action 2a</button>
    <button type="submit" name="action2" value="value3">Do Action 2b</button>
</form>

</body>

</html>

Если он должен работать только в IE7, а не в IE6, функция fiXValue() может быть уменьшена до:

this.value = this.getAttributeNode('value').value
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...