jerrybendy / vue-touch-events

Support simple touch events (tap / swipe / touch hold)
MIT License
538 stars 51 forks source link

touchhold event is firing multiple times despite not touching button that initiated method #97

Open sts-ryan-holton opened 2 years ago

sts-ryan-holton commented 2 years ago

I've got this library integrated into my Nuxt JS project. I'd like to create a "peek" function that, when a user long-presses a button then some functionality is triggered. I've created a function called peek and have attached it onto 3 buttons, passing some text through each function.

My buttons aren't initially shown, they're inside a v-if as part of a "FAB" that I've created.

When I open the FAB using the main button, my peek function is running 3 times, when it shouldn't be running at all, and is then running 6 times when I tap on a button that has the function, this should be running once.

What am I missing, my structure for my HTML is:

<div class="tw-flex tw-fixed tw-bottom-0 tw-mb-6 has-safe-area--padding-bottom" :class="$store.state.storage.app_settings.refreshButtonPlacement == 'left' ? 'tw-left-0 tw-ml-6' : 'tw-right-0 tw-mr-6'">
          <ul v-if="isFabOpen" class="tw-flex tw-items-center tw-space-x-3" :class="$store.state.storage.app_settings.refreshButtonPlacement == 'left' ? 'tw-ml-6 tw-order-1' : 'tw-mr-6'">
            <li>
              <nuxt-link v-touch:touchhold.self="peek('Edit Beam')" :to="`/account/beams/${id}/edit/`" class="tw-appearance-none tw-rounded-lg tw-w-11 tw-h-11 lg:tw-w-12 lg:tw-h-12 tw-font-semibold tw-text-md lg:tw-text-lg tw-flex tw-items-center tw-justify-center tw-outline-none focus:tw-ring-4 tw-text-white tw-shadow-sm tw-bg-secondary hover:tw-bg-secondary-lighten dark:tw-bg-gray-700 dark:hover:tw-bg-gray-800 focus:tw-ring-white/40 tw-mx-auto tw-rounded-full disabled:tw-opacity-50 disabled:tw-cursor-wait">
                <svg xmlns="http://www.w3.org/2000/svg" class="tw-h-4 tw-w-4" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                  <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M11 5H6a2 2 0 00-2 2v11a2 2 0 002 2h11a2 2 0 002-2v-5m-1.414-9.414a2 2 0 112.828 2.828L11.828 15H9v-2.828l8.586-8.586z" />
                </svg>
              </nuxt-link>
            </li>
            <li>
              <button v-touch:touchhold.self="peek('Fetch Beam')" :disabled="isRefreshingBeam" @click="requestBeamRefresh" type="button" class="tw-appearance-none tw-rounded-lg tw-w-11 tw-h-11 lg:tw-w-12 lg:tw-h-12 tw-font-semibold tw-text-md lg:tw-text-lg tw-flex tw-items-center tw-justify-center tw-outline-none focus:tw-ring-4 tw-text-white tw-shadow-sm tw-bg-secondary hover:tw-bg-secondary-lighten dark:tw-bg-gray-700 dark:hover:tw-bg-gray-800 focus:tw-ring-white/40 tw-mx-auto tw-rounded-full disabled:tw-opacity-50 disabled:tw-cursor-wait">
                <svg v-if="isRefreshingBeam" class="tw-animate-spin tw-my-auto tw-h-4 tw-w-4 tw-text-white" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24">
                  <circle class="tw-opacity-25" cx="12" cy="12" r="10" stroke="currentColor" stroke-width="4"></circle>
                  <path class="tw-opacity-75" fill="currentColor" d="M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"></path>
                </svg>
                <svg v-else xmlns="http://www.w3.org/2000/svg" class="tw-h-4 tw-w-4" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                  <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 7h12m0 0l-4-4m4 4l-4 4m0 6H4m0 0l4 4m-4-4l4-4" />
                </svg>
              </button>
            </li>
            <li>
              <button v-touch:touchhold.self="peek('Refresh Beam')" :disabled="isFetchingBeam" @click="fetchBeam" type="button" class="tw-appearance-none tw-rounded-lg tw-w-11 tw-h-11 lg:tw-w-12 lg:tw-h-12 tw-font-semibold tw-text-md lg:tw-text-lg tw-flex tw-items-center tw-justify-center tw-outline-none focus:tw-ring-4 tw-text-white tw-shadow-sm tw-bg-secondary hover:tw-bg-secondary-lighten dark:tw-bg-gray-700 dark:hover:tw-bg-gray-800 focus:tw-ring-white/40 tw-mx-auto tw-rounded-full disabled:tw-opacity-50 disabled:tw-cursor-wait">
                <svg v-if="isFetchingBeam" class="tw-animate-spin tw-my-auto tw-h-4 tw-w-4 tw-text-white" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24">
                  <circle class="tw-opacity-25" cx="12" cy="12" r="10" stroke="currentColor" stroke-width="4"></circle>
                  <path class="tw-opacity-75" fill="currentColor" d="M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"></path>
                </svg>
                <svg v-else xmlns="http://www.w3.org/2000/svg" class="tw-h-4 tw-w-4" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                  <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M7 16a4 4 0 01-.88-7.903A5 5 0 1115.9 6L16 6a5 5 0 011 9.9M9 19l3 3m0 0l3-3m-3 3V10" />
                </svg>
              </button>
            </li>
          </ul>
          <button @click="isFabOpen = !isFabOpen" type="button" class="tw-appearance-none tw-rounded-lg tw-w-14 tw-h-14 lg:tw-w-16 lg:tw-h-16 tw-font-semibold tw-text-md lg:tw-text-lg tw-flex tw-items-center tw-justify-center tw-outline-none focus:tw-ring-4 tw-text-white tw-shadow-sm tw-bg-secondary hover:tw-bg-secondary-lighten dark:tw-bg-gray-700 dark:hover:tw-bg-gray-800 focus:tw-ring-white/40 tw-mx-auto tw-rounded-full disabled:tw-opacity-50 disabled:tw-cursor-wait">
            <div v-if="$store.state.storage.app_settings.refreshButtonPlacement == 'left'">
              <svg v-if="!isFabOpen" xmlns="http://www.w3.org/2000/svg" class="tw-h-5 tw-w-5" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16M4 18h7" />
              </svg>
              <svg v-else xmlns="http://www.w3.org/2000/svg" class="tw-h-5 tw-w-5" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12" />
              </svg>
            </div>
            <div v-else>
              <svg v-if="!isFabOpen" xmlns="http://www.w3.org/2000/svg" class="tw-h-5 tw-w-5" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16m-7 6h7" />
              </svg>
              <svg v-else xmlns="http://www.w3.org/2000/svg" class="tw-h-5 tw-w-5" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12" />
              </svg>
            </div>
          </button>
        </div>

My function is:

/*
** Peek & Toast
*/
async peek (text = '') {
  if (text == '') return

  console.log('runs now')

  try {
    await this.$CapacitorHaptics.impact({ style: this.$CapacitorImpactStyle.Light })
  } catch (err) { }

  try {
    await this.$CapacitorToast.show({
      text: text
    })
  } catch (err) { }

},
jerrybendy commented 2 years ago

The parameter of v-touch must be a function. So that your peek method should return a function, not a Promise.

adamxi commented 2 years ago

I'm having a similar issue. v-thouch:tap is actually firing on hover even though it's calling a plain function.

jerrybendy commented 2 years ago

@adamxi Could you paste your code here?