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

كيف نعمل مؤقت زمني بطريقة صحيحة

بدأه عبد العزيز اليوسفي في 26 ديسمبر 2007 · 11 رد · 14,325 مشاهدة · في لغة Ms Visual Basic 6 وما قبلها من إصدارات
مشاركة: واتساب X فيسبوك تيليجرام
#1 صاحب الموضوع

بسم الله الرحمن الرحيم نبدأ

أضع هذا الموضوع وهو إجتهاد شخصي وهو كيف نعمل مؤقت أوعداد زمني سنحتاجه عندما نريد أن يعمل بشكل صحيح دون تغيير في زمنه ،

حيث كنت سأضعه أيام عيد الأضحى المبارك ولكنني إنشغلت ولم أكمله إلى هذا اليوم.

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

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

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

هذا الكود البرمجي معروف للكل لعمل عداد زمني بالزيادة حيث يصل العداد للنقطة المطلوبة ويقوم بعمل ماتريد كإيقاف تشغيل الجهاز أو ..

Dim T As Integer

Private Sub Form_Load()
	Timer1.Interval = 1000
End Sub

Private Sub Timer1_Timer()
  T = T + 1
	If T = 60 Then MsgBox "إكتمل الوقت المطلوب": End
End Sub

شرح بسيط للكود :

حيث صرحنا في الأول عن متغير T في قسم التصريحات العامة ، وهنا عند تشغيل البرنامج ستكون قيمة المتحول T هي الصفر كونه عددي (Integer)

نقطة هامة يجب ذكرها هنا وهي أن التصريح عن المتحولات العددية من نوع (Integer) سيتعامل مع كمية محدودة من الأعداد ولا يمكن أن يزيد عنها ، مثلاً لوأعطينا قيمة ما كبيرة للمتحول (T) السابق ولتكن 50000 وقمنا بتشغيل البرنامج فإن رسالة الطفحان (OverFlow) ستظهر ، مثال:

Dim T As Integer

Private Sub Command1_Click()
	T = 50000
End Sub

لذلك عند التعامل مع أعداد كبيرة سنستعمل النوع (Long) في التصريح عن المتحول

وإذا كنا سنتعامل مع أعداد قليلة سيكون النوع (Byte) هو المناسب ويتعامل مع الأعداد من الصفر وحتى 255 فقط

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

فنحن نعرف أن النوع (Long) يحجز مكان له في الذاكرة وهو 4 بايت وهذا يؤدي عند كثرته في البرنامج لتقليل الذاكرة وهذا يعني تقليل أداء جهازك وسرعته

والنوع (Integer) سيستحل 2 بايت في الذاكرة وهو نصف المتحول السابق

والنوع (Byte) سيأخذ 1 بايت من الذاكرة وهو أقل المتحولات العددية وكشكل عام

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

أي أننا يمكن جعل الكود السابق هكذا:

Dim T As Byte

Private Sub Form_Load()
	Timer1.Interval = 1000
End Sub

Private Sub Timer1_Timer()
  T = T + 1
	If T = 60 Then MsgBox "إكتمل الوقت المطلوب": End
End Sub

فجعلنا هنا T من نوع (Byte) وهذا سبب أنه أعطينا T = 60 والعدد 60 هو من ضمن مجال النوع (Byte) كما ذكرت من 0 وحتى 255

حيث يمكن أن نستخدم المتحول في مثالنا السابق لأربع دقائق وثلث تقريباً (255 ثانية ÷ 60 = 4.25 دقيقة )

ملاحظة عند إستعمالك للنوع (Byte) من إجراءات متعددة في برنامجك فيجب عليك تذكر أن هذا النوع محدود ولا يمكن أن نساوي معه نوع آخر وقيم أكبر منه.

نعود لبدء الحديث بشرح الكود حيث ذكرت أن عند تشغيل البرنامج ستكون قيمة المتحول T مساوية الصفر كونه عددي (الشرح معروف للجميع ولكن وضعته للمبتدىء والذي لا يعرف ذلك)

ثم قمنا في إجراء بدء التحميل بإعطاء القيمة 1000 للتايمر1 أي أن التايمر سينفذ نفسه كل 1000 ميلي ثانية أي 1 ثانية (طبعاً يمكن إضافة القيمة لخاصية Interval للتايمر فوراً أو أي قيمة نريد ولكن كتبتها في بدء التحميل لمعرفة أننا نتعامل في هذا المثال مع الثواني).

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

ثم في الخطوة التالية من الكود أضفنا للمتحول T في إجراء تنفيد التايمر القيمة 1 (T = T + 1) أي أن المتحول ستزداد قيمته كل ثانية ب 1 وهكذا حتى نصل للزمن المحدد لتنفيد أمر محدد وفي مثالنا هو 60 ثانية وهذا هو مبدأ أي عداد زمني.

كما يمكن عمل العداد تراجعي كأن نعطي للمتحول قيمة ما ويقوم التايمر بإنقاصها إلى حين نقطة معينة وكمثال :

Dim T As Byte

Private Sub Form_Load()
	Timer1.Interval = 1000
	T = 60 
End Sub

Private Sub Timer1_Timer()
  T = T - 1
	If T = 0 Then MsgBox "OK": End
End Sub

********************************************************************

هنا نأتي لمستوى المتوسطين

طيب ماذا عن أسطر تعليمات برنامجك وكثرتها وخاصة الأسطر التي تستخدم التعليمة For .. To أو ماشابها من Loop هذا كله يستهلك من قدرة المعالج ومن الذاكرة ،ويجب دراسته جيداً لزيادة السرعة وتقليل الذاكرة.

فعند تصريح متحول في ال For .. To مثلاً ستجد أن الفوجول بيسك سيتعامل مع المتحول فوراً بأنه من النوع (Integer) ولو قمنا بكتابة العبارة Option Explicit في أول التصريحات العامة لوجدنا أن معظم المبرمجين يصرح عن المتحول ب Dim i As Integer وقد يكون المتحول أصلاً من 0 إلى 20 مثلاً ، أليس من الأفضل التصريح عن المتغير بنوع بايت(Byte) في ذلك السطر ليكون ملائم لكوده الصغير وخاصة عندما يكون برنامجك كبير.

Dim i As Byte
For i = 0 To 20
	'...   
Next

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

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

وأعلم أيضاً أنه يمكنك إختصار المتحولات لمتحول واحد ولكن هذا سيؤدي لزيادة المعالجة وسيؤدي للإبطاء في تنفيد البرنامج والإبطاء في سرعة معالج جهازك (ستلاحظ ذلك في أكوادك الكثيرة وبرامجك قيد التشغيل والعمل) ،والعكس صحيح يمكنك الإكثار من المتحولات في الذاكرة على حساب توفير من سرعة المعالج ،مثال بسيط جداً للتوضيح وسنتعامل مع الأعداد في هذا المثال من 0 إلى 9 فقط :

Dim A As Byte, B As Byte

Private Sub Form_Load()
	A = 1
	B = 5
End Sub

Private Sub Command1_Click()
	MsgBox A + B
End Sub

فقمنا بالتصريح عن متحولين من نوع بايت في الذاكرة فهذا يعني أنه سيتم حجز 1 + 1 = 2 بايت في الذاكرة حتى إغلاق البرنامج

ثم أعطينا قيمة لهذين المتحولين 1 و 5 ، وعند تنفيد عملية الجمع سيقوم المعالج بأخذ قيمة أول متحول من الذاكرة ويجمعها مع القيمة الثانية ويظهر النتيجة ، فهنا كان إستخدامنا للذاكرة 2 بايت ، فهل يمكن أن نحجز 1 بايت فقط في الذاكرة ،الجواب يمكن كما يلي:

Dim C As Byte

Private Sub Form_Load()
	C = 1
	C = C & 5
End Sub

Private Sub Command1_Click()
	MsgBox Val(Left(C, 1)) + Val(Right(C, 1))
End Sub

النتيجة هي نفسها (6) حيث قمنا هنا بالتصريح عن متحول واحد فقط © ،وأستطعنا إعطاء المتحول رقمين بجانب بعضهم بإستعمال الدالة (&)، ولكن كانت عملية تحليل هذا المتحول طويلة أي أنه قللنا الذاكرة على حساب المعالج الذي قام بإستدعاء دالة Val مرتين ودالة أخذ أول حرف من اليسار ودالة اليمين ودالة الجمع ، وأيضاً من أجل ماحدا يزعل (دالة المسج).

سيقول لي البعض لماذا تذكر النوع بايت (Byte) كثيراً فسأقول لأنني أحببت التعامل معه وهو أصغر المتحولات في الذاكرة والأمر عائد لك.

طبعاً كان المثال السابق للتوضيح ولا يمكن تطبيقه على كل شيىء فهذا كله كما ذكرت عائد لك وما تمليه عليك متطلبات برنامجك وجهازك

*************************************************************

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

فما هو الحل ؟ وكيف سنحل هذه المشكلة ؟ فستقول لي نعمل العداد من الساعة الموجود بالجهاز كما في هذا المثال :

Dim A As Long

Private Sub Command1_Click()
	A = Timer
	Timer1.Interval = 1000 
End Sub

Private Sub Timer1_Timer()
	Dim B As Long: B = Timer
	'Label1 = B - A
	If B - A >= 60 Then MsgBox "إكتمل الوقت المطلوب": End
End Sub

الدالة Timer تقوم بإعطاءك قيمة الوقت الحالي بالثانية مضافاً إليها فاصلة ثم ثلاث أرقام هم بالملي ثانية ، مثال: 46800.999

وهذا الرقم كمثال هو عدد الثواني من منتصف الليل الساعة 12 ليلاً إلى الساعة 1 ظهراً ، فعند بدء اليوم الجديد أي اللحظة التي بعد 12 ليلاً ستعود الدالة بإعطاءك الرقم صفر من جديد وتبدأ بالعد من جديد.

قمنا في المثال السابق بالتصريح عن المتحول A بنوع (Long) وذلك لحذف الفاصلة من الرقم وجعله رقم صحيح

وإذا قمنا بالتصريح عن المتحول A بالنوع (Integer) لن يفيد لأن القيمة المسندة للمتحول ستكون خارج نطاق هذا النوع وسيظهر لك عند بدء تشغيل البرنامج رسالة الطفحان كما أن هذا النوع أو غيره سيتعرف على الفاصلة العشرية.

ففي المثال السابق عند الضغط على الزر (Command1) سيقوم الإجراء بإعطاء قيمة الوقت الحالية بالثانية للمتحول A ( وسيحتفظ المتحول A بهذه القيمة لنهاية برنامجنا) وبعد ذلك نجد أمر تشغيل التايمر وتنفيد كوده كل 1 ثانية (ملاحظة عندما تكون قيمة أي تايمر مساوية الصفر وكانت خاصية القدرة Enabled = True فإن إدراج أي قيمة للتايمر ستؤدي لتشغيل التايمر)

وأيضاً قمنا بإعطاء المتحول B - A > 60 بإشارة أكبر من 60 وذلك لضمان شرط تنفيد الأمر المطلوب إذا ظهر العد أكثر من 60

الآن عندما سيعمل التايمر فبكل بساطة سيقوم بطرح قيمة الزمن الحالي من الزمن الثابت(A) وستكون النتيجة عداد يعتمد على ساعة الجهاز بالثواني.

ضع الكود السابق في برنامجك وشغل البرنامج وستجد أن العداد قد نفذ رسالة المسج بوكس بالتحديد في الوقت المحدد دون أي تأخير رغم كل ماسيجد من معوقات .

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

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

[HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Policies\Explorer]
"HideClock"=dword:00000001

أو أمر عدم الدخول للوحة التحكم كهذا :

[HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Policies\Explorer]
"nocontrolpanel"=dword:00000001

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

time 11:30:30
date 20-12-2007

إذا الطريقة السابقة لم تنفع فدعونا نبحث عن طريقة أو وقت ما في النظام لا يمكن تغييره ولا يمكن لأحد العبث به وطبعاً سيكون يعتمد على تردد كرستالة البيوس ، فسنجد الدالة GetTickCount التابعة للمكتبة الشهيرة (kernel32) التي ستبدأ العد من الصفر عند بدء تشغيل الوندوز حتى إنهاء تشغيل الوندور .

فلنصرح عن الأداة في قسم التصريحات العامة :

Private Declare Function GetTickCount Lib "kernel32" () As Long
Dim A As Long

وسنحصل على الوقت الذي مضى على تشغيل الجهاز بالميلي ثانية كما يلي ، وفي مثالنا سنحوله للثواني ليصبح :

 A = GetTickCount \ 1000

وهنا إستخدامنا إشارة التقسيم بدون الباقي .

وننتقل لكتابة باقي أسطر الكود كما فعلنا سابقاً :

Private Sub Timer1_Timer()
	Dim B As Long: B = GetTickCount \ 1000
	If B - A >= 60 Then MsgBox "إكتمل الوقت المطلوب": End
End Sub

ولا ننسى ضبط قيمة التايمر في مثالنا على 1000 ملي ثانية وشغل البرنامج وجرب الكود وستجد هذا المؤقت سيعطيك الوقت المطلوب بالزمن المحدد

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

في المرفق مثال للطريقة السابقة ، جربها مع الضغط على المعالج مع الطريقة العادية فإذا لم تقتنع وكنت تملك جهاز حديث وسريع فإنه ليس الكل لديه مثل جهازك ،فهناك أجهزة تعمل إلى الآن بمعالج 300 ميغا أو500 وبذاكرة 128 ميغا هرتز

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

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

تم بعون الله تعالى .. والله المستعان

TickCount.rar

تم تعديل هذه المشاركة بواسطة عبد العزيز اليوسفي في 26 ديسمبر 2007 في 13:56

#2

ممكن شرح طريقة عمل امر Sleep

#3

الدالة Sleep تقوم بإيقاف كلي لعمل البرنامج لمدة محدود ولا يمكنك التعامل معها بعدة مؤقتات ، وإذا أردت التعامل معها وتجريبها فتفضل :

Private Declare Sub Sleep Lib "kernel32" (ByVal dwMilliseconds As Long)

Private Sub Form_Load()
	Timer1.Interval = 1000
	Text1 = 0
End Sub

Private Sub Command1_Click()
	Sleep 3000 'نوم لثلاث ثواني
End Sub

Private Sub Timer1_Timer()
	Text1 = Text1 + 1
End Sub
#4

بالإضافة لطريقتك توجد طريقة اخرى لعمل هذا المؤخر الزمنى

سأقول لك الفكره على شكل مثال، فالنفترض انك تريد تأخير تنفيذ إغلاق الجهاز لمدة ساعه و 10 دقائق و عشرين ثانيه فكل ما افعله هو تحويل الوقت السابق كل إلى عدد من الثوانى ثم جمع تلك الثوانى داخل متغير رقمى كالتالى

Dim Total Secs as long

Dim Hr as long
Dim Min as integer
dim Scnd as byte


Hr  = 1 * 60 * 60   ' أقوم بتحويل الساعات لثوانى
Min= 10 * 60		' تحويل الدقائق لثوانى
Scnd=20

TotalSecs=Hr+Min+Scnd

بعد ذلك اقوم بإضافة قيمة المتغير TotalSecs إلى الوقت الحالى للجهاز و اقوم بحفظه داخل متغير من نوع Date هذا المتغير يتم التصريح عنه فى الجزء العام للتصريحات داخل الفورم

Dim TargetTime as Date  ' هذا المتغير يصرح عنه فى الجزء الخاص بالتصريحات العامه

TargetTime = DateAdd("s", TotalSecs, Now)


'بعد ذلك و داخل تايمر نكتب الكود التالى
'Interval=1000

Private Sub Timer1_Timer()

  dim t as string

   if t="00:00:00" then
	   msgbox "انتهى الوقت سيتم غلق الجهاز الأن"
	   Timer1.Enabled=False
	   Exit sub
	end if

   t=Format$(TargetTime - Now, "hh:mm:ss")
End sub

كل ما افعله هو طرح قيمة الوقت الموجود فى TargetTime من الوقت الحالى للجهاز، و حيث ان المتغير TargetTime يحتوى على وقت بداية تنفيذ الكود بالإضافة إلى الوقت الذى تريد انتظاره قبل تنفيذ كود معين لذا فالمتغير TargetTime سيحتوى على وقت اكبر من الوقت الحالى و حيث ان الوقت الحالى الموجود فى المتغير Now دائم الزيادة و قيمة المتغير TagetTime ثابته، لذا فعملية الطرح ستظل تنقص الوقت حتى يصبح كالتالى "00:00:00" لإنى طلبت من الدالة Format$ أن تعود بالناتج على هذا الشكل.

و الله ولى التوفيق

مدونتي: C++ Tips and Tricks

#5

أخي Game Expert طريقتك صحيحة لعمل المؤخر أو المؤقت الزمني أو عداد أو تنبيه ... كلها بنفس المعنى

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

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

أرجو أن يكون قصدي مفهوم بما شرحت سابقاً .

وأعجبتني طريقتك هذه في التصريح عن المتغيرات كل بما يناسبه وهذه تعتبر مثال جيد لما قلته سابقاً :

Dim Hr as long
Dim Min as integer
dim Scnd as byte

والله ولي التوفيق ..

#6

مشكوررررين يسلموا ايديكم على توضيح بعض الامور التي كانت لي غامضة قليلا ...

شكوت الى وكيع سوء حفظي فأشار على بترك المعاصي واخبرني ان علم الله نور و نور الله لا يأتي لعاصي

#7

بصراحه درس متعوب عليه

وتشكر عليه اخي عبدالعزيز

ولكن الاخير صعب ومافهمت

عندي سؤال هل ممكن تساعدني؟ ( سؤال صعب بالنسبه لي)

#8

العفو أيها الأفاضل

الأخ "جالس على البحر" عفواً الساحل :rolleyes: ،وماهو السؤال الذي تريد الإجابة عليه تفضل

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

#9

السلام عليكم

أخي الفاضل ..

أنا مبتدئ في عالم البرمجة وخصوصا في الVB.NET فاعذرني على اسئلتي

لم أفهم هذا السطر جيدا

Timer1.Interval = 1000

كيف أفعل مثل كودك حيث انني :

احتاج في برنامجي تايمر كل 10 دقائق يقوم بحدث معين وهو اظهار فورم أخرى

شكرا لك ولتعاونك

#10

الله يجزاك الف خير

كنت لم اضع تصريح عن متحول دائما اضع Integer

وعدم مراعاة ما هي منطقة الاعداد

الف شكر على تنبيهكم الجميل والشرحكم الوافي :)

#11

جزاك الله خيرا أخي الكريم

#12

شكرا لكم انا مبرمج دلفي كنت ابحث عن الامر sleep ولم اجده كنت قد نسيته :wacko: وانا بحاجة اليه ثم قرات الردود وتذكرت الكلمة شكرا لكم :wub: :wub:

تم تعديل هذه المشاركة بواسطة the virus deadly في 19 يونيو 2011 في 16:38

استغفر الله العظيم

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