Add support for acceptable types to lib/system/file/upload/ functionality
authorTim Düsterhus <duesterhus@woltlab.com>
Tue, 30 Jun 2020 09:27:19 +0000 (11:27 +0200)
committerTim Düsterhus <duesterhus@woltlab.com>
Tue, 30 Jun 2020 09:40:10 +0000 (11:40 +0200)
see #3414

com.woltlab.wcf/templates/uploadFieldComponent.tpl
wcfsetup/install/files/acp/templates/uploadFieldComponent.tpl
wcfsetup/install/files/js/WoltLabSuite/Core/Ui/File/Upload.js
wcfsetup/install/files/lib/system/file/upload/UploadField.class.php

index fbf0c328593098572a9f9ba40377e6d029e35fbc..bd736ee225c81fc6908c3f46e985be0b84987674 100644 (file)
                new Upload("{$uploadFieldId}UploadButtonDiv", "{$uploadFieldId}uploadFileList", {
                        internalId: '{$uploadField->getInternalId()}',
                        {if $uploadField->getMaxFiles()}maxFiles: {$uploadField->getMaxFiles()},{/if}
-                       imagePreview: {if !$uploadField->supportMultipleFiles() && $uploadField->isImageOnly()}true{else}false{/if}
+                       imagePreview: {if !$uploadField->supportMultipleFiles() && $uploadField->isImageOnly()}true{else}false{/if},
+                       {if $uploadField->getAcceptableFiles()}
+                               acceptableFiles: [
+                                       {implode from=$uploadField->getAcceptableFiles() item=accept}'{$accept|encodeJS}'{/implode}
+                               ],
+                       {/if}
                });
        });
-</script>
\ No newline at end of file
+</script>
index fbf0c328593098572a9f9ba40377e6d029e35fbc..bd736ee225c81fc6908c3f46e985be0b84987674 100644 (file)
                new Upload("{$uploadFieldId}UploadButtonDiv", "{$uploadFieldId}uploadFileList", {
                        internalId: '{$uploadField->getInternalId()}',
                        {if $uploadField->getMaxFiles()}maxFiles: {$uploadField->getMaxFiles()},{/if}
-                       imagePreview: {if !$uploadField->supportMultipleFiles() && $uploadField->isImageOnly()}true{else}false{/if}
+                       imagePreview: {if !$uploadField->supportMultipleFiles() && $uploadField->isImageOnly()}true{else}false{/if},
+                       {if $uploadField->getAcceptableFiles()}
+                               acceptableFiles: [
+                                       {implode from=$uploadField->getAcceptableFiles() item=accept}'{$accept|encodeJS}'{/implode}
+                               ],
+                       {/if}
                });
        });
-</script>
\ No newline at end of file
+</script>
index 6789618bd0463c3260c5db12494d02fe5ec9ebb2..24a657278e5d0eb58c97d8b3dbb4245942ba2516 100644 (file)
@@ -31,7 +31,9 @@ define(['Core', 'Language', 'Dom/Util', 'WoltLabSuite/Core/Ui/File/Delete', 'Upl
                        // image preview
                        imagePreview: false,
                        // max files
-                       maxFiles: null
+                       maxFiles: null,
+                       // array of acceptable file types, null if any file type is allowed
+                       acceptableFiles: null,
                }, options);
                
                this._options.multiple = this._options.maxFiles === null || this._options.maxFiles > 1; 
index 83938b1f23316c918cf5fbdc40b4db42c51e4983..eb42f08c745ba0310bddeed7fd8b3df0f07e2e12 100644 (file)
@@ -43,6 +43,13 @@ class UploadField {
         */
        public $allowSvgImage = false;
        
+       /**
+        * Acceptable file types.
+        * @var string[]|null
+        * @since 5.3
+        */
+       public $acceptableFiles = null;
+       
        /**
         * UploadField constructor.
         *
@@ -119,10 +126,24 @@ class UploadField {
         * Sets the flag for `imageOnly`. This flag indicates whether only images
         * can uploaded via this field. Other file types will be rejected during upload.
         * 
+        * If set to `true` will also set the acceptable types to `image/*`. If set to
+        * false it will clear the acceptable types if they are `image/*`.
+        * 
         * @param       boolean       $imageOnly
         */
        public function setImageOnly($imageOnly) {
                $this->imageOnly = $imageOnly;
+               
+               if ($imageOnly) {
+                       $this->setAcceptableFiles(['image/*']);
+               }
+               else {
+                       // Using == here is safe, because we match a single element array containing
+                       // a scalar value.
+                       if ($this->getAcceptableFiles() == ['image/*']) {
+                               $this->setAcceptableFiles(null);
+                       }
+               }
        }
        
        /**
@@ -145,4 +166,36 @@ class UploadField {
                
                $this->allowSvgImage = $allowSvgImage;
        }
+       
+       /**
+        * Specifies acceptable file types. Use null to not specify any restrictions.
+        * 
+        * <strong>Heads up:</strong> This feature is used to improve user experience, by removing
+        * unacceptable files from the file picker. It does not validate the type of the uploaded
+        * file. You are responsible to perform (proper) validation on the server side.
+        * 
+        * Valid values are specified as "Unique file type specifiers":
+        * - A case insensitive file extension starting with a dot.
+        * - A mime type.
+        * - `audio/*`
+        * - `image/*`
+        * - `video/*`
+        * 
+        * @see         https://developer.mozilla.org/en-US/docs/Web/HTML/Element/input/file#Unique_file_type_specifiers
+        * @param       string[]|null     $acceptableFiles
+        * @since       5.3
+        */
+       public function setAcceptableFiles($acceptableFiles = null) {
+               $this->acceptableFiles = $acceptableFiles;
+       }
+       
+       /**
+        * Returns the acceptable file types.
+        * 
+        * @return      string[]|null
+        * @since       5.3
+        */
+       public function getAcceptableFiles() {
+               return $this->acceptableFiles;
+       }
 }