سؤال

أريد أن أكون قادرًا على تحريك جسيم في خط مستقيم داخل بيئة ثلاثية الأبعاد ولكن لا يمكنني التفكير في كيفية تحديد الموقع التالي بناءً على نقطتين داخل مساحة ثلاثية الأبعاد؟

لقد قمت بإنشاء بنية تمثل جسيمًا له موقع وموقع تالٍ؟هل سيكون هذا مناسبًا لتحديد الموقع التالي للانتقال إليه أيضًا؟أعرف كيفية تعيين الموقع التالي في البداية باستخدام الطريقة التالية:

// Set particle's direction to a random direction
void setDirection(struct particle *p)
{
    float xnm = (p->location.x * -1) - p->velocity;
    float xnp = p->location.x + p->velocity;
    float ynm = (p->location.y * -1) - p->velocity;
    float ynp = p->location.y + p->velocity;
    float znm = (p->location.z * -1) - p->velocity;
    float znp = p->location.z + p->velocity;

    struct point3f nextLocation = { randFloat(xnm, xnp), randFloat(ynm, ynp), randFloat(znm, znp) };
    p->nextLocation = nextLocation;
}

الهياكل التي استخدمتها هي:

// Represents a 3D point
struct point3f
{
    float x;
    float y;
    float z;
};

// Represents a particle
struct particle
{
    enum TYPES type;
    float radius;
    float velocity;
    struct point3f location;
    struct point3f nextLocation;
    struct point3f colour;
};

هل سأقوم بهذا بطريقة خاطئة تمامًا؟

هنا كل ما عندي من التعليمات البرمجية http://pastebin.com/m469f73c2

هل كانت مفيدة؟

المحلول

والجواب الآخر هو قليلا mathish، انها فعلا جميلة على التوالي إلى الأمام.

وكنت في حاجة الى "السرعة" التي تقوم بنقله. كما أن لديها س، ص والإحداثيات ض.

في فترة زمنية واحدة، لنقل لكم فقط إضافة سرعة العاشر إلى المركز العاشر الخاص بك للحصول على موقف العاشر الجديد الخاص بك، كرر لذ و z.

وعلاوة على ذلك، يمكن أن يكون على "تسريع" (X أيضا، ص، ض) على سبيل المثال، يمكن أن ض تسريع الخاص بك سيكون الجاذبية، ثابت.

وكل فترة زمنية يجب recalcualted سرعة الخاصة بك في نفس الطريق، وسرعة الاتصال X "VX"، يجب أن تصبح كذلك VX VX + الفأس، كرر لصاد وعين (مرة أخرى).

ولقد كان منذ بعض الوقت الرياضيات، ولكن هذه هي الطريقة التي أتذكرها، جميلة على التوالي إلى الأمام إلا إذا كنت بحاجة إلى تتبع وحدات، فإنه يحصل على أكثر من ذلك بقليل للاهتمام (ولكن لا يزال ليس سيئا)

نصائح أخرى

وأنا أقترح أن الجسيمات ينبغي أن يكون سوى عضو ومكان واحد - الموقع الحالي. أيضا، يجب أن تكون سرعة مثالي متجه من 3 مكونات نفسه. إنشاء دالة (يطلق عليه move، displace أيا كان) أن يأخذ particle والمدة الزمنية t. وهذا حساب الموقف النهائي بعد حدات t من الوقت قد انقضى:

struct point3f move(struct *particle, int time) {
    particle->location->x = particle->velocity->x * t;
    /* and so on for the other 2 dimensions */
    return particle->location;
}

أود أن أوصي بشيئين:

  1. اقرأ مقالًا أو مقالين عن الرياضيات المتجهة الأساسية للرسوم المتحركة.على سبيل المثال، هذا هو موقع يشرح المتجهات ثنائية الأبعاد للفلاش.

  2. ابدأ ببساطة، ابدأ بنقطة 1d، أي نقطة تتحرك فقط على طول x.ثم حاول إضافة البعد الثاني (نقطة ثنائية الأبعاد في مساحة ثنائية الأبعاد) والبعد الثالث.قد يساعدك هذا في الحصول على فهم أفضل للآليات الأساسية.أتمنى أن يساعدك هذا

والتفكير في الفيزياء. كائن لديه موقف (س، ص، ض) وناقل الحركة (أ، ب، ج). يجب أن تكون موجودة الكائن في موقفها. أنه يحتوي على ناقل الحركة المرتبطة به التي تصف زخمها. في عدم وجود أي قوات إضافية على الكائن، وعلى افتراض أن ناقلات حركتك يصف الحركة خلال فترة زمنية ر، فإن الموقف من وجوه الخاص بك في وقت س يكون (س + (أ <م> ر)، ص + ( ب ر)، ض + (ج ر *)).

وباختصار؛ لا تخزن الوضع الحالي والوضع القادم. تخزين الوضع الحالي والزخم للكائن. فمن السهل بما فيه الكفاية ل"القراد على مدار الساعة" وتحديث موقع الكائن ببساطة عن طريق إضافة الزخم لهذا المنصب.

ومخزن سرعة باعتباره point3f البنية، ومن ثم يكون لديك شيء من هذا القبيل:

void move(struct particle * p)
{
  p->position.x += p->velocity.x;
  p->position.y += p->velocity.y;
  p->position.z += p->velocity.z;
}

وأساسا على السرعة هي وكم كنت تريد وضع يمكنها من تغيير كل ثانية / علامة / أيا كان.

وترغب في تنفيذ X_{i+1} = X_{i} + Vt ناقل الرياضيات. لXs وناقلات V تمثل الموقف وسرعة على التوالي، وt تمثل الوقت. لقد معلمات المسافة على طول المسار من الوقت لأنني فيزيائي، لكنها في الحقيقة الشيء الطبيعي أن تفعل. تطبيع ناقل السرعة إذا كنت تريد أن تعطي مسافة المسار (أي نطاق V بحيث V.x*V.x + V.y*V.y + V.z*V.z = 1).

وباستخدام struct يجعل فوقه الطبيعية للوصول إلى العناصر، ولكن ليس مريحة جدا للقيام بالإضافة إلى ذلك: صفائف أفضل لذلك. مثل هذا:

double X[3];
double V[3];

// initialize

for (int i=0; i<3 ++1){
  X[i] = X[i] + V[i]*t;
}

ومع الاتحاد، يمكنك الحصول على مزايا كل من:

struct vector_s{
  double x;
  double y;
  double z;
}
typedef
union vector_u {
  struct vector_s s; // s for struct
  double a[3];       // a for array
} vector;

إذا كنت تريد ربط كل من موقف وسرعة مع الجسيمات (شيء معقول جدا القيام به) لك بناء هيكل التي تدعم متجهين

typedef
struct particle_s {
  vector position;
  vector velocity;
  //...
} particle_t;

ووتشغيل روتين التحديث الذي يبدو تقريبا مثل:

void update(particle *p, double dt){
  for (int i=0; i<3 ++i){
    p->position.a[i] += p->velocity.a[i]*dt;
  }
}

وAFAIK، هناك أساسا طريقتان حول كيف يمكنك حساب الموضع الجديد. واحد يشبه الآخر قد explaint لاستخدام سرعة صريحة. والاحتمال الاخر هو لتخزين آخر والوضع الحالي واستخدام Verlet التكامل . في كلا الاتجاهين لديها مزايا وعيوب. هل يمكن أيضا أن نلقي نظرة على هذه .

إذا كنت تحاول التحرك على طول خط مستقيم بين نقطتين، يمكنك استخدام الصيغة الاستيفاء:

P(t) = P1*(1-t) + P2*t

وP (ر) هو موقف يحسب نقطة، تي هو العددية تتراوح 0-1، P1 و P2 هي النهاية، وبالإضافة إلى ذلك في ما سبق هو إضافة ناقلات (بحيث تطبق هذه الصيغة على حدة ل س، ص المكونات و z من النقاط الخاصة بك). عندما ر = 0، تحصل P1. عندما ر = 1، وتحصل P2، والقيم المتوسطة، يمكنك الحصول على وسيلة جزء نقطة على طول الخط الفاصل بين P1 و P2. حتى ر = 0.5 يمنحك نقطة الوسط بين P1 و P2، ر = 0.333333 يمنحك نقطة 1/3 من الطريق من P1 إلى P2، الخ قيم ر خارج النطاق [0، 1] استقراء للنقاط على طول خط خارج الجزء من P1 إلى P2.

وباستخدام الصيغة الاستيفاء يمكن أن يكون أفضل من الحوسبة سرعة وبشكل متكرر مضيفا أنه إذا كانت السرعة هي صغيرة بالمقارنة مع المسافة بين النقاط، لأنك لحد من خطأ roundoff.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top