Jak zapobiec przesyłaniu formularza?

243

Mam formularz, w którym jest gdzieś przycisk przesyłania.

Chciałbym jednak jakoś „złapać” zdarzenie przesyłania i zapobiec jego wystąpieniu.

Czy jest jakiś sposób, aby to zrobić?

Nie mogę zmodyfikować przycisku przesyłania, ponieważ jest to część niestandardowej kontroli.

Nathan Osman
źródło
Nadal możesz uzyskać dostęp do przycisku przesyłania. Renderuj stronę i pobierz jej identyfikator klienta, wyświetlając źródło strony. Następnie, używając czegoś takiego jak jQuery, możesz zrobić coś takiego jak $ ('# ctl01_cph01_controlBtn1'). Click (function () {return false;});
rebeliant
@Rafael: To prawda ... ale to byłaby ostateczność - to bardzo skomplikowana kontrola.
Nathan Osman,
@ Raf, który jest oparty na asp.net, a także nie jest najlepszą praktyką. Ale to w zasadzie poprawne. Po prostu unikałbym podglądania źródła i używania nazwy kontrolnej, ponieważ może się to zmienić, jeśli ktoś edytuje stronę. Niezamierzone skutki uboczne i takie.

Odpowiedzi:

260

W przeciwieństwie do innych odpowiedzi, zwrot falsejest tylko częścią odpowiedzi. Rozważ scenariusz, w którym występuje błąd JS przed instrukcją return ...

HTML

<form onsubmit="return mySubmitFunction(event)">
  ...
</form>

scenariusz

function mySubmitFunction()
{
  someBug()
  return false;
}

powrót falsetutaj nie zostanie wykonany, a formularz zostanie przesłany w obu przypadkach. Powinieneś także zadzwonić, preventDefaultaby zapobiec domyślnej akcji formularza dla formularzy Ajax.

function mySubmitFunction(e) {
  e.preventDefault();
  someBug();
  return false;
}

W takim przypadku nawet w przypadku błędu formularz nie zostanie przesłany!

Alternatywnie można zastosować try...catchblok.

function mySubmit(e) { 
  e.preventDefault(); 
  try {
   someBug();
  } catch (e) {
   throw new Error(e.message);
  }
  return false;
}
Ben Rowe
źródło
4
Dlaczego nie wrócić falsebezpośrednio z onsumbit?
ProfK
1
Możesz chcieć pokazać użytkownikowi komunikat o błędzie w przesłanym formularzu. Na przykład: „wypełnij to obowiązkowe pole, a następnie prześlij”. W takim przypadku event.preventDefault przyda się bardzo
Mark Chorley
1
@ProfK, jeśli używasz event.preventDefault (), nie ma to znaczenia, niezależnie od tego, try / catch będzie po prostu częścią twojej obsługi błędów
Ben Rowe
11
<form onsubmit = "return mySubmitFunction (event)"> działał ... musiał użyć słowa event w nawiasach w
firefoxie
5
@BenRowe Powinieneś dodać parametr evt do wywoływanej metody. (<form onsubmit="return mySubmitFunction(evt)">).W przeciwnym razie pojawia się niezdefiniowany błąd.
UfukSURMEN
143

Możesz użyć onsubmittakiego zdarzenia inline

<form onsubmit="alert('stop submit'); return false;" >

Lub

<script>
   function toSubmit(){
      alert('I will not submit');
      return false;
   }
</script>

<form onsubmit="return toSubmit();" >

Próbny

To może nie być dobry pomysł przy tworzeniu dużych projektów. Może być konieczne użycie Detektorów zdarzeń.

Proszę przeczytać więcej o Inline Events vs Event Listeners (addEventListener i IE's attachEvent) tutaj . Bo nie potrafię tego wyjaśnić bardziej niż Chris Baker .

Oba są poprawne, ale żadne z nich nie jest „najlepsze” per se, i może istnieć powód, dla którego deweloper zdecydował się na oba podejścia.

Reigel
źródło
Ładne, szybkie rozwiązanie na drodze.
Fernando Torres,
z jakiegoś powodu <form onsubmit="return false;" >nie działa dla mnie.
Ruan
102

Dołącz detektor zdarzeń do formularza za pomocą, .addEventListener()a następnie wywołaj .preventDefault()metodę event:

const element = document.querySelector('form');
element.addEventListener('submit', event => {
  event.preventDefault();
  // actual logic, e.g. validate the form
  console.log('Form submission cancelled.');
});
<form>
  <button type="submit">Submit</button>
</form>

Myślę, że jest to lepsze rozwiązanie niż zdefiniowanie submitprocedury obsługi zdarzeń zgodnej z onsubmitatrybutem, ponieważ oddziela ona logikę i strukturę strony. Znacznie łatwiej jest utrzymać projekt, w którym logika jest oddzielona od HTML. Zobacz: dyskretny JavaScript .

Korzystanie z .onsubmitwłaściwości formobiektu DOM nie jest dobrym pomysłem, ponieważ uniemożliwia dołączenie wielu wywołań zwrotnych do jednego elementu. Zobacz addEventListener vs onclick .

Michał Perłakowski
źródło
1
i dla jquery: $("button").click(function(e) { e.preventDefault() });
Nixen85
2
+1 nie wiem, dlaczego wszystkie pozostałe odpowiedzi nadal korzystają z wbudowanych podań, ponieważ OP wspomniał, że nie może zmienić przycisku (co oznacza, że ​​prawdopodobnie nie może zmienić formy). Zastanawiasz się, czy istnieje sposób na uzyskanie „formy”, jeśli mamy identyfikator przycisku
Robert Sinclair
16

Spróbuj tego...

Kod HTML

<form class="submit">
    <input type="text" name="text1"/>
    <input type="text" name="text2"/>
    <input type="submit" name="Submit" value="submit"/>
</form>

Kod jQuery

$(function(){
    $('.submit').on('submit', function(event){
        event.preventDefault();
        alert("Form Submission stopped.");
    });
});

lub

$(function(){
    $('.submit').on('submit', function(event){
       event.preventDefault();
       event.stopPropagation();
       alert("Form Submission prevented / stopped.");
    });
});
Sach
źródło
18
W tym pytaniu nie ma tagu jQuery.
Michał Perłakowski,
6
@Gothdo, a jednak rozwiązanie jest nadal takie samo. szalony prawda?
Kevin B
7
@Gothdo tak, jest dokładnie tak samo. eventObject.preventDefault. Sposób powiązania modułu obsługi nie zmienia rozwiązania. Twierdziłbym nawet, że twoja odpowiedź nie różni się od przyjętej.
Kevin B
stopPropagationbyła jedyną rzeczą, która działała w moim przypadku. dzięki! :)
cregox,
13

Następujące działa teraz (testowane w chrome i Firefox):

<form onsubmit="event.preventDefault(); return validateMyForm();">

gdzie validateMyForm () to funkcja zwracana w falseprzypadku niepowodzenia sprawdzania poprawności. Kluczową kwestią jest użycie nazwy event. Nie możemy używać do npe.preventDefault()

Vikram Pudi
źródło
1
onsubmit = "return validateMyForm ();" wystarczy, ale validateMyForm () powinien zwrócić true lub false.
Adrian P.
8
var form = document.getElementById("idOfForm");
form.onsubmit = function() {
  return false;
}
naikus
źródło
2
Myślę, że używanie .onsubmitjest złym pomysłem, ponieważ uniemożliwia dołączenie wielu submitwywołań zwrotnych do jednego elementu. Polecam używać .addEventListener().
Michał Perłakowski,
3
Nawet jeśli ustawiłeś moduł obsługi zdarzeń za pomocą właściwości .onsubmit, nadal możesz dodać dodatkowe moduły obsługi za pomocą metody .addEventListener (). Program obsługi zarejestrowany przez właściwość zostanie najpierw wywołany, a następnie zarejestrowany w .addEventListener () w kolejności, w jakiej zostały zarejestrowane.
Daniel Granger
2

Aby postępować zgodnie z dyskretnymi konwencjami programowania JavaScript i w zależności od tego, jak szybko DOM się ładuje, dobrym pomysłem może być skorzystanie z następujących opcji:

<form onsubmit="return false;"></form>

Następnie połącz zdarzenia za pomocą onload lub DOM ready, jeśli korzystasz z biblioteki.

$(function() {
    var $form = $('#my-form');
    $form.removeAttr('onsubmit');
    $form.submit(function(ev) {
        // quick validation example...
        $form.children('input[type="text"]').each(function(){
            if($(this).val().length == 0) {
                alert('You are missing a field');
                ev.preventDefault();
            }
        });
    });
});
label {
    display: block;
}

#my-form > input[type="text"] {
    background: cyan;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<form id="my-form" action="http://google.com" method="GET" onsubmit="return false;">
    <label>Your first name</label>
    <input type="text" name="first-name"/>
    <label>Your last name</label>
    <input type="text" name="last-name" /> <br />
    <input type="submit" />
</form>

Ponadto zawsze używałbym tego actionatrybutu, ponieważ niektóre osoby mogą mieć uruchomioną wtyczkę typu NoScript, która wtedy przerwałaby sprawdzanie poprawności. Jeśli używasz atrybutu akcji, przynajmniej użytkownik zostanie przekierowany przez serwer na podstawie sprawdzania poprawności wewnętrznej bazy danych. window.locationZ drugiej strony, jeśli używasz czegoś takiego , będzie źle.

Sebastian Palma
źródło
2

Aby zapobiec przesłaniu formularza, wystarczy to zrobić.

<form onsubmit="event.preventDefault()">
    .....
</form>

Użycie powyższego kodu zapobiegnie przesłaniu formularza.

Zuhair Taha
źródło
0

Oto moja odpowiedź:

<form onsubmit="event.preventDefault();searchOrder(event);">
...
</form>
<script>
const searchOrder = e => {
    e.preventDefault();
    const name = e.target.name.value;
    renderSearching();

    return false;
}
</script>

Dodam event.preventDefault();na onsubmiti to działa.

yozawiratama
źródło
0

Możesz dodać eventListner do formularza, który preventDefault()i przekonwertować dane formularza do JSON, jak poniżej:

const formToJSON = elements => [].reduce.call(elements, (data, element) => {
  data[element.name] = element.value;
  return data;

}, {});

const handleFormSubmit = event => {
    event.preventDefault();
    const data = formToJSON(form.elements);
    console.log(data);
  //  const odata = JSON.stringify(data, null, "  ");
  const jdata = JSON.stringify(data);
    console.log(jdata);

    (async () => {
      const rawResponse = await fetch('/', {
        method: 'POST',
        headers: {
          'Accept': 'application/json',
          'Content-Type': 'application/json'
        },
        body: jdata
      });
      const content = await rawResponse.json();

      console.log(content);
    })();
};

const form = document.forms['myForm']; 
form.addEventListener('submit', handleFormSubmit);
<form id="myForm" action="/" method="post" accept-charset="utf-8">
    <label>Checkbox:
        <input type="checkbox" name="checkbox" value="on">
    </label><br /><br />

    <label>Number:
        <input name="number" type="number" value="123" />
    </label><br /><br />

    <label>Password:
        <input name="password" type="password" />
    </label>
    <br /><br />

    <label for="radio">Type:
        <label for="a">A
            <input type="radio" name="radio" id="a" value="a" />
        </label>
        <label for="b">B
            <input type="radio" name="radio" id="b" value="b" checked />
        </label>
        <label for="c">C
            <input type="radio" name="radio" id="c" value="c" />
        </label>
    </label>
    <br /><br />

    <label>Textarea:
        <textarea name="text_area" rows="10" cols="50">Write something here.</textarea>
    </label>
    <br /><br />

    <label>Select:
        <select name="select">
            <option value="a">Value A</option>
            <option value="b" selected>Value B</option>
            <option value="c">Value C</option>
        </select>
    </label>
    <br /><br />

    <label>Submit:
        <input type="submit" value="Login">
    </label>
    <br /><br />


</form>

Hasan A Yousef
źródło