Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

формула вывода прямой по двум точкам

42K
07 апреля 2010 года
goodking
19 / / 09.06.2009
Привет! Вопрос следующий: пытаюсь вывести на графический ЖКИ линию по двум заданным точкам (x1,x2,y1,y2)

Код:
x1=10;
y1=15;

x2=67;
y2=50;


for (x=x1;x<x2;x++)
{
y=((((x-x1)/(x2-x1))*(y2-y1))+y1);

PutPixelXYLCD(x,y,1);//подпрограмма установки бита по заданному адресу
};


но переменная y вообще не изменяется, поэтому линия получается только горизонтальной! Подскажите, с чем это связано?
9.7K
07 апреля 2010 года
oltzowwa
105 / / 15.02.2007
Видимо переменные целочисленного типа?
42K
07 апреля 2010 года
goodking
19 / / 09.06.2009
Цитата: oltzowwa
Видимо переменные целочисленного типа?



да, unsigned char

14K
07 апреля 2010 года
Fenja
138 / / 20.03.2009
При делении у тебя ж получаются дробные числа :)
43K
07 апреля 2010 года
loki231
76 / / 27.09.2009
Согласно правилам языка C (и C++) результатом деления целых чисел является целое число, равное целой части частного. Т.е. 3/2=1, 3/4=0, 8/3=2.

В Вашем примере (x-x1) меньше по модулю, чем (x2-x1). поэтому (x-x1)/(x2-x1) равно 0, соответственно и всё первое слагаемое равно 0 и y==y1.

Ситуацию можно попытаться улучшить, если вычислять выражение в другом порядке: (x-x1)*(y2-y1)/(x2-x1)+y1. В этом случае, сначала выполнится умножение, потом деление и результат будет гораздо ближе к тому, который Вы ожидаете. Но (x-x1)*(y2-y1) легко может вызвать переполнение, со всеми вытекающими последствиями. Поэтому лучше сперва преобразовать операнды к какому-либо плавающему типу. Например так y=(float)(x-x1)/(float)(x2-x1)*(y2-x1)+y1. Но скорость работы такотго алгоритма очень низкая. Известен гораздо более эффективный алгоритм рисования линии - алгоритм Брезенхема. С некоторыми модификациями он применим и к рисованию окружности.
42K
07 апреля 2010 года
goodking
19 / / 09.06.2009
спасибо. с линией уже получилось! А вот насчет окружности, я вывожу ее по такому способу:

Код:
void circle (double x1,double y1, double radius)

{


for (x=x1-radius;x<x1+radius;x++)
{
y= sqrt(radius*radius-((x-x1)*(x-x1)))+y1;// рассчет окружности

yi=(unsigned char) y;
xi=(unsigned char) x;


PutPixelXYLCD(xi,yi,1);

y=y1- sqrt(radius*radius-((x-x1)*(x-x1)));// верхний полукруг
yi=(unsigned char)y;

PutPixelXYLCD(xi,yi,1);
}
}


окружность выводится, но почему-то не совсем четко, многие точки, ближе к горизонтальной оси не высвечиваются, как это улучшить??:)
30K
07 апреля 2010 года
cpentyc
85 / / 23.02.2010
а что если пробегать 360 градусов по окружности
 
Код:
...
double alfa=0;
while(a<6.28)// вот только не помню в сях какой угол в радианах или градусах
{
x=radiys*cos(alfa);
y=radiys*sin(alfa);
a+=0.001;
...
}
7
07 апреля 2010 года
@pixo $oft
3.4K / / 20.09.2006
В радианах он,в радианах…Вот только ваш код не совсем понятен,особенно a и alfa.Ну я,допустим,понял,а [SIZE="1"][COLOR="Silver"]нерадивый[/COLOR][/SIZE] студент,создавший эту тему?

И да,надо с достаточной точностью увеличивать угол,а то получится не сплошной круг,а из точечек:)
42K
08 апреля 2010 года
goodking
19 / / 09.06.2009
Цитата: cpentyc
а что если пробегать 360 градусов по окружности
 
Код:
...
double alfa=0;
while(a<6.28)// вот только не помню в сях какой угол в радианах или градусах
{
x=radiys*cos(alfa);
y=radiys*sin(alfa);
a+=0.001;
...
}


А зачем нужно a? Почему нельзя использовать alfa
и еще, почему-то

 
Код:
alfa+=0,001
не работало, :confused: alfa вообще не изменялось, поменял на
 
Код:
alfa++
-все нормально.

А так все получилось, спасибо большое!:):)
Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог