bo8ster Posted April 20, 2009 Share Posted April 20, 2009 (edited) Hi all. I have seen a number of requests for something like this in the Help and Support section so I thought I would post it. All the credit goes to SmOke_N - I just touched it up. This script was created when trying to get a ControlHandle that has next to no information displayed in the AutoIT Info Tool. expandcollapse popup; =============================================================================== ;~ This script gets the control under the mouse pointer (active or inactive) ;~ The information then can be used with in conjunction with control functions. ;~ Requires AutoIt v3.3.6.0 or later to run and to view apps maximized. ;~ Big thanks to SmOke_N and Valik their help in creating it. ; =============================================================================== #include <WinAPI.au3> #include <Array.au3> #include <WindowsConstants.au3> AutoItSetOption("MustDeclareVars", 1) AutoItSetOption("MouseCoordMode", 1) AdlibRegister("_Mouse_Control_GetInfoAdlib", 10) HotKeySet("^!x", "MyExit") ; Press Ctrl+Alt+x to stop the script ;~ #AutoIt3Wrapper_run_debug_mode=Y Global $pos1 = MouseGetPos() Global $pos2 = MouseGetPos() ; must be initialized Global $appHandle = 0 While 1 Sleep(0xFFFFFFF) WEnd ; =============================================================================== ;~ Retrieves the information of a Control located under the mouse and displayes it in a tool tip next to the mouse. ;~ Function uesd ;~ _Mouse_Control_GetInfo() ;~ GetDlgCtrlID ; =============================================================================== Func _Mouse_Control_GetInfoAdlib() $pos1 = MouseGetPos() If $pos1[0] <> $pos2[0] Or $pos1[1] <> $pos2[1] Then ; has the mouse moved? Local $a_info = _Mouse_Control_GetInfo() Local $aDLL = DllCall('User32.dll', 'int', 'GetDlgCtrlID', 'hwnd', $a_info[0]) ; get the ID of the control If @error Then Return ToolTip("Handle = " & $a_info[0] & @CRLF & _ "Class = " & $a_info[1] & @CRLF & _ "ID = " & $aDLL[0] & @CRLF & _ "Mouse X Pos = " & $a_info[2] & @CRLF & _ "Mouse Y Pos = " & $a_info[3] & @CRLF & _ "ClassNN = " & $a_info[4] & @CRLF & _ ; optional "Parent Hwd = " & _WinAPI_GetAncestor($appHandle, $GA_ROOT)) $pos2 = MouseGetPos() EndIf EndFunc ;==>_Mouse_Control_GetInfoAdlib ; =============================================================================== ;~ Retrieves the information of a Control located under the mouse. ;~ Uses Windows functions WindowFromPoint and GetClassName to retrieve the information. ;~ Functions used ;~ _GetHoveredHwnd() ;~ _ControlGetClassnameNN() ;~ Returns ;~ [0] = Control Handle of the control ;~ [1] = The Class Name of the control ;~ [2] = Mouse X Pos (converted to Screen Coord) ;~ [3] = Mouse Y Pos (converted to Screen Coord) ;~ [4] = ClassNN ; =============================================================================== Func _Mouse_Control_GetInfo() Local $client_mpos = $pos1 ; gets client coords because of "MouseCoordMode" = 2 Local $a_mpos ;~ Call to removed due to offset issue $a_mpos = _ClientToScreen($appHandle, $client_mpos[0], $client_mpos[1]) ; $a_mpos now screen coords $a_mpos = $client_mpos $appHandle = GetHoveredHwnd($client_mpos[0], $client_mpos[1]) ; Uses the mouse to do the equivalent of WinGetHandle() If @error Then Return SetError(1, 0, 0) Local $a_wfp = DllCall("user32.dll", "hwnd", "WindowFromPoint", "long", $a_mpos[0], "long", $a_mpos[1]) ; gets the control handle If @error Then Return SetError(2, 0, 0) Local $t_class = DllStructCreate("char[260]") DllCall("User32.dll", "int", "GetClassName", "hwnd", $a_wfp[0], "ptr", DllStructGetPtr($t_class), "int", 260) Local $a_ret[5] = [$a_wfp[0], DllStructGetData($t_class, 1), $a_mpos[0], $a_mpos[1], "none"] Local $sClassNN = _ControlGetClassnameNN($a_ret[0]) ; optional, will run faster without it $a_ret[4] = $sClassNN Return $a_ret EndFunc ;==>_Mouse_Control_GetInfo ; =============================================================================== ; Retrieves the Handle of GUI/Application the mouse is over. ; Similar to WinGetHandle except it used the current mouse position ; Taken from http://www.autoitscript.com/forum/index.php?showtopic=444962 ; Changed to take params to allow only one set of coords to be used. ; Params ;~ $i_xpos - x position of the mouse - usually from MouseGetPos(0) ;~ $i_ypos - x position of the mouse - usually from MouseGetPos(1) ; =============================================================================== Func GetHoveredHwnd($i_xpos, $i_ypos) Local $iRet = DllCall("user32.dll", "int", "WindowFromPoint", "long", $i_xpos, "long", $i_ypos) If IsArray($iRet) Then $appHandle = $iRet[0] Return HWnd($iRet[0]) Else Return SetError(1, 0, 0) EndIf EndFunc ;==>GetHoveredHwnd ; =============================================================================== ;~ Gets the ClassNN of a control (Classname and Instance Count). This is checked with ControlGetHandle ;~ The instance is really a way to uniquely identify classes with the same name ;~ Big thanks to Valik for writing the function, taken from - http://www.autoitscript.com/forum/index.php?showtopic=97662 ;~ Param ;~ $hControl - the control handle from which you want the ClassNN ;~ Returns ;~ the ClassNN of the given control ; =============================================================================== Func _ControlGetClassnameNN($hControl) If Not IsHWnd($hControl) Then Return SetError(1, 0, "") Local Const $hParent = _WinAPI_GetAncestor($appHandle, $GA_ROOT) ; get the Window handle, this is set in GetHoveredHwnd() If Not $hParent Then Return SetError(2, 0, "") Local Const $sList = WinGetClassList($hParent) ; list of every class in the Window Local $aList = StringSplit(StringTrimRight($sList, 1), @LF, 2) _ArraySort($aList) ; improves speed Local $nInstance, $sLastClass, $sComposite For $i = 0 To UBound($aList) - 1 If $sLastClass <> $aList[$i] Then ; set up the first occurrence of a unique classname $sLastClass = $aList[$i] $nInstance = 1 EndIf $sComposite = $sLastClass & $nInstance ;build the ClassNN for testing with ControlGetHandle. ClassNN = Class & ClassCount ;if ControlGetHandle(ClassNN) matches the given control return else look at the next instance of the classname If ControlGetHandle($hParent, "", $sComposite) = $hControl Then Return $sComposite EndIf $nInstance += 1 ; count the number of times the class name appears in the list Next Return SetError(3, 0, "") EndFunc ;==>_ControlGetClassnameNN Func MyExit() ; stops the script ConsoleWrite("Script Stoppted By User" & @CR) Exit EndFunc ;==>MyExit Edit: Sept 09 Enhancement by corgano Added ControlID Added ClassNN and now requires AutoIt v3.3.0.0 or later to run Removed _WinAPI_GetParent and added global $appHandle 06 Apr 10 Removed ClientToScreenCall Made _ControlGetClassnameNN apart of the script General Updates Edited April 6, 2010 by bo8ster IgImAx, coibaka and oapjr 2 1 Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
rexx Posted June 28, 2009 Share Posted June 28, 2009 Hi, I'm finding how to get ClassNN under mouse, and i found this post. But it only get the Class, not the ClassNN. Is it possible to get ClassNN? Link to comment Share on other sites More sharing options...
corgano Posted June 29, 2009 Share Posted June 29, 2009 added Global $pos1 = MouseGetPos() Global $pos2 = MouseGetPos() to the begining and changed Func _Mouse_Control_GetInfoAdlib() $pos1 = MouseGetPos() If $pos1[0] <> $pos2[0] and $pos1[1] <> $pos2[1] Then Local $a_info = _Mouse_Control_GetInfo() If @error Then Return ToolTip("Handle = " & $a_info[0] & @CRLF & _ "Class = " & $a_info[1] & @CRLF & _ "Mouse X Pos = " & $a_info[2] & @CRLF & _ "Mouse Y Pos = " & $a_info[3]) $pos2 = MouseGetPos() EndIf EndFunc so it would not flicker. i am impressed, it got the handle of win 7's IE (shown nothing in au3info) 0x616e2069646561206973206c696b652061206d616e20776974686f7574206120626f64792c20746f206669676874206f6e6520697320746f206e657665722077696e2e2e2e2e Link to comment Share on other sites More sharing options...
bo8ster Posted June 30, 2009 Author Share Posted June 30, 2009 @rexx, this was not designed to give the ClassNN but I understand that it can be handy.SmOke_N also created a function called WinGetCtrlInfo which will give you the ClassNN.Once you get the handle from my function, pass it to WinGetCtrlInfo. The original post is here - http://www.autoitscript.com/forum/index.php?showtopic=32781@corgano - that's the beauty of black box calling Window's dlls, the implementation does not matter. I cannot comment why au3info tool did not work, that's the dev's area. Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
corgano Posted June 30, 2009 Share Posted June 30, 2009 You should update script with the fix i posted a few posts ago. It reduces flicker 0x616e2069646561206973206c696b652061206d616e20776974686f7574206120626f64792c20746f206669676874206f6e6520697320746f206e657665722077696e2e2e2e2e Link to comment Share on other sites More sharing options...
bo8ster Posted June 30, 2009 Author Share Posted June 30, 2009 You should update script with the fix i posted a few posts ago. It reduces flickerThanks corgano. I experience no flicker using XP so I almost missed what your enhancement actually does. I see it is to stop _Mouse_Control_GetInfo() from being called if the mouse does not move which helps reduce flicker.I will update my original post. Thanks again. Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
rexx Posted June 30, 2009 Share Posted June 30, 2009 (edited) @rexx, this was not designed to give the ClassNN but I understand that it can be handy. SmOke_N also created a function called WinGetCtrlInfo which will give you the ClassNN. Once you get the handle from my function, pass it to WinGetCtrlInfo. The original post is here - http://www.autoitscript.com/forum/index.php?showtopic=32781Thanks! But I got problem using this. I added a line Local $a_classnn = _WinGetCtrlInfo($a_info[0]) in func Func _Mouse_Control_GetInfoAdlib() But I got 0 in $a_classnn[0][0], i cant get the correct classnn of the control. I also tried Local $a_classnn = _WinGetCtrlInfo(WinGetHandle("[active]")) and it does return a list of controls. What's going wrong? Edited June 30, 2009 by rexx Link to comment Share on other sites More sharing options...
bo8ster Posted July 2, 2009 Author Share Posted July 2, 2009 (edited) Sorry for the delayed response been away from the computer and it has taken some time to get up to SmOke_N's level of thinking (even briefly). ClassNN is the Class name combined with the instance count of that class. SmOke_N builds a count of the instances returned from WinGetClassList in _WinGetCtrlInfo, he does not get the instance from a control handle as I originally thought/hoped. WinGetCtrlInfo thaks a handle to a Window, not a control, which is why it did not work for you, sorry for that. If it is at all helpful, Local $aDLL = DllCall('User32.dll', 'int', 'GetDlgCtrlID', 'hwnd', $a_info[0]) ; get the ID of the control, will get the control ID for you At this time I do not know how to get the instance (HINSTANCE) from a control to get the ClassNN, cleanly. They only solution I can think of (which just came to me) is to get the control ID from above line (put it in _Mouse_Control_GetInfoAdlib) then match that to the ID in the array created by WinGetCtrlInfo . I know how handy knowing the instance of the control you have is so I'll keep trying. Edit: Minor corrections Edited July 2, 2009 by bo8ster Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
burlip Posted July 2, 2009 Share Posted July 2, 2009 Nice one, bo8ster. If you change line 25 to: If $pos1[0] <> $pos2[0] or $pos1[1] <> $pos2[1] Then then the Tool Tip behaves much smoother and more responsive. Cheers... Link to comment Share on other sites More sharing options...
bo8ster Posted July 3, 2009 Author Share Posted July 3, 2009 @burlip, thanks for the pickup - I have updated the script. @rexx, you can now get the ClassNN. Thanks must go to Valik for making that possible. The tool tip now displays just about everything you need to know about any control. Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
rexx Posted July 3, 2009 Share Posted July 3, 2009 @rexx, you can now get the ClassNN. Thanks must go to Valik for making that possible.Thank you bo8ster! But I tried it and it seem not working correctly. It always get the first instance. I also tried to add while loop around $sComposite = $sLastClass & $nInstance ;build the ClassNN for testing with ControlGetHandle ;if ControlGetHandle(ClassNN) matches the given control return else look at the next instance of the classname If ControlGetHandle($hParent, "", $sComposite) = $hControl Then Return $sComposite $nInstance += 1 ; count the number of times the class name appears in the list But still the first instance. Thanks again for you help! Link to comment Share on other sites More sharing options...
bo8ster Posted July 6, 2009 Author Share Posted July 6, 2009 The function should work. The code you displayed gets run each iteration of the For loop anyhow. If you just use that code, $nInstance will not be setip correctly. If $sLastClass <> $aList[$i] Then sets up the first instance and $nInstance += 1 does the rest (> 1 Instance). Make sure you have the latest version of AutoIt or StringSplit won't work and you have ClassNNs that are Foo2 or Foo3. Check off against the AutoIT info tool. I tested with Scite as there are two controls that have the same classname. Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
rexx Posted July 6, 2009 Share Posted July 6, 2009 The function should work. The code you displayed gets run each iteration of the For loop anyhow. If you just use that code, $nInstance will not be setip correctly. If $sLastClass <> $aList[$i] Then sets up the first instance and $nInstance += 1 does the rest (> 1 Instance). Make sure you have the latest version of AutoIt or StringSplit won't work and you have ClassNNs that are Foo2 or Foo3. Check off against the AutoIT info tool. I tested with Scite as there are two controls that have the same classname.Hi, I tried it again, and somtimes it works but sometimes not. I test it on 7zip file manager, and use 2 panel, but on both panel it shows instance 1, both syslistview32 and edit. but it works on the toolbarwindow32, it shows instance 1 and 2 correctly. Link to comment Share on other sites More sharing options...
bo8ster Posted July 6, 2009 Author Share Posted July 6, 2009 Hi, I tried it again, and somtimes it works but sometimes not.I test it on 7zip file manager, and use 2 panel, but on both panel it shows instance 1, both syslistview32 and edit.but it works on the toolbarwindow32, it shows instance 1 and 2 correctly.Sorry rexx, you will need to provide more information. I did see that if I have the AutoIt Info tool displayed the mouse does funny things so I suggest you keep it minimized.I tested it with 7Zip FM as well and had no issues. I see that most is syslistview321 but there is one section that is syslistview322, I could find an edit.Have you tried viewing the list of classes to ensure there are duplicates and do you know where they are? Did you get different results from the info tool, if so how? Did you get output you did not expect, is so what did you expect and what did you get? Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
rexx Posted July 6, 2009 Share Posted July 6, 2009 Sorry rexx, you will need to provide more information. I did see that if I have the AutoIt Info tool displayed the mouse does funny things so I suggest you keep it minimized.I tested it with 7Zip FM as well and had no issues. I see that most is syslistview321 but there is one section that is syslistview322, I could find an edit.Have you tried viewing the list of classes to ensure there are duplicates and do you know where they are? Did you get different results from the info tool, if so how? Did you get output you did not expect, is so what did you expect and what did you get?Thanks for your fast reply.http://img160.imageshack.us/img160/5836/87199679.pngIn the first screenshot, it shows SysListView321, which is correct. (mouse is on the left panel)http://img56.imageshack.us/img56/8663/43540544.pngBut in the second one, it shows still SysListView321, but it's SysListView322 in AU3Info. (mouse on right panel) Link to comment Share on other sites More sharing options...
bo8ster Posted July 6, 2009 Author Share Posted July 6, 2009 (edited) Thanks for your fast reply. http://img160.imageshack.us/img160/5836/87199679.png In the first screenshot, it shows SysListView321, which is correct. (mouse is on the left panel) http://img56.imageshack.us/img56/8663/43540544.png But in the second one, it shows still SysListView321, but it's SysListView322 in AU3Info. (mouse on right panel)I can now see your issue. Everything is correct except for the ClassNN. The only thing I can think of is the ordering returned from WinGetClassList is not consistent - see http://www.autoitscript.com/forum/index.php?showtopic=97662. I will need to debug it to find out why it is the case. Either way for whatever reason, it is clear that the for loop only runs once as you indirectly pointed out before. Edit/Update: The WinGetClassList is not returning the desired List, it is not getting the top level window handle from _WinAPI_Getparent or _WinAPI_GetAncestor. for 7 Zip it returns - thus there is only ever one instance of SysListView32. SysListView32 SysHeader32 ReBarWindow32 ComboBoxEx32 ComboBox Edit ToolbarWindow32 msctls_statusbar32 Edited July 7, 2009 by bo8ster Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
bo8ster Posted July 7, 2009 Author Share Posted July 7, 2009 @rexx, give that a try. The original script was made to be used when apps where maximized, it does funny things if they are not. Tested with 7 Zip and Scite maximized. Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
rexx Posted July 7, 2009 Share Posted July 7, 2009 @rexx, give that a try. The original script was made to be used when apps where maximized, it does funny things if they are not.Tested with 7 Zip and Scite maximized.It works now!So it can only used in a maximized window?it stop updating if a window is not maximized. Link to comment Share on other sites More sharing options...
bo8ster Posted July 7, 2009 Author Share Posted July 7, 2009 At this stage it only works with maximized window. I did a lot of messing round to stop that but could not do it. It translates mouse coords so what ends up happening is when not maximized, info is grabbed not where the mouse is. It could be as much as half the screen away which is so confusing! You won't see that as it now though. I have not idea how the Info Tool does it so well, I have been through the WinAPI calls and MSDN but still can't nail it. It will have to be maximized for the time being, that was the original concept for the script anyway. Post your code because code says more then your words can. SciTe Debug mode - it's magic: #AutoIt3Wrapper_run_debug_mode=Y. Use Opt("MustDeclareVars", 1)[topic="84960"]Brett F's Learning To Script with AutoIt V3[/topic][topic="21048"]Valuater's AutoIt 1-2-3, Class... is now in Session[/topic]Contribution: [topic="87994"]Get SVN Rev Number[/topic], [topic="93527"]Control Handle under mouse[/topic], [topic="91966"]A Presentation using AutoIt[/topic], [topic="112756"]Log ConsoleWrite output in Scite[/topic] Link to comment Share on other sites More sharing options...
wraithdu Posted July 8, 2009 Share Posted July 8, 2009 (edited) Opt("MouseCoordMode", 0) -> relative coords to the active windowOpt("MouseCoordMode", 2) -> relative coords to the client area of the active windowI haven't looked at your UDF, but have you considered the WindowFromPoint() function?The WindowFromPoint function retrieves a handle to the window that contains the specified point.'Window' also means control (every control is a window too). Edited July 8, 2009 by wraithdu Link to comment Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now