一个前端,爱跑步、爱吉他、爱做饭、爱生活、爱编程、爱南芳姑娘,爱我所爱。世间最温暖又无价的是阳光、空气与爱,愿它们能带你去更远的地方。

  • 文章
  • 心情
  • 照片墙
  • 工具
  • 开发技术分享

    原生的文件拖拽上传

    技术 119 2022-02-14 10:19

    老规矩先说需求:上传文件需要拖拽上传

    正常来讲一个UI库就支持了 比如antd的uploads组件

    但是考虑到设计图的差异太大了,所以需要自己来实现

    也是很简单的:

    直接上代码吧

    这个代码中包括了上传s3的步骤

    如果不需要可以去掉

    <!DOCTYPE html>
    <html lang="en">
      <head>
        <meta charset="UTF-8" />
        <title>原生拖拽上传</title>
        <style>
          #container {
            border: 1px solid #aaa;
            padding: 10px;
            margin: 10px;
            width: 1050px;
            min-height: 300px;
          }
        </style>
      </head>
      <body>
        <h1>原生拖拽上传</h1>
        <h3>请拖拽您的头像到下方区域</h3>
        <div id="container"></div>
        <script>
          /*拖拽的目标对象------ document 监听drop 并防止浏览器打开客户端的图片*/
                这里是全局的方法 不太友好 参考下面container,ondrop的写法
           document.ondragover = function (e) {
              e.preventDefault(); //只有在ondragover中阻止默认行为才能触发 ondrop 而不是 ondragleave
          };
          document.ondrop = function (e) {
            e.preventDefault(); //阻止 document.ondrop的默认行为  *** 在新窗口中打开拖进的图片
          };
          /*拖拽的源对象----- 客户端的一张图片 */
          /*拖拽目标对象-----div#container  若图片释放在此元素上方,则需要在其中显示*/
          container.ondragover = function (e) {
            e.preventDefault();
          };
          container.ondrop = function (e) {
                    在这里取消掉默认的跳转事件即可 不然会影响到全局的方法
                    e.preventDefault();
            console.log(e);
            console.log(e.dataTransfer.files);
            //        chrome 此处的显示有误
            var list = e.dataTransfer.files;
            for (var i = 0; i < list.length; i++) {
              var f = list[i];
              //            console.log(f);
              reader(f);
              //            读取指定文件的内容 作为“数据URL”
              //            reader.readAsDataURL(f);
              //            当客户端文件读取完成 触发onload事件
            }
          };
          async function reader(file) {
            // 这里能获取到拖拽过来的文件了
            // 我这边是经过了一层s3上传 如果不需要可以去掉
            // 根据具体的业务去处理
            console.log(file);
            const s3Url = await fetch(
              "s3urlxxxxx",
              {
                method: "GET",
                headers: {
                  "Content-Type": "image/png",
                  authorization:
                    "Bearer xxxxxx",
                },
              }
            )
              .then((res) => {
                return res.json();
              })
              .then((data) => {
                return data.item;
              });
    
            const imgsUrl = await fetch(s3Url, {
              method: "PUT",
              headers: {
                "Content-Type": "image/png",
              },
              body: file,
            }).then((res) => {
              if (res.url) {
                return res.url.split("?")[0];
              }
            });
    
            console.log(imgsUrl);
    
            var img = new Image();
            img.src = imgsUrl;
            container.appendChild(img);
          }
        </script>
      </body>
    </html>
    

    下课