我正在将画布的比例大小从 webgl 更改为 hammer.js

问题描述 投票:0回答:0

正在开发中,以便可以使用 spine 程序校正头发图像。

https://bxkrl.com/maskon-master/public/hair.html 这是测试网址。

本例中使用hammer.js来增减画布比例。 如果放大或缩小画布的比例,图像校正触摸点会有所不同。

Image usage examples

为了调整不同的触摸点,我需要改变x和y。我应该如何根据比例的变化来改变它们?

头发.html `

<center>
    <div class="aspect standalone"></div>

</center>

<script>
    spineDemos.init();
    spineDemos.addDemo(vineDemo, document.getElementsByClassName("aspect")[0]);
</script>

 </body>

</html>

`

hair_1.js

var vineDemo = function(canvas, bgColor) {
var COLOR_INNER = new spine.Color(0.0, 0, 0, 0.0);
var COLOR_OUTER = new spine.Color(0.0, 0, 0, 0.0);
var COLOR_INNER_SELECTED = new spine.Color(0.0, 0, 0.0, 0.0);
var COLOR_OUTER_SELECTED = new spine.Color(0.0, 0, 0.0, 0.0);

  var canvas, gl, renderer, input, assetManager;
  var skeleton, state, bounds, position;
  var target = null;
  var hoverTargets = [null, null, null, null, null, null, null];
  var controlBones = [
    "bone2", "bone3", "bone4", "bone5", "bone6", "bone7", "bone8", "bone9", "bone10", "bone11", "bone12", "bone13", "bone14", "bone15", "bone16", "bone17", "bone18", "bone19", "bone20", "bone21", "bone22", "bone23", "bone24", "bone25", "bone26", "middlebone1", "middlebone2", "middlebone3", "middlebone4", "middlebone5", "middlebone6", "middlebone7", "middlebone8", "middlebone9", "middlebone10", "bone27", "bone28", "bone29", "bone30", "bone31", "bone32"
  ];
  var coords = new spine.Vector3(),
    temp = new spine.Vector3(),
    temp2 = new spine.Vector2();

  bgColor = new spine.Color(0, 0, 0, 0);
  canvas.context = new spine.ManagedWebGLRenderingContext(canvas, {
    alpha: true,
    premultipliedAlpha: false
  });

  function init() {
    gl = canvas.context.gl;
    renderer = new spine.SceneRenderer(canvas, gl);
    input = new spine.Input(canvas);
    assetManager = new spine.AssetManager(gl, spineDemos.path, spineDemos.downloader);

    assetManager.loadTextureAtlas("skeleton.atlas");
    assetManager.loadJson("skeleton.json");
  }

  function loadingComplete() {
    var atlasLoader = new spine.AtlasAttachmentLoader(assetManager.get("skeleton.atlas"));
    var skeletonJson = new spine.SkeletonJson(atlasLoader);
    var skeletonData = skeletonJson.readSkeletonData(assetManager.get("skeleton.json"));
    skeleton = new spine.Skeleton(skeletonData);
    skeleton.setToSetupPose();
    skeleton.updateWorldTransform();
    var offset = new spine.Vector2();
    bounds = new spine.Vector2();


    skeleton.getBounds(offset, bounds, []);
    skeleton.updateWorldTransform();

    skeleton.color = {
      r: 0.2,
      g: 0.2,
      b: 0.2,
      a: 1
    };



    renderer.camera.position.x = offset.x + bounds.x / 2;
    renderer.camera.position.y = offset.y + bounds.y / 2;

    renderer.skeletonDebugRenderer.drawMeshHull = false;
    renderer.skeletonDebugRenderer.drawMeshTriangles = false;

    setupUI();
    setupInput();

  }

  function setupUI() {

    renderer.skeletonDebugRenderer.drawPaths = false;
    renderer.skeletonDebugRenderer.drawBones = false;
  }

  function setupInput() {


    input.addListener({
      down: function(x, y) {
        target = spineDemos.closest(canvas, renderer, skeleton, controlBones, hoverTargets, x, y);
      },
      up: function(x, y) {
        target = null;
      },
      dragged: function(x, y) {
        spineDemos.dragged(canvas, renderer, target, x, y);
      },
      moved: function(x, y) {
        spineDemos.closest(canvas, renderer, skeleton, controlBones, hoverTargets, x, y);
      }
    });
 }

  function render() {


    skeleton.updateWorldTransform();

    renderer.camera.viewportWidth = bounds.x * 1.2;
    renderer.camera.viewportHeight = bounds.y * 1.2;
    renderer.resize(spine.ResizeMode.Fit);


    gl.clearColor(bgColor.r, bgColor.g, bgColor.b, bgColor.a);


    gl.clear(gl.COLOR_BUFFER_BIT);


    renderer.begin();
    renderer.drawSkeleton(skeleton, true);

    renderer.end();

    let stage = document.querySelector("canvas");



    let mc = new Hammer.Manager(stage);
    let pan = new Hammer.Pan({
      pointers: 2
    });
    let rotate = new Hammer.Rotate();
    let pinch = new Hammer.Pinch();

    mc.add([pan, pinch, rotate]);
    mc.get('pinch').set({
      enable: true
    });
    mc.get('rotate').set({
      enable: true
    });

    let adjustDeltaX = 0;
    let adjustDeltaY = 0;
    let adjustScale = 1;
    let adjustRotation = 0;

    let currentDeltaX = null;
    let currentDeltaY = null;
    let currentScale = null;
    let currentRotation = null;

    mc.on("panstart pinchstart rotatestart", function(e) {
      adjustRotation -= e.rotation;
    });

    mc.on("panmove pinchmove rotatemove", function(e) {
      currentRotation = adjustRotation + e.rotation;
      currentScale = adjustScale * e.scale;
      currentDeltaX = adjustDeltaX + (e.deltaX / currentScale);
      currentDeltaY = adjustDeltaY + (e.deltaY / currentScale);

      let transforms = ['scale(' + currentScale + ')'];
      if (transforms) {

        let e = canvas.clientWidth * currentScale;
        let t = canvas.clientHeight * currentScale;
        // resizescale = currentScale-1;

      }
      transforms.push('translate(' + currentDeltaX + 'px,' + currentDeltaY + 'px)');
      transforms.push('rotate(' + Math.round(currentRotation) + 'deg)');
      stage.style.transform = transforms.join(' ');
    });

    mc.on("panend pinchend rotateend", function(e) {
      adjustScale = currentScale;
      adjustRotation = currentRotation;
      adjustDeltaX = currentDeltaX;
      adjustDeltaY = currentDeltaY;
    });
  }

  init();
  vineDemo.assetManager = assetManager;
  vineDemo.loadingComplete = loadingComplete;
  vineDemo.render = render;
};`

util.js

`

    var spineDemos = {
    HOVER_COLOR_INNER: new spine.Color(0, 0, 0, 0.0),
    HOVER_COLOR_OUTER: new spine.Color(1, 1, 1, 1.0),
    NON_HOVER_COLOR_INNER: new spine.Color(0, 0, 0, 0.0),
    NON_HOVER_COLOR_OUTER: new spine.Color(0, 0, 0, 0.0),
    demos: [],
    loopRunning: false,
    canvases: [],
    downloader: new spine.Downloader(),
    path: "assets/"
    };

(function() {
  var timeKeeper = new spine.TimeKeeper();

  function loop() {
    timeKeeper.update();
    if (spineDemos.log) console.log(timeKeeper.delta + ", " + timeKeeper.framesPerSecond);
    requestAnimationFrame(loop);
    var demos = spineDemos.demos;
    for (var i = 0; i < demos.length; i++) {
      var demo = demos[i];
      checkElementVisible(demo);
      renderDemo(demo);
    }
  }

  function renderDemo(demo) {
    if (demo.visible) {
      var canvas = demo.canvas;

      if (canvas.parentElement != demo.placeholder) {
        $(canvas).detach();
        demo.placeholder.appendChild(canvas);
      }
      let complete = demo.assetManager.isLoadingComplete();
      if (complete) {
        if (!demo.loaded) {
          demo.loaded = true;
          demo.loadingComplete();
        }
        if (spineDemos.log) console.log("Rendering: " + canvas.id);
        demo.render();
      }
      demo.loadingScreen.draw(complete);
    }
  }

  function checkElementVisible(demo) {
    const rect = demo.placeholder.getBoundingClientRect();
    const windowHeight = (window.innerHeight || document.documentElement.clientHeight);
    const windowWidth = (window.innerWidth || document.documentElement.clientWidth);
    const vertInView = (rect.top <= windowHeight * 1.1) && ((rect.top + rect.height) >= windowHeight * -0.1);
    const horInView = (rect.left <= windowWidth * 1.1) && ((rect.left + rect.width) >= windowWidth * -0.1);

    demo.visible = (vertInView && horInView);
  }

  function createCanvases(numCanvases) {
    for (var i = 0; i < numCanvases; i++) {
      var canvas = document.createElement("canvas");

      canvas.width = 0;
      canvas.height = 0;
      // canvas.context = new spine.ManagedWebGLRenderingContext(canvas, { alpha: true });
      canvas.context = new spine.ManagedWebGLRenderingContext(canvas, {
        alpha: true,
        premultipliedAlpha: false
      });
      canvas.id = "canvas-" + i;
      canvas.style.cssText = `
           position: absolute;
           `
      spineDemos.canvases.push(canvas);
    }
  }

  spineDemos.init = function() {
    var numCanvases = 5;
    var isFirefox = navigator.userAgent.toLowerCase().indexOf('firefox') > -1;
    var isAndroid = navigator.userAgent.toLowerCase().indexOf("android") > -1;
    if (isFirefox && isAndroid) numCanvases = 2;
    createCanvases(numCanvases);

    requestAnimationFrame(loop);

  }

  spineDemos.addDemo = function(demo, placeholder) {
    var canvas = spineDemos.canvases[spineDemos.demos.length % spineDemos.canvases.length];
    demo(canvas);
    demo.placeholder = placeholder;
    demo.canvas = canvas;
    demo.visible = false;
    var renderer = new spine.SceneRenderer(canvas, canvas.context.gl);
    demo.loadingScreen = new spine.LoadingScreen(renderer);

    $(window).on('DOMContentLoaded load resize scroll', function() {
      checkElementVisible(demo);
      renderDemo(demo);
    });
    checkElementVisible(demo);
    spineDemos.demos.push(demo);
  }

  var coords = new spine.Vector3();
  var mouse = new spine.Vector3();
  spineDemos.closest = function(canvas, renderer, skeleton, controlBones, hoverTargets, x, y) {
    mouse.set(x, canvas.clientHeight - y, 0)
    var bestDistance = 250,
      index = 0;
    var best;
    for (var i = 0; i < controlBones.length; i++) {
      hoverTargets[i] = null;
      let bone = skeleton.findBone(controlBones[i]);
      var position = new spine.Vector2(bone.length, 0);
      bone.localToWorld(position);
      let distance = renderer.camera.worldToScreen(
        coords.set(bone.worldX, bone.worldY, 0),
        canvas.clientWidth, canvas.clientHeight).distance(mouse);
      if (distance < bestDistance) {
        bestDistance = distance;
        best = bone;
        index = i;
      }
    }
    if (best) hoverTargets[index] = best;
    return best;
  };

  var position = new spine.Vector3();
  spineDemos.dragged = function(canvas, renderer, target, x, y) {
    if (target) {
      x = spine.MathUtils.clamp(x, 0, canvas.clientWidth)
      y = spine.MathUtils.clamp(y, 0, canvas.clientHeight);
      renderer.camera.screenToWorld(coords.set(x, y, 0), canvas.clientWidth, canvas.clientHeight);
      if (target.parent !== null) {
        target.parent.worldToLocal(position.set(coords.x, coords.y));
        target.x = position.x;
        target.y = position.y;
      } else {
        target.x = coords.x;
        target.y = coords.y;
      }
    }
  };


})();`

尝试代码 `

let transforms = 'scale(' + currentScale + ')';
    if (transforms) {

    let e = canvas.clientWidth * currentScale;
    let t = canvas.clientHeight * currentScale;
    // resizescale = currentScale-1;

  }

` 随着画布比例的增加和减小,x、y 坐标被赋予相同的比例大小,但在不同的方向上移动。

       x = x - canvas.width / 2 + centerX / resizescale;         y = canvas.height / 2 - y + centerY / resizescale;

hammer.js
© www.soinside.com 2019 - 2024. All rights reserved.