{% extends "_templates/base.html" %}
{% block content %}
{% markdown %}

# Browser Support {: .page-header }

Currently, Fine Uploader supports the following browsers:

* Internet Explorer 8+
* Firefox
* Chrome
* Chrome mobile (iOS & Android)
* Opera 15+
* Android 2.3.x+
* iOS 6+
* Safari 5+ (OS X)

We plan on supporting the following browsers/OSes in the very near future:

* Mobile Firefox (probably already works)
* Opera Mini
* Firefox OS
* Dolphin

## Feature Support Matrix

Note: Any features not listed here are supported in all browsers.

<table class='table table-condensed table-hover table-striped'>
    <thead>
        <tr>
            <th><strong>Browser</strong></th>
            <th>XHR2</th>
            <th>Multiple File Selection</th>
            <th>File Drop</th>
            <th>Folder Drop</th>
            <th>Folder Selection</th>
            <th>Chunking / Resume</th>
            <th>Non-MPE Requests</th>
            <th>Upload via Paste</th>
            <th>CORS</th>
            <th>Size Validation</th>
            <th>Progress reporting</th>
            <th>Image Previews</th>
            <th>Image Scaling</th>
            <th>Image Validation</th>
            <th>Pause Uploads</th>
            <th>S3 Uploads</th>
            <th>Azure Uploads</th>
        </tr>
    </thead>
    <tbody>
        <tr>
            <td>Chrome</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>Chrome for iOS 6+</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}<a style="font-size: 24px" href="#ios-multiple">*</a></td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>Chrome for Android 4+</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>Opera 15+</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>Firefox</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>IE 11</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>IE 10</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>IE 9</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
        </tr>
        <tr>
            <td>IE 8</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
        </tr>
        <tr>
            <td>Android
                4 stock</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>Android
                2.3.x stock</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('y', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
        </tr>
        <tr>
            <td>iOS
                6+</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}<a style="font-size: 24px" href="#ios-multiple">*</a></td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('x', "") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>Safari
                6</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
        <tr>
            <td>Safari
                5.1</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('x', "important") }}</td>
            <td>{{ label('√', "success") }}</td>
            <td>{{ label('√', "success") }}</td>
        </tr>
    </tbody>
</table>

<small><a style="font-size: 24px" name="ios-multiple">*</a> - iOS browsers are unable to upload multiple files when video files are allowed to be uploaded due to a long-standing iOS bug. See case <a href="https://github.com/Widen/fine-uploader/issues/990">#990</a> on our bug tracker for more details.</small>
<small><a style="font-size: 24px" name="ios-multiple">*</a> - iOS8 Safari is unable to upload any files due to bugs in Apple's code.  Please see [the blog post on this topic for more details](http://blog.fineuploader.com/2014/09/10/ios8-presents-serious-issues-that-prevent-file-uploading/).</small>


### Upload size Limitations

