Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Прочее";
Текущий архив: 2008.12.28;
Скачать: [xml.tar.bz2];

Вниз

Помогите разобраться с построением   Найти похожие ветки 

 
@!!ex ©   (2008-11-01 16:52) [0]

TPoint = record
 x,y,z:single;  //Позиция точки в пространстве
 time:integer;  //Время
end;

Есть
список точек в 3D пространстве Points:array of TPoint отсортированных по time.
текущее время CurrentTime:integer;
инертность inert:single;

По сути набор точек задает траекторию движения объекта. Ключевые позиции.
Нужно получить позицию объекта в текущий момент времени.
Если время попадает на ключевую позицию, то просто значение позиции возвращается.
А вот если нужно интерполировать, то проблема.
inert - это коэфициент инертности. Если коэфициент 0 - то все просто, линейная интерполяция дает нужный результат.
Если коэфициент 1 - нужен идеально гладкий сплайн.

Проблема в том, что я не умею сплайны в 3Д строить. и инет не очень то делится инфой.
Математических знаний хватило на то, чтобы понять, что будет кривая третьего порядка, но как ее строить - х.з.


 
MBo ©   (2008-11-01 17:06) [1]

>нужен идеально гладкий сплайн.
Если устроит гладкость первого порядка (согласование по первой производной), то легче всего использовать сплайны Кэтмулл-Рома (частный случай TCB-сплайнов). По четырем соседним точкам рассчитывается полином между второй и третьей точкой.

Гладкость второго порядка - согласование в узлах по производной (наклону) и по второй производной (кривизне)
Кубичеси\кие интерполяционные сплайны достаточно широко освещены, иcходники найти нетрудно (например, alglib.sources.ru).
Правда, в большинстве случаев рассматривается двумерный случай с параметризацией по X, тебе же лучше использовать параметрические сплайны, выбрав нужную параметризацию. Единого мнения о том, какая параметризация кошернее, нету. В простейшем случае - по номеру точки, если точки относительно равномерно расположены. Можно и по расстоянию между ними.


 
MBo ©   (2008-11-01 17:15) [2]

Да, еще обратил внимание на твой коэффициент 0-1. Если нужны и промежуточные значения, то TCB-сплайны (Kochanek-Bartels) - то, что доктор прописал - параметр T (tension) меняешь в нужных пределах, а С и B нулевые (или единичные, не помню), и получаешь нужные результаты


 
@!!ex ©   (2008-11-01 18:56) [3]

Нашел аглоритм построения сплайна Кэтмулл-Рома.
Но пробелма в том, что он для 2Д случая. Как на 3Д переделать? Знаний не хватает. :(

PROCEDURE Spline_Calc (Ap, Bp, Cp, Dp: Point3D; T, D: Real; Var X, Y: Real);
VAR T2, T3: Real;
BEGIN
  T2 := T * T;           { Square of t }
  T3 := T2 * T;          { Cube of t }
  X := ((Ap.X*T3) + (Bp.X*T2) + (Cp.X*T) + Dp.X)/D;  { Calc x value }
  Y := ((Ap.Y*T3) + (Bp.Y*T2) + (Cp.Y*T) + Dp.Y)/D;  { Calc y value }
END;

PROCEDURE Catmull_Rom_ComputeCoeffs (N: Integer; Var Ap, Bp, Cp, Dp: Point3D);
BEGIN
  Ap.X := -CtrlPt[N-1].X + 3*CtrlPt[N].X - 3*CtrlPt[N+1].X + CtrlPt[N+2].X;
  Bp.X := 2*CtrlPt[N-1].X - 5*CtrlPt[N].X + 4*CtrlPt[N+1].X - CtrlPt[N+2].X;
  Cp.X := -CtrlPt[N-1].X + CtrlPt[N+1].X;
  Dp.X := 2*CtrlPt[N].X;
  Ap.Y := -CtrlPt[N-1].Y + 3*CtrlPt[N].Y - 3*CtrlPt[N+1].Y + CtrlPt[N+2].Y;
  Bp.Y := 2*CtrlPt[N-1].Y - 5*CtrlPt[N].Y + 4*CtrlPt[N+1].Y - CtrlPt[N+2].Y;
  Cp.Y := -CtrlPt[N-1].Y + CtrlPt[N+1].Y;
  Dp.Y := 2*CtrlPt[N].Y;
END;


 
@!!ex ©   (2008-11-01 18:57) [4]

Стоп. Или все просто и я туплю??


 
@!!ex ©   (2008-11-01 18:59) [5]

Координаты же вроде одинаково считаются...
Для трех координат будет так:
PROCEDURE Spline_Calc (Ap, Bp, Cp, Dp: Point3D; T, D: Real; Var X, Y, Z: Real);
VAR T2, T3: Real;
BEGIN
  T2 := T * T;           { Square of t }
  T3 := T2 * T;          { Cube of t }
  X := ((Ap.X*T3) + (Bp.X*T2) + (Cp.X*T) + Dp.X)/D;  { Calc x value }
  Y := ((Ap.Y*T3) + (Bp.Y*T2) + (Cp.Y*T) + Dp.Y)/D;  { Calc y value }
  Y := ((Ap.Z*T3) + (Bp.Z*T2) + (Cp.Z*T) + Dp.Z)/D;  { Calc z value }
END;

PROCEDURE BSpline_ComputeCoeffs (N: Integer; Var Ap, Bp, Cp, Dp: Point3D);
BEGIN
  Ap.X := -CtrlPt[N-1].X + 3*CtrlPt[N].X - 3*CtrlPt[N+1].X + CtrlPt[N+2].X;
  Bp.X := 3*CtrlPt[N-1].X - 6*CtrlPt[N].X + 3*CtrlPt[N+1].X;
  Cp.X := -3*CtrlPt[N-1].X + 3*CtrlPt[N+1].X;
  Dp.X := CtrlPt[N-1].X + 4*CtrlPt[N].X + CtrlPt[N+1].X;

  Ap.Y := -CtrlPt[N-1].Y + 3*CtrlPt[N].Y - 3*CtrlPt[N+1].Y + CtrlPt[N+2].Y;
  Bp.Y := 3*CtrlPt[N-1].Y - 6*CtrlPt[N].Y + 3*CtrlPt[N+1].Y;
  Cp.Y := -3*CtrlPt[N-1].Y + 3*CtrlPt[N+1].Y;
  Dp.Y := CtrlPt[N-1].Y + 4*CtrlPt[N].Y + CtrlPt[N+1].Y;

  Ap.Z := -CtrlPt[N-1].Z + 3*CtrlPt[N].Z - 3*CtrlPt[N+1].Z + CtrlPt[N+2].Z;
  Bp.Z := 3*CtrlPt[N-1].Z - 6*CtrlPt[N].Z + 3*CtrlPt[N+1].Z;
  Cp.Z := -3*CtrlPt[N-1].Z + 3*CtrlPt[N+1].Z;
  Dp.Z := CtrlPt[N-1].Z + 4*CtrlPt[N].Z + CtrlPt[N+1].Z;
END;

?


 
@!!ex ©   (2008-11-01 19:01) [6]

Упс. не тот код:
PROCEDURE Spline_Calc (Ap, Bp, Cp, Dp: Point3D; T, D: Real; Var X, Y, Z: Real);
VAR T2, T3: Real;
BEGIN
  T2 := T * T;           { Square of t }
  T3 := T2 * T;          { Cube of t }
  X := ((Ap.X*T3) + (Bp.X*T2) + (Cp.X*T) + Dp.X)/D;  { Calc x value }
  Y := ((Ap.Y*T3) + (Bp.Y*T2) + (Cp.Y*T) + Dp.Y)/D;  { Calc y value }
  Y := ((Ap.Z*T3) + (Bp.Z*T2) + (Cp.Z*T) + Dp.Z)/D;  { Calc z value }
END;

PROCEDURE Catmull_Rom_ComputeCoeffs (N: Integer; Var Ap, Bp, Cp, Dp: Point3D);
BEGIN
  Ap.X := -CtrlPt[N-1].X + 3*CtrlPt[N].X - 3*CtrlPt[N+1].X + CtrlPt[N+2].X;
  Bp.X := 2*CtrlPt[N-1].X - 5*CtrlPt[N].X + 4*CtrlPt[N+1].X - CtrlPt[N+2].X;
  Cp.X := -CtrlPt[N-1].X + CtrlPt[N+1].X;
  Dp.X := 2*CtrlPt[N].X;

  Ap.Y := -CtrlPt[N-1].Y + 3*CtrlPt[N].Y - 3*CtrlPt[N+1].Y + CtrlPt[N+2].Y;
  Bp.Y := 2*CtrlPt[N-1].Y - 5*CtrlPt[N].Y + 4*CtrlPt[N+1].Y - CtrlPt[N+2].Y;
  Cp.Y := -CtrlPt[N-1].Y + CtrlPt[N+1].Y;
  Dp.Y := 2*CtrlPt[N].Y;

  Ap.Z := -CtrlPt[N-1].Z + 3*CtrlPt[N].Z - 3*CtrlPt[N+1].Z + CtrlPt[N+2].Z;
  Bp.Z := 2*CtrlPt[N-1].Z - 5*CtrlPt[N].Z + 4*CtrlPt[N+1].Z - CtrlPt[N+2].Z;
  Cp.Z := -CtrlPt[N-1].Z + CtrlPt[N+1].Z;
  Dp.Z := 2*CtrlPt[N].Z;
END;


 
@!!ex ©   (2008-11-01 19:05) [7]

Похоже что нет...


 
Sapersky   (2008-11-01 19:15) [8]

Вроде одинаково. У тебя опечатка в Spline_Calc, там Z = должно быть.
Можно ещё B-сплайны использовать (искать TBSpline), хотя считать их сложнее, но кривая получается более плавная.


 
@!!ex ©   (2008-11-01 19:20) [9]

> У тебя опечатка в Spline_Calc, там Z = должно быть.

Исправил уже. Толку нету.


> Можно ещё B-сплайны использовать (искать TBSpline), хотя
> считать их сложнее, но кривая получается более плавная.


У меня как раз код, который сравнивает два варианта, БСплайны и Кэтмулл-Рома.
Отсюда код:
http://www.enlight.ru/demo/faq/smth.phtml?query=alg_curves_splines

На 2Д отлично работает. А вот 3Д не хотит.


 
@!!ex ©   (2008-11-01 19:20) [10]

Вот еще нашел:
http://newsgroups.cryer.info/borland/public.delphi.graphics/200802/0802026065.html

попытаюсь понять что там.

MBo, спасибо за пинок в нужном направлении!


 
Sapersky   (2008-11-01 19:43) [11]

У меня как раз код, который сравнивает два варианта, БСплайны и Кэтмулл-Рома.
На 2Д отлично работает. А вот 3Д не хотит.


У меня работает:
http://sapersky.narod.ru/files/Splines.rar


 
@!!ex ©   (2008-11-01 20:28) [12]

Все. у меня заработало.
Спасибо всем!!!!!


> [11] Sapersky   (01.11.08 19:43)

Уже заработало. :) Видимо я где-то косячил.
Спасибо!


 
MBo ©   (2008-11-02 08:35) [13]

>Видимо я где-то косячил.
пополам не делил



Страницы: 1 вся ветка

Форум: "Прочее";
Текущий архив: 2008.12.28;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.48 MB
Время: 0.006 c
15-1223781352
Riply
2008-10-12 07:15
2008.12.28
Тем, кому я не смогла ответить.


15-1224858487
Petr V. Abramov
2008-10-24 18:28
2008.12.28
Не форматируется винт


3-1211873955
<bvv>
2008-05-27 11:39
2008.12.28
ORACLE доступ к "чужой" сессии


15-1224873194
Andy BitOff
2008-10-24 22:33
2008.12.28
MS Access или не MS Access, вот в чем вопрос.


15-1224145808
Kerk
2008-10-16 12:30
2008.12.28
MMP 24 октября





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский