{"size": 2361, "ext": "js", "max_stars_repo_path": "src/image-target/icp/utils.js", "max_stars_repo_name": "mrdysbv/mm", "max_stars_repo_stars_event_min_datetime": "2020-09-24T04:47:53.000Z", "max_stars_repo_stars_event_max_datetime": "2021-08-31T21:53:09.000Z", "max_issues_repo_path": "src/image-target/icp/utils.js", "max_issues_repo_name": "mrdysbv/mm", "max_issues_repo_issues_event_min_datetime": "2021-08-31T22:02:13.000Z", "max_issues_repo_issues_event_max_datetime": "2021-08-31T22:02:13.000Z", "max_forks_repo_path": "vc/src/image-target/icp/utils.js", "max_forks_repo_name": "mrdysbv/mrdysbv.github.io", "max_forks_repo_forks_event_min_datetime": "2020-12-07T14:21:27.000Z", "max_forks_repo_forks_event_max_datetime": "2021-08-31T21:53:23.000Z"}
{"max_stars_count": 14, "max_issues_count": 1, "max_forks_count": 2, "avg_line_length": 47.22, "max_line_length": 105, "alphanum_fraction": 0.6874205845}
const buildModelViewProjectionTransform = (projectionTransform, modelViewTransform) => {
  const modelViewProjectionTransform = [[],[],[]];
  for (let j = 0; j < 3; j++ ) {
    for (let i = 0; i < 4; i++) {
      modelViewProjectionTransform[j][i] = projectionTransform[j][0] * modelViewTransform[0][i]
                                         + projectionTransform[j][1] * modelViewTransform[1][i]
                                         + projectionTransform[j][2] * modelViewTransform[2][i];
    }
  }
  return modelViewProjectionTransform;
}

const applyModelViewProjectionTransform = (modelViewProjectionTransform, x, y, z) => {
  const ux = modelViewProjectionTransform[0][0] * x + modelViewProjectionTransform[0][1] * y
     + modelViewProjectionTransform[0][2] * z + modelViewProjectionTransform[0][3];
  const uy = modelViewProjectionTransform[1][0] * x + modelViewProjectionTransform[1][1] * y
     + modelViewProjectionTransform[1][2] * z + modelViewProjectionTransform[1][3];
  const uz  = modelViewProjectionTransform[2][0] * x + modelViewProjectionTransform[2][1] * y
     + modelViewProjectionTransform[2][2] * z + modelViewProjectionTransform[2][3];
  return {x: ux, y: uy, z: uz};
}

const computeScreenCoordiate = (modelViewProjectionTransform, x, y, z) => {
  const {x: ux, y: uy, z: uz} = applyModelViewProjectionTransform(modelViewProjectionTransform, x, y, z);
  if( Math.abs(uz) < 0.000001 ) return null;
  return {x: ux/uz, y: uy/uz};
}

const screenToMarkerCoordinate = (modelViewProjectionTransform, sx, sy) => {
  const c11 = modelViewProjectionTransform[2][0] * sx - modelViewProjectionTransform[0][0];
  const c12 = modelViewProjectionTransform[2][1] * sx - modelViewProjectionTransform[0][1];
  const c21 = modelViewProjectionTransform[2][0] * sy - modelViewProjectionTransform[1][0];
  const c22 = modelViewProjectionTransform[2][1] * sy - modelViewProjectionTransform[1][1];
  const b1  = modelViewProjectionTransform[0][3] - modelViewProjectionTransform[2][3] * sx;
  const b2  = modelViewProjectionTransform[1][3] - modelViewProjectionTransform[2][3] * sy;

  const m = c11 * c22 - c12 * c21;
  return {
    x: (c22 * b1 - c12 * b2) / m,
    y: (c11 * b2 - c21 * b1) / m
  }
}

module.exports = {
  screenToMarkerCoordinate,
  buildModelViewProjectionTransform,
  applyModelViewProjectionTransform,
  computeScreenCoordiate
}