Upload size limitations are present in all browsers, but are most likely to affect the users of older browsers
which do not support the [File API](http://caniuse.com/fileapi). Fine Uploader uses [chunking]({{ URL_ROOT }}/features/chunking.html) to work around
the maximum upload size limit in browsers that do support the File API. When you are designing your upload form
for users of these older browsers, or if you are not using chunking, make sure you keep the imposed file size limits in mind:

<table class='table table-condensed table-hover table-striped'>
    <thead>
        <tr>
            <th>Browser</th>
            <th>Upload Limit</th>
        </tr>
    </thead>

    <tbody>
        <tr>
            <td>IE8</td>
            <td>2GB</td>
        </tr>
        <tr>
            <td>IE9</td>
            <td>4GB</td>
        </tr>
    </tbody>

</table>

[Source](http://blogs.msdn.com/b/ieinternals/archive/2011/03/10/wininet-internet-explorer-file-download-and-upload-maximum-size-limits.aspx)

# Feature Detection

## Feature Flags

Fine Uploader provides a set of flags that can be used to determine which
features are supported in the current browser. These flags are set during
initialization of the uploader.

Reading the feature flags in the feature detection module is easy.  Each flag
has a boolean value. Simply call `qq.supportedFeatures.{featureFlagName}`
and examine the return value.  For example, if you'd like to check if the
current user agent supports dropping folders, call `qq.supportedFeatures.folderDrop`.

Feature     | Description
------------|------------
`ajaxUploading` | Is uploading via XHR2 supported? Indicates File API support
`blobUploading` | Is it possible to upload `Blob` objects in this browser?
`canDetermineSize` | Can file size be determined client-side?
`chunking` | Is chunking supported?
`fileDrop` | Is dragging and dropping files supported?
`folderDrop` | Is drag and dropping folders supported?
`folderSelection` | Can folders be selected via a file dialog?
`imagePreviews` | Is client-side image preview generation possible?
`imageValidation` | Can we validate image properties client-side?
`limitedScaledImageSize` | Does the browser have an upper limit on the size of a `<canvas>`?  Directly related to the maximum allowable dimensions of a scaled image.
`itemSizeValidation` | Is client-side file size validation supported?
`pause` | Can chunked file uploads be paused?
`progressBar` | Are progress bars supported?
`resume` | Is the auto-resume feature supported?
`scaling` | Is client-side image scaling possible?
`tiffPreviews` | Can TIFFs be rendered natively in the current browser?
`unlimitedScaledImageSize` | `true` if there is no known upper limit for `<canvas>` (used to scale images).  Will be `false` for iOS and scaled images may be further downsampled by Fine Uploader to work around this limit.
`uploadCors` | Are cross-domain uploads supported?
`uploading` | Is uploading of any sort supported? (Note: This will return true for browsers that are not explicitly supported such as IE6)
`uploadCustomHeaders` | Are custom headers allowed to be sent along with the upload request?
`uploadNonMultipart` | Are non-multipart-encoded requests supported?
`uploadViaPaste` | Is uploading via paste supported?


## Mobile Safari (iOS)

Fine Uploader supports mobile Safari found on iOS 6+. One caveat to take into
account is that iOS saves all image files on the camera roll is "image.jpg".
Ensure that your server is saving files with some sort of unique identifier appended to the path
because otherwise your iOS users will be overwriting each others' images.
Fine Uploader automatically generates a Level 4 UUID per file and sends that
UUID along with the request to the server in the `qquuid` parameter.

## Internet Explorer

IE continues to lag far behind all other browsers in terms of features. IE10 finally competes
with existing modern browsers. For those of you with customers suffering with IE9 and older, here are some of the limitations
you may want to be aware of when using Fine Uploader. The limitations that are overcome
by upgrading to IE10 are listed as well.

<table class="table table-bordered table-striped">
    <thead>
        <tr>
            <th>Limitation</th>
            <th>Reason</th>
            <th>Supported/Fixed in IE10+</th>
        </tr>
    </thead>
    <tbody>
        <tr>
            <td>No progress indicator
            </td>
            <td>Lack of File API support
            </td>
            <td>
                <span class="label label-success">Yes</span>
            </td>
        </tr>
        <tr>
            <td>Lack of File API support
            </td>
            <td>Only multipart form requests may be used to send files via form submission
            </td>
            <td>
                <span class="label label-success">Yes</span>
            </td>
        </tr>
        <tr>
            <td>Size restriction options not enforced
            </td>
            <td>Lack of File API Support
            </td>
            <td>
                <span class="label label-success">Yes</span>
            </td>
        </tr>
        <tr>
            <td>Cannot select multiple files in the file selection dialog
            </td>
            <td>The <code>&lt;input&gt;</code> element does not support the <code>multiple</code> attribute</td>
            <td>
                <span class="label label-success">Yes</span>
            </td>
        </tr>
        <tr>
            <td>No logging
            </td>
            <td><code>console.log</code> is not implemented (IE8 and older only)
            </td>
            <td>
                <span class="label label-success">Yes</span>
            </td>
        </tr>
        <tr>
            <td>Unable to cancel uploads
            </td>
            <td>Not really an IE problem, but since we are forced to upload files via
                form submission, I thought I’d include it. There may be a way to
                make this work, but I haven’t spent time playing around with the
                available options yet. In the meantime, you should probably set the <code>disableCancelForFormUploads</code> option
                to true. If I can’t find a way to properly allow cancel to work when
                using the form uploader, I’ll probably remove the cancel link when
                the form uploader is in use.
            </td>
            <td>
                <span class="label label-success">Yes</span>
            </td>
        </tr>
       <tr>
           <td>Requires response of type <code>text/plain</code>
           </td>
           <td>IE does strange things with the response when the content-type is, for
               example, “application/json” or “text/html”. The latter is only a
               problem if you return HTML in your JSON response.
           </td>
           <td>
               <span class="label label-success">Yes</span>
           </td>
       </tr>
       <tr>
           <td>Cannot determine response code
           </td>
           <td>Not really an IE problem, but since we are forced to upload files via
               form submission, I thought I’d include it. This is really a side-effect
               of using a form submission to upload files.
           </td>
            <td>
                <span class="label label-success">Yes</span>
            </td>
       </tr>
        <tr>
            <td>Content-size header field value does not match the actual file size
            </td>
            <td>This isn’t technically an IE issue, but I’m going to call it one since
                we are forced to use multipart request in IE. The content-size for
                multipart data requests does not refer only to the file. Rather,
                it refers to the the total size of all sections in the request.
            </td>
            <td>
                <span class="label label-default">N/A</span>
            </td>
        </tr>
        <tr>
            <td>Cannot parse JSON response if response code is not 200
            </td>
            <td>If the response code is not 200, and the size of the response is less
                than 512, or, apparently, sometimes, less than 256 bytes, IE replaces
                the response with a “friendly” error message. If you insist on returning
                responses with a status code other than 200, you can work around
                this by instructing IE users to uncheck the “show friendly HTTP error
                messages” setting or by padding the response JSON with whitespace
                as described
            </td>
            <td>
                <span class="label label-default">N/A</span>
            </td>
        </tr>
        <tr>
            <td>Cannot use a <code>&lt;button&gt;</code> element in the <code>button</code> option</td>
            <td>The button receives the click event instead of the child <code>&lt;input&gt;</code> element</td>
            <td>
                <span class="label label-default">N/A</span>
            </td>
        </tr>
    </tbody>
</table>



{% endmarkdown %}
{% endblock %}
