精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

在瀏覽器里裁剪圖片:純?cè)⒘阋蕾嚨?JavaScript 小妙招

開發(fā) 前端 瀏覽器
?今天帶你用瀏覽器原生能力實(shí)現(xiàn)圖片裁剪:不裝庫、不走服務(wù)端、即時(shí)預(yù)覽、即可下載。

先用一個(gè)極簡 demo 走一遍流程。

你將做出什么

  • 從用戶設(shè)備本地上傳圖片
  • 在 <canvas> 中實(shí)時(shí)展示與裁剪
  • 拖拽框調(diào)整裁剪區(qū)域
  • 即時(shí)預(yù)覽裁剪結(jié)果
  • 一鍵生成并下載裁剪后的圖片,無需服務(wù)器

Demo(原生 HTML/CSS/JS)

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <style>
      .container {
        max-width: 600px;
        margin: 20px auto;
        text-align: center;
        font-family: system-ui, -apple-system, Segoe UI, Roboto, Arial, sans-serif;
      }
      .image-wrapper {
        position: relative;
        display: inline-block;
      }
      .crop-frame {
        display: none;
        position: absolute;
        border: 3px dashed #28a745; /* 視覺反饋更明顯 */
        box-sizing: border-box;
        cursor: move;
      }
      .resize-handle {
        position: absolute;
        width: 12px;
        height: 12px;
        background: #28a745;
        cursor: nwse-resize;
      }
      .preview-area {
        margin-top: 20px;
      }
      button {
        padding: 10px20px;
        background: #28a745;
        color: #fff;
        border: none;
        cursor: pointer;
        border-radius: 6px;
      }
      button:disabled {
        opacity: .6;
        cursor: not-allowed;
      }
    </style>
</head>
<body>
    <div class="container">
      <input type="file" id="imageInput" accept="image/*" />
      <div class="image-wrapper">
        <canvas id="mainCanvas"></canvas>
        <div class="crop-frame" id="cropFrame"></div>
      </div>
      <button id="cropButton" disabled>Crop & Download</button>
      <div class="preview-area">
        <canvas id="previewCanvas"></canvas>
      </div>
    </div>

    <script>
      const imageInput = document.getElementById("imageInput");
      const mainCanvas = document.getElementById("mainCanvas");
      const ctx = mainCanvas.getContext("2d");
      const cropFrame = document.getElementById("cropFrame");
      const previewCanvas = document.getElementById("previewCanvas");
      const previewCtx = previewCanvas.getContext("2d");
      const cropButton = document.getElementById("cropButton");

      let image = new Image();
      let cropData = { x: 100, y: 100, width: 150, height: 150 };
      let isDragging = false;

      // 初始尺寸設(shè)為 0(數(shù)值),避免拉伸
      mainCanvas.width = 0;
      mainCanvas.height = 0;

      imageInput.addEventListener("change", (e) => {
        const file = e.target.files && e.target.files[0];
        if (!file) return;

        image.src = URL.createObjectURL(file);
        image.onload = () => {
          // 固定畫布演示尺寸(也可按比例自適應(yīng))
          mainCanvas.width = 600;
          mainCanvas.height = 450;

          // 繪制整圖到畫布
          ctx.clearRect(0, 0, mainCanvas.width, mainCanvas.height);
          ctx.drawImage(image, 0, 0, mainCanvas.width, mainCanvas.height);

          // 啟用裁剪
          updateCropFrame();
          cropButton.disabled = false;
        };
      });

      function updateCropFrame() {
        cropFrame.style.display = "block";
        cropFrame.style.left = `${cropData.x}px`;
        cropFrame.style.top = `${cropData.y}px`;
        cropFrame.style.width = `${cropData.width}px`;
        cropFrame.style.height = `${cropData.height}px`;
        cropFrame.innerHTML =
          '<div class="resize-handle" style="bottom: -6px; right: -6px;"></div>';
      }

      cropFrame.addEventListener("mousedown", (e) => {
        isDragging = true;
        if (e.target.classList.contains("resize-handle")) {
          cropFrame.dataset.mode = "resize";
        } else {
          cropFrame.dataset.mode = "move";
        }
      });

      document.addEventListener("mousemove", (e) => {
        if (!isDragging) return;
        const rect = mainCanvas.getBoundingClientRect();
        const mouseX = e.clientX - rect.left;
        const mouseY = e.clientY - rect.top;

        if (cropFrame.dataset.mode === "move") {
          cropData.x = Math.max(
            0,
            Math.min(
              mouseX - cropData.width / 2,
              mainCanvas.width - cropData.width
            )
          );
          cropData.y = Math.max(
            0,
            Math.min(
              mouseY - cropData.height / 2,
              mainCanvas.height - cropData.height
            )
          );
        } elseif (cropFrame.dataset.mode === "resize") {
          cropData.width = Math.max(50, mouseX - cropData.x);
          cropData.height = Math.max(50, mouseY - cropData.y);
          // 限制在畫布范圍內(nèi)
          cropData.width = Math.min(cropData.width, mainCanvas.width - cropData.x);
          cropData.height = Math.min(cropData.height, mainCanvas.height - cropData.y);
        }

        updateCropFrame();
      });

      document.addEventListener("mouseup", () => {
        isDragging = false;
        cropFrame.dataset.mode = "";
      });

      cropButton.addEventListener("click", () => {
        if (!image.width) return;

        previewCanvas.width = cropData.width;
        previewCanvas.height = cropData.height;

        // 將畫布坐標(biāo)映射回原圖坐標(biāo)
        const scaleX = image.width / mainCanvas.width;
        const scaleY = image.height / mainCanvas.height;

        previewCtx.clearRect(0, 0, previewCanvas.width, previewCanvas.height);
        previewCtx.drawImage(
          image,
          cropData.x * scaleX,
          cropData.y * scaleY,
          cropData.width * scaleX,
          cropData.height * scaleY,
          0,
          0,
          cropData.width,
          cropData.height
        );

        const link = document.createElement("a");
        link.download = "cropped-image.png";
        link.href = previewCanvas.toDataURL("image/png");
        link.click();
      });
    </script>
</body>
</html>

原理一眼看懂

  • 用一個(gè) <canvas> 承擔(dān)圖片渲染,輕量且原生
  • 用戶選擇本地圖片,加載到固定尺寸的畫布里;拖動(dòng)裁剪框或其縮放手柄,實(shí)時(shí)改變裁剪區(qū)域。
  • 綠框與手柄提供直觀的視覺反饋;布局簡單,移動(dòng)端/桌面端都能順利操作。
  • 點(diǎn)擊按鈕后,按比例把畫布坐標(biāo)映射到原圖像素,把裁剪結(jié)果繪到預(yù)覽畫布,并生成 Data URL 觸發(fā)下載——全程不觸服務(wù)器

重點(diǎn)回顧

  • 純 HTML/CSS/JS 即可完成:上傳 → 裁剪 → 預(yù)覽 → 下載
  • canvas.drawImage() + 比例換算是關(guān)鍵
  • 交互只需拖動(dòng)移動(dòng)單點(diǎn)縮放兩種模式,邏輯清晰、易擴(kuò)展

把它塞進(jìn)你的下一個(gè)小項(xiàng)目里試試吧。

責(zé)任編輯:姜華 來源: 大遷世界
相關(guān)推薦

2025-09-09 10:00:00

前端瀏覽器API

2015-01-21 15:45:50

斯巴達(dá)瀏覽器

2017-01-05 09:07:25

JavaScript瀏覽器驅(qū)動(dòng)

2016-10-09 08:38:01

JavaScript瀏覽器事件

2013-11-15 13:22:22

瀏覽器JavaScript

2011-01-05 09:52:30

微軟谷歌零日漏洞

2020-03-12 11:29:51

JavaScript瀏覽器語言

2012-03-30 14:52:03

瀏覽器大戰(zhàn)

2011-08-02 14:23:09

iPhone UIScrollVi 圖片

2010-09-15 09:12:03

JavaScript瀏覽器兼容

2020-12-15 11:05:21

JavascriptChrome瀏覽器

2010-04-05 21:57:14

Netscape瀏覽器

2013-08-22 10:09:00

2023-08-29 08:28:43

React并發(fā)更新

2024-02-02 12:52:34

瀏覽器時(shí)間切片線程

2012-11-06 11:37:26

傲游瀏覽器

2014-05-16 11:18:14

瀏覽器ChromeFirefox

2017-12-04 09:39:41

瀏覽器Chrome小技巧

2017-03-03 16:50:01

2012-03-20 11:07:08

點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)

av大片在线| 国产三级三级在线观看| 蜜臀91精品国产高清在线观看| 欧美视频在线免费| 亚洲成人第一| 亚洲精品一区二区三区不卡| 西西人体一区二区| 久久精品国产2020观看福利| 亚洲欧美激情一区二区三区| 中文字幕在线免费观看视频| 国产精品乱码久久久久久| 91精品国产综合久久久久久丝袜| 日韩三级视频在线| 色综合狠狠操| 日韩大陆欧美高清视频区| 91欧美视频在线| 国产精选在线| 日本一区二区三区视频视频| 97久久夜色精品国产九色| 波多野结衣在线电影| 欧美成人一区二免费视频软件| 亚洲欧美另类人妖| 久久av一区二区三| 激情久久一区二区| 欧美视频在线观看免费| 日韩欧美猛交xxxxx无码| 国产裸舞福利在线视频合集| 成人永久免费视频| 成人有码在线播放| 小泽玛利亚一区二区三区视频| 亚洲视频久久| 久久精品视频在线播放| 四虎国产精品成人免费入口| 国产劲爆久久| 欧美一区2区视频在线观看| 白嫩少妇丰满一区二区| 国产深夜视频在线观看| 亚洲欧美色图小说| 亚洲精品日韩精品| 日本一本草久在线中文| 波多野结衣中文字幕一区二区三区| 国产欧美精品日韩| 国产成人a v| 欧美在线综合| 欧美在线www| 99热国产在线观看| 国产精品乱看| 久久久人成影片一区二区三区观看| 三级黄色在线观看| 天天射综合网视频| 久久精品视频一| 在线观看黄网址| 日韩电影一区| xxav国产精品美女主播| 精品日韩在线视频| 日韩精品诱惑一区?区三区| 亚洲人成绝费网站色www| 亚洲第一页av| 中文字幕亚洲影视| 亚洲欧洲午夜一线一品| 亚洲国产无码精品| 国产aⅴ精品一区二区三区久久| 日韩电影中文字幕| 欧美性xxxx图片| 蜜桃精品wwwmitaows| 亚洲老板91色精品久久| 日韩精品无码一区二区三区久久久| 要久久爱电视剧全集完整观看 | 欧美在线观看成人| 日韩欧美一中文字暮专区| 欧美日韩性生活视频| 欧美亚洲另类色图| 欧美国产日韩电影| 欧美精品一卡两卡| 亚洲欧美日韩中文字幕在线观看| 日韩中文字幕视频网| 精品久久久久久久久久久久包黑料| 久久无码专区国产精品s| 精品淫伦v久久水蜜桃| 精品香蕉一区二区三区| 亚洲精品视频网址| 欧美91大片| 97精品免费视频| 这里只有久久精品视频| 国产自产视频一区二区三区| 春色成人在线视频| 户外极限露出调教在线视频| 亚洲国产成人午夜在线一区| 老汉色影院首页| 成av人片在线观看www| 欧日韩精品视频| 国产又粗又猛大又黄又爽| 色天下一区二区三区| 中文字幕亚洲色图| 国产第100页| 日日夜夜精品视频天天综合网| 成人免费网站在线观看| 亚洲欧美日本在线观看| 亚洲欧洲av在线| 欧美日韩黄色一级片| 伦一区二区三区中文字幕v亚洲| 日韩一区二区免费在线观看| 久久久久亚洲av无码专区桃色| 日韩欧美综合| 97人人做人人爱| 国产精品久久久久久久久久久久久久久久 | 国产欧美三级电影| 伊人伊成久久人综合网站| 久久久久亚洲AV成人| 久久激情综合| 国产传媒一区| 免费av不卡| 欧美性xxxx极品hd欧美风情| aaaaaaaa毛片| 欧美三级美国一级| 91精品国产91久久久| 国产麻豆免费视频| 国产亚洲美州欧州综合国| 99er在线视频| 国产精品白丝久久av网站| 亚洲男人天堂网站| 国产污视频在线看| 国产一区二区三区免费看| 日产精品久久久一区二区| 免费在线中文字幕| 欧美久久久久免费| www.av天天| 99pao成人国产永久免费视频| 91精品免费看| aaa在线观看| 欧美日韩国产限制| 黄色网址在线视频| 欧美日本一区二区视频在线观看| 国产精品综合不卡av| 黄色免费在线播放| 一本到三区不卡视频| 国产精品无码在线| 悠悠资源网久久精品| 亚洲最大av网| gogogogo高清视频在线| 欧美精品日日鲁夜夜添| 国产91在线播放九色| 日本色综合中文字幕| 欧美亚洲精品日韩| 在线观看欧美日韩电影| 日韩电影中文 亚洲精品乱码| 久久精品久久国产| av高清不卡在线| 91免费黄视频| 九色丨蝌蚪丨成人| 国产91精品久久久| 可以在线观看的av网站| 在线欧美小视频| 日韩一级片在线免费观看| 免费欧美在线视频| 杨幂一区欧美专区| 伊人久久一区| 欧美成人精品一区二区三区| hs视频在线观看| 亚洲电影第三页| 亚洲永久无码7777kkk| 免播放器亚洲| 亚洲精品成人三区| 在线观看欧美| 欧美黑人巨大xxx极品| 日日躁夜夜躁白天躁晚上躁91| 亚洲国产精品尤物yw在线观看| 欧美夫妇交换xxx| 久久激情视频| 综合网五月天| 97se亚洲国产一区二区三区| 97视频在线观看免费高清完整版在线观看 | 六十路精品视频| 成人a在线观看高清电影| 日韩中文在线中文网三级| a天堂在线视频| 精品久久久久人成| 国产在视频线精品视频| 国产在线看一区| 国产在线播放观看| 免费视频亚洲| 亚洲一区二区三区四区在线播放| 欧美家庭影院| 亚洲男人天堂2024| 国产精品视频久久久久久| 亚洲国产精品久久艾草纯爱| 好吊日免费视频| 精品一区二区在线播放| 真人抽搐一进一出视频| 欧美日韩在线二区| 97久久夜色精品国产九色| 伊人久久视频| 久久最新资源网| 久久久资源网| 日韩免费电影网站| 免费无码国产精品| 一二三四社区欧美黄| 国产黄片一区二区三区| 国产乱子伦视频一区二区三区| 久色视频在线播放| 久久久国产精品| 欧美日韩电影一区二区三区| 日韩精品一区二区三区免费视频| 97超碰国产精品女人人人爽 | 国产福利视频在线播放| 在线国产一区| 欧美久久综合性欧美| 视频成人永久免费视频| 国产精品高清在线观看| 91九色美女在线视频| 日韩一区二区欧美| 国产区av在线| 这里只有精品电影| 国产在线一级片| 天天做天天摸天天爽国产一区| 男女男精品视频网站| 国产高清精品网站| 中文字幕 日韩 欧美| 亚洲日本视频| 欧美国产视频一区| 91精品啪在线观看国产81旧版| 欧美一区二区三区四区在线观看地址 | 久久综合伊人77777麻豆| 亚洲wwww| 97在线视频免费观看| caopo在线| 久久精品99久久久久久久久| 国产午夜精品一区理论片| 亚洲精品按摩视频| av网站在线观看免费| 欧美日韩精品欧美日韩精品| 香蕉影院在线观看| 亚洲福利视频三区| 国产亚洲欧美精品久久久久久| 最新国产の精品合集bt伙计| 亚洲AV无码成人精品区明星换面| av在线播放不卡| zjzjzjzjzj亚洲女人| 国产乱子伦视频一区二区三区| 99九九99九九九99九他书对| 蜜臀国产一区二区三区在线播放| 免费大片在线观看| 久久久成人网| 欧美成人黑人猛交| 日韩在线一区二区三区| 久久久久久香蕉| 久久亚洲精选| 国产免费视频传媒| 奇米精品一区二区三区在线观看一 | 一区二区三区在线电影| 永久域名在线精品| 一区二区免费不卡在线| 精品嫩模一区二区三区| 欧美日本一区二区视频在线观看| 青青草综合在线| 亚洲特色特黄| 99精品视频在线看| 亚洲欧美日本视频在线观看| 日韩欧美xxxx| 久草精品在线观看| 韩国一区二区三区四区| 不卡影院免费观看| 麻豆精品免费视频| 久久精品一区二区| 久久久久久久久久97| 亚洲综合在线五月| 国产又色又爽又黄的| 色就色 综合激情| 中文字幕在线播放不卡| 91精品在线麻豆| 欧美 日韩 人妻 高清 中文| 日韩av综合中文字幕| 福利在线播放| 操91在线视频| av电影免费在线看| 国产成人精品a视频一区www| 欧美在线一级| 国产精品区一区二区三在线播放| 美女视频免费精品| 亚洲国产精品一区二区第一页 | 91日韩精品一区| 国产又粗又硬视频| 一区二区三区 在线观看视频| 免费在线观看黄网站| 在线精品国精品国产尤物884a| 一本到在线视频| 亚洲精品一线二线三线无人区| 日本中文字幕电影在线观看| 日韩中文字幕网站| 黄视频免费在线看| 国产欧美一区二区三区久久| 日韩精品久久久久久久软件91| 麻豆精品传媒视频| 一区二区电影| 国产熟人av一二三区| 成人在线视频首页| 成年人视频软件| 五月天激情小说综合| 97超视频在线观看| 亚洲精品自在久久| 中文字幕伦理免费在线视频 | 久久久电影免费观看完整版| 97人人在线视频| 91美女高潮出水| 蜜桃精品wwwmitaows| www.夜夜爱| 蜜桃久久精品一区二区| 欧美肉大捧一进一出免费视频| 国产精品全国免费观看高清 | 欧美乱大交做爰xxxⅹ小说| 午夜精品一区二区三区免费视频 | 亚洲成色999久久网站| 69视频在线观看| 欧美在线视频观看免费网站| 蜜桃在线一区| 亚洲一区三区| 久久动漫亚洲| 国产原创剧情av| 亚洲女厕所小便bbb| 欧美成人一区二区视频| 日韩国产精品一区| av影片在线| 福利视频久久| 欧美精品一卡| 九九热精品国产| 国产精品入口麻豆九色| 小泽玛利亚一区二区三区视频| 日韩精品极品视频| 搞黄网站在线看| 99在线视频播放| 自由日本语亚洲人高潮| 亚洲精品免费一区亚洲精品免费精品一区 | 麻豆视频在线观看免费| 国产精品电影网站| 中文字幕亚洲影视| 无码人妻丰满熟妇区毛片| 26uuu亚洲| 一级黄色免费网站| 精品一区电影国产| 亚洲优女在线| 欧美精品一区二区视频| 久久久噜噜噜| 天天躁日日躁aaaxxⅹ| 色综合一个色综合| 久久免费看视频| 国产精品久久久精品| 日韩免费视频| 午夜免费福利视频在线观看| 中文字幕一区二区三区精华液| 久久午夜鲁丝片| 中日韩美女免费视频网站在线观看 | 亚洲精品成人天堂一二三| 99在线小视频| 欧美激情中文网| 青青草久久爱| 欧美成人xxxxx| 国产喷白浆一区二区三区| 一区二区三区在线免费观看视频 | 日韩视频免费直播| 国内小视频在线看| 蜜桃欧美视频| 视频一区视频二区中文| 成人在线观看免费高清| 91麻豆精品久久久久蜜臀| а√天堂8资源在线官网| 高清不卡日本v二区在线| 亚洲乱亚洲高清| 欧美做受高潮6| 欧美精品久久99久久在免费线| av大片在线| 久久av一区二区三区漫画| 日韩福利电影在线| 成人在线观看高清| 亚洲成人激情在线| 亚洲一区二区三区四区| 一本一本a久久| 成人免费视频视频| 在线免费观看av网址| 日韩一区二区福利| 精品国产一区二区三区成人影院 | 日本黄色a视频| 成人免费高清视频在线观看| 天天干天天干天天干天天| 综合国产在线观看| 粉嫩av一区二区| 免费看污污网站| 亚洲一区二区三区精品在线| 天堂a√中文在线| 成人福利网站在线观看| 日韩午夜av| 日韩福利小视频| 亚洲免费视频观看| 亚洲天堂中文字幕在线观看| 黄色片一级视频| 洋洋成人永久网站入口| 成人在线观看黄色| 国产一区二区三区高清视频| 日韩1区2区3区| 国产又大又黑又粗免费视频| 色偷偷av一区二区三区|