Точка пересечения для круговых морфов

Я пытаюсь найти точки пересечения для круга с помощью этой ссылки.

введите здесь описание изображения

В следующем примечании описывается, как найти точку (точки) пересечения двух окружностей на плоскости. Используются следующие обозначения. Цель состоит в том, чтобы найти две точки P3 = (x3, y3), если они существуют.

Сначала рассчитайте расстояние d между центрами кругов. d = ||P1 - P0||.

Если d > r0 + r1, то решений нет, кружки отдельные. Если d ‹ |r0 - r1| тогда решений нет, потому что один круг содержится внутри другого. Если d = 0 и r0 = r1, то окружности совпадают и существует бесконечное число решений. Рассматривая два треугольника P0P2P3 и P1P2P3, мы можем написать

a2 + h2 = r02 и b2 + h2 = r12

Используя d = a + b, мы можем найти a,

a = (r02 - r12 + d2 ) / (2 d)

Легко показать, что это сводится к r0, когда две окружности соприкасаются в одной точке, т.е.: d = r0 + r1 Решите для h, подставив a в первое уравнение, h2 = r02 - a2 Итак

P2 = P0 + a ( P1 - P0 ) / d

И, наконец, P3 = (x3,y3) через P0 = (x0,y0), P1 = (x1,y1) и P2 = (x2,y2), равно

x3 = x2 +- h ( y1 - y0 ) / d

y3 = y2 - + h ( x1 - x0 ) / d http://paulbourke.net/geometry/2circle/

b:=CircleMorph new.
b center: 60@60.
b openInWorld.
b1:=CircleMorph new.
b center: 100@100.
b1 openInWorld.
d:= b1 center - b center. // distance between 2 circles
r1:= (((b center x abs)squared +(b  center y abs)squared)sqrt).
r2:= (((b1 center x abs)squared +(b1  center y abs)squared)sqrt).
r3:= r1+ r2.
(d) > (r3) ifTrue:[Transcript show:'Circles are seprate';cr]

Когда я сравниваю расстояние с суммой радиусов двух кругов, получается расстояние меньше, чем радиус обоих кругов, что, как я знаю, неверно, когда круги разделены. Правильно ли я вычисляю радиус или нет, с этой помощью возникает некоторая проблема.


person Irfan    schedule 12.09.2012    source источник
comment
Вы думали об использовании DrGeo2   -  person aka.nice    schedule 14.09.2012
comment
Обратите внимание, что // не является началом комментария. "Comments in Smalltalk look like this".   -  person Frank Shearar    schedule 23.09.2012


Ответы (1)


Одно из возможных решений таково:

| b b1 d r1 r2 r3 |
b := CircleMorph new.
b center: 60@60.
b bounds: (Rectangle origin: 100@40 corner: 40@100).
b openInWorld.
b1 := CircleMorph new.
b center: 100@100.
b bounds: (Rectangle origin: 100@40 corner: 40@100).
b1 openInWorld.
r1 := b bounds width / 2.
r2 := b1 bounds width / 2.
r3 := r1+ r2.
(d < r3)
    ifTrue: [| a h mid |
        a := (r1 squared - r2 squared + d squared) / (2 * d).
        h := (r1 squared - a squared) sqrt.
        mid := (b1 center x - b center x) @ (b1 center y - b center y).
        {(mid x + (h * (b1 center y - b center y))) @ (mid y - (h * (b1 center x - b center x))).
        (mid x - (h * (b1 center y - b center y))) @ (mid y + (h * (b1 center x - b center x)))}]
    ifFalse: ['separate']

Вы захотите проверить мою арифметику. (Обновление: я не использовал точку между двумя центрами окружностей для расчета точек.)

person Frank Shearar    schedule 12.09.2012
comment
Также d - это не расстояние, это точка, представляющая координаты x@y вектора от b до b1, используйте (b1 center dist: b center). - person aka.nice; 12.09.2012
comment
Спасибо, теперь я понял, что, если расстояние = радиус1 + радиус2 (d = r1 + r2), как мне получить только одну точку пересечения??? - person Irfan; 14.09.2012
comment
Вам понадобится особый случай, возможно, с (d - (r1 + r2)) < 0.001 ifTrue: [...] или подобным. - person Frank Shearar; 14.09.2012
comment
Вот что я сделал, чтобы получить только одну точку пересечения, когда расстояние равно радиусу окружности '(d)=(r1+r2) ifTrue[|m| m:=((b1 center x + b center x)/2)@ ((b1 center y + b center y)/2)]' как вы думаете, его истинная центральная точка может быть точкой пересечения??? - person Irfan; 16.09.2012
comment
Рассмотрим две окружности с одинаковым радиусом, которые просто касаются друг друга. Присоединяйтесь к их центрам. Круги будут касаться друг друга в середине этой линии. Если радиус одного круга в два раза больше радиуса другого, круги будут касаться линии на расстоянии 2/3 ее длины от большего круга, и так далее. - person Frank Shearar; 16.09.2012
comment
Привет, можешь мне помочь, например, создать метод для радиуса. Я хочу создать отдельный метод радиуса, который я могу использовать в любое время для вычисления радиуса любого заданного круга. - person Irfan; 23.09.2012
comment
Радиус равен половине ширины круга bounds. Так что это просто radius\n^ self bounds width / 2 - person Frank Shearar; 23.09.2012
comment
Спасибо за помощь, я все еще пытаюсь все это изучить, я также хочу добавить метод пересечения, как мне это сделать, который будет выполнять все проверки условий и давать результирующие точки пересечения. - person Irfan; 23.09.2012
comment
Вы задаете много разных вопросов. На них легче ответить, задавая отдельные вопросы, а не задавая их в комментариях. - person Frank Shearar; 23.09.2012