Javascript 找角0-360

Javascript 找角0-360,javascript,Javascript,需要数学问题的帮助: 我需要使用x和y坐标从0度得到真实角度 我现在正在使用这个: Math.atan((x2-x1)/(y1-y2))/(Math.PI/180) 但是/(Math.PI/180)将结果限制在-90到90之间 我需要0-360 注意:我使用角度表示方向: 0=向上 90=对 135=向右45度+向下 180=向下 270=左 等 这应该可以做到: 如果y2 如果小于0,则添加360 示例: (x1,y1)=0 Math.atan将您限制在单位圆上最右边的两个象限内。要获得完

需要数学问题的帮助: 我需要使用x和y坐标从0度得到真实角度 我现在正在使用这个:

Math.atan((x2-x1)/(y1-y2))/(Math.PI/180)
但是
/(Math.PI/180)
将结果限制在-90到90之间 我需要0-360

注意:我使用角度表示方向:

  • 0=向上
  • 90=对
  • 135=向右45度+向下
  • 180=向下
  • 270=左

    • 这应该可以做到:

    • 如果y2
    • 如果小于0,则添加360 示例:

      (x1,y1)=0


      Math.atan将您限制在单位圆上最右边的两个象限内。要获得完整的0-360度,请执行以下操作:

      if x < 0 add 180 to the angle
      else if y < 0 add 360 to the angle. 
      
      如果x<0,则角度增加180
      否则,如果y<0,则向角度添加360。
      
      与我的坐标系相比,您的坐标系是旋转和反转的(与常规坐标系相比)。正x在右边,正y在上面。0度向右(x>0,y=0,90度向上(x=0,y>0)135度向左(y>0,x=-y)等。x轴和y轴指向何处?

      另请注意:

      if (y1==y2) {
          if (x1>x2)
              angle = 90;
          else if (x1<x2)
              angle = 270;
          else
              angle = 0;
      }
      
      if(y1==y2){
      如果(x1>x2)
      角度=90;
      否则如果(x1<代码>功能角度(x1,y1,x2,y2)
      {
      eangle=数学atan((x2-x1)/(y1-y2))/(数学PI/180)
      如果(角度>0)
      {
      if(y1
      atan函数只给出-pi/2和+pi/2之间的一半单位圆(x轴上为0),还有一个库函数可以给出-pi和+pi之间的整个单位圆,atan2

      我认为您最好使用atan2来获得正确的象限,而不是自己进行分支,然后像以前那样进行缩放,比如

      Math.atan2(y2 - y1, x2 - x1) * 180 / Math.PI + 180
      
      与问题中一样,+180乘以π只是从弧度到度的比例(但由于除法简化,+180确保其始终为正,即0-360度,而不是-180到180度

      angle=Math.atan(此.k)*180/Math.pi;
      
      angle = Math.atan(this.k) * 180 / Math.PI;
      angle = 180 - (angle < 0 ? 180 + angle : angle);
      angle = p2.Y > p1.Y || (p2.Y == p1.Y && p2.X > p1.X) ? 180 + angle : angle;
      
      角度=180-(角度<0?180+角度:角度); 角度=p2.Y>p1.Y | |(p2.Y==p1.Y&&p2.X>p1.X)?180+角度:角度;
      关于@jilles de wit和@jk.的回答让我走上了正确的道路,但由于某种原因,没有为我的问题提供正确的解决方案,我认为这与最初的问题非常相似

      我想像在航空导航系统中一样,向上=0°,向右=90°,向下=180°,向左=270°

      假设问题涉及画布绘画,我得出了以下解决方案:

      我首先使用
      ctx.translate(ctx.canvas.width/2,ctx.canvas.height/2)
      转换画布原点。我还将画布上鼠标事件得到的e.offsetX和e.offsedY减半,以获得与画布具有相同坐标系的x和y

      let radianAngle = Math.atan2(y, x);    // x has the range [-canvas.width/2 ... +canvas.width/2], y is similar
      let northUpAngle = radianAngle * 180 / PI + 90;    // convert to degrees and add 90 to shift the angle counterclockwise from it's default "left" = 0°
      if (x < 0 && y < 0) {    // check for the top left quadrant
          northUpAngle += 360;    // add 360 to convert the range of the quadrant from [-90...0] to [270...360] (actual ranges may vary due to the way atan2 handles quadrant boundaries)
      }
      northUpAngle.toFixed(2)    // to avoid getting 360° near the "up" position
      
      让radianAngle=Math.atan2(y,x);//x的范围为[-canvas.width/2…+canvas.width/2],y类似
      让northUpAngle=radianAngle*180/PI+90;//转换为度,再加上90,将角度从默认的“左”=0°逆时针移动
      如果(x<0&&y<0){//检查左上象限
      northUpAngle+=360;//添加360以将象限的范围从[-90…0]转换为[270…360](实际范围可能因atan2处理象限边界的方式而异)
      }
      northUpAngle.toFixed(2)//避免在“向上”位置附近获得360度
      

      使用模运算可能有一个更简洁的解决方案,但我找不到它。

      对于0=向上,90=向右,180=向下,270=向左等(x=x2-x1,y=y2-y1)

      您可以使用以下公式:

      f(x,y)=180-90*(1+sign(y))* (1-sign(x^2))-45*(2+sign(y))*sign(x)
      
      -(180/pi())*sign(x*y)*atan((abs(y)-abs(x))/(abs(y)+abs(x)))
      

      这里有两个解决方案,一个是Math.atan(取相反/相邻的分数),另一个是Math.atan2(取两个参数)

      具有讽刺意味的是,解决方案是用ES6(ES2015+)语法编写的,因为这个问题早于此javascript

      请注意,“向右”为0°(=0弧度);向上为90°(=PI/2);向左为180°(PI),向下为270°(PI*1.5)

      所以用一个decesion(我希望这个丑陋的basiclike符号可以解释它):

      如果x=0,则

      360度=270-(符号(x)+1)*90

      否则

      360度=模数(180+(符号(y)+1)*90+ATAN(x/y),360)

      恩迪夫

      要顺时针从北0度到360度绘制一个完整的圆:

      x=SIN(0到360)y=COS(0到360)


      干杯,列夫

      像这样吗?var add=0 var x=x2-x1 var y=y2-y1 if(xcorrection:var add=0 var x=x2-x1 var y=y2-y1 if(xNo,在除以(pi/180)后加上数字)否则,加法应该是math.PI而不是180,2*math.PI而不是360。你能解释一下……atan2给出了什么吗?为什么你从180乘然后除以math。PI+180atan2可以给你正确的象限不起作用,原因如下:他们从字母顺序颠倒了x和y。愚蠢但正确。@CandiedOrange TA-fixedIn除了加90,再加450,然后使用模:
      (Math.atan2(y,x)*180/Math.PI+450)%360
      。为什么向上=0°?不应该是0°?我在基于矢量的坐标中工作system@JasonFB我正在创建一个交互式航向仪表,所以我想显示角度值。旋转坐标系以实现此目的。对。我只是问坐标系旋转的地方是否有不同的字段/扇区?(我认为0°=‘向右’是标准的,直到我遇到其他人将其实现为0°=‘向上’)这个解决方案尽管被否决,但解决了象限问题。我认为也许正确的术语是“轨迹”而不是“角度”
      let radianAngle = Math.atan2(y, x);    // x has the range [-canvas.width/2 ... +canvas.width/2], y is similar
      let northUpAngle = radianAngle * 180 / PI + 90;    // convert to degrees and add 90 to shift the angle counterclockwise from it's default "left" = 0°
      if (x < 0 && y < 0) {    // check for the top left quadrant
          northUpAngle += 360;    // add 360 to convert the range of the quadrant from [-90...0] to [270...360] (actual ranges may vary due to the way atan2 handles quadrant boundaries)
      }
      northUpAngle.toFixed(2)    // to avoid getting 360° near the "up" position
      
      f(x,y)=180-90*(1+sign(y))* (1-sign(x^2))-45*(2+sign(y))*sign(x)
      
      -(180/pi())*sign(x*y)*atan((abs(y)-abs(x))/(abs(y)+abs(x)))
      
      angleGivenCoords(coord1,coord2) {
          // given two coords {x,y}, calculate the angle in radians with
          // right being 0° (0 radians)
      
          if (coord1.x === coord2.x) return (coord1.y > coord2.y ? Math.PI * 0.5 : Math.PI * 1.5)
          if (coord1.y === coord2.y) return (coord1.x > coord2.x ? Math.PI : 0 )
      
          let opposite = coord2.x - coord1.x
          let adjacent = coord1.y - coord2.y
          let adjustor = ((coord2.x < coord1.x && coord2.y < coord1.y) || (coord2.x < coord1.x && coord2.y > coord1.y)) ?  Math.PI : 0
      
          let res = Math.atan(opposite/adjacent) + adjustor
      
          if (res < 0) { res = res + Math.PI*2  }
          return res ;
        }
      
        angleGivenCoords(coord1,coord2) {
          // given two coords {x,y}, calculate the angle in radians with
          // left being 0° (0 radians)
          let opposite = coord2.x - coord1.x
          let adjacent = coord1.y - coord2.y
          let res = Math.atan2(adjacent, opposite)
          if (res < 0) { res = res + Math.PI*2  }
          return res ;
        }
      
       it('for right 0°', () => {
          let coord1 = {x: 500, y: 500},
            coord2 = {x: 600, y: 500}
          expect(Trig.angleGivenCoords(coord1,coord2)).toEqual(Trig.degreesToRadians(0))
        })
      
      
        it('for up-right 45°', () => {
          let coord1 = {x: 500, y: 500},
            coord2 = {x: 600, y: 400}
          expect(Trig.angleGivenCoords(coord1,coord2)).toEqual(Trig.degreesToRadians(45))
        })
      
        it('for 90° up', () => {
          let coord1 = {x: 500, y: 500},
            coord2 = {x: 500, y: 400}
          expect(Trig.angleGivenCoords(coord1,coord2)).toEqual(Trig.degreesToRadians(90))
        })
      
      
        it('for 135° up to left', () => {
          let coord1 = {x: 500, y: 500},
            coord2 = {x: 400, y: 400}
          expect(Trig.angleGivenCoords(coord1,coord2)).toEqual(Trig.degreesToRadians(135))
        })
      
        it('for 180° to left', () => {
          let coord1 = {x: 500, y: 500},
            coord2 = {x: 400, y: 500}
          expect(Trig.angleGivenCoords(coord1,coord2)).toEqual(Trig.degreesToRadians(180))
        })
      
      
        it('for 225° to to bottom left', () => {
          let coord1 = {x: 500, y: 500},
            coord2 = {x: 400, y: 600}
          expect(Trig.angleGivenCoords(coord1,coord2)).toEqual(Trig.degreesToRadians(225))
        })
      
        it('for 270° to the bottom', () => {
          let coord1 = {x: 500, y: 500},
            coord2 = {x: 500, y: 600}
          expect(Trig.angleGivenCoords(coord1,coord2)).toEqual(Trig.degreesToRadians(270))
        })
      
        it('for 315° to the bottom', () => {
          let coord1 = {x: 500, y: 500},
            coord2 = {x: 600, y: 600}
          expect(Trig.angleGivenCoords(coord1,coord2)).toEqual(Trig.degreesToRadians(315))
        })