[WIN32SS]
[reactos.git] / reactos / win32ss / user / ntuser / cursoricon.c
index 7ba56db..335aa87 100644 (file)
@@ -2,7 +2,7 @@
  * COPYRIGHT:        See COPYING in the top level directory
  * PROJECT:          ReactOS Win32k subsystem
  * PURPOSE:          Cursor and icon functions
- * FILE:             subsystems/win32/win32k/ntuser/cursoricon.c
+ * FILE:             win32ss/user/ntuser/cursoricon.c
  * PROGRAMER:        ReactOS Team
  */
 /*
@@ -77,7 +77,7 @@ PCURICON_OBJECT FASTCALL UserGetCurIconObject(HCURSOR hCurIcon)
         return NULL;
     }
 
-    CurIcon = (PCURICON_OBJECT)UserReferenceObjectByHandle(hCurIcon, otCursorIcon);
+    CurIcon = (PCURICON_OBJECT)UserReferenceObjectByHandle(hCurIcon, TYPE_CURSOR);
     if (!CurIcon)
     {
         /* We never set ERROR_INVALID_ICON_HANDLE. lets hope noone ever checks for it */
@@ -178,7 +178,7 @@ IntFindExistingCurIconObject(HMODULE hModule,
     LIST_FOR_EACH(CurIcon, &gCurIconList, CURICON_OBJECT, ListEntry)
     {
 
-        // if (NT_SUCCESS(UserReferenceObjectByPointer(Object, otCursorIcon))) // <- huh????
+        // if (NT_SUCCESS(UserReferenceObjectByPointer(Object, TYPE_CURSOR))) // <- huh????
 //      UserReferenceObject(  CurIcon);
 //      {
         if ((CurIcon->hModule == hModule) && (CurIcon->hRsrc == hRsrc))
@@ -203,13 +203,13 @@ IntFindExistingCurIconObject(HMODULE hModule,
     return NULL;
 }
 
-PCURICON_OBJECT
-IntCreateCurIconHandle()
+HANDLE
+IntCreateCurIconHandle(BOOLEAN Anim)
 {
     PCURICON_OBJECT CurIcon;
     HANDLE hCurIcon;
 
-    CurIcon = UserCreateObject(gHandleTable, NULL, NULL, &hCurIcon, otCursorIcon, sizeof(CURICON_OBJECT));
+    CurIcon = UserCreateObject(gHandleTable, NULL, NULL, &hCurIcon, TYPE_CURSOR, sizeof(CURICON_OBJECT));
 
     if (!CurIcon)
     {
@@ -220,17 +220,19 @@ IntCreateCurIconHandle()
     CurIcon->Self = hCurIcon;
     InitializeListHead(&CurIcon->ProcessList);
 
-    if (! ReferenceCurIconByProcess(CurIcon))
+    if (!ReferenceCurIconByProcess(CurIcon))
     {
         ERR("Failed to add process\n");
-        UserDeleteObject(hCurIcon, otCursorIcon);
+        UserDeleteObject(hCurIcon, TYPE_CURSOR);
         UserDereferenceObject(CurIcon);
         return NULL;
     }
 
     InsertHeadList(&gCurIconList, &CurIcon->ListEntry);
 
-    return CurIcon;
+    UserDereferenceObject(CurIcon);
+
+    return hCurIcon;
 }
 
 BOOLEAN FASTCALL
@@ -240,7 +242,7 @@ IntDestroyCurIconObject(PCURICON_OBJECT CurIcon, PPROCESSINFO ppi)
     HBITMAP bmpMask, bmpColor;
     BOOLEAN Ret, bListEmpty, bFound = FALSE;
     PCURICON_PROCESS Current = NULL;
-    
+
     /* For handles created without any data (error handling) */
     if(IsListEmpty(&CurIcon->ProcessList))
         goto emptyList;
@@ -256,7 +258,7 @@ IntDestroyCurIconObject(PCURICON_OBJECT CurIcon, PPROCESSINFO ppi)
             break;
         }
     }
-    
+
     if(!bFound)
     {
         /* This object doesn't belong to this process */
@@ -273,7 +275,7 @@ IntDestroyCurIconObject(PCURICON_OBJECT CurIcon, PPROCESSINFO ppi)
         {
             /* Set the first process of the list as owner */
             Current = CONTAINING_RECORD(CurIcon->ProcessList.Flink, CURICON_PROCESS, ListEntry);
-            UserSetObjectOwner(CurIcon, otCursorIcon, Current->Process);
+            UserSetObjectOwner(CurIcon, TYPE_CURSOR, Current->Process);
         }
         UserDereferenceObject(CurIcon);
         return TRUE;
@@ -310,7 +312,7 @@ emptyList:
 
     /* We were given a pointer, no need to keep the reference anylonger! */
     UserDereferenceObject(CurIcon);
-    Ret = UserDeleteObject(CurIcon->Self, otCursorIcon);
+    Ret = UserDeleteObject(CurIcon->Self, TYPE_CURSOR);
 
     return Ret;
 }
@@ -328,6 +330,55 @@ IntCleanupCurIcons(struct _EPROCESS *Process, PPROCESSINFO Win32Process)
     }
 }
 
+HCURSOR FASTCALL
+IntSetCursor(
+    HCURSOR hCursor)
+{
+    PCURICON_OBJECT pcurOld, pcurNew;
+    HCURSOR hOldCursor = NULL;
+
+    if (hCursor)
+    {
+        pcurNew = UserGetCurIconObject(hCursor);
+        if (!pcurNew)
+        {
+            EngSetLastError(ERROR_INVALID_CURSOR_HANDLE);
+            goto leave;
+        }
+    }
+    else
+    {
+        pcurNew = NULL;
+    }
+
+    pcurOld = UserSetCursor(pcurNew, FALSE);
+    if (pcurOld)
+    {
+        hOldCursor = (HCURSOR)pcurOld->Self;
+        UserDereferenceObject(pcurOld);
+    }
+leave:
+    return hOldCursor;
+}
+
+BOOL FASTCALL
+IntDestroyCursor(
+  HANDLE hCurIcon,
+  BOOL bForce)
+{
+    PCURICON_OBJECT CurIcon;
+    BOOL ret;
+
+    if (!(CurIcon = UserGetCurIconObject(hCurIcon)))
+    {
+        return FALSE;
+    }
+
+    ret = IntDestroyCurIconObject(CurIcon, PsGetCurrentProcessWin32Process());
+    /* Note: IntDestroyCurIconObject will remove our reference for us! */
+
+    return ret;
+}
 
 /*
  * @implemented
@@ -386,6 +437,18 @@ NtUserGetIconInfo(
         ProbeForWrite(IconInfo, sizeof(ICONINFO), 1);
         RtlCopyMemory(IconInfo, &ii, sizeof(ICONINFO));
 
+        /// @todo Implement support for lpInstName
+        if (lpInstName)
+        {
+            RtlInitEmptyUnicodeString(lpInstName, NULL, 0);
+        }
+
+        /// @todo Implement support for lpResName
+        if (lpResName)
+        {
+            RtlInitEmptyUnicodeString(lpResName, NULL, 0);
+        }
+
         if (pbpp)
         {
             ProbeForWrite(pbpp, sizeof(DWORD), 1);
@@ -613,8 +676,8 @@ NtUserClipCursor(
 BOOL
 APIENTRY
 NtUserDestroyCursor(
-    HANDLE hCurIcon,
-    DWORD Unknown)
+  _In_  HANDLE hCurIcon,
+  _In_  BOOL bForce)
 {
     PCURICON_OBJECT CurIcon;
     BOOL ret;
@@ -1049,7 +1112,7 @@ UserDrawIconEx(
     RECTL rcDest, rcSrc;
     CLIPOBJ* pdcClipObj = NULL;
     EXLATEOBJ exlo;
-    
+
     /* Stupid case */
     if((diFlags & DI_NORMAL) == 0)
     {
@@ -1059,12 +1122,12 @@ UserDrawIconEx(
 
     hbmMask = pIcon->IconInfo.hbmMask;
     hbmColor = pIcon->IconInfo.hbmColor;
-    
+
     if (istepIfAniCur)
         ERR("NtUserDrawIconEx: istepIfAniCur is not supported!\n");
-    
+
     /*
-     * Get our objects. 
+     * Get our objects.
      * Shared locks are enough, we are only reading those bitmaps
      */
     psurfMask = SURFACE_ShareLockSurface(hbmMask);
@@ -1073,7 +1136,7 @@ UserDrawIconEx(
         ERR("Unable to lock the mask surface.\n");
         return FALSE;
     }
-    
+
     /* Color bitmap is not mandatory */
     if(hbmColor == NULL)
     {
@@ -1087,7 +1150,7 @@ UserDrawIconEx(
         SURFACE_ShareUnlockSurface(psurfMask);
         return FALSE;
     }
-    
+
     /* Set source rect */
     RECTL_vSetRect(&rcSrc, 0, 0, pIcon->Size.cx, pIcon->Size.cy);
 
@@ -1119,17 +1182,17 @@ UserDrawIconEx(
     if (!cxWidth)
     {
         if(diFlags & DI_DEFAULTSIZE)
-            cxWidth = pIcon->IconInfo.fIcon ? 
+            cxWidth = pIcon->IconInfo.fIcon ?
                 UserGetSystemMetrics(SM_CXICON) : UserGetSystemMetrics(SM_CXCURSOR);
         else
             cxWidth = pIcon->Size.cx;
     }
-    
+
     /* Fix height parameter, if needed */
     if (!cyHeight)
     {
         if(diFlags & DI_DEFAULTSIZE)
-            cyHeight = pIcon->IconInfo.fIcon ? 
+            cyHeight = pIcon->IconInfo.fIcon ?
                 UserGetSystemMetrics(SM_CYICON) : UserGetSystemMetrics(SM_CYCURSOR);
         else
             cyHeight = pIcon->Size.cy;
@@ -1143,9 +1206,9 @@ UserDrawIconEx(
         /* Yes: Allocate and paint the offscreen surface */
         EBRUSHOBJ eboFill;
         PBRUSH pbrush = BRUSH_ShareLockBrush(hbrFlickerFreeDraw);
-        
+
         TRACE("Performing off-screen rendering.\n");
-        
+
         if(!pbrush)
         {
             ERR("Failed to get brush object.\n");
@@ -1154,6 +1217,12 @@ UserDrawIconEx(
             return FALSE;
         }
 
+        if (!psurfColor)
+        {
+           ERR("Attention HAX FIX API DrawIconEx TEST Line 37: psurfColor is NULL going with Mask!\n");
+           psurfColor = SURFACE_ShareLockSurface(hbmMask);
+        }
+
         psurfOffScreen = SURFACE_AllocSurface(STYPE_BITMAP,
             cxWidth, cyHeight, psurfColor->SurfObj.iBitmapFormat,
             0, 0, NULL);
@@ -1165,11 +1234,11 @@ UserDrawIconEx(
             BRUSH_ShareUnlockBrush(pbrush);
             return FALSE;
         }
-        
+
         /* Paint the brush */
         EBRUSHOBJ_vInit(&eboFill, pbrush, psurfOffScreen, 0x00FFFFFF, 0, NULL);
         RECTL_vSetRect(&rcDest, 0, 0, cxWidth, cyHeight);
-        
+
         Ret = IntEngBitBlt(&psurfOffScreen->SurfObj,
             NULL,
             NULL,
@@ -1185,7 +1254,7 @@ UserDrawIconEx(
         /* Clean up everything */
         EBRUSHOBJ_vCleanup(&eboFill);
         BRUSH_ShareUnlockBrush(pbrush);
-            
+
         if(!Ret)
         {
             ERR("Failed to paint the off-screen surface.\n");
@@ -1194,7 +1263,7 @@ UserDrawIconEx(
             GDIOBJ_vDeleteObject(&psurfOffScreen->BaseObject);
             return FALSE;
         }
-        
+
         /* We now have our destination surface */
         psurfDest = psurfOffScreen;
     }
@@ -1202,7 +1271,7 @@ UserDrawIconEx(
     {
         /* We directly draw to the DC */
         TRACE("Performing on screen rendering.\n");
-        
+
         psurfOffScreen = NULL;
         pdc = DC_LockDc(hDc);
         if(!pdc)
@@ -1216,16 +1285,16 @@ UserDrawIconEx(
         RECTL_vSetRect(&rcDest, xLeft, yTop, xLeft + cxWidth, yTop + cyHeight);
         IntLPtoDP(pdc, (LPPOINT)&rcDest, 2);
         RECTL_vOffsetRect(&rcDest, pdc->ptlDCOrig.x, pdc->ptlDCOrig.y);
-        
+
         /* Prepare the underlying surface */
-        DC_vPrepareDCsForBlit(pdc, rcDest, NULL, rcDest);
-        
+        DC_vPrepareDCsForBlit(pdc, &rcDest, NULL, NULL);
+
         /* Get the clip object */
-        pdcClipObj = pdc->rosdc.CombinedClip;
-        
+        pdcClipObj = &pdc->co.ClipObj;
+
         /* We now have our destination surface and rectangle */
         psurfDest = pdc->dclevel.pSurface;
-        
+
         if(psurfDest == NULL)
         {
             /* Empty DC */
@@ -1275,10 +1344,10 @@ UserDrawIconEx(
                                ptr += 4;
             }
         }
-        
+
         /* Initialize color translation object */
         EXLATEOBJ_vInitialize(&exlo, psurf->ppal, psurfDest->ppal, 0xFFFFFFFF, 0xFFFFFFFF, 0);
-        
+
         /* Now do it */
         Ret = IntEngAlphaBlend(&psurfDest->SurfObj,
                                &psurf->SurfObj,
@@ -1287,9 +1356,9 @@ UserDrawIconEx(
                                &rcDest,
                                &rcSrc,
                                &blendobj);
-        
+
         EXLATEOBJ_vCleanup(&exlo);
-        
+
     CleanupAlpha:
         if(psurf) SURFACE_ShareUnlockSurface(psurf);
         if(hsurfCopy) NtGdiDeleteObjectApp(hsurfCopy);
@@ -1300,9 +1369,9 @@ UserDrawIconEx(
     if (diFlags & DI_MASK)
     {
         DWORD rop4 = (diFlags & DI_IMAGE) ? ROP4_SRCAND : ROP4_SRCCOPY;
-        
+
         EXLATEOBJ_vInitSrcMonoXlate(&exlo, psurfDest->ppal, 0x00FFFFFF, 0);
-        
+
         Ret = IntEngStretchBlt(&psurfDest->SurfObj,
                                &psurfMask->SurfObj,
                                NULL,
@@ -1315,7 +1384,7 @@ UserDrawIconEx(
                                NULL,
                                NULL,
                                rop4);
-        
+
         EXLATEOBJ_vCleanup(&exlo);
 
         if(!Ret)
@@ -1330,9 +1399,9 @@ UserDrawIconEx(
                if (psurfColor)
         {
             DWORD rop4 = (diFlags & DI_MASK) ? ROP4_SRCINVERT : ROP4_SRCCOPY ;
-            
+
             EXLATEOBJ_vInitialize(&exlo, psurfColor->ppal, psurfDest->ppal, 0x00FFFFFF, 0x00FFFFFF, 0);
-            
+
             Ret = IntEngStretchBlt(&psurfDest->SurfObj,
                                    &psurfColor->SurfObj,
                                    NULL,
@@ -1345,7 +1414,7 @@ UserDrawIconEx(
                                    NULL,
                                    NULL,
                                    rop4);
-        
+
             EXLATEOBJ_vCleanup(&exlo);
 
             if(!Ret)
@@ -1359,9 +1428,9 @@ UserDrawIconEx(
             /* Mask bitmap holds the information in its bottom half */
             DWORD rop4 = (diFlags & DI_MASK) ? ROP4_SRCINVERT : ROP4_SRCCOPY;
             RECTL_vOffsetRect(&rcSrc, 0, pIcon->Size.cy);
-            
+
             EXLATEOBJ_vInitSrcMonoXlate(&exlo, psurfDest->ppal, 0x00FFFFFF, 0);
-        
+
             Ret = IntEngStretchBlt(&psurfDest->SurfObj,
                                    &psurfMask->SurfObj,
                                    NULL,
@@ -1374,7 +1443,7 @@ UserDrawIconEx(
                                    NULL,
                                    NULL,
                                    rop4);
-            
+
             EXLATEOBJ_vCleanup(&exlo);
 
             if(!Ret)
@@ -1401,13 +1470,13 @@ done:
         RECTL_vSetRect(&rcDest, xLeft, yTop, xLeft + cxWidth, yTop + cyHeight);
         IntLPtoDP(pdc, (LPPOINT)&rcDest, 2);
         RECTL_vOffsetRect(&rcDest, pdc->ptlDCOrig.x, pdc->ptlDCOrig.y);
-        
+
         /* Prepare the underlying surface */
-        DC_vPrepareDCsForBlit(pdc, rcDest, NULL, rcDest);
-        
+        DC_vPrepareDCsForBlit(pdc, &rcDest, NULL, NULL);
+
         /* Get the clip object */
-        pdcClipObj = pdc->rosdc.CombinedClip;
-        
+        pdcClipObj = &pdc->co.ClipObj;
+
         /* We now have our destination surface and rectangle */
         psurfDest = pdc->dclevel.pSurface;
         if(!psurfDest)
@@ -1416,10 +1485,10 @@ done:
             DC_UnlockDc(pdc);
             goto Cleanup2;
         }
-        
+
         /* Color translation */
         EXLATEOBJ_vInitialize(&exlo, psurfOffScreen->ppal, psurfDest->ppal, 0x00FFFFFF, 0x00FFFFFF, 0);
-        
+
         /* Blt it! */
         Ret = IntEngBitBlt(&psurfDest->SurfObj,
                            &psurfOffScreen->SurfObj,
@@ -1432,7 +1501,7 @@ done:
                            NULL,
                            NULL,
                            ROP4_SRCCOPY);
-                           
+
         EXLATEOBJ_vCleanup(&exlo);
     }
 Cleanup:
@@ -1441,12 +1510,12 @@ Cleanup:
         DC_vFinishBlit(pdc, NULL);
         DC_UnlockDc(pdc);
     }
-    
+
 Cleanup2:
     /* Delete off screen rendering surface */
     if(psurfOffScreen)
         GDIOBJ_vDeleteObject(&psurfOffScreen->BaseObject);
-    
+
     /* Unlock other surfaces */
     SURFACE_ShareUnlockSurface(psurfMask);
     if(psurfColor) SURFACE_ShareUnlockSurface(psurfColor);
@@ -1501,4 +1570,20 @@ NtUserDrawIconEx(
     return Ret;
 }
 
+/*
+ * @unimplemented
+ */
+HCURSOR
+NTAPI
+NtUserGetCursorFrameInfo(
+    HCURSOR hCursor,
+    DWORD istep,
+    INT* rate_jiffies,
+    DWORD* num_steps)
+{
+    STUB
+
+    return 0;
+}
+
 /* EOF */