ホームページ > ウェブフロントエンド > H5 チュートリアル > Canvas オフスクリーン テクノロジーと虫眼鏡の実装コード例

Canvas オフスクリーン テクノロジーと虫眼鏡の実装コード例

青灯夜游
リリース: 2018-10-09 15:43:40
転載
2600 人が閲覧しました

この記事では主にキャンバスのオフスクリーン技術と虫眼鏡の実装コード例について紹介します。必要な方は参考にしていただければ幸いです。

canvas の使用 フィルターの実装に加えて、オフスクリーン テクノロジー 虫眼鏡機能も使用できます。

説明の便宜上、この記事は 2 つのアプリケーション部分に分かれています:

  • ウォーターマークとセンター スケーリングの実現

  • 拡大鏡の実現

1. オフスクリーン テクノロジーとは何ですか?

キャンバス学習とフィルターの実装では、drawImage インターフェイスが導入されました。このインターフェイスでは、イメージの描画に加えて、次のこともできます。 canvas オブジェクトを別の canvas オブジェクト に描画します。これはオフスクリーンテクノロジーです。

2. ウォーターマークと中央スケーリングを実装する

コードには、2 つの Canvas タグがあります。それらはそれぞれ目に見えるものと見えないものです。非表示のキャンバス オブジェクト上の Context オブジェクトは、画像の透かしを配置する場所です。

詳細については、コードのコメントを参照してください:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

<!DOCTYPE html>

<html lang="en">

<head>

  <meta charset="UTF-8">

  <title>Learn Canvas</title>

  <style>

    canvas {

      display: block;

      margin: 0 auto;

      border: 1px solid #222;

    }

 

    input {

      display: block;

      margin: 20px auto;

      width: 800px

    }

  </style>

</head>

<body>

  <p id="app">

    <canvas id="my-canvas"></canvas>

    <input type="range" value="1.0" min="0.5" max="3.0" step="0.1">

    <canvas id="watermark-canvas" style="display: none;"></canvas>

  </p>

  <script type="text/javascript">

    window.onload = function () {

      var canvas = document.querySelector("#my-canvas")

      var watermarkCanvas = document.querySelector("#watermark-canvas")

      var slider = document.querySelector("input")

 

      var scale = slider.value

 

      var ctx = canvas.getContext(&#39;2d&#39;)

      var watermarkCtx = watermarkCanvas.getContext("2d")

 

      /* 给第二个canvas获取的Context对象添加水印 */

      watermarkCanvas.width = 300

      watermarkCanvas.height = 100

      watermarkCtx.font = "bold 20px Arial"

      watermarkCtx.lineWidth = "1"

      watermarkCtx.fillStyle = "rgba(255 , 255 , 255, 0.5)"

      watermarkCtx.fillText("=== yuanxin.me ===", 50, 50)

      /****************************************/

 

      var img = new Image()

      img.src = "./img/photo.jpg"

 

      /* 加载图片后执行操作 */

      img.onload = function () {

        canvas.width = img.width;

        canvas.height = img.height;

        drawImageByScale(canvas, ctx, img, scale, watermarkCanvas);

        // 监听input标签的mousemove事件

        // 注意:mousemove实时监听值的变化,内存消耗较大

        slider.onmousemove = function () {

          scale = slider.value

          drawImageByScale(canvas, ctx, img, scale, watermarkCanvas);

        }

      }

      /******************/

    }

    /**

    *

    * @param {Object} canvas 画布对象

    * @param {Object} ctx

    * @param {Object} img

    * @param {Number} scale 缩放比例

    * @param {Object} watermark 水印对象

    */

    function drawImageByScale(canvas, ctx, img, scale, watermark) {

      // 图像按照比例进行缩放

      var width = img.width * scale,

        height = img.height * scale

      // (dx, dy): 画布上绘制img的起始坐标

      var dx = canvas.width / 2 - width / 2,

        dy = canvas.height / 2 - height / 2

      ctx.clearRect(0, 0, canvas.width, canvas.height) // No1 清空画布

      ctx.drawImage(img, dx, dy, width, height) // No2 重新绘制图像

      if (watermark) {

        // No3 判断是否有水印: 有, 绘制水印

        ctx.drawImage(watermark, canvas.width - watermark.width, canvas.height - watermark.height)

      }

    }

  </script>

</body>

</html>

ログイン後にコピー

効果は次のとおりです:

スライダーをドラッグすると、画像を拡大・縮小できます。次に、右クリックして画像を保存します。保存された画像には、以下に示すようにすでに透かしが入っています:

#3. 虫眼鏡を実装します#。 ##上記の中央ズームに基づいて、虫眼鏡の所有者は次の 2 つの部分に注意する必要があります:

    キャンバス マウス応答イベントの洗練された処理: スライド イン、スライド アウト、クリック
  • #オフスクリーン座標を再計算します (詳細な数式計算のアイデアについてはコード コメントを参照してください)
  • キャンバスを基準にしてマウスを再計算しますラベル座標 (詳細な数式計算のアイデアについては、コードのコメントを参照してください)
  • コードは次のとおりです:
  • 1

    2

    3

    4

    5

    6

    7

    8

    9

    10

    11

    12

    13

    14

    15

    16

    17

    18

    19

    20

    21

    22

    23

    24

    25

    26

    27

    28

    29

    30

    31

    32

    33

    34

    35

    36

    37

    38

    39

    40

    41

    42

    43

    44

    45

    46

    47

    48

    49

    50

    51

    52

    53

    54

    55

    56

    57

    58

    59

    60

    61

    62

    63

    64

    65

    66

    67

    68

    69

    70

    71

    72

    73

    74

    75

    76

    77

    78

    79

    80

    81

    82

    83

    84

    85

    86

    87

    88

    89

    90

    91

    92

    93

    94

    95

    96

    97

    98

    99

    100

    101

    102

    103

    104

    105

    106

    107

    108

    109

    110

    111

    112

    113

    114

    115

    116

    117

    118

    <!DOCTYPE html>

    <html lang="en">

    <head>

      <meta charset="UTF-8">

      <title>Document</title>

      <style>

        canvas {

          display: block;

          margin: 0 auto;

          border: 1px solid #222;

        }

      </style>

    </head>

    <body>

      <canvas id="my-canvas"></canvas>

      <canvas id="off-canvas" style="display: none;"></canvas>

      <script>

        var isMouseDown = false,

          scale = 1.0

        var canvas = document.querySelector("#my-canvas")

        var offCanvas = document.querySelector("#off-canvas") // 离屏 canvas

        var ctx = canvas.getContext("2d")

        var offCtx = offCanvas.getContext("2d") // 离屏 canvas 的 Context对象

        var img = new Image()

     

        window.onload = function () {

          img.src = "./img/photo.jpg"

     

          img.onload = function () {

            canvas.width = img.width

            canvas.height = img.height

     

            offCanvas.width = img.width

            offCanvas.height = img.height

     

            // 计算缩放比例

            scale = offCanvas.width / canvas.width

     

            // 初识状态下, 两个canvas均绘制Image

            ctx.drawImage(img, 0, 0, canvas.width, canvas.height)

            offCtx.drawImage(img, 0, 0, canvas.width, canvas.height)

     

          }

     

          // 鼠标按下

          canvas.onmousedown = function (event) {

            event.preventDefault() // 禁用默认事件

            var point = windowToCanvas(event.clientX, event.clientY) // 获取鼠标相对于 canvas 标签的坐标

            isMouseDown = true

            drawCanvasWithMagnifier(true, point) // 绘制在离屏canvas上绘制放大后的图像

          }

     

          // 鼠标移动

          canvas.onmousemove = function (event) {

            event.preventDefault() // 禁用默认事件

            if (isMouseDown === true) {

              var point = windowToCanvas(event.clientX, event.clientY)

              drawCanvasWithMagnifier(true, point)

            }

          }

     

          // 鼠标松开

          canvas.onmouseup = function (event) {

            event.preventDefault() // 禁用默认事件

            isMouseDown = false

            drawCanvasWithMagnifier(false) // 不绘制离屏放大镜

          }

     

          // 鼠标移出canvas标签

          canvas.onmouseout = function (event) {

            event.preventDefault() // 禁用默认事件

            isMouseDown = false

            drawCanvasWithMagnifier(false) // 不绘制离屏放大镜

          }

        }

     

        /**

        * 返回鼠标相对于canvas左上角的坐标

        * @param {Number} x 鼠标的屏幕坐标x

        * @param {Number} y 鼠标的屏幕坐标y

        */

        function windowToCanvas(x, y) {

          var bbox = canvas.getBoundingClientRect() // bbox中存储的是canvas相对于屏幕的坐标

          return {

            x: x - bbox.x,

            y: y - bbox.y

          }

        }

     

        function drawCanvasWithMagnifier(isShow, point) {

          ctx.clearRect(0, 0, canvas.width, canvas.height) // 清空画布

          ctx.drawImage(img, 0, 0, canvas.width, canvas.height) // 在画布上绘制图像

     

          /* 利用离屏,绘制放大镜 */

          if (isShow) {

            var { x, y } = point

     

            var mr = 50 // 正方形放大镜边长

     

            // (sx, sy): 待放大图像的开始坐标

            var sx = x - mr / 2,

              sy = y - mr / 2

     

            // (dx, dy): 已放大图像的开始坐标

            var dx = x - mr,

              dy = y - mr

     

            // 将offCanvas上的(sx,sy)开始的长宽均为mr的正方形区域

            // 放大到

            // canvas上的(dx,dy)开始的长宽均为 2 * mr 的正方形可视区域

            // 由此实现放大效果

            ctx.drawImage(offCanvas, sx, sy, mr, mr, dx, dy, 2 * mr, 2 * mr)

          }

          /*********************/

        }

      </script>

    </body>

    </html>

    ログイン後にコピー
    虫眼鏡の効果は次のとおりです ( でマークされた領域)赤いペンは正方形の虫眼鏡です):

    要約: 上記がこの記事の全内容です。皆さんの学習に役立つことを願っています。関連チュートリアルの詳細については、Html5 ビデオ チュートリアル

    をご覧ください。

    関連する推奨事項:

    php 公共福祉トレーニング ビデオ チュートリアル

    HTML5 グラフィック チュートリアル

    HTML5オンライン マニュアル

    以上がCanvas オフスクリーン テクノロジーと虫眼鏡の実装コード例の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

関連ラベル:
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート