Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

get current mouse cursor type

How do I get the current GLOBAL mouse cursor type (hourglass/arrow/..)? In Windows.

Global - I need it even if the mouse is ouside of my application or even if my program is windlowless.

In C#, Delphi or pure winapi, nevermind...

Thank you very much in advance!!

like image 556
Alex from Jitbit Avatar asked Jan 19 '09 09:01

Alex from Jitbit


People also ask

What is the I shaped cursor called?

The I-beam pointer (also called the I-cursor) is a cursor shaped like a serifed capital letter "I". The purpose of this cursor is to indicate that the text beneath the cursor can be highlighted and sometimes inserted or changed.

How do I change my cursor to type?

Select Start > Settings > Ease of Access > Text cursor. Select Turn on text cursor indicator. Adjust the Change text cursor indicator size slider until it looks like you want in the preview. Select one of the Suggested text cursor indicator colors, or select Pick a custom color to choose your own.

What are the different cursor types?

There are 2 types of Cursors: Implicit Cursors, and Explicit Cursors.

How do I find my cursor?

Once you're in Mouse settings, select Additional mouse options from the links on the right side of the page. In Mouse Properties, on the Pointer Options tab, at the bottom, select Show location of pointer when I press the CTRL key, and then select OK. To see it in action, press CTRL.


2 Answers

OEM cursors are shared resources, so all processes requesting a specific cursor will retrieve the same handle. An application can cache standard system cursor handles at start-up, then it can use GetCursorInfo to get the global cursor handle, and look-up this handle in the cache to retrieve its kind - if it is of a system cursor.

The below Delphi sample code demonstrates. Cursor handles are populated to an array by using LoadImage at form creation. A timer polls the global cursor by using GetCursorInfo at regular intervals, the code looks-up the handle in the array to retrieve the cursor's name from a constant array of names:

const
  HighCursor = 13;

type
  TForm1 = class(TForm)
    Timer1: TTimer;
    Label1: TLabel;
    procedure FormCreate(Sender: TObject);
    procedure Timer1Timer(Sender: TObject);
  private
    FCursorHandles: array [0..HighCursor] of HCURSOR;
  public
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

const
  OEMCursors: array [0..HighCursor] of Integer = (OCR_NORMAL, OCR_IBEAM,
      OCR_WAIT, OCR_CROSS, OCR_UP, OCR_SIZENWSE, OCR_SIZENESW, OCR_SIZEWE,
      OCR_SIZENS, OCR_SIZEALL, OCR_NO, OCR_HAND, OCR_APPSTARTING,
      32651 {OCR_HELP?});

  CursorNames: array [0..HighCursor] of string = ('OCR_NORMAL', 'OCR_IBEAM',
      'OCR_WAIT', 'OCR_CROSS', 'OCR_UP', 'OCR_SIZENWSE', 'OCR_SIZENESW',
      'OCR_SIZEWE', 'OCR_SIZENS', 'OCR_SIZEALL', 'OCR_NO', 'OCR_HAND',
      'OCR_APPSTARTING', 'OCR_HELP');

procedure TForm1.FormCreate(Sender: TObject);
var
  i: Integer;
begin
  for i := 0 to HighCursor do
    FCursorHandles[i] := LoadImage(0, MakeIntResource(OEMCursors[i]),
        IMAGE_CURSOR, 0, 0, LR_DEFAULTCOLOR or LR_DEFAULTSIZE or LR_SHARED);
end;

procedure TForm1.Timer1Timer(Sender: TObject);

  function GetCursorName(Cursor: HCURSOR): string;
  var
    i: Integer;
  begin
    for i := 0 to HighCursor do
      if Cursor = FCursorHandles[i] then begin
        Result := CursorNames[i];
        Exit;
      end;
    Result := 'Unknown Cursor';  // A custom cursor.
  end;

var
  CursorInfo: TCursorInfo;
begin
  CursorInfo.cbSize := SizeOf(CursorInfo);
  if GetCursorInfo(CursorInfo) then
    Label1.Caption := GetCursorName(CursorInfo.hCursor)
  else
    Label1.Caption := 'Fail: ' + SysErrorMessage(GetLastError);
end;

Note that when using Delphi one does not have to cache cursor handles, since Delphi does it through its Screen.Cursors list. The sample code does not use it to have better portability.

Also note that there's no 'OCR_HELP' in 'winuser.h', but the provided constant corresponding to 'IDC_HELP' seems to work fine (though I couldn't find a dialog in W7 which makes use of the "Help Select" cursor).

like image 60
Sertac Akyuz Avatar answered Sep 21 '22 22:09

Sertac Akyuz


After thee years its time to answer my own question. Here's how you check if the current global cursor is hourglass in C# (extend the code for you own needs if you need):

private static bool IsWaitCursor()
{
    var h = Cursors.WaitCursor.Handle;

    CURSORINFO pci;
    pci.cbSize = Marshal.SizeOf(typeof(CURSORINFO));
    GetCursorInfo(out pci);

    return pci.hCursor == h;
}

[StructLayout(LayoutKind.Sequential)]
struct POINT
{
    public Int32 x;
    public Int32 y;
}

[StructLayout(LayoutKind.Sequential)]
struct CURSORINFO
{
    public Int32 cbSize;        // Specifies the size, in bytes, of the structure. 
    // The caller must set this to Marshal.SizeOf(typeof(CURSORINFO)).
    public Int32 flags;         // Specifies the cursor state. This parameter can be one of the following values:
    //    0             The cursor is hidden.
    //    CURSOR_SHOWING    The cursor is showing.
    public IntPtr hCursor;          // Handle to the cursor. 
    public POINT ptScreenPos;       // A POINT structure that receives the screen coordinates of the cursor. 
}

[DllImport("user32.dll")]
static extern bool GetCursorInfo(out CURSORINFO pci);
like image 35
Alex from Jitbit Avatar answered Sep 19 '22 22:09

Alex from Jitbit