Seite 1 von 1

Transparentes Overlay Window mit Alpha

Verfasst: 10.10.2019 13:40
von Derren
Hallo zusammen,

ich weiß, zu dem Thema gibt es einige Threads, aber irgendwie nicht das, was ich suche.

Ich such nach einer Möglichkeit, ein vollständig transparentes Fenster zu erstellen, auf dem ich dann aber immer noch zeichnen kann.
Die Windows API bietet mit folgendem Code (danke RSBasic's API-Library) eine relativ simple Möglichkeit entweder eine Farbe transparent/unsichtbar zu machen (wie früher bei Sprites), oder das komplette Fenster transparenter zu machen.

Code: Alles auswählen

If OpenWindow(0,0,0,500,250,"Window",#PB_Window_SystemMenu|#PB_Window_ScreenCentered)
  SetWindowLongPtr_(WindowID(0),#GWL_EXSTYLE,GetWindowLongPtr_(WindowID(0),#GWL_EXSTYLE) | #WS_EX_LAYERED)
  SetLayeredWindowAttributes_(WindowID(0), 0, (255 * 50) / 100, #LWA_ALPHA)
Repeat : Until WaitWindowEvent() = #PB_Event_CloseWindow
EndIf
Erinnert sich noch jemand an diesen "App Launcher" nenne ich es mal, der transparente "Kugeln" in einem Kreis angeordnet hat? Das war ein schönes, komplett unsichtbares Fenster, mit Grafiken mit verschiedenen Alphawerten. Ich finde diesen Thread leider nicht :(

Im Prinzip möchte ich so etwas basteln. Hat da vielleicht jemand einen Tipp?

Danke :)
Bild

Re: Transparentes Overlay Window mit Alpha

Verfasst: 10.10.2019 15:17
von hjbremer
Hi, so was ?

Code: Alles auswählen

If OpenWindow(0, 0, 0, 400, 200, "VectorDrawing", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
    CanvasGadget(0, 0, 0, 400, 200)
    
    LoadFont(0, "Times", 20, #PB_Font_Bold)
    LoadImage(0, #PB_Compiler_Home + "examples/Sources/Data/PureBasicLogo.bmp")

    If StartVectorDrawing(CanvasVectorOutput(0))
    
      MovePathCursor(00, 00)
      DrawVectorImage(ImageID(0), $FF, 400, 200)
      
      VectorFont(FontID(0), 25)
      VectorSourceColor($FF000000+#White)

      MovePathCursor(20, 10): DrawVectorText("Hurra")
      MovePathCursor(20, 50): DrawVectorText("Hallo")
      
    
      VectorFont(FontID(0), 35)
      VectorSourceColor($FF000000+#Red)

      MovePathCursor(220, 110): DrawVectorText("Hallo")
      MovePathCursor(220, 150): DrawVectorText("Hallo")
      
      VectorFont(FontID(0), 10)
      VectorSourceColor($FF000000+#Black)
      MovePathCursor(150, 20): DrawVectorParagraph("Hallo du bist ein Glückspilz", 100, 66, #PB_VectorParagraph_Center)
      
    
      StopVectorDrawing()
    EndIf
    
    Repeat
      Event = WaitWindowEvent()
    Until Event = #PB_Event_CloseWindow
  EndIf

Re: Transparentes Overlay Window mit Alpha

Verfasst: 11.10.2019 00:35
von chi
quick & dirty

Code: Alles auswählen

BlendMode.BLENDFUNCTION
BlendMode\SourceConstantAlpha = 255
BlendMode\AlphaFormat = #AC_SRC_ALPHA

OpenWindow(0, 0, 0, 150, 50, "", #PB_Window_BorderLess|#PB_Window_ScreenCentered|#PB_Window_Invisible, GetShellWindow_())
SetWindowLongPtr_(WindowID(0), #GWL_EXSTYLE, GetWindowLongPtr_(WindowID(0), #GWL_EXSTYLE)|#WS_EX_LAYERED|#WS_EX_TRANSPARENT)
HideWindow(0, #False)
AddWindowTimer(0, 0, 1000)

Repeat
  event = WaitWindowEvent()
  Select event
    Case #PB_Event_Timer
      Select EventTimer()
          
        Case 0
          hWnd = WindowID(0)
          GetWindowRect_(hWnd, wRect.RECT)
          OffsetRect_(wRect, -wRect\left, -wRect\top)
          hdc = GetWindowDC_(hWnd)
          mdc = CreateCompatibleDC_(hdc)
          CreateImage(0, wRect\right, wRect\bottom, 32, #PB_Image_Transparent)
          StartDrawing(ImageOutput(0))
            DrawingMode(#PB_2DDrawing_AlphaBlend|#PB_2DDrawing_Outlined)
            Box(0, 0, OutputWidth(), OutputHeight(), RGBA(0,0,255,100))
            DrawText(10, 10, FormatDate("%hh:%ii:%ss", Date()), RGBA(255,0,0,255), RGBA(0,0,0,0))
            x + 1
            DrawText(10, 30, "Hello World" + LSet("", x % 4, "."), RGBA(255,0,0,255), RGBA(0,0,0,0))
          StopDrawing()
          old = SelectObject_(mdc, ImageID(0))
          UpdateLayeredWindow_(hWnd, 0, 0, @wRect+8, mdc, @ContextOffset.POINT, 0, @BlendMode, #ULW_ALPHA)
          SelectObject_(mdc, old)
          DeleteDC_(mdc)
          ReleaseDC_(hWnd, hdc)
          
      EndSelect
  EndSelect
Until event = #PB_Event_CloseWindow Or GetAsyncKeyState_(#VK_ESCAPE) & 1
[/size]

Re: Transparentes Overlay Window mit Alpha

Verfasst: 11.10.2019 08:44
von Derren
@chi: Oh, vielen Dank, ich glaube damit kann ich was anfangen :praise: :allright:

Re: Transparentes Overlay Window mit Alpha

Verfasst: 11.10.2019 13:37
von chi
Derren hat geschrieben:@chi: Oh, vielen Dank, ich glaube damit kann ich was anfangen :praise: :allright:
Kein Problem ;)

2 kleine Änderungen:
  • SetWindowPos_(#HWND_BOTTOM) -> startet am Desktop
  • DesktopHandle() anstatt GetShellWindow_() -> somit funktioniert auch "Desktop anzeigen" wie erwartet

Code: Alles auswählen

Procedure DesktopHandle()
  Protected hProgman, hDesktopWnd, hShellViewWin, hWorkerW, hDesktopListView
  hProgman = GetShellWindow_()
  If hProgman
    hShellViewWin = FindWindowEx_(hProgman, 0, "SHELLDLL_DefView", 0)
    If hShellViewWin
      hDesktopListView = FindWindowEx_(hShellViewWin, 0, "SysListView32", 0)
    Else
      hDesktopWnd = GetDesktopWindow_()
      Repeat
        hWorkerW = FindWindowEx_(hDesktopWnd, hWorkerW, "WorkerW", #Null)
        hShellViewWin = FindWindowEx_(hWorkerW, 0, "SHELLDLL_DefView", 0)
      Until hShellViewWin <> #Null And hWorkerW <> #Null      
      hDesktopListView = FindWindowEx_(hShellViewWin, 0, "SysListView32", 0)
    EndIf    
    ProcedureReturn hDesktopListView
  EndIf
EndProcedure

BlendMode.BLENDFUNCTION
BlendMode\SourceConstantAlpha = 255
BlendMode\AlphaFormat = #AC_SRC_ALPHA

OpenWindow(0, 0, 0, 150, 50, "", #PB_Window_BorderLess|#PB_Window_ScreenCentered|#PB_Window_Invisible, DesktopHandle())
SetWindowLongPtr_(WindowID(0), #GWL_EXSTYLE, GetWindowLongPtr_(WindowID(0), #GWL_EXSTYLE)|#WS_EX_LAYERED|#WS_EX_TRANSPARENT)
HideWindow(0, #False)
SetWindowPos_(WindowID(0), #HWND_BOTTOM, 0, 0, 0, 0, #SWP_NOSIZE|#SWP_NOMOVE)
AddWindowTimer(0, 0, 1000)

Repeat
  event = WaitWindowEvent()
  Select event
    Case #PB_Event_Timer
      Select EventTimer()
          
        Case 0
          hWnd = WindowID(0)
          GetWindowRect_(hWnd, wRect.RECT)
          OffsetRect_(wRect, -wRect\left, -wRect\top)
          hdc = GetWindowDC_(hWnd)
          mdc = CreateCompatibleDC_(hdc)
          CreateImage(0, wRect\right, wRect\bottom, 32, #PB_Image_Transparent)
          StartDrawing(ImageOutput(0))
            DrawingMode(#PB_2DDrawing_AlphaBlend|#PB_2DDrawing_Outlined)
            Box(0, 0, OutputWidth(), OutputHeight(), RGBA(0,0,255,100))
            DrawText(10, 10, FormatDate("%hh:%ii:%ss", Date()), RGBA(255,0,0,255), RGBA(0,0,0,0))
            x + 1
            DrawText(10, 30, "Hello World" + LSet("", x % 4, "."), RGBA(255,0,0,255), RGBA(0,0,0,0))
          StopDrawing()
          old = SelectObject_(mdc, ImageID(0))
          UpdateLayeredWindow_(hWnd, 0, 0, @wRect+8, mdc, @ContextOffset.POINT, 0, @BlendMode, #ULW_ALPHA)
          SelectObject_(mdc, old)
          DeleteDC_(mdc)
          ReleaseDC_(hWnd, hdc)
          
      EndSelect
  EndSelect
Until event = #PB_Event_CloseWindow Or GetAsyncKeyState_(#VK_ESCAPE) & 1
[/size]