; Module/File: Window_GadgetOnTransparentBackground_gtk3.pb ; Function: 'Free' Gadget on transparent window - Linux gtk3 ; Author: Omi ; Date: Aug. 02, 2017 ; Version: 0.1 ; Target Compiler: PureBasic 5.45/5.46/5.61/5.62/5.7 ; Target OS: Linux: (X/K/L)ubuntu, Mint, 32/64, Ascii/Uni ;-------------------------------------------------------------- ; Window is slightly visible for demonstration ; Problems with the new Layout in PB5.46+ ? EnableExplicit ImportC "" g_signal_connect(*instance, detailed_signal.p-utf8, *c_handler, *pdata, destroy= 0, flags= 0) As "g_signal_connect_data" gdk_cairo_create(*drawable.GdkDrawable) gdk_display_get_pointer(*display.GdkDisplay, *screen.GdkScreen, *x, *y, *mask); gtk2.2+ gdk_screen_get_rgba_visual(*screen.GdkScreen) gdk_screen_get_system_visual(*screen.GdkScreen) gtk_widget_get_window(*widget.GtkWidget) gtk_widget_set_visual(*widget.GtkWidget, *visual.GdkVisual) cairo_destroy(*cairocontext) cairo_fill_preserve(*cairocontext) cairo_paint(*cairocontext) cairo_rectangle(*cairocontext, x.d, y.d, width.d, height.d) cairo_set_line_width(*cairocontext, width.d) cairo_set_operator(*cairoregion, op) cairo_set_source_rgba(*cairoregion, red.d, green.d, blue.d, alpha.d) cairo_stroke(*cairocontext) EndImport #CAIRO_OPERATOR_SOURCE = 1 #Win_Main = 0 #But = 0 ProcedureC Callback_ButtonMotion(*widget.GtkWindow, *event.GdkEventButton, window); based on a mestnyi-example Static.i isPressed Static.i wX, wY; pointer window relative Static.i wBorderL, wBorderT; left, upper window delta Protected.i rX, rY, rMask; pointer root relative If PeekS(gtk_widget_get_name_(*widget), -1, #PB_UTF8) = "GtkButton" *widget= gtk_widget_get_parent_window_(*widget) gdk_window_get_user_data_(*widget, @*widget) EndIf If *event\type = #GDK_BUTTON_PRESS And *event\button= 1; 2 / 3 wX = WindowMouseX(window); see Window_GetInnerMousePos.pb wY = WindowMouseY(window) isPressed= #True gdk_window_get_position_(gtk_widget_get_window(*widget), @wBorderL, @wBorderT) gdk_window_get_root_origin_(gtk_widget_get_window(*widget), @rX, @rY) wBorderL- rX : wBorderT- rY ElseIf *event\type = #GDK_BUTTON_RELEASE isPressed= #False EndIf If isPressed gdk_display_get_pointer(gdk_display_get_default_(), #Null, @rX, @rY, @rMask) gtk_window_move_(*widget, rX- wX- wBorderL, rY- wY- wBorderT) If Not (rMask & #GDK_BUTTON1_MASK) : isPressed= #False : EndIf; against trailing, quick stop EndIf ProcedureReturn #False EndProcedure ProcedureC Callback_DrawGadgetBackground(*Widget.GtkWidget, *Event.GdkEventExpose, user_data) Protected *cr= gdk_cairo_create(gtk_widget_get_window(*widget)) ; ----- Draw transparent background cairo_set_source_rgba(*cr, 1, 1, 1, 0) cairo_set_operator(*cr, #CAIRO_OPERATOR_SOURCE) cairo_paint(*cr) ; ----- A frame + slight-opacity-background to show window and it's borders. cairo_rectangle(*cr, 0, 0, WindowWidth(user_data), WindowHeight(user_data)) cairo_set_source_rgba(*cr, 1.0, 1.0, 0.0, 0.15) cairo_fill_preserve(*cr) ; cairo_set_source_rgba(*cr, 0.0, 0.0, 1.0, 1.0) ; cairo_set_line_width(*cr, 5) ; cairo_stroke(*cr) cairo_destroy(*cr) EndProcedure ProcedureC Callback_ScreenChanged(*widget.GtkWidget, *old_screen.GdkScreen, user_data) Protected *Screen.GdkScreen= gtk_widget_get_screen_(*widget) Protected *Visual.GdkVisual= gdk_screen_get_rgba_visual(*Screen) If Not *Visual *Visual = gdk_screen_get_system_visual(*Screen) EndIf gtk_widget_set_visual(*widget, *Visual) EndProcedure Procedure CreateWindow_Main() Protected *Window.GtkWindow Protected *MainContainer.GtkContainer OpenWindow(#Win_Main, 140, 100, 200, 200, "Gadget without background (gtk3)", #PB_Window_Invisible) *Window= WindowID(#Win_Main) *MainContainer= g_list_nth_data_(gtk_container_get_children_(gtk_bin_get_child_(WindowID(#Win_Main))), 0) gtk_window_set_decorated_(*Window, #False); no Window border/titlebar gtk_widget_set_app_paintable_(*Window, #True); suppress default themed drawing of the window's background gtk_widget_set_app_paintable_(*MainContainer, #True); suppress default themed drawing of the contaiiners background gtk_widget_unrealize_(*Window) g_signal_connect(*Window, "screen-changed", @Callback_ScreenChanged(), #Null) g_signal_connect(*Window, "draw", @Callback_DrawGadgetBackground(), #Win_Main) Callback_ScreenChanged(*Window, #Null, #Null) g_signal_connect(*Window, "event", @Callback_ButtonMotion(), #Win_Main); event to use for moving window gtk_widget_show_all_(*Window) ButtonGadget(#But, 10, 10, 180, 180, "A gtk3-ButtonGadget" + #LF$ + "in an invisible window.") GadgetToolTip(#But, "Button is clickable, grab on semi-transparent yellow frame to move the window. [Esc] to close.") AddKeyboardShortcut(#Win_Main, #PB_Shortcut_Escape, 0) EndProcedure CreateWindow_Main() Repeat Select WaitWindowEvent() Case #PB_Event_Menu If EventMenu() = 0 RemoveWindowTimer(#Win_Main, 0) Break EndIf Case #PB_Event_Gadget If EventGadget() = #But Debug "Button clicked" EndIf EndSelect ForEver ; IDE Options = PureBasic 5.70 LTS beta 3 (Linux - x64) ; CursorPosition = 10 ; Folding = - ; EnableXP ; EnableUnicode