Safari IOS causing issues with Vue 2.6 functionality

I have implemented a button that, when clicked or pressed, triggers a click event on an input type=file, allowing the user to upload a file. This functionality works seamlessly on all platforms, but there is an issue with Safari/iOS Safari. In Safari, when I need to make a request before opening the upload window, the request is made and I receive a response, but the input click event is not triggered.

Below is the code snippet:

 async handleClickUpload(origin: string) {
    try {
      this._setDocumentType({ origin });
      const { code: documentCode } = this.currentDocument;

      if (this._isDocumentBackVariant(documentCode)) {
        await this._variantBackDocumentHandler();
      }
      this._handleUploadMethod();
    } catch (e) {
      console.error(e);
    }
  }

The above code handles making the request and setting the variation of the document, which functions correctly on Safari as well.

 async _variantBackDocumentHandler() {
    const { variation } = await this.getSpecificDocument("cnh_rg_frente");

    console.error("Encontrou variação", variation);
    if (!variation) {
      this._setDocumentType({ open: true });
      throw new Error("Variação não encontrada");
    }
    this._setDocumentType({ variation });
  }

This method determines whether to open the camera or allow the user to upload files, which also works well on Safari.

 _handleUploadMethod() {
    const { origin = "" } = this.documentType;
    if (origin === "camera") {
      this.cameraController.open = true;
    } else {
      this._uploadInputHandler();
    }
  }

In the following method, I trigger the click event for a hidden input element. Even in Safari, the hidden input element can be successfully selected. However, on Safari, clicking the input to open the upload window does not work.

 _uploadInputHandler() {
    const uploadInput: HTMLInputElement | null = document.querySelector("#uploadInput");

    uploadInput?.click();
  }

Here is the input element:

    <input
      id="uploadInput"
      @change="(event) => $emit('receiveFile', event)"
      type="file"
      style="visibility: hidden"
      accept="application/pdf, image/png, image/jpeg"
    />

.browserlistrc configuration:

defaults
not IE 11
maintained node versions
last 10 ios_saf versions
last 10 safari versions

babel.config.js configuration:

const plugins = () => {
  const defaultPlugins = [
    "@babel/plugin-proposal-optional-chaining",
    "@babel/plugin-proposal-throw-expressions",
    "@babel/plugin-syntax-throw-expressions",
    [
      "@babel/plugin-transform-runtime",
      {
        absoluteRuntime: false,
        corejs: false,
        helpers: true,
        regenerator: true,
        useESModules: false,
      },
    ],
  ];
  
  return defaultPlugins;
};

module.exports = {
  presets: [
    [
      "@vue/cli-plugin-babel/preset",
      {
        polyfills: [
          "es.array.iterator",
          "es.promise",
          "es.object.assign",
          "es.promise.finally",
          "es.symbol",
        ],
      },
    ],
  ],
  plugins: plugins(),
};

Imports in main.ts:

import "core-js/stable";
import "regenerator-runtime/runtime";

The functionality works flawlessly on other browsers, but on iOS Safari, when a request needs to be made before triggering the click event, nothing happens.

Answer №1

This particular problem has been widely acknowledged.

Safari, in order to uphold security measures, does not acknowledge `click` events on certain elements that possess these attributes:

  • visibility: hidden;
  • opacity: 0
  • display: none
  • or those which do not meet the criteria of a 'valid click target' - a term they continuously adjust but one example is their perception of an <a> without an href attribute as invalid. This results in clicks on <a href> functioning while clicks on <a> do not. The inclusion of an undefined href contributes to meeting Apple's standards for a valid click target.

If your intention is to allow users to interact with an 'invisible' element, refrain from using visibility: hidden. Instead, consider adjusting its opacity to 0.01.

Note: Your issue is not limited to Vue. It can also be observed in React, Angular, or vanilla JS. Consider revising the title to emphasize the compatibility issues with Safari IOS.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

obtain or retrieve a data file from the server

I am working with JSON data received from the backend in a specific format. { id: 2 name: dream file file : /home/bakcend/go/uploads/173ba017f27b69b42d7e747.png //backend path } Currently, files uploaded from the front end are stored in a separate dir ...

Enable the event listener for the newly created element

I am attempting to attach an event listener to this HTML element that is being created with an API call handleProducts() function handleProducts() { var display = document.getElementById("display") var url = "http://127.0.0.1:800 ...

HyperText Markup Language, Cascading Style Sheets, and JavaScript

In my div, I have a combination of icons and text. I'm trying to center only the text within the div, with two icons on the left and 4 to 5 icons on the right. Although I managed to position the icons correctly, I am having trouble aligning the text ...

Unexpected loading glitches occurring in vue-material components

I recently delved into the world of Vue.js and VueMaterial, which has been a refreshing and new experience for me since I've mostly focused on Native Android development in the past. Currently, I'm facing an unusual issue that seems to stem from ...

The utilization of ES Modules within a Next.js server.js

After reviewing a few examples in the Next.js repository, I came across: https://github.com/zeit/next.js/tree/master/examples/custom-server-express https://github.com/zeit/next.js/tree/master/examples/custom-server-koa I observed that these examples ut ...

Elements with v-for directive failing to display

I am attempting to incorporate a component using v-for. The data source infoTexts is structured as an Object where the locale code serves as the key and the corresponding message is the value. For example: { nl: 'Text in Dutch', fr: &apo ...

Looking for guidance on implementing throttle with the .hover() function in jQuery?

Seeking a way to efficiently throttle a hover function using jQuery. Despite various examples, none seem to work as intended. The use of $.throttle doesn't throw errors but ends up halting the animation completely. Here is the code snippet in question ...

Exploring the universal scope in NodeJS Express for each request

I am working with a basic express server that is in need of storing global variables during request handling. Specifically, each request involves multiple operations that require information to be stored in a variable like global.transaction[]. However, u ...

Randomly selecting an element from an array as the default option in vue.js

I am working on a neat little tool to learn vue.js where users can find out the time it takes to travel from one location to another: Codepen It's functioning fairly well at the moment, but I want to include a random value from each array when the pa ...

Managing and Streaming Music in a Rails Application

Currently, I am storing mp3s using paperclip and they only play back if I utilize Amazon S3. However, I am hesitant to use Amazon S3 because I am unsure how to secure the files. Now, I am reconsidering my approach as I need to secure the mp3s and provide ...

Modify the background color of the entire page when the main div is clicked

I am attempting to alter the background color of my entire page when the div with id main is clicked. You can view the code here: $(document).ready(function() { var color = 1; $('#main').click(function(){ if (colo ...

Using scope in ng-style to manipulate a portion of a CSS property value in Angular

I've been attempting to add a border using ng-style, but I'm struggling to figure out how to concatenate the value from the scope variable. None of the methods below seem to be working for me: <div ng-style="{'border-top' :'1p ...

Notify user with a Javascript alert if there are no search results found

I have developed a search index for Chicago employees and want to create an alert if no matching records are found. However, I am struggling to determine the value that needs to be inserted in case of an empty result set. Ideally, upon submission of the fu ...

Vitest React Redux - anticipating that the "spy" will be invoked with certain arguments

When testing my React application that utilizes Redux, I encountered an error with my thunk function for registering users. The specific error message I received was: "AssertionError: expected 'spy' to be called with arguments: [ [Function] ]" // ...

When utilizing jQuery lightbox to pull data from a database using PHP/Ajax, it may require a double click the

Encountering a strange issue where I must click on specific buttons with unique IDs. These IDs are then sent through Ajax to a PHP script, which searches for corresponding entries in the database. The retrieved data is then displayed in a jQuery lightbox. ...

Can you explain the purpose of the state object that is passed to history.pushState? What role does it play in

Can you explain the purpose of the stateObj parameter in the function history.pushState? For instance, when calling the function history.pushState(stateObj, title, url). ...

JavaScript code that activates several hovering elements

I am a beginner in the world of JavaScript and I'm attempting to create a simple function that will activate multiple div hover effects. I have tried various approaches so far, but I believe this code is closer to the solution. Any assistance from som ...

Error: Material-UI prop type validation failed - Please specify either `children`, `image`, `src`, or `component` prop

Despite having an image prop in CardMedia, I kept encountering this error. Here is a snippet of the code: Error description: const Post = ({ post, setter }) => { const classes = useStyles(); return( <Card className={classes.card} ...

Using jQuery to insert the AJAX upload response into a textarea

Currently, I am in the process of designing a form that includes a textarea where users can upload AJAX images using a unique [image UUID] tag. This allows users to upload multiple images and adjust them to their desired position. This is how it currently ...

Could offering a Promise as a module's export be considered a legitimate approach for asynchronous initialization in a Node.js environment?

I am in the process of developing modules that will load data once and create an interface for accessing that data. I am interested in implementing asynchronous loading of the data, especially since my application already utilizes promises. Is it considere ...