PDA

View Full Version : سوال: غیر فعال کردن یه دکمه داخل منوی یک بازی با استفاده از هندل



ferankyy
سه شنبه 12 بهمن 1389, 13:23 عصر
سلام دوستان

میخوام ببینم میشه با استفاده از هندل ها یه دکمه که داخل منوی یک بازی هست رو غیر فعال کنم ؟

من میخوام کسی نتونه روی این دکمه کلیک کنه.

لطفا اگه راه دیگه ای هست که بشه این کارو کرد ، بهم معرفی کنید.

محسن واژدی
سه شنبه 12 بهمن 1389, 16:31 عصر
سلام علیکم،
میشه با APIی FindWindowو FindWindowEx و یکی دوتای دیگه هندل دکمه رو یافته و غیر فعال کنین

ferankyy
چهارشنبه 13 بهمن 1389, 00:07 صبح
ممنون از پاسخی که دادید

میشه یه نمونه برام بزارین ؟

محسن واژدی
چهارشنبه 13 بهمن 1389, 08:15 صبح
ممنون از پاسخی که دادید

میشه یه نمونه برام بزارین ؟

کد زیر را برای غیرفعال کردن صفحه نوشتاری Notepad هست که شما میتونین بجای کلاس Notepad و Editbox آن، کلاس فرم بازی و دکمه مورد نظرتون رو جایگزین آن کنین؛ برای تست کد زیر ابتدا برنامه Notepad را اجرا سپس داخل وی بی یک دکمه داخل صفحه ایجاد کنین و کد های زیر رو در ماژول بریزین:


Option Explicit
Private Declare Function EnableWindow Lib "user32" (ByVal hwnd As Long, ByVal fEnable As Long) As Long
Private Declare Function FindWindowEx Lib "user32" Alias "FindWindowExA" (ByVal hwnd1 As Long, ByVal hwnd2 As Long, ByVal lpsz1 As String, ByVal lpsz2 As String) As Long
Private Declare Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long

Private Sub Command1_Click()
Dim hwnd1&, hwnd2&
Stop
hwnd1& = FindWindow("Notepad", vbNullString)
hwnd2& = FindWindowEx(hwnd1&, ByVal 0&, "Edit", vbNullString)

If hwnd2& <> 0 Then
MsgBox EnableWindow(hwnd2&, False)
Else
MsgBox "Not found Notepad.exe"
End If
End Sub

موفق باشید
یاعلی

_behnam_
چهارشنبه 13 بهمن 1389, 13:35 عصر
با سلام ؛
دوست عزیز البته اگه شما تو بازیتون بیخواید یک گذینه از منو رو غیر فعال کنید با این کد نمیشه , چون این کد واسه اشیا استفاده میشه , واسه حذف یه گذینه از منو به شکل زیر عمل میشه ؛

تعریف توابع :

پیدا کردن هندل پنجره اصلی بازی

Private Declare Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long


پیدا کردن هندل کلی منو های بازی

Private Declare Function GetMenu Lib "user32" (ByVal hwnd As Long) As Long


پیدا کردن تک تک منو ها

Private Declare Function GetSubMenu Lib "user32" (ByVal hMenu As Long, ByVal nPos As Long) As Long


حذف یک گذینه از گذینه های یک منو

Const MF_BYPOSITION = &H400&
Const MF_REMOVE = &H1000&
Private Declare Function RemoveMenu Lib "user32.dll" (ByVal hMenu As Long, ByVal nPosition As Long, ByVal wFlags As Long) As Long


کد نویسی : ( من میخوام گذینه Exit رو از منوی فایل Notepad حذف کنم)
1. این توابع رو تو پروژه تعریف میکنی
2. با تابع ّFindWindow هندل پنجره اصلی رو پیدا میکنی

Dim Hnd As String
Hnd = FindWindow("notepad", vbNullString)

3. باید یه هندل از منو کلی پیدا کنی که به وسیله اون بتونی هندل تک تک منو هارو گیر بیاری
(تو کد زیر من به تابع GetMenu هندل پنجره اصلی برنامه رو دادم و به جاش هندل کلی منو های موجود تو امن پنجره رو گرفتم)

Dim HndMnu As String
HndMnu = GetMenu(Hnd)

4. حالا ما هندل کلی منو هارو داریم . باید هندل تک تک اونهارو گیر بیاریم , چون من میخوام یک گذینه از منو File رو حذف کنم پس اول باید هندل منو File رو گیر بیارم
(باید ببینم فایل چندمین منو از منوهای تو پنجره Notepadهست , اولیشه , پس تو تو تابه GetSubMenu , واسه nPosition منو مورد نظر رو 0 میزارم ( آیتم اول میشه 0 آیتم دوم میشه 1 آیتم سوم میشه 2 همینجوری ادامه داره))

HndMnu = GetSubMenu(HndMnu, 0)


5. الان هندل منو فایل رو گیر آوردیم و باید آیتم گذینه ایرو که میخوایم حذف کنیم رو داشته باشیم و اونو حذف کنیم
(Exit گذینه هشتم منوی ّّFile هستش , تو منو ها خطهای جدا کننده هم یک گزینه حساب میشن)

RemoveMenu HndMnu, 8, MF_BYPOSITION
کد بالا ما اومدیم هندل منو فایل رو به تابع RemoveMenu دادیم و مشخص کردیم که از منوی مورد نظر گذینه 8 رو حذف کنه

=============
کد کامل :
کد زیر تمام کدایه که من اینجا درموردشون توضیح دادم , تو ویژوال کپی کن یا کامند هم بزار و Notepat رو اجرا کن به روری کامند کلیک کن و بعد برو تو منوی File
میبینی که گذینه Exit حذف شده


Private Declare Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long
Private Declare Function GetSubMenu Lib "user32" (ByVal hMenu As Long, ByVal nPos As Long) As Long
Private Declare Function GetMenu Lib "user32" (ByVal hwnd As Long) As Long
Const MF_BYPOSITION = &H400&
Const MF_REMOVE = &H1000&
Private Declare Function RemoveMenu Lib "user32.dll" (ByVal hMenu As Long, ByVal nPosition As Long, ByVal wFlags As Long) As Long
Private Sub Command1_Click()
Dim Hnd As String
Hnd = FindWindow("notepad", vbNullString)
Dim HndMnu As String
HndMnu = GetMenu(Hnd)
HndMnu = GetSubMenu(HndMnu, 0)
RemoveMenu HndMnu, 8, MF_BYPOSITION
End Sub
موفق باشی

ferankyy
پنج شنبه 14 بهمن 1389, 21:17 عصر
با تشکر از جناب _behnam_

خوب حالا یه مشکلی هست ، چطور Classe name اون دکمه که داخل بازی هست رو پیدا کنم تا بتونم غیر فعالش کنم ؟

البته یه برنامه دارم که وقتی نشانه گر موس روی کنترل میبری Classe name اون را نشون میده ولی متاسفانه بازی من به صورت Full Screen باز میشه و نمیشه از این برنامه استفاده کرد .

آیا راه حلی سراغ دارین ؟

_behnam_
پنج شنبه 14 بهمن 1389, 22:23 عصر
خوب تو تنظیمات بازی برید و اونو از Full Screen خارج کنید
در ضمن میتونید بجای اینکه Class NaME رو وارد کنید Caption رو وارد کنید

ferankyy
جمعه 15 بهمن 1389, 23:09 عصر
یه مشکل دیگه :گریه:
من با استفاده از Caption اون دکمه ، هندلش رو میگیرم ولی متاسفانه هندل برابر با صفر هست !!
آیا امکان داره که اون دکمه اصلا دکمه نباشه ؟؟ یعنی یه کنترل دیگه باشه !! آخه خودتون میدونید که شکل ظاهری بازیها خیلی گرافیکی هست و معلوم نیست از چی استفاده کردن.
وقتی هم با استفاده از برنامه خودم نشانه گر موس رو روی اون دکمه میبرم اصلا چیزی نشون نمیده فقط Classe Name پنجره اصلی بازی رو نشون میده !!
اگه میشه کمکم کنید .

_behnam_
شنبه 16 بهمن 1389, 02:24 صبح
caption رو به شکل زیر وارد کنید

Hnd = FindWindow(vbNullString, "Caption")

محسن واژدی
شنبه 16 بهمن 1389, 06:05 صبح
یه مشکل دیگه :گریه:
من با استفاده از Caption اون دکمه ، هندلش رو میگیرم ولی متاسفانه هندل برابر با صفر هست !!
آیا امکان داره که اون دکمه اصلا دکمه نباشه ؟؟ یعنی یه کنترل دیگه باشه !! آخه خودتون میدونید که شکل ظاهری بازیها خیلی گرافیکی هست و معلوم نیست از چی استفاده کردن.
وقتی هم با استفاده از برنامه خودم نشانه گر موس رو روی اون دکمه میبرم اصلا چیزی نشون نمیده فقط Classe Name پنجره اصلی بازی رو نشون میده !!
اگه میشه کمکم کنید .

چه معلوم که اون captionیی که برای یافتن کلاس دکمه بکار میبندینش اصلا خودش یک تصویر باشه
همینطور میشه دکمه های بازیه با driectx طراحی شده باشن یعنی نه یک دکمه استاندارد یا یک یوزکنترل باشه که در اینصورت فکر نکنم بشه کاریش کرد
چون توابع FindWindow برای دکمه هایی هست که هندل داشته باشن و بشه هندلشون رو گرفت واسه همین وقتی نشانگر رو رو فرم بازی میبری نمیشه کلاس اشیاء داخل بازی رو گرفت و فقط کلاس فرم رو میگیره، البته امیدوارم خلاف این باشه.

موفق باشید

ferankyy
شنبه 16 بهمن 1389, 13:47 عصر
چه معلوم که اون captionیی که برای یافتن کلاس دکمه بکار میبندینش اصلا خودش یک تصویر باشه
همینطور میشه دکمه های بازیه با driectx طراحی شده باشن یعنی نه یک دکمه استاندارد یا یک یوزکنترل باشه که در اینصورت فکر نکنم بشه کاریش کرد
چون توابع FindWindow برای دکمه هایی هست که هندل داشته باشن و بشه هندلشون رو گرفت واسه همین وقتی نشانگر رو رو فرم بازی میبری نمیشه کلاس اشیاء داخل بازی رو گرفت و فقط کلاس فرم رو میگیره، البته امیدوارم خلاف این باشه.

موفق باشید

خوب به احتماله زیاد از Driectx استفاده شده . حالا هیچ راهی نیست که بشه این دکمه رو غیر فعال کرد . یا اینکه یه کاری کنم که کاربر نتونه روی اون کلیک کنه ؟