Pete
Pete

Reputation: 58422

StopPropagation allowing click on parent

I have the following code where I have a label where I prevent the default action so that I can instead focus on the an editable span when it is clicked instead of an input. However, if the user clicks on the span, I want it to ignore the click event bound to the parent so I use stopPropagation.

However, it doesn't seem to work and the parent click event is still fired:

var $quantitySpan = $('.quantity-span'), 
    $quantityTextbox = $('.textbox'),
    $quantityHolder = $('.product-checkbox__quantity');

$quantitySpan
  .on('click', e => {
    e.stopPropagation();                        // I thought this would stop the bubbling up to the parents click event
    console.log('span clicked');
  })
  .on('keyup', () => {
    $quantityTextbox.val($quantitySpan.text());
  })
  .on('blur', () => {
    const textVal = $quantitySpan.text();
    if (isNaN(textVal) || textVal === '') {
      $quantitySpan.text("0");
      $quantityTextbox.val("0");
    }
  });

$quantityHolder.on('click', (e) => {
  e.preventDefault();
  console.log(e.target, e.currentTarget);                     // this seems to suggest that the target is the label that has been clicked allthough it changes the target to the input and not the span (even though I have prevented the default action of the label and stopped propagation on the span)
});
* {
  box-sizing: border-box;
}

.product-checkbox__quantity {
  display: block;
  padding-top: 1rem;
}

.product-checkbox__quantity-holder {
  margin-top: 0.5rem;
  display: flex;
  flex-direction: row;
  border: 1px solid #c6c6c6;
  background: #FFF;
  border-radius: 5px;
  padding: 1rem 1.25rem;
  width: 100%;
  overflow: hidden;
  position: relative;
}

.product-checkbox__quantity-holder .off-screen {
  position: fixed;
  left: 105%;
  top: 125%;
  border: 0;
  outline: 0;
}

.product-checkbox__quantity-holder .quantity-span {
  outline: none;
  flex-shrink: 1;
  padding-right: 0.5em;
  max-width: 80%;
  white-space: nowrap;
  overflow: hidden;
}

.product-checkbox__quantity-unit {
  flex-grow: 1;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<label class="product-checkbox__quantity">
  Quantity:
  <br>
  <span class="product-checkbox__quantity-holder">
            <input type="text" name="Quantities[VARIANT2]" autocomplete="off" class="product-checkbox__quantity-input textbox off-screen" id="quantity-variant2" value="0" data-unit="m2" data-rule-required="true" data-msg-required="required" data-rule-integer="true" data-msg-integer="Integers only"><span class="quantity-span" contenteditable="true">0</span>
  <span class="product-checkbox__quantity-unit">m<sup>2</sup></span>
  </span>
  <span class="field-validation-valid" data-valmsg-for="quantity-variant2" data-valmsg-replace="true"></span>
</label>

How do I change the above code so that when you click on the 0, it registers as a click on the span instead of on the label / input (or how do I see I have clicked the span in the label click event)

Weirdly, if you inspect the 0, it says that it is the span, so not sure why the target is changed to the input in the console.log

Upvotes: 3

Views: 54

Answers (1)

Nikola Andreev
Nikola Andreev

Reputation: 634

You also need to add preventDefault() together with stopPropagation().

$quantitySpan
  .on('click', e => {
    e.stopPropagation();
    e.preventDefault();                     
    console.log('span clicked');
  }) 

Upvotes: 1

Related Questions