الفريق العربي للبرمجةأرشيف المنتديات · 2000 – 2023
نسخة أرشيفية للقراءة فقط — التسجيل والمشاركة مغلقان، والمحتوى محفوظ كما كان.

نقاش مفتوح في حزمة المحرك AAnimation

بدأه Speed_Of_Light في 17 مارس 2010 · 37 رد · 1,897 مشاهدة · في JavaSE
مشاركة: واتساب X فيسبوك تيليجرام
#1 صاحب الموضوع

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

هدف الحزمة دعم التحريك في جافا. ويقصد به تحريك الرسومات ثنائية الأبعاد على الشاشة.

الحزمة في وضعها الحالي تحرك المكونات Components على الحاوية الموجودة فيها Container. ويكفي بعض التعديلات والإضافات وتصبح شبه كاملة.

وهي مفيدة جداً للبريمجات/الألعاب الصغيرة والتي يلزمك فيها بعض التحريك البسيط.

لكن لا أظنها مناسبة كفاية لبرامج تحتاج إلى إمكانيات تحريك متقدمة، فالأمر يصبح مرهقاً نوعاً ما حيث أنها غير مخصصة لتحريك الرسوم Graphices بل لتحريك المكونات Components. وهذه نقطة هامة وحد كبير Constrain على تطور الحزمة ومستقبلها.

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

- تطوير الحزمة على وضعها الحالي (تحريك مكونات) وذلك بتحسين التصميم وإضافة المزيد من الميزات.

- إعادة بناء الحزمة بالاعتماد على Java 2D Graphics (أو أي حزمة رسم أخرى).

في المستقبل البعيد !!!

يمكن التفكير بإضافة دعم تصدير الحركات بشكل رسومات svg.

وربما يتم اعتمادها لاحقاً كتوسعة extention للـ G2D أو Batik

لكن النقاش في هذا الموضوع سيكون حول تطوير الحزمة على وضعها الحالي (تحريك مكونات).

تم تعديل هذه المشاركة بواسطة Speed_Of_Light في 17 مارس 2010 في 17:56

#2

ما زلت -حتى الآن- أحاول فهم الحزمة بشكل كامل :)، وخاصة أن الحزمة في مرحلة التطوير وهناك الكثير من الكود "التجريبي" والتعليقات، فقرائة الكود صعبة والتوثيق متوافر فقط بالقليل من الفئات.

لذا أعتذر سلفاًً عن أي رأي ناتج عن فهم خاطئ للحزمة.

ملاحظات على الحزمة:

الملاحظات التالية خطرت ببالي عند رؤية الكود للمرة الأولى. بعضها لا يجب تصحيحه موضعياً بل يحتاج إلى إعادة التفكير بالأمر قليلاً (انظر الاقتراحات الأولية).

- بدلاً من الاستفادة من المنهجية غرضية التوجه في تغليف الأغراض وإخفاء التعقيد، أدّت زيادة الفئات/الأصناف والتعقيد إلى صعوبات ليس فقط عليك (مصمم الحزمة) بل أيضاَ على المبرمج (مستخدم الحزمة).

- ماذا لو رغب المبرمج بتحريك مكون مدار بمدير التنسيق LayoutManager ؟ لن تفيدك الحزمة كثيراً في هذه الناحية!

- في الـ AnimationObject أجد عضواً بيانياً AnimationList، وأفهم منه أن كل AnimationObject يخضع لقائمة من الحركات.

ثم أنظر إلى AnimationList فأجد قائمة من الـ AnimationObject، وأفهم منه أن قائمة من الحركات تطبق على قائمة من الـ AnimationObjects !!

ملاحظات أخرى:

• من وجهة نظر غرضية، يجب أن تكون الطرق insertAnimationXXXX تأخذ وسيطاً غرض من Animation

• من وجهة نظر غرضية، يجب أن تحوي الفئة Animation طريقة method اسمها مثلاً getType

• هناك الكثير من الأسماء التي تحتاج إلى تصحيح لأسباب إملائية أو منطقية أو لتسهيل استخدامها (excute / delet).

• لم استخدمت setBounds بدلاً من setLocation ؟ حيث أن الحزمة تقوم بالتحريك وليس بالتحجيم (مع أن النتيجة واحدة)

• لم استخدمت:

 for (; x1 < x2;)

في الفئة PointToPointAnimation بدلاً من :

while(x1 < x2)

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

اقتراح لميزات وإمكانات إضافية:

- إضافة حركات مخصصة أخرى (كالحركة الدائرية، الدورانية rotation)، دعم تغيير الأبعاد والشفافية أثناء التحريك.

- إضافة دعم للتسارع، وتحكم إضافي بالسرعة.

- إضافة مزايا أحداث إضافية.

اقتراحات أولية:

فيما يتعلق بالتحريك (بالتحديد: Animation، ِAnimationScript, PointToPointAnimation، AnimationList)، أرى أنه يجب أن تكون كما يلي:

فئة باسم AnimationStep تمثل خطوة واحدة بالحركة، أي نقلة واحدة من نقطة إلى نقطة (ويمكن في المستقبل تضمين تدوير rotation فيها، وتغيير بالأبعاد transformation، وتغيير بالشفافية opacity بحيث تدعم حركات متقدمة).

واجهة باسم Animation (بدل AnimationScript) تمثل الحركات الكاملة المختلفة (مثل حركة مستقيمة، دائرية، دورانية، وفق مسار)، تقوم بتوليد LinkedList<AnimationStep> (كما في الكود الحالي).

أي أن يتم الاستغناء عن الفئة AnimationList واستبدالها بـ LinkedList<AnimationStep> لأنها لا تقدم أي قيمة مضافة عنها !!

كما يجب إعادة ترتيب بعض الأمور، على سبيل المثال animateComponent موجودة داخل الـ AnimationObject لكن من المنطقي أكثر أن توجد ضمن الـ AnimationEngine.

دعنا نتناقش بهذا كبداية ...

تم تعديل هذه المشاركة بواسطة Speed_Of_Light في 17 مارس 2010 في 18:01

#3

السلام عليكم

بداية أحب أن أشكر الأخ حسام على الاهتمام بحزمة المحرك

وأتمنى أن يلاقي النقاش اعجابكم واستحسانكم وأن يستفيد الجميع بإذن الله

في البداية أحب أن أوضح أهدافي من بناء الحزمة

من وجهة نظري كمصمم للحزمة فأنا لم أكن أقصد الرسومات ثنائية الأبعاد

أنا قصدت تحريك المكونات الخاصة بـ swing على الحاوية فقط

بمعنى آخر حزمتي تمثل نوع من الحزم المساعدة utility لحزمة swing

والمعنية هنا بتوفير إمكانية تصميم واجهات أكثر احترافية في حزمة swing بأقل تكلفة ممكنة مع إمكانيات تصميم ألعاب بسيطة ومحاكيات متوسطة الحجم

بمعنى آخر هذه الحزمة خيارك لو كنت تريد تحريك شيء ما في واجهتك مع الاستفادة من إمكانيات swing الكبيرة

لذا لا يمكننا القول أن الحزمة تعمل على التحريك لوحده وإنما تحريك مكونات swing

بالطبع لا أجد ما يمنع التحول إلى تحريك Graphics وأراها خطوة جيدة جداً

لكني أحبذ أن يكون في حزمة أخرى مع إمكانية الاستفادة الكاملة والتامة من جميع الأساليب التي استخدمتها في الحزمة AAnimation

مع تحبيذ تغيير اسم الحزمة الحالية حتى يكون الوضع أفصل بالنسبة للمستخدمين

لي عودة بإذن الله لأناقش مايرتئيه الأخ حسام لكن بعد يوم الأحد القادم لضغط الدراسة

تحياتي

تم تعديل هذه المشاركة بواسطة علاء الصالحي في 17 مارس 2010 في 21:34

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#4

الموضوع شيق.

ممكن ياعلاء تدلني على مكان استطيع ان اقرأ عن اساسيات استخدام الحزمة مع امثلة لو امكن؟

بحثت عن قلمي البارحة فلم أجدة!

...............

لم أجد سوى لوحة المفاتيح هذة

.............

تتطلع إلي بشفقة..

.............

أكاد أسمعها .. تقول (ألم يسمع بGoogle ؟!؟؟)

#6

مشكور اخي

تم تعديل هذه المشاركة بواسطة Dr.Robert في 18 مارس 2010 في 18:05

بحثت عن قلمي البارحة فلم أجدة!

...............

لم أجد سوى لوحة المفاتيح هذة

.............

تتطلع إلي بشفقة..

.............

أكاد أسمعها .. تقول (ألم يسمع بGoogle ؟!؟؟)

#7

بالمناسبة هناكعارض الصور

وهناك نقاشات حصلت بيني وبين الأخ الشمري وقد ساهمت في تطور الحزمة بشكل كبير في هذا الموضوع

نقاش حصل بيني وبين الأخ Speed_Of_Light في موضوع لعبة الأربعة تربح

أخيراً موضوع كتبته عن كيفية إدارة الأحداث في حزمة المحرك

بالإضافة إلا ذلك تأتي مع الحزمة ثلاثة ملفات معنونة باسم Test ومنتهية برقم 1و2و3 هذه أمثلة بسيطة على الحزمة

أتمنى أن أسمع رأيك أخ مازن

تحياتي

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#8

أكيد , وسأخذ وقتي الكافي لدراستها

بحثت عن قلمي البارحة فلم أجدة!

...............

لم أجد سوى لوحة المفاتيح هذة

.............

تتطلع إلي بشفقة..

.............

أكاد أسمعها .. تقول (ألم يسمع بGoogle ؟!؟؟)

#9
اقتباس
بالمناسبة هناكعارض الصور

لم أعلم بوجوده مسبقاً

الآن عرفت أين أجد الـ ImagePanel المستخدمة في Test1 فهي غير مضمنة بالحزمة !

تم تعديل هذه المشاركة بواسطة Speed_Of_Light في 18 مارس 2010 في 19:18

#10

احم احم احم

تأخرت بعض الشيء وأعتذر بشدة لأن ضغط الجامعة والعمل كبير بعض الشيء

على العموم أنا موجود وبإذن الله سنناقش كل شيء

دعنا نبدأ من الرد الثاني

اقتباس

- بدلاً من الاستفادة من المنهجية غرضية التوجه في تغليف الأغراض وإخفاء التعقيد، أدّت زيادة الفئات/الأصناف والتعقيد إلى صعوبات ليس فقط عليك (مصمم الحزمة) بل أيضاَ على المبرمج (مستخدم الحزمة).

دعني في البداية أوضح المنطقية التي تعمل بها حزمة المحرك

هناك فئتان رئيسيتان في حزمة المحرك (من وجهة نظر المستخدم):

1- فئة المحرك

2- فئة الكائنات المتحركة

فئة المحرك وهي تمثل فعلياً المسؤول المباشر عن إعطاء أمر التحريك للكائنات المتحركة وتنبيه المستمعين بوجود أحداث جديدة هذه الفئة تحتوي على الحاوية التي يجب أن يتحرك عليها الكائنات

يقوم المحرك بإدارة زمن الخاص بالحزمة بحيث يتم تحريك الكائنات المتحركة وفق هذا الزمن

بالنسبة لفئة الكائن المتحرك فهي الفئة المسؤولة عن الحركة الفعلية للمكون component على الحاوية الخاصة بفئة المحرك

كما هو مسؤول عن تغير حجم المكون بما يضمن تزامن بين تغيير حجم المكون وعملية التحريك التي تتم عليه

هناك بعض الفئات الفرعية التي يحتاج المستخدم لفهمها حتى يتعامل مع الحزمة

1- الفئة حركة Animation

وهي الفئة التي تحتوي على مواصفات الحركة الخاصة بالكائن المتحرك

وعلى أساس مواصفات الحركة التالية للكائن المتحرك يقوم المحرك بجدولة الكائن في جدول التحريك الخاص به (قائمة من الكائنات المتحركة)

ويتم تحديد مقدار الحركة التي يريد أن يتحركها الكائن والجهة التي سيتحرك إليها

2- الفئة قائمة الحركات AnimationList

وهذه الفئة تحتوي على مجموعة الحركات الخاص بالكائن المتحرك

الآن دعنا ننظر في الملاحظات التي تكلمت عنها أخي

اقتباس

- بدلاً من الاستفادة من المنهجية غرضية التوجه في تغليف الأغراض وإخفاء التعقيد، أدّت زيادة الفئات/الأصناف والتعقيد إلى صعوبات ليس فقط عليك (مصمم الحزمة) بل أيضاَ على المبرمج (مستخدم الحزمة).

ممممممممممممم

كلمني عن الصعوبات الخاصة بالمبرمج

بالنسبة للصعوبات الخاصة بمصمم الحزمة أنا مقتنع تماماً أن أي حزمة لكي تكون مرنة كفاية يجب أن تنتقل الصعوبات إلى مستوى أعلى وهو مستوى التصميم

لذا أحتاج أن أسمع عن الصعوبات التي تواجه المستخدم وكيف يمكنني حلها

لاحظ أن عملية التحريك نفسها عملية ليست سهلة بالمرة

اقتباس

- ماذا لو رغب المبرمج بتحريك مكون مدار بمدير التنسيق LayoutManager ؟ لن تفيدك الحزمة كثيراً في هذه الناحية!

يستطيع المستخدم أن يضيف panel وتسخدمها على أساس أنها هي الحاوية الخاصة به

لو أردت رأيي فأنا أرى أن على المستخدم أن يلعب بقواعدي أنا

لأني وفرت عليه الكثير من الوقت الذي كان سيقضيه في عملية التحريك (وهي عملية خارجة عن حدود منطق البرنامج)

ثم ما الذي يمكنني فعله حيال هذه النقطة , Layout Manager يتعارض مع التحريك فما الذي يمكنني عمله؟

اقتباس

- في الـ AnimationObject أجد عضواً بيانياً AnimationList، وأفهم منه أن كل AnimationObject يخضع لقائمة من الحركات.

ثم أنظر إلى AnimationList فأجد قائمة من الـ AnimationObject، وأفهم منه أن قائمة من الحركات تطبق على قائمة من الـ AnimationObjects !!

لاحظ أنك لا تستطيع إضافة كائن متحرك لقائمة الكائنات الخاصة بقائمة الحركات

هذا يعطيك انطباعاً أن استخدام هذا القائمة في داخل الحزمة

أما لماذا توجد قائمة بالكائنات المتحركة

فلأن قائمة الحركات عندما تضاف عليها حركة جديدة أوتحذف حركة منها واحدة تقوم بتنبيه عملية الحركة لكي تتخذ احتياطها

وبما أن قائمة الحركات قد تكون لأكثر من كائن متحرك في نفس الوقت تحتم أن تكون هناك قائمة من الكائنات

أطلت عليكم سأقسم ردي على الملاحظات في نقاط

لأنه يبدو لي أن الرد سيطول :)

انتظر أراءك على هذه النقاط حتى نعود ونناقش نقاط أخرى

تحياتي

تم تعديل هذه المشاركة بواسطة علاء الصالحي في 23 مارس 2010 في 06:26

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#11

شكراً على التوضيح وعلى وقتك

أرجو استخدام أسماء الفئات والطرق/الدوال كما هي بدلاً من ترجمتها للتسهيل ولزيادة الوضوح

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

بالنسبة لـ Animation و AnimationList :

الـ AnimationList تحوي قائمة من الحركات Animation ، أي يمكننا القول بأن الـ AnimationList هي عبارة عن حركة كاملة مؤلفة من قائمة من الخطوات Animation، أليس كذلك ؟

إذا كان كذلك فقد كان من الممكن اختيار اسماء أوضح.

- من الخطأ تضمين اتجاه الحركة horzintal و vertical ضمن الـ Animation، فبالنهاية كل ما تحتاج إليه من معلومات حول الخطوة التالية هو إحداثياتها! والتي يتم توليدها حسب نوع الحركة من قبل AnimationScript.

- ولا يصح تضمين horzintalIncrementStep و verticalIncrementStep لسببين: عندما يكون عندنا حركة أفقية وعمودية (معاً) لا تكون الخطوة الأفقية = الخطوة العمودية = الخطوة المدخلة من قبل المستخدم! )حسب فيثاغورس :) (

كما أن الخطوة بالأساس تحدد حسب نوع الحركة من قبل AnimationScript والتي هي عبارة عن تغير في الإحداثيات ولا داعي لتخزينها ضمن Animation ! وهو أحد أهم ميزات الحزمة: إمكانية تطوير أكواد تحريك AnimationScript بشكل منفصل عن باقي الحزمة.

اقتباس
كما هو مسؤول عن تغير حجم المكون بما يضمن تزامن بين تغيير حجم المكون وعملية التحريك التي تتم عليه

إذاً لقد تعمدت استخدام setBounds بدلاً من setLocation لهذا السبب :D

اقتباس
لاحظ أنك لا تستطيع إضافة كائن متحرك لقائمة الكائنات الخاصة بقائمة الحركات

بل يمكنني ! حيث لاحظت وجود طريقتين/دالتين : addAnimationObject و removeAnimationObject داخل الفئة AnimationList

اقتباس
أما لماذا توجد قائمة بالكائنات المتحركة

فلأن قائمة الحركات عندما تضاف عليها حركة جديدة أوتحذف حركة منها واحدة تقوم بتنبيه عملية الحركة لكي تتخذ احتياطها

هل يمكن أن تشير إلى الكود المتعلق بهذا ؟

اقتباس
ثم ما الذي يمكنني فعله حيال هذه النقطة , Layout Manager يتعارض مع التحريك فما الذي يمكنني عمله؟

أعتذر، كنت أريد ذكر هذا المثال عن محدودية الحزمة في تحريك الرسوميات في المشاركة الأولى، لا أدري ما الذي أتى به إلى هنا :D

لا أحب طرح المشاكل دون حلول، عندي تصور لشكل محسّن من الحزمة سأطرحه بعد إنهاء هذه النقاط

#12

بإذن الله سيكون يهمني أن أسهل عليك القراءة

فعلياً لم يكن يعمل على الحزمة سواي ولم أجد تمحمس لها غير الأخ الشمري (سقا الله أيامك يا أبو شمر)

لذا أنا هنا الذي يجب أن أشكرك على وقتك الذي تحاول فيه فهم الحزمة :)

(ولولا أني كنت أتعامل مع الحزمة على أساس أني أتعلم منها ألية التعبئة ومفاهيم في البرمجة الكائنية وتوسيع لمعلوماتي في جافا لما رأيتها هنا أبداً)

كلام منطقي جداً وأؤيده تماماً

لكن التصميم القوي حلم جميل بتبخر مع المرونة العالية فتجد فجأة أن الحزمة تحتاج إلى إعادة تصنيع refactoring للحزمة بأكملها

على العموم لا مانع لدي من تبني أي تصميم جديد يكون قوي وفي نفس الوقت يبقى بسيطاً

اقتباس

بالنسبة لـ Animation و AnimationList :

الـ AnimationList تحوي قائمة من الحركات Animation ، أي يمكننا القول بأن الـ AnimationList هي عبارة عن حركة كاملة مؤلفة من قائمة من الخطوات Animation، أليس كذلك ؟

هذا الكلام صحيح مئة بالمئة

اقتباس

إذا كان كذلك فقد كان من الممكن اختيار اسماء أوضح.

بالنسبة لهذا المقطع كنت وما زلت أعتبر نفسي سيئاً في اختيار تسميات مناسبة للحزمة

اقتباس

- من الخطأ تضمين اتجاه الحركة horzintal و vertical ضمن الـ Animation، فبالنهاية كل ما تحتاج إليه من معلومات حول الخطوة التالية هو إحداثياتها! والتي يتم توليدها حسب نوع الحركة من قبل AnimationScript.

هنا أنا أبقي هذه النقطة مفتوحة للمطورين على الحزمة

بمعنى أنا قمت بتطوير الحركة الخطية من النقطة أ إلى النقطة ب في PointToPointScript

هناك آخرين قد يقومون بتطوير حركات أخرى فلماذا أقطع عليهم الخط ولا أسمح لهم إلى باستخدام الحركة التي أولدها أنا في حزمتي

اقتباس

- ولا يصح تضمين horzintalIncrementStep و verticalIncrementStep لسببين: عندما يكون عندنا حركة أفقية وعمودية (معاً) لا تكون الخطوة الأفقية = الخطوة العمودية = الخطوة المدخلة من قبل المستخدم! )حسب فيثاغورس :) (

هذه النقطة كانت مدار حديث بيني وبين الأخ الشمري

بالطبع كانت ضمن النقاط المعلقة في النظام وعندما راجعت النقاط التي أضيفت إلى آخر إصدارة من حزمة المحرك

وجدتها مضافة واستعجب أني كتباعل في قائمة الخصائص المضافة إلى الحزمة في الإصدارة 0.8

على العموم وجدت أني أضفت صانع كائنات يعمل على الموضوع في الفئة Animation

	public Animation(int horzintalIncrementStep, int verticalIncrementStep,
			int time) {
		intiateHorzintalVerticalVariables(AnimationType.vertical_horzintal,
				horzintalIncrementStep, verticalIncrementStep);
		this.time = time > 0 ? time : DEFUALT_TIME;
	}

وأظن أنه يقوم بالغرض المطلوب تماماً

اقتباس

كما أن الخطوة بالأساس تحدد حسب نوع الحركة من قبل AnimationScript والتي هي عبارة عن تغير في الإحداثيات ولا داعي لتخزينها ضمن Animation ! وهو أحد أهم ميزات الحزمة: إمكانية تطوير أكواد تحريك AnimationScript بشكل منفصل عن باقي الحزمة.

لم أستطع فهم هذه النقطة جيداً

كيف ستستطيع القيام بتطوير أكواد التحريك وتستطيع الحزمة فهم ذلك ما لم يكن كود التحريك يبقي انطباع لدى المحرك بحيث يعمل المحرك على أساسه

اقتباس

بل يمكنني ! حيث لاحظت وجود طريقتين/دالتين : addAnimationObject و removeAnimationObject داخل الفئة AnimationList

هاتان الدالتان يفترض بهما أن يكونا protected يمكن استخدامهما من داخلة الحزمة وليس من خارجها

اقتباس

أما لماذا توجد قائمة بالكائنات المتحركة

فلأن قائمة الحركات عندما تضاف عليها حركة جديدة أوتحذف حركة منها واحدة تقوم بتنبيه عملية الحركة لكي تتخذ احتياطها

اطلع على الدوال insertAnimationFirst و insertAnimationLast و deletFirstAnimation و deletLastAnimation في الفئة AnimationList

ستجد فيها تحديث للكائن الخاص بعملية الجدولة SchedulerObject

لكل كائن متحرك كائن خاص به لعملية الجدولة

تحياتي

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#13
اقتباس
اطلع على الدوال insertAnimationFirst و insertAnimationLast و deletFirstAnimation و deletLastAnimation في الفئة AnimationList

ستجد فيها تحديث للكائن الخاص بعملية الجدولة SchedulerObject

نعم (لكن التحديث لا يتم في insertAnimationLast)

أرجو أن تشرح لي الفئتين Scheduler + SchedulerObject

بالتحديد ما يلي:

getAnimationObjectsReadyToAnimate

getSchedulerObjectToExcute

(مع إنهما كلاهما يعيدان قائمة من SchedulerObject ) :wacko:

مع شرح عن كيفية تفاعلهما مع باقي فئات الحزمة

#14

السلام عليكم

الفكرة بدأت بالتالي

في البداية كان لدي Scheduler والأخ Scheduler هو المسؤول عن جدولة حركة الكائنات المتحركة حركة تلو الأخرى

بحيث هناك وقت افتراضي للمحرك هذا الوقت يعتبر صفر مع بداية تشغيل المحرك

والأخ Scheduler يحدد الكائنات المتحركة التي عليها الدور لكي تؤدي دورها

بالنسبة للأخ SchedulerObjec فالأمر يتعلق بمعرفة ما الحركة التالية على الكائن المتحرك

أما لماذا لم يكن الموضوع مقتصر على الكائن المتحرك

لأني أعتقد أن المطورين على الحزمة ربما يريدون أن يقوموا بتغيير آلية Scheduling للكائنات المتحركة بحيث يكون هناك نوعية من الكائنات المتحركة لها أفضلية في عملية التحريك

أو أي شيء مماثل (ممكن القول Priority)

أما عن آلية تغيير الجدولة فعلى المطور أن يقوم بإعادة كتابة الدالة compareTo بحيث تتوافق مع هواه

ربما أطرح مثال عليها مستقبلاً (بعد أن أن أرى أن الحزمة مستقرة تماماً)

طيب ما الذي سيحصل لو أضفنا حركة جديدة على المحرك

لو أضفنا الحركة في البداية فسيحل لدينا تغيير في ترتيب الحركات في القائمة

مثال الحركة رقم 0 ستصبح رقم 1 والحركة رقم 1 ستصبح 2 وهكذا

بمعنى أن كل الحركات تقدمت بمقدار 1

وهذا فعلياً يعني أن يتم تنفيذ الحركة التي تعمل حالياً مرة أخرى وهذا خطأ بين

لهذا تجدني أزيد القيمة في schedulerObject حتى أضمن أن لا تحصل هذه المشكلة

نفس الموضوع في الحذف من الأول سينقص العدد بمقدار واحد

مما يعني أن هناك حركة لن يتم تنفيذها

بالنسبة للدالة getAnimationObjectsReadyToAnimate

تعمل على تحديد الكائنات المتحركة التي عليها الدور في الحركة

(مازال هناك حركات لم يتم تنفيذها في AnimationList أو انتهت الحركات لكن الكائن المتحرك له خاصية تكرار الحركة)

دعنا نأخذ مثال بسيط

لدينا ثلاث كائنات متحركة أ و ب و ج

وقت المحرك لدينا هو 100 م.ث

وقت الكائن أ هو 90 م.ث (أقصد هنا وقت آخر عملية تحريك جرت له وهذا الوقت موجود في كائن الجدولة SchedulerObject)

والحركة الأخيرة التي يقوم بها مدتها 20 م.ث

بمعنى أن حركته التالية ستحصل عند وقت المحرك 110 م.ث

وقت الكائن ب هو 100 م.ث

والحركة الآخيرة التي قام بها مقدارها 20 م.ث

بمعنى أن حركته التالية ستحصل عند 120 م.ث

وقت الكائن ج هو 90 م.ث

والحركة الآخيرة التي قام بها مقدارها 20 م.ث

بمعنى أن حركته التالية ستحصل عند 110 م.ث

الدالة سترجع قائمة من كائنات الجدولة فيها الكائنين الخاصين بجدولة الكائنات المتحركة أ و ج

فعلياً الدالة لا تحتوي على logic حقيقي

هي مسؤولة عن إيقاف المحرك لو كان لو يحتوي على كائنات تريد الحركة و هي التي يتعامل معها AnimationEngine

بينما هي تقوم فقط بمناداة الدالة getSchedulerObjectToExcute

بالنسبة للدالة getSchedulerObjectToExcute

فهي فعلياً التي تحتوي على logic حقيقي

ويمكن تلخيصه كالتالي

1- ترتيب جميع الكائنات المتحركة على حسب وقت حركته التالية

2- أخذ الكائنات المتحركة ذات الوقت الأقرب إلى وقت المحرك الحالي

3- استثناء الكائنات المتحركة التي في إحدى حالتين الحالة الأولى

أ- الكائن المتحرك وصل إلى نهاية الحاوية وقيمة ActionWhenAnimationObjectReachBoundsOfAnimationEngineContatiner تساوي IGNORE_ALL_REJECTED_ANIMATION

ب- الكائن المتحرك وصل إلى نهاية الحاوية وقيمة ActionWhenAnimationObjectReachBoundsOfAnimationEngineContatiner تساوي STOP_ANIMATION_UNTIL_CHANGE_CURRENT_POSITION_OF_ANIMATION_OBJECT

4- إرجاع قائمة بالكائنات التي عليها الدور في عملية التحريك

بالمناسبة هل لي أن أعرف لماذا تهتم بحزمة المحرك وبغض النظر عن السبب فلن يؤثر في كلامي هنا

لكن مجرد فضول لا أكثر ولا أقل

حيث أن هذه الحزمة موجودة هنا منذ أكثر من سنة ولم تثير اهتمام سوى الأخ الشمري

والذي له ميول واضحة لبرمجة الألعاب ولديه هدف أن يصمم المحرك الذري

على العموم تحتفظ بحق الرد على هذا السؤال إن لم ترد ذلك

تحياتي

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#15

ممممممممم تمام ! الآن بدأت الغشاوة تنقشع ! سأقوم بالنظر لهذه المعلومات الجديدة لأرى إمكانية تحسينها

لقد قمت بإجراء الكثير من التعديلات والتحسينات حتى الآن ... والآن سأبدء بالإقترب من نواة التحريك الحقيقية.

سأشارككم الكود قريباً

الفكرة التي في مخيلتي هي كالتالي:

ذكرت سابقاً أنه لا يمكن حقيقة الفصل بين التحريك والرسم، فالحركة هي عبارة عن سلسلة من الخطوات التي يمر بها المكون Component، وفي كل خطوة )AnimationStep( يجري تغيير لبعض خصائصه (الإحداثيات، الأبعاد، الشفافية، اللون ...) وذلك بعد زمن مضبوط.

يمكن تطوير الحركات بشكل منفصل عن تطوير الحزمة، بواسطة فئات Classes تحقق واجهة Implement an Interface تحوي طريقة method تعيد قائمة من الخطوات

List<AnimationStep>

والتنفيذ الفعلي لهذه الخطوات يتم قبل المحرك

وذلك يتطلب حذف ونقل وتعديل بعض الطرق من هنا وهناك

لاحظ أن الخطوات لا تحوي القيم الفعلية لخصائص للمكون (كلإحداثيات أو الأبعاد أو الشفافية...)، إنما تحوي التغيّر في هذه القيم

وهذا يعني أنه يمكن إضافة ميزات هائلة في المستقبل: كجمع حركتين أو طرحهما أو وصلهما مع بعضهما ...

لماذا أهتم بالحزمة ؟

حسناً، هناك عشرات الأسباب! مشروع عربي جميل ومفتوح المصدر، فريد من نوعه في جافا (وليس إعادة اختراع للعجلة!)، وهو أول مشروع مفتوح المصدر أساهم به!

كنت أرغب بالإطلاع عليه منذ زمن طويل! لكن الانشغال منعني من ذلك.

كما أني أحاول الهروب من الضغط الدراسي إلى شيء ممتع :D

تم تعديل هذه المشاركة بواسطة Speed_Of_Light في 26 مارس 2010 في 18:09

#16

يبدو لي أنا بصدد نسخة جديدة من AAnimation لأنه يبدو أن هناك الكثير من الأفكار و التعديلات هنا وهناك

يهيألي أني لن أعرف الشيفرة بعد أن أراها :)

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

بالنسبة للهروب من الدراسة فهو لذيذ أنا أيضاً هارب من هناك

بما أنا أنهينا النقاط الأولى دعني أعود لأعقب على بعض من النقاط القديمة

Speed_Of_Light كتب:

ملاحظات أخرى:

• من وجهة نظر غرضية، يجب أن تكون الطرق insertAnimationXXXX تأخذ وسيطاً غرض من Animation

• من وجهة نظر غرضية، يجب أن تحوي الفئة Animation طريقة method اسمها مثلاً getType

• هناك الكثير من الأسماء التي تحتاج إلى تصحيح لأسباب إملائية أو منطقية أو لتسهيل استخدامها (excute / delet).

• لم استخدمت setBounds بدلاً من setLocation ؟ حيث أن الحزمة تقوم بالتحريك وليس بالتحجيم (مع أن النتيجة واحدة)

• لم استخدمت:

 for (; x1 < x2;)

في الفئة PointToPointAnimation بدلاً من :

while(x1 < x2)

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

بالنسبة للنقطة الأولى فأعتقد أنك محق كنت أفكر في أن أحجب التفاصيل عن المستخدم (المبرمج) لكني لم أفلح

بالنسبة للنقطة الثانية فلم أجد لها فائدة حيث أن الدوال isHorzintal و isVertical كفاية

بالنسبة للنقطة الثالثة لا تعليق :)

بالنسبة للنقطة الرابعة كنت فصلت فيها مسبقاً

بالنسبة للنقطة الخامسة كنت استخدم for لشيء ما وفي النهاية كسلت أن أغيرها إلى واحد شيء آخر

بالنسبة للنقطة السادسة أنا أفترض أن إنشاء الحركة مفصول تماماً عن الكائن (كما قلت ممكن أن تستخدم قائمة الحركات لأكثر من كائن)

احم احم

أكمل في مرة أخرى

(وكأني قمت بعمل الكثير)

تحياتي

تم تعديل هذه المشاركة بواسطة علاء الصالحي في 26 مارس 2010 في 23:38

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#17

اعذروني للتأخير............ لكن أين الحزمة؟.

#18

آسف.... وجدتها بعد البحث.. لكن لا أستطيع تحميلها..

تم تعديل هذه المشاركة بواسطة JDurrah في 27 مارس 2010 في 03:34

#19

لماذا لا تستطيع تحميلها؟

آخر إصدارة مع الحزمة هي الموجودة في موضوع لعبة الأربعة تربح

تحياتي

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#20

شكراً جزيلاً، تم التحميل، وجاري الدراسة..

#21

على الرحب والسعة :)

تحياتي

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#22
اقتباس

اقتراح لميزات وإمكانات إضافية:

- إضافة حركات مخصصة أخرى (كالحركة الدائرية، الدورانية rotation)، دعم تغيير الأبعاد والشفافية أثناء التحريك.

- إضافة دعم للتسارع، وتحكم إضافي بالسرعة.

- إضافة مزايا أحداث إضافية.

بأمانة اقتراحات جميلة وستضيف للحزمة الكثير

مع أني مشتاق أن أعرف الأحداث الإضافية :)

اقتباس

اقتراحات أولية:

فيما يتعلق بالتحريك (بالتحديد: Animation، ِAnimationScript, PointToPointAnimation، AnimationList)، أرى أنه يجب أن تكون كما يلي:

فئة باسم AnimationStep تمثل خطوة واحدة بالحركة، أي نقلة واحدة من نقطة إلى نقطة (ويمكن في المستقبل تضمين تدوير rotation فيها، وتغيير بالأبعاد transformation، وتغيير بالشفافية opacity بحيث تدعم حركات متقدمة).

واجهة باسم Animation (بدل AnimationScript) تمثل الحركات الكاملة المختلفة (مثل حركة مستقيمة، دائرية، دورانية، وفق مسار)، تقوم بتوليد LinkedList<AnimationStep> (كما في الكود الحالي).

أي أن يتم الاستغناء عن الفئة AnimationList واستبدالها بـ LinkedList<AnimationStep> لأنها لا تقدم أي قيمة مضافة عنها !!

كما يجب إعادة ترتيب بعض الأمور، على سبيل المثال animateComponent موجودة داخل الـ AnimationObject لكن من المنطقي أكثر أن توجد ضمن الـ AnimationEngine.

بالنسبة لـ AnimationStep فأعتقد أنها ستمثل ما تمثله Animation حالياً مع بعض الإضافات التي أراها رائعة

وعلى كل أجد الاسم الجديد جيد

بالنسبة لـ AnimationList أعتقد أني وضحت رأيي فيها وأن القيم المضافة التي تقوم بها واضحة من ناحية غرضية

بالنسبة للدالة animateComponent هذا أمر نسبي هل المحرك من يحرك الكائنات المتحركة أم المحرك من يعطي أمر التحريك والكائنات المتحركة هي التي تتحرك بنفسها

على العموم أعتقد أن مكانها الحالي أكثر منطقية ففي الأغلب الكائنات المتحركة تتحرك بعد إذن التحريك

بهذا أكون رددت على جميع التساؤلات في الموضوع

أنتظر تساؤلات أخرى :)

تحياتي

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#23

ممكن class diagram للمحرك، حتى ما أتخبط دون فائدة بالـ Code.

تم تعديل هذه المشاركة بواسطة JDurrah في 28 مارس 2010 في 01:31

#24

احم احم

لا وجود له في آخر إصدارات

على العموم هناك واحد كروكي تقريباً في الإصدارة 0.2 ربمع يعطيك شيئاً

http://modonat-alaa.freehostia.com/2009/03/%D8%AD%D8%B2%D9%85%D8%A9-%D8%A7%D9%84%D9%85%D8%AD%D8%B1%D9%83-%D8%A7%D9%84%D8%A5%D8%B5%D8%AF%D8%A7%D8%B1%D8%A9-02/

تحياتي

حزمة المحرك الإصدارة 0.8

أي أحد يجد أني ظلمته فليراسلني

وبإذن الله لو كان له حق سيأخذه

728x90.png

#25

السلام عليكم

بداية أعتذر عن التأخير في هذه المشاركة ...

كنت أرغب في تقديم نسخة "شبه" كاملة ... لكني فضلت التعاون مرحلة مرحلة، وهذه روح المصادر المفتوحة ! أليس كذلك ؟!

الحزمة أبعد ما تكون عن الكمال، لكنها تبيّن بوضوح كافة ميزات التصميم الجديد وفوائده.

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

مزايا التصميم الجديد بشكل مختصر:

- فصل تطوير أكواد توليد الحركات عن أكواد التحريك الفعلي

- أبسط وأوضح وأكثر قابلية للتطوير

- إمكانات جديدة وقوية (كالدوران والشفافية، وإعادة التحجيم ...) )ليست جميعها محقق بشكل كامل(

أهم التعديلات:

- حذف كل من الفئات: AnimationGroup، AnimationList، AnimationListEvent، AnimationType مع القيام بالتعديلات الضرورية.

- تم إعادة تسمية الكثير من الأمور :D للسهولة والوضوح والاختصار. مثل: تغيير اسم الحزمة script إلى AnimationGenerators، وتغيير اسم الواجهة AnimationScript إلى AnimationGenerator، واختصار كلمة Animation في معظم الحزمة إلى الحرف A.

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

- إعادة تصميم وصياغة الفئة Animation باسم AStep وهي عبارة عن خطوة واحدة في أي حركة.

- إنشاء فئة P2PAnimation والتي تقوم مقام الفئة PointToPointAnimation تدعم التحريك بين أي نقطتين (مازالت ببداياتها).

- إنشاء فئة اختبار باسم t تقوم بتحريك وإعادة تحجيم غرضين بنفس المحرك.

- إعادة ترتيب الحزم الفرعية وفصل الاختبارات عن الكود.

- حذف كافة التعليقات ! (لا أحب وجود تعليقات في الكود أثناء تطويره ! يمكن إعادة صياغتها لاحقاً)

ما الذي نحتاج العمل عليه ؟

(بالترتيب)

- التخلص نهائياً عن الفئتين Scheduler و SchedulerObject (سأفصّل في ذلك لاحقاً) وإعادة ربط تزامن المحرك بالـ AObject والـ AStep.

- إضافة المزيد من الـ AnimationGenerators وإعطائهم المزيد من الخصائص، مع تحقيق دعم لهذه الخصائص بالمحرك.

- استخدام المتنصتات على خصائص الصف PropertyChangeListener في مواضع الحاجة (مثل stop !)

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

________________________________

مشاكل Scheduler و SchedulerObject ... والتخطيط لقتلهما !!

لقد واجهت صعوبة في محاولة "تفكيك" هذه الفئتين واستعصتا علي كثيراً ...

لم تعجبني الفئة SchedulerObject بالتحديد لعدة أسباب:

• الفئة وظيفياً هي جزء من الـ AObject ومن الخطأ فصلها في فئة منفصلة من غير حاجة ضرورية.

• يجب أن يتم تخزين زمن الانتظار قبل البدء بتنفيذ الخطوة التالية من aStep.getTime() وليس من aObjectTime وهذا يلغي الحاجة إلى جزء كبير منه الفئة.

• لو كانت وظائفه مدمجة في AObject لألغينا الحاجة لأهم الأعضاء البيانية الموجودة فيه: aObject، aObjectTime، aStep وهذا يدل على أنه لا يقوم بوظيفة حقيقية

• لو كانت وظائفه مدمجة لبسطنا الكثير من الكود وألغينا الحاجة إلى الوصول غير المباشر، مثل: SchedulerObject.getAObject() و SchedulerObject.getStep()

• لا أجد فائدة فعلية لتحقيقه لواجهة Comparable.

الآن الكود يعمل من دونهما تقريباً ... وسيتم حذفهما قريباً والقيام بالتعديلات الضرورية.

قبل أن أنسى ! يمكنك تحميل الحزمة بعد التعديل بالمرفقات:

AAnimation+test (new).zip

تم تعديل هذه المشاركة بواسطة Speed_Of_Light في 2 أبريل 2010 في 02:40

مواضيع مشابهة