View Issue Details

IDProjectCategoryView StatusLast Update
0036348LazarusWidgetsetpublic2020-04-27 13:54
ReporterCudaText man Assigned ToJuha Manninen  
PrioritynormalSeverityminorReproducibilityalways
Status resolvedResolutionfixed 
PlatformUbuntu 19.10 x64 
Product Version2.1 (SVN) 
Summary0036348: gtk3: Clipboard.AsText crash
DescriptionMake empty app with a button and do this in OnClick of btn:

uses clipbrd;

procedure TForm1.Button1Click(Sender: TObject);
begin
  Clipboard.AsText:= 'zz'0000010'ee'0000010'aa';
end;

this gives crash:
[Debugger Exception Notification]
Project project1 raised exception class 'Exception' with message:
IndexOfCachedFormatID: Internal Error: invalid FormatID 0 for clipboard
 In file 'include/clipbrd.inc' at line 58
TagsNo tags attached.
Fixed in Revisionr62426, r63015
LazTarget-
WidgetsetGTK 3
Attached Files

Relationships

has duplicate 0036441 closedBart Broersma GTK3: Crash when string assigned to clipboard 

Activities

Anton Kavalenka

2019-11-23 15:45

reporter   ~0119454

I think copy-paste from GTK2 would work

CudaText man

2019-12-20 21:19

reporter   ~0119980

fix added-- it implements ClipboardRegisterFormat in WS, please check the code - Im not sure that I've ok changed result of Gtk3 functions: TGtkAtom->PGtkAtom, but seems it is ok, Gtk3 cannot return TGtkAtom.
c1.diff (3,060 bytes)   
Index: lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas
===================================================================
--- lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas	(revision 62425)
+++ lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas	(working copy)
@@ -2885,8 +2885,8 @@
   PGdkAtom = ^TGdkAtom;
   TGdkAtom = object
     function name: Pgchar; cdecl; inline;
-    function intern(atom_name: Pgchar; only_if_exists: gboolean): TGdkAtom; cdecl; inline; static;
-    function intern_static_string(atom_name: Pgchar): TGdkAtom; cdecl; inline; static;
+    function intern(atom_name: Pgchar; only_if_exists: gboolean): PGdkAtom; cdecl; inline; static;
+    function intern_static_string(atom_name: Pgchar): PGdkAtom; cdecl; inline; static;
   end;
   TGdkDisplay = object(TGObject)
     function get_default: PGdkDisplay; cdecl; inline; static;
@@ -3891,8 +3891,8 @@
 
 
 function gdk_app_launch_context_get_type: TGType; cdecl; external;
-function gdk_atom_intern(atom_name: Pgchar; only_if_exists: gboolean): TGdkAtom; cdecl; external;
-function gdk_atom_intern_static_string(atom_name: Pgchar): TGdkAtom; cdecl; external;
+function gdk_atom_intern(atom_name: Pgchar; only_if_exists: gboolean): PGdkAtom; cdecl; external;
+function gdk_atom_intern_static_string(atom_name: Pgchar): PGdkAtom; cdecl; external;
 function gdk_atom_name(atom: TGdkAtom): Pgchar; cdecl; external;
 function gdk_cairo_create(window: PGdkWindow): Pcairo_t; cdecl; external;
 function gdk_cairo_get_clip_rectangle(cr: Pcairo_t; rect: PGdkRectangle): gboolean; cdecl; external;
@@ -4502,12 +4502,12 @@
   Result := LazGdk3.gdk_atom_name(self);
 end;
 
-function TGdkAtom.intern(atom_name: Pgchar; only_if_exists: gboolean): TGdkAtom; cdecl;
+function TGdkAtom.intern(atom_name: Pgchar; only_if_exists: gboolean): PGdkAtom; cdecl;
 begin
   Result := LazGdk3.gdk_atom_intern(atom_name, only_if_exists);
 end;
 
-function TGdkAtom.intern_static_string(atom_name: Pgchar): TGdkAtom; cdecl;
+function TGdkAtom.intern_static_string(atom_name: Pgchar): PGdkAtom; cdecl;
 begin
   Result := LazGdk3.gdk_atom_intern_static_string(atom_name);
 end;
Index: lcl/interfaces/gtk3/gtk3winapi.inc
===================================================================
--- lcl/interfaces/gtk3/gtk3winapi.inc	(revision 62425)
+++ lcl/interfaces/gtk3/gtk3winapi.inc	(working copy)
@@ -170,13 +170,13 @@
     FormatCount, Formats);
 end;
 
-function TGtk3WidgetSet.ClipboardRegisterFormat(const AMimeType: string
-  ): TClipboardFormat;
+function TGtk3WidgetSet.ClipboardRegisterFormat(const AMimeType: string): TClipboardFormat;
 begin
-  {$IFDEF GTK3DEBUGNOTIMPLEMENTED}
-  DebugLn('WARNING: TGtk3WidgetSet.ClipboardRegisterFormat not implemented ...');
-  {$ENDIF}
-  Result:=inherited ClipboardRegisterFormat(AMimeType);
+  if Assigned(Application) then
+    Result := TClipboardFormat(TGdkAtom.intern(PChar(AMimeType), False))
+  else
+    RaiseGDBException(
+      'ERROR: TGtk3WidgetSet.ClipboardRegisterFormat gdk not initialized');
 end;
 
 function TGtk3WidgetSet.CombineRgn(Dest, Src1, Src2: HRGN;
c1.diff (3,060 bytes)   

CudaText man

2019-12-20 22:11

reporter   ~0119982

Last edited: 2019-12-20 22:13

View 4 revisions

If i am right then ALL occurrences of ": TGdkAtom" must be replaced to ": PGdkAtom".
i 've done it in next patch. c2.diff.
it makes no sence to have fields of TGdkAtom since it's FAKE OBJECT used only to have PGdkAtom ptr.

c2.diff (14,760 bytes)   
Index: lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas
===================================================================
--- lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas	(revision 62425)
+++ lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas	(working copy)
@@ -2885,8 +2885,8 @@
   PGdkAtom = ^TGdkAtom;
   TGdkAtom = object
     function name: Pgchar; cdecl; inline;
-    function intern(atom_name: Pgchar; only_if_exists: gboolean): TGdkAtom; cdecl; inline; static;
-    function intern_static_string(atom_name: Pgchar): TGdkAtom; cdecl; inline; static;
+    function intern(atom_name: Pgchar; only_if_exists: gboolean): PGdkAtom; cdecl; inline; static;
+    function intern_static_string(atom_name: Pgchar): PGdkAtom; cdecl; inline; static;
   end;
   TGdkDisplay = object(TGObject)
     function get_default: PGdkDisplay; cdecl; inline; static;
@@ -2911,7 +2911,7 @@
     procedure notify_startup_complete(startup_id: Pgchar); cdecl; inline;
     function peek_event: PGdkEvent; cdecl; inline;
     procedure put_event(event: PGdkEvent); cdecl; inline;
-    function request_selection_notification(selection: TGdkAtom): gboolean; cdecl; inline;
+    function request_selection_notification(selection: PGdkAtom): gboolean; cdecl; inline;
     procedure set_double_click_distance(distance: guint); cdecl; inline;
     procedure set_double_click_time(msec: guint); cdecl; inline;
     procedure store_clipboard(clipboard_window: PGdkWindow; time_: guint32; targets: PGdkAtom; n_targets: gint); cdecl; inline;
@@ -3045,7 +3045,7 @@
     function get_associated_device: PGdkDevice; cdecl; inline;
     function get_axis(axes: Pgdouble; use: TGdkAxisUse; value: Pgdouble): gboolean; cdecl; inline;
     function get_axis_use(index_: guint): TGdkAxisUse; cdecl; inline;
-    function get_axis_value(axes: Pgdouble; axis_label: TGdkAtom; value: Pgdouble): gboolean; cdecl; inline;
+    function get_axis_value(axes: Pgdouble; axis_label: PGdkAtom; value: Pgdouble): gboolean; cdecl; inline;
     function get_device_type: TGdkDeviceType; cdecl; inline;
     function get_display: PGdkDisplay; cdecl; inline;
     function get_has_cursor: gboolean; cdecl; inline;
@@ -3495,7 +3495,7 @@
     type_: TGdkEventType;
     window: PGdkWindow;
     send_event: gint8;
-    atom: TGdkAtom;
+    atom: PGdkAtom;
     time: guint32;
     state: TGdkPropertyState;
   end;
@@ -3509,9 +3509,9 @@
     type_: TGdkEventType;
     window: PGdkWindow;
     send_event: gint8;
-    selection: TGdkAtom;
-    target: TGdkAtom;
-    property_: TGdkAtom;
+    selection: PGdkAtom;
+    target: PGdkAtom;
+    property_: PGdkAtom;
     time: guint32;
     requestor: PGdkWindow;
   end;
@@ -3530,7 +3530,7 @@
     send_event: gint8;
     owner: PGdkWindow;
     reason: TGdkOwnerChange;
-    selection: TGdkAtom;
+    selection: PGdkAtom;
     time: guint32;
     selection_time: guint32;
   end;
@@ -3891,9 +3891,9 @@
 
 
 function gdk_app_launch_context_get_type: TGType; cdecl; external;
-function gdk_atom_intern(atom_name: Pgchar; only_if_exists: gboolean): TGdkAtom; cdecl; external;
-function gdk_atom_intern_static_string(atom_name: Pgchar): TGdkAtom; cdecl; external;
-function gdk_atom_name(atom: TGdkAtom): Pgchar; cdecl; external;
+function gdk_atom_intern(atom_name: Pgchar; only_if_exists: gboolean): PGdkAtom; cdecl; external;
+function gdk_atom_intern_static_string(atom_name: Pgchar): PGdkAtom; cdecl; external;
+function gdk_atom_name(atom: PGdkAtom): Pgchar; cdecl; external;
 function gdk_cairo_create(window: PGdkWindow): Pcairo_t; cdecl; external;
 function gdk_cairo_get_clip_rectangle(cr: Pcairo_t; rect: PGdkRectangle): gboolean; cdecl; external;
 function gdk_cairo_region_create_from_surface(surface: Pcairo_surface_t): Pcairo_region_t; cdecl; external;
@@ -3914,7 +3914,7 @@
 function gdk_device_get_associated_device(device: PGdkDevice): PGdkDevice; cdecl; external;
 function gdk_device_get_axis(device: PGdkDevice; axes: Pgdouble; use: TGdkAxisUse; value: Pgdouble): gboolean; cdecl; external;
 function gdk_device_get_axis_use(device: PGdkDevice; index_: guint): TGdkAxisUse; cdecl; external;
-function gdk_device_get_axis_value(device: PGdkDevice; axes: Pgdouble; axis_label: TGdkAtom; value: Pgdouble): gboolean; cdecl; external;
+function gdk_device_get_axis_value(device: PGdkDevice; axes: Pgdouble; axis_label: PGdkAtom; value: Pgdouble): gboolean; cdecl; external;
 function gdk_device_get_device_type(device: PGdkDevice): TGdkDeviceType; cdecl; external;
 function gdk_device_get_display(device: PGdkDevice): PGdkDisplay; cdecl; external;
 function gdk_device_get_has_cursor(device: PGdkDevice): gboolean; cdecl; external;
@@ -3958,7 +3958,7 @@
 function gdk_display_open(display_name: Pgchar): PGdkDisplay; cdecl; external;
 function gdk_display_open_default_libgtk_only: PGdkDisplay; cdecl; external;
 function gdk_display_peek_event(display: PGdkDisplay): PGdkEvent; cdecl; external;
-function gdk_display_request_selection_notification(display: PGdkDisplay; selection: TGdkAtom): gboolean; cdecl; external;
+function gdk_display_request_selection_notification(display: PGdkDisplay; selection: PGdkAtom): gboolean; cdecl; external;
 function gdk_display_supports_clipboard_persistence(display: PGdkDisplay): gboolean; cdecl; external;
 function gdk_display_supports_composite(display: PGdkDisplay): gboolean; cdecl; external;
 function gdk_display_supports_cursor_alpha(display: PGdkDisplay): gboolean; cdecl; external;
@@ -3978,7 +3978,7 @@
 function gdk_drag_context_get_type: TGType; cdecl; external;
 function gdk_drag_context_list_targets(context: PGdkDragContext): PGList; cdecl; external;
 function gdk_drag_drop_succeeded(context: PGdkDragContext): gboolean; cdecl; external;
-function gdk_drag_get_selection(context: PGdkDragContext): TGdkAtom; cdecl; external;
+function gdk_drag_get_selection(context: PGdkDragContext): PGdkAtom; cdecl; external;
 function gdk_drag_motion(context: PGdkDragContext; dest_window: PGdkWindow; protocol: TGdkDragProtocol; x_root: gint; y_root: gint; suggested_action: TGdkDragAction; possible_actions: TGdkDragAction; time_: guint32): gboolean; cdecl; external;
 function gdk_error_trap_pop: gint; cdecl; external;
 function gdk_event_copy(event: PGdkEvent): PGdkEvent; cdecl; external;
@@ -4058,7 +4058,7 @@
 function gdk_pixbuf_get_from_window(window: PGdkWindow; src_x: gint; src_y: gint; width: gint; height: gint): PGdkPixbuf; cdecl; external;
 function gdk_pointer_grab(window: PGdkWindow; owner_events: gboolean; event_mask: TGdkEventMask; confine_to: PGdkWindow; cursor: PGdkCursor; time_: guint32): TGdkGrabStatus; cdecl; external;
 function gdk_pointer_is_grabbed: gboolean; cdecl; external;
-function gdk_property_get(window: PGdkWindow; property_: TGdkAtom; type_: TGdkAtom; offset: gulong; length: gulong; pdelete: gint; actual_property_type: PGdkAtom; actual_format: Pgint; actual_length: Pgint; data: PPguint8): gboolean; cdecl; external;
+function gdk_property_get(window: PGdkWindow; property_: PGdkAtom; type_: PGdkAtom; offset: gulong; length: gulong; pdelete: gint; actual_property_type: PGdkAtom; actual_format: Pgint; actual_length: Pgint; data: PPguint8): gboolean; cdecl; external;
 function gdk_rectangle_get_type: TGType; cdecl; external;
 function gdk_rectangle_intersect(src1: PGdkRectangle; src2: PGdkRectangle; dest: PGdkRectangle): gboolean; cdecl; external;
 function gdk_rgba_copy(rgba: PGdkRGBA): PGdkRGBA; cdecl; external;
@@ -4099,15 +4099,15 @@
 function gdk_screen_make_display_name(screen: PGdkScreen): Pgchar; cdecl; external;
 function gdk_screen_width: gint; cdecl; external;
 function gdk_screen_width_mm: gint; cdecl; external;
-function gdk_selection_owner_get(selection: TGdkAtom): PGdkWindow; cdecl; external;
-function gdk_selection_owner_get_for_display(display: PGdkDisplay; selection: TGdkAtom): PGdkWindow; cdecl; external;
-function gdk_selection_owner_set(owner: PGdkWindow; selection: TGdkAtom; time_: guint32; send_event: gboolean): gboolean; cdecl; external;
-function gdk_selection_owner_set_for_display(display: PGdkDisplay; owner: PGdkWindow; selection: TGdkAtom; time_: guint32; send_event: gboolean): gboolean; cdecl; external;
+function gdk_selection_owner_get(selection: PGdkAtom): PGdkWindow; cdecl; external;
+function gdk_selection_owner_get_for_display(display: PGdkDisplay; selection: PGdkAtom): PGdkWindow; cdecl; external;
+function gdk_selection_owner_set(owner: PGdkWindow; selection: PGdkAtom; time_: guint32; send_event: gboolean): gboolean; cdecl; external;
+function gdk_selection_owner_set_for_display(display: PGdkDisplay; owner: PGdkWindow; selection: PGdkAtom; time_: guint32; send_event: gboolean): gboolean; cdecl; external;
 function gdk_selection_property_get(requestor: PGdkWindow; data: PPguint8; prop_type: PGdkAtom; prop_format: Pgint): gint; cdecl; external;
 function gdk_setting_get(name: Pgchar; value: PGValue): gboolean; cdecl; external;
 function gdk_test_simulate_button(window: PGdkWindow; x: gint; y: gint; button: guint; modifiers: TGdkModifierType; button_pressrelease: TGdkEventType): gboolean; cdecl; external;
 function gdk_test_simulate_key(window: PGdkWindow; x: gint; y: gint; keyval: guint; modifiers: TGdkModifierType; key_pressrelease: TGdkEventType): gboolean; cdecl; external;
-function gdk_text_property_to_utf8_list_for_display(display: PGdkDisplay; encoding: TGdkAtom; format: gint; text: Pguint8; length: gint; list: PPPgchar): gint; cdecl; external;
+function gdk_text_property_to_utf8_list_for_display(display: PGdkDisplay; encoding: PGdkAtom; format: gint; text: Pguint8; length: gint; list: PPPgchar): gint; cdecl; external;
 function gdk_threads_add_idle(function_: TGSourceFunc; data: gpointer): guint; cdecl; external;
 function gdk_threads_add_idle_full(priority: gint; function_: TGSourceFunc; data: gpointer; notify: TGDestroyNotify): guint; cdecl; external;
 function gdk_threads_add_timeout(interval: guint; function_: TGSourceFunc; data: gpointer): guint; cdecl; external;
@@ -4242,8 +4242,8 @@
 procedure gdk_parse_args(argc: Pgint; argv: PPPgchar); cdecl; external;
 procedure gdk_pointer_ungrab(time_: guint32); cdecl; external;
 procedure gdk_pre_parse_libgtk_only; cdecl; external;
-procedure gdk_property_change(window: PGdkWindow; property_: TGdkAtom; type_: TGdkAtom; format: gint; mode: TGdkPropMode; data: Pguint8; nelements: gint); cdecl; external;
-procedure gdk_property_delete(window: PGdkWindow; property_: TGdkAtom); cdecl; external;
+procedure gdk_property_change(window: PGdkWindow; property_: PGdkAtom; type_: PGdkAtom; format: gint; mode: TGdkPropMode; data: Pguint8; nelements: gint); cdecl; external;
+procedure gdk_property_delete(window: PGdkWindow; property_: PGdkAtom); cdecl; external;
 procedure gdk_query_depths(depths: PPgint; count: Pgint); cdecl; external;
 procedure gdk_query_visual_types(visual_types: PPGdkVisualType; count: Pgint); cdecl; external;
 procedure gdk_rectangle_union(src1: PGdkRectangle; src2: PGdkRectangle; dest: PGdkRectangle); cdecl; external;
@@ -4252,9 +4252,9 @@
 procedure gdk_screen_get_monitor_workarea(screen: PGdkScreen; monitor_num: gint; dest: PGdkRectangle); cdecl; external;
 procedure gdk_screen_set_font_options(screen: PGdkScreen; options: Pcairo_font_options_t); cdecl; external;
 procedure gdk_screen_set_resolution(screen: PGdkScreen; dpi: gdouble); cdecl; external;
-procedure gdk_selection_convert(requestor: PGdkWindow; selection: TGdkAtom; target: TGdkAtom; time_: guint32); cdecl; external;
-procedure gdk_selection_send_notify(requestor: PGdkWindow; selection: TGdkAtom; target: TGdkAtom; property_: TGdkAtom; time_: guint32); cdecl; external;
-procedure gdk_selection_send_notify_for_display(display: PGdkDisplay; requestor: PGdkWindow; selection: TGdkAtom; target: TGdkAtom; property_: TGdkAtom; time_: guint32); cdecl; external;
+procedure gdk_selection_convert(requestor: PGdkWindow; selection: PGdkAtom; target: PGdkAtom; time_: guint32); cdecl; external;
+procedure gdk_selection_send_notify(requestor: PGdkWindow; selection: PGdkAtom; target: PGdkAtom; property_: PGdkAtom; time_: guint32); cdecl; external;
+procedure gdk_selection_send_notify_for_display(display: PGdkDisplay; requestor: PGdkWindow; selection: PGdkAtom; target: PGdkAtom; property_: PGdkAtom; time_: guint32); cdecl; external;
 procedure gdk_set_double_click_time(msec: guint); cdecl; external;
 procedure gdk_set_program_class(program_class: Pgchar); cdecl; external;
 procedure gdk_set_show_events(show_events: gboolean); cdecl; external;
@@ -4499,20 +4499,20 @@
 
 function TGdkAtom.name: Pgchar; cdecl;
 begin
-  Result := LazGdk3.gdk_atom_name(self);
+  Result := LazGdk3.gdk_atom_name(@self);
 end;
 
-function TGdkAtom.intern(atom_name: Pgchar; only_if_exists: gboolean): TGdkAtom; cdecl;
+function TGdkAtom.intern(atom_name: Pgchar; only_if_exists: gboolean): PGdkAtom; cdecl;
 begin
   Result := LazGdk3.gdk_atom_intern(atom_name, only_if_exists);
 end;
 
-function TGdkAtom.intern_static_string(atom_name: Pgchar): TGdkAtom; cdecl;
+function TGdkAtom.intern_static_string(atom_name: Pgchar): PGdkAtom; cdecl;
 begin
   Result := LazGdk3.gdk_atom_intern_static_string(atom_name);
 end;
 
-function TGdkDisplay.request_selection_notification(selection: TGdkAtom): gboolean; cdecl;
+function TGdkDisplay.request_selection_notification(selection: PGdkAtom): gboolean; cdecl;
 begin
   Result := LazGdk3.gdk_display_request_selection_notification(@self, selection);
 end;
@@ -4837,7 +4837,7 @@
   Result := LazGdk3.gdk_device_get_axis_use(@self, index_);
 end;
 
-function TGdkDevice.get_axis_value(axes: Pgdouble; axis_label: TGdkAtom; value: Pgdouble): gboolean; cdecl;
+function TGdkDevice.get_axis_value(axes: Pgdouble; axis_label: PGdkAtom; value: Pgdouble): gboolean; cdecl;
 begin
   Result := LazGdk3.gdk_device_get_axis_value(@self, axes, axis_label, value);
 end;
Index: lcl/interfaces/gtk3/gtk3winapi.inc
===================================================================
--- lcl/interfaces/gtk3/gtk3winapi.inc	(revision 62425)
+++ lcl/interfaces/gtk3/gtk3winapi.inc	(working copy)
@@ -170,13 +170,13 @@
     FormatCount, Formats);
 end;
 
-function TGtk3WidgetSet.ClipboardRegisterFormat(const AMimeType: string
-  ): TClipboardFormat;
+function TGtk3WidgetSet.ClipboardRegisterFormat(const AMimeType: string): TClipboardFormat;
 begin
-  {$IFDEF GTK3DEBUGNOTIMPLEMENTED}
-  DebugLn('WARNING: TGtk3WidgetSet.ClipboardRegisterFormat not implemented ...');
-  {$ENDIF}
-  Result:=inherited ClipboardRegisterFormat(AMimeType);
+  if Assigned(Application) then
+    Result := TClipboardFormat(TGdkAtom.intern(PChar(AMimeType), False))
+  else
+    RaiseGDBException(
+      'ERROR: TGtk3WidgetSet.ClipboardRegisterFormat gdk not initialized');
 end;
 
 function TGtk3WidgetSet.CombineRgn(Dest, Src1, Src2: HRGN;
c2.diff (14,760 bytes)   

Juha Manninen

2019-12-20 23:02

developer   ~0119984

I applied the first patch in r62426. The exception is gone now which is good, but the clipboard still does not work. There is no data to be pasted.
I am uploading a test app for it.
ClipboardTest.zip (128,992 bytes)

CudaText man

2019-12-24 20:53

reporter   ~0120056

Juha,
as continue to c1.diff+c2.diff I upload c3.diff.
it changes parameters of type "TGdkAtom" to "PGdkAtom". why? only using params of P* is correct, not of T*. LCL functions pass generic pointers to GTK3 so they must pass P*. and also - TGdkAtom objects cannot be made (see how this type is made - it's FAKE TYPE, it's only to make type difference in parameters)
c3.diff (12,721 bytes)   
Index: lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas
===================================================================
--- lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas	(revision 62430)
+++ lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas	(working copy)
@@ -2911,7 +2911,7 @@
     procedure notify_startup_complete(startup_id: Pgchar); cdecl; inline;
     function peek_event: PGdkEvent; cdecl; inline;
     procedure put_event(event: PGdkEvent); cdecl; inline;
-    function request_selection_notification(selection: TGdkAtom): gboolean; cdecl; inline;
+    function request_selection_notification(selection: PGdkAtom): gboolean; cdecl; inline;
     procedure set_double_click_distance(distance: guint); cdecl; inline;
     procedure set_double_click_time(msec: guint); cdecl; inline;
     procedure store_clipboard(clipboard_window: PGdkWindow; time_: guint32; targets: PGdkAtom; n_targets: gint); cdecl; inline;
@@ -3045,7 +3045,7 @@
     function get_associated_device: PGdkDevice; cdecl; inline;
     function get_axis(axes: Pgdouble; use: TGdkAxisUse; value: Pgdouble): gboolean; cdecl; inline;
     function get_axis_use(index_: guint): TGdkAxisUse; cdecl; inline;
-    function get_axis_value(axes: Pgdouble; axis_label: TGdkAtom; value: Pgdouble): gboolean; cdecl; inline;
+    function get_axis_value(axes: Pgdouble; axis_label: PGdkAtom; value: Pgdouble): gboolean; cdecl; inline;
     function get_device_type: TGdkDeviceType; cdecl; inline;
     function get_display: PGdkDisplay; cdecl; inline;
     function get_has_cursor: gboolean; cdecl; inline;
@@ -3495,7 +3495,7 @@
     type_: TGdkEventType;
     window: PGdkWindow;
     send_event: gint8;
-    atom: TGdkAtom;
+    atom: PGdkAtom;
     time: guint32;
     state: TGdkPropertyState;
   end;
@@ -3509,9 +3509,9 @@
     type_: TGdkEventType;
     window: PGdkWindow;
     send_event: gint8;
-    selection: TGdkAtom;
-    target: TGdkAtom;
-    property_: TGdkAtom;
+    selection: PGdkAtom;
+    target: PGdkAtom;
+    property_: PGdkAtom;
     time: guint32;
     requestor: PGdkWindow;
   end;
@@ -3530,7 +3530,7 @@
     send_event: gint8;
     owner: PGdkWindow;
     reason: TGdkOwnerChange;
-    selection: TGdkAtom;
+    selection: PGdkAtom;
     time: guint32;
     selection_time: guint32;
   end;
@@ -3893,7 +3893,7 @@
 function gdk_app_launch_context_get_type: TGType; cdecl; external;
 function gdk_atom_intern(atom_name: Pgchar; only_if_exists: gboolean): PGdkAtom; cdecl; external;
 function gdk_atom_intern_static_string(atom_name: Pgchar): PGdkAtom; cdecl; external;
-function gdk_atom_name(atom: TGdkAtom): Pgchar; cdecl; external;
+function gdk_atom_name(atom: PGdkAtom): Pgchar; cdecl; external;
 function gdk_cairo_create(window: PGdkWindow): Pcairo_t; cdecl; external;
 function gdk_cairo_get_clip_rectangle(cr: Pcairo_t; rect: PGdkRectangle): gboolean; cdecl; external;
 function gdk_cairo_region_create_from_surface(surface: Pcairo_surface_t): Pcairo_region_t; cdecl; external;
@@ -3914,7 +3914,7 @@
 function gdk_device_get_associated_device(device: PGdkDevice): PGdkDevice; cdecl; external;
 function gdk_device_get_axis(device: PGdkDevice; axes: Pgdouble; use: TGdkAxisUse; value: Pgdouble): gboolean; cdecl; external;
 function gdk_device_get_axis_use(device: PGdkDevice; index_: guint): TGdkAxisUse; cdecl; external;
-function gdk_device_get_axis_value(device: PGdkDevice; axes: Pgdouble; axis_label: TGdkAtom; value: Pgdouble): gboolean; cdecl; external;
+function gdk_device_get_axis_value(device: PGdkDevice; axes: Pgdouble; axis_label: PGdkAtom; value: Pgdouble): gboolean; cdecl; external;
 function gdk_device_get_device_type(device: PGdkDevice): TGdkDeviceType; cdecl; external;
 function gdk_device_get_display(device: PGdkDevice): PGdkDisplay; cdecl; external;
 function gdk_device_get_has_cursor(device: PGdkDevice): gboolean; cdecl; external;
@@ -3958,7 +3958,7 @@
 function gdk_display_open(display_name: Pgchar): PGdkDisplay; cdecl; external;
 function gdk_display_open_default_libgtk_only: PGdkDisplay; cdecl; external;
 function gdk_display_peek_event(display: PGdkDisplay): PGdkEvent; cdecl; external;
-function gdk_display_request_selection_notification(display: PGdkDisplay; selection: TGdkAtom): gboolean; cdecl; external;
+function gdk_display_request_selection_notification(display: PGdkDisplay; selection: PGdkAtom): gboolean; cdecl; external;
 function gdk_display_supports_clipboard_persistence(display: PGdkDisplay): gboolean; cdecl; external;
 function gdk_display_supports_composite(display: PGdkDisplay): gboolean; cdecl; external;
 function gdk_display_supports_cursor_alpha(display: PGdkDisplay): gboolean; cdecl; external;
@@ -3978,7 +3978,7 @@
 function gdk_drag_context_get_type: TGType; cdecl; external;
 function gdk_drag_context_list_targets(context: PGdkDragContext): PGList; cdecl; external;
 function gdk_drag_drop_succeeded(context: PGdkDragContext): gboolean; cdecl; external;
-function gdk_drag_get_selection(context: PGdkDragContext): TGdkAtom; cdecl; external;
+function gdk_drag_get_selection(context: PGdkDragContext): PGdkAtom; cdecl; external;
 function gdk_drag_motion(context: PGdkDragContext; dest_window: PGdkWindow; protocol: TGdkDragProtocol; x_root: gint; y_root: gint; suggested_action: TGdkDragAction; possible_actions: TGdkDragAction; time_: guint32): gboolean; cdecl; external;
 function gdk_error_trap_pop: gint; cdecl; external;
 function gdk_event_copy(event: PGdkEvent): PGdkEvent; cdecl; external;
@@ -4058,7 +4058,7 @@
 function gdk_pixbuf_get_from_window(window: PGdkWindow; src_x: gint; src_y: gint; width: gint; height: gint): PGdkPixbuf; cdecl; external;
 function gdk_pointer_grab(window: PGdkWindow; owner_events: gboolean; event_mask: TGdkEventMask; confine_to: PGdkWindow; cursor: PGdkCursor; time_: guint32): TGdkGrabStatus; cdecl; external;
 function gdk_pointer_is_grabbed: gboolean; cdecl; external;
-function gdk_property_get(window: PGdkWindow; property_: TGdkAtom; type_: TGdkAtom; offset: gulong; length: gulong; pdelete: gint; actual_property_type: PGdkAtom; actual_format: Pgint; actual_length: Pgint; data: PPguint8): gboolean; cdecl; external;
+function gdk_property_get(window: PGdkWindow; property_: PGdkAtom; type_: PGdkAtom; offset: gulong; length: gulong; pdelete: gint; actual_property_type: PGdkAtom; actual_format: Pgint; actual_length: Pgint; data: PPguint8): gboolean; cdecl; external;
 function gdk_rectangle_get_type: TGType; cdecl; external;
 function gdk_rectangle_intersect(src1: PGdkRectangle; src2: PGdkRectangle; dest: PGdkRectangle): gboolean; cdecl; external;
 function gdk_rgba_copy(rgba: PGdkRGBA): PGdkRGBA; cdecl; external;
@@ -4099,15 +4099,15 @@
 function gdk_screen_make_display_name(screen: PGdkScreen): Pgchar; cdecl; external;
 function gdk_screen_width: gint; cdecl; external;
 function gdk_screen_width_mm: gint; cdecl; external;
-function gdk_selection_owner_get(selection: TGdkAtom): PGdkWindow; cdecl; external;
-function gdk_selection_owner_get_for_display(display: PGdkDisplay; selection: TGdkAtom): PGdkWindow; cdecl; external;
-function gdk_selection_owner_set(owner: PGdkWindow; selection: TGdkAtom; time_: guint32; send_event: gboolean): gboolean; cdecl; external;
-function gdk_selection_owner_set_for_display(display: PGdkDisplay; owner: PGdkWindow; selection: TGdkAtom; time_: guint32; send_event: gboolean): gboolean; cdecl; external;
+function gdk_selection_owner_get(selection: PGdkAtom): PGdkWindow; cdecl; external;
+function gdk_selection_owner_get_for_display(display: PGdkDisplay; selection: PGdkAtom): PGdkWindow; cdecl; external;
+function gdk_selection_owner_set(owner: PGdkWindow; selection: PGdkAtom; time_: guint32; send_event: gboolean): gboolean; cdecl; external;
+function gdk_selection_owner_set_for_display(display: PGdkDisplay; owner: PGdkWindow; selection: PGdkAtom; time_: guint32; send_event: gboolean): gboolean; cdecl; external;
 function gdk_selection_property_get(requestor: PGdkWindow; data: PPguint8; prop_type: PGdkAtom; prop_format: Pgint): gint; cdecl; external;
 function gdk_setting_get(name: Pgchar; value: PGValue): gboolean; cdecl; external;
 function gdk_test_simulate_button(window: PGdkWindow; x: gint; y: gint; button: guint; modifiers: TGdkModifierType; button_pressrelease: TGdkEventType): gboolean; cdecl; external;
 function gdk_test_simulate_key(window: PGdkWindow; x: gint; y: gint; keyval: guint; modifiers: TGdkModifierType; key_pressrelease: TGdkEventType): gboolean; cdecl; external;
-function gdk_text_property_to_utf8_list_for_display(display: PGdkDisplay; encoding: TGdkAtom; format: gint; text: Pguint8; length: gint; list: PPPgchar): gint; cdecl; external;
+function gdk_text_property_to_utf8_list_for_display(display: PGdkDisplay; encoding: PGdkAtom; format: gint; text: Pguint8; length: gint; list: PPPgchar): gint; cdecl; external;
 function gdk_threads_add_idle(function_: TGSourceFunc; data: gpointer): guint; cdecl; external;
 function gdk_threads_add_idle_full(priority: gint; function_: TGSourceFunc; data: gpointer; notify: TGDestroyNotify): guint; cdecl; external;
 function gdk_threads_add_timeout(interval: guint; function_: TGSourceFunc; data: gpointer): guint; cdecl; external;
@@ -4242,8 +4242,8 @@
 procedure gdk_parse_args(argc: Pgint; argv: PPPgchar); cdecl; external;
 procedure gdk_pointer_ungrab(time_: guint32); cdecl; external;
 procedure gdk_pre_parse_libgtk_only; cdecl; external;
-procedure gdk_property_change(window: PGdkWindow; property_: TGdkAtom; type_: TGdkAtom; format: gint; mode: TGdkPropMode; data: Pguint8; nelements: gint); cdecl; external;
-procedure gdk_property_delete(window: PGdkWindow; property_: TGdkAtom); cdecl; external;
+procedure gdk_property_change(window: PGdkWindow; property_: PGdkAtom; type_: PGdkAtom; format: gint; mode: TGdkPropMode; data: Pguint8; nelements: gint); cdecl; external;
+procedure gdk_property_delete(window: PGdkWindow; property_: PGdkAtom); cdecl; external;
 procedure gdk_query_depths(depths: PPgint; count: Pgint); cdecl; external;
 procedure gdk_query_visual_types(visual_types: PPGdkVisualType; count: Pgint); cdecl; external;
 procedure gdk_rectangle_union(src1: PGdkRectangle; src2: PGdkRectangle; dest: PGdkRectangle); cdecl; external;
@@ -4252,9 +4252,9 @@
 procedure gdk_screen_get_monitor_workarea(screen: PGdkScreen; monitor_num: gint; dest: PGdkRectangle); cdecl; external;
 procedure gdk_screen_set_font_options(screen: PGdkScreen; options: Pcairo_font_options_t); cdecl; external;
 procedure gdk_screen_set_resolution(screen: PGdkScreen; dpi: gdouble); cdecl; external;
-procedure gdk_selection_convert(requestor: PGdkWindow; selection: TGdkAtom; target: TGdkAtom; time_: guint32); cdecl; external;
-procedure gdk_selection_send_notify(requestor: PGdkWindow; selection: TGdkAtom; target: TGdkAtom; property_: TGdkAtom; time_: guint32); cdecl; external;
-procedure gdk_selection_send_notify_for_display(display: PGdkDisplay; requestor: PGdkWindow; selection: TGdkAtom; target: TGdkAtom; property_: TGdkAtom; time_: guint32); cdecl; external;
+procedure gdk_selection_convert(requestor: PGdkWindow; selection: PGdkAtom; target: PGdkAtom; time_: guint32); cdecl; external;
+procedure gdk_selection_send_notify(requestor: PGdkWindow; selection: PGdkAtom; target: PGdkAtom; property_: PGdkAtom; time_: guint32); cdecl; external;
+procedure gdk_selection_send_notify_for_display(display: PGdkDisplay; requestor: PGdkWindow; selection: PGdkAtom; target: PGdkAtom; property_: PGdkAtom; time_: guint32); cdecl; external;
 procedure gdk_set_double_click_time(msec: guint); cdecl; external;
 procedure gdk_set_program_class(program_class: Pgchar); cdecl; external;
 procedure gdk_set_show_events(show_events: gboolean); cdecl; external;
@@ -4499,7 +4499,7 @@
 
 function TGdkAtom.name: Pgchar; cdecl;
 begin
-  Result := LazGdk3.gdk_atom_name(self);
+  Result := LazGdk3.gdk_atom_name(@self);
 end;
 
 function TGdkAtom.intern(atom_name: Pgchar; only_if_exists: gboolean): PGdkAtom; cdecl;
@@ -4512,7 +4512,7 @@
   Result := LazGdk3.gdk_atom_intern_static_string(atom_name);
 end;
 
-function TGdkDisplay.request_selection_notification(selection: TGdkAtom): gboolean; cdecl;
+function TGdkDisplay.request_selection_notification(selection: PGdkAtom): gboolean; cdecl;
 begin
   Result := LazGdk3.gdk_display_request_selection_notification(@self, selection);
 end;
@@ -4837,7 +4837,7 @@
   Result := LazGdk3.gdk_device_get_axis_use(@self, index_);
 end;
 
-function TGdkDevice.get_axis_value(axes: Pgdouble; axis_label: TGdkAtom; value: Pgdouble): gboolean; cdecl;
+function TGdkDevice.get_axis_value(axes: Pgdouble; axis_label: PGdkAtom; value: Pgdouble): gboolean; cdecl;
 begin
   Result := LazGdk3.gdk_device_get_axis_value(@self, axes, axis_label, value);
 end;
c3.diff (12,721 bytes)   

Juha Manninen

2019-12-25 14:36

developer   ~0120060

The patch does not really do anything. I would rather combine it with some functionality.

Yes, TGdkAtom is "object", not class.

Anton Kavalenka

2020-04-18 18:59

reporter   ~0122229

At least in test App, the text is Copied/Pasted
gtk3clip.diff (6,151 bytes)   
Index: lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas
===================================================================
--- lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas	(revision 63011)
+++ lcl/interfaces/gtk3/gtk3bindings/lazgdk3.pas	(working copy)
@@ -2880,14 +2880,17 @@
   PPGdkEvent = ^PGdkEvent;
   PGdkEvent = ^TGdkEvent;
 
-  PPPGdkAtom = ^PPGdkAtom;
-  PPGdkAtom = ^PGdkAtom;
+  //typedef struct _GdkAtom *GdkAtom;
+  {PPPGdkAtom = ^PPGdkAtom;}
+  PPGdkAtom = ^GdkAtom;
   PGdkAtom = ^TGdkAtom;
+  GdkAtom = PGdkAtom; // pointer alias
   TGdkAtom = object
     function name: Pgchar; cdecl; inline;
     function intern(atom_name: Pgchar; only_if_exists: gboolean): PGdkAtom; cdecl; inline; static;
     function intern_static_string(atom_name: Pgchar): PGdkAtom; cdecl; inline; static;
   end;
+
   TGdkDisplay = object(TGObject)
     function get_default: PGdkDisplay; cdecl; inline; static;
     function open(display_name: Pgchar): PGdkDisplay; cdecl; inline; static;
Index: lcl/interfaces/gtk3/gtk3bindings/lazgtk3.pas
===================================================================
--- lcl/interfaces/gtk3/gtk3bindings/lazgtk3.pas	(revision 63011)
+++ lcl/interfaces/gtk3/gtk3bindings/lazgtk3.pas	(working copy)
@@ -4631,8 +4631,8 @@
   PGtkClipboardClearFunc = ^TGtkClipboardClearFunc;
   TGtkClipboardClearFunc = procedure(clipboard: PGtkClipboard; user_data_or_owner: gpointer); cdecl;
   TGtkClipboard = object(TGObject)
-    function get(selection: TGdkAtom): PGtkClipboard; cdecl; inline; static;
-    function get_for_display(display: PGdkDisplay; selection: TGdkAtom): PGtkClipboard; cdecl; inline; static;
+    function get(selection: GdkAtom): PGtkClipboard; cdecl; inline; static;
+    function get_for_display(display: PGdkDisplay; selection: GdkAtom): PGtkClipboard; cdecl; inline; static;
     procedure clear; cdecl; inline;
     function get_display: PGdkDisplay; cdecl; inline;
     function get_owner: PGObject; cdecl; inline;
@@ -11493,9 +11493,9 @@
 function gtk_check_menu_item_new_with_label(label_: Pgchar): PGtkCheckMenuItem; cdecl; external;
 function gtk_check_menu_item_new_with_mnemonic(label_: Pgchar): PGtkCheckMenuItem; cdecl; external;
 function gtk_check_version(required_major: guint; required_minor: guint; required_micro: guint): Pgchar; cdecl; external;
-function gtk_clipboard_get(selection: TGdkAtom): PGtkClipboard; cdecl; external;
+function gtk_clipboard_get(selection: GdkAtom): PGtkClipboard; cdecl; external;
 function gtk_clipboard_get_display(clipboard: PGtkClipboard): PGdkDisplay; cdecl; external;
-function gtk_clipboard_get_for_display(display: PGdkDisplay; selection: TGdkAtom): PGtkClipboard; cdecl; external;
+function gtk_clipboard_get_for_display(display: PGdkDisplay; selection: GdkAtom): PGtkClipboard; cdecl; external;
 function gtk_clipboard_get_owner(clipboard: PGtkClipboard): PGObject; cdecl; external;
 function gtk_clipboard_get_type: TGType; cdecl; external;
 function gtk_clipboard_set_with_data(clipboard: PGtkClipboard; targets: PGtkTargetEntry; n_targets: guint; get_func: TGtkClipboardGetFunc; clear_func: TGtkClipboardClearFunc; user_data: gpointer): gboolean; cdecl; external;
@@ -20083,12 +20083,12 @@
   LazGtk3.gtk_check_menu_item_toggled(@self);
 end;
 
-function TGtkClipboard.get(selection: TGdkAtom): PGtkClipboard; cdecl;
+function TGtkClipboard.get(selection: GdkAtom): PGtkClipboard; cdecl;
 begin
   Result := LazGtk3.gtk_clipboard_get(selection);
 end;
 
-function TGtkClipboard.get_for_display(display: PGdkDisplay; selection: TGdkAtom): PGtkClipboard; cdecl;
+function TGtkClipboard.get_for_display(display: PGdkDisplay; selection: GdkAtom): PGtkClipboard; cdecl;
 begin
   Result := LazGtk3.gtk_clipboard_get_for_display(display, selection);
 end;
Index: lcl/interfaces/gtk3/gtk3winapi.inc
===================================================================
--- lcl/interfaces/gtk3/gtk3winapi.inc	(revision 63011)
+++ lcl/interfaces/gtk3/gtk3winapi.inc	(working copy)
@@ -141,13 +141,30 @@
   Result:=inherited ClipboardFormatToMimeType(FormatID);
 end;
 
+const
+  sPrimary = 'PRIMARY';
+  sClipboard = 'CLIPBOARD';
+
 function TGtk3WidgetSet.ClipboardGetData(ClipboardType: TClipboardType;
   FormatID: TClipboardFormat; Stream: TStream): boolean;
+var
+  pclp:PGtkClipboard;
+  pc:pgchar;
+  pcname:PgdkAtom;
 begin
-  {$IFDEF GTK3DEBUGNOTIMPLEMENTED}
-  DebugLn('WARNING: TGtk3WidgetSet.ClipboardGetData not implemented ...');
-  {$ENDIF}
-  Result:=inherited ClipboardGetData(ClipboardType, FormatID, Stream);
+  case ClipboardType of
+  ctPrimarySelection: pcname:=TGdkAtom.intern(sPrimary,false);
+  ctSecondarySelection: pcname:=nil;
+  ctClipboard: pcname:=TGdkAtom.intern(sClipboard,false);
+  end;
+  if not Assigned(pcname) then exit;
+  pclp:=TGtkClipboard.get(pcname);
+  if not Assigned(pclp) then exit(false);
+  // text handling
+  //pclp^.request_text(@ClipboardTextReceivedFunc,Stream);
+  pc:=pclp^.wait_for_text;
+  Stream.Write(pc^,strlen(pc));
+  Result:=true;
 end;
 
 function TGtk3WidgetSet.ClipboardGetFormats(ClipboardType: TClipboardType;
@@ -162,12 +179,24 @@
 function TGtk3WidgetSet.ClipboardGetOwnerShip(ClipboardType: TClipboardType;
   OnRequestProc: TClipboardRequestEvent; FormatCount: integer;
   Formats: PClipboardFormat): boolean;
+var
+  pclp:PGtkClipboard;
+  pc:pgchar;
+  pcname:PgdkAtom;
 begin
-  {$IFDEF GTK3DEBUGNOTIMPLEMENTED}
-  DebugLn('WARNING: TGtk3WidgetSet.ClipboardGetOwnerShip not implemented ...');
-  {$ENDIF}
-  Result:=inherited ClipboardGetOwnerShip(ClipboardType, OnRequestProc,
-    FormatCount, Formats);
+  case ClipboardType of
+  ctPrimarySelection: pcname:=TGdkAtom.intern(sPrimary,false);
+  ctSecondarySelection: pcname:=nil;
+  ctClipboard: pcname:=TGdkAtom.intern(sClipboard,false);
+  end;
+  if not Assigned(pcname) then exit;
+  pclp:=TGtkClipboard.get(pcname);
+  if not Assigned(pclp) then exit(false);
+{  // text handling
+  //pclp^.request_text(@ClipboardTextReceivedFunc,Stream);
+  pc:=pclp^.wait_for_text;
+  Stream.Write(pc^,strlen(pc)); }
+  Result:=true;
 end;
 
 function TGtk3WidgetSet.ClipboardRegisterFormat(const AMimeType: string): TClipboardFormat;
gtk3clip.diff (6,151 bytes)   

Juha Manninen

2020-04-19 11:55

developer   ~0122245

Applied, thanks.
Works well.

Chris Rorden

2020-04-20 13:28

reporter   ~0122273

Demo application shows how you can copy text to Clipboard and Copy text from the Clipboard to the application's Menubar caption. Note with GTK3, copying text to clipboard only impacts the application itself, global clipboard used by other applications does not change. Quiting the Lazarus application forgets text in application clipboard, reverts to system clipboard. Ideally, text would be in global clipboard, where we can copy to other applications, and is persistent even when application is restarted.
gtk3_clipboard.zip (109,820 bytes)

Zeljan Rikalo

2020-04-20 13:33

developer   ~0122275

@Chris Rorden, under X11 clipboard needs some clipboard utility to remember contents of clipboard when an application quits. But, if you copy some text inside LCL gtk3 app, it must be possible to paste it into another application, or vice versa of course and that's bug.

Chris Rorden

2020-04-21 16:57

reporter   ~0122320

Anton - I think "Clipboard.AsText" is not saving to the PRIMARY clipboard. Is it possible to make this the default clipboard for this function?


  https://developer.gnome.org/gtk3/stable/gtk3-Clipboards.html
clipboard of data shared between different processes or between different widgets IN THE SAME PROCESS.... The default clipboard corresponds to the “CLIPBOARD” atom; another commonly used clipboard is the “PRIMARY” clipboard, which, in X, traditionally contains the currently selected text.

Issue History

Date Modified Username Field Change
2019-11-23 15:00 CudaText man New Issue
2019-11-23 15:45 Anton Kavalenka Note Added: 0119454
2019-12-14 23:29 Bart Broersma Relationship added has duplicate 0036441
2019-12-20 21:19 CudaText man File Added: c1.diff
2019-12-20 21:19 CudaText man Note Added: 0119980
2019-12-20 22:11 CudaText man File Added: c2.diff
2019-12-20 22:11 CudaText man Note Added: 0119982
2019-12-20 22:12 CudaText man Note Edited: 0119982 View Revisions
2019-12-20 22:12 CudaText man Note Edited: 0119982 View Revisions
2019-12-20 22:13 CudaText man Note Edited: 0119982 View Revisions
2019-12-20 23:02 Juha Manninen File Added: ClipboardTest.zip
2019-12-20 23:02 Juha Manninen Note Added: 0119984
2019-12-20 23:03 Juha Manninen Fixed in Revision => r62426
2019-12-20 23:03 Juha Manninen LazTarget => -
2019-12-20 23:03 Juha Manninen Widgetset GTK 3 => GTK 3
2019-12-20 23:04 Juha Manninen Assigned To => Juha Manninen
2019-12-20 23:04 Juha Manninen Status new => assigned
2019-12-24 20:53 CudaText man File Added: c3.diff
2019-12-24 20:53 CudaText man Note Added: 0120056
2019-12-25 14:36 Juha Manninen Note Added: 0120060
2020-04-18 18:59 Anton Kavalenka Note Added: 0122229
2020-04-18 18:59 Anton Kavalenka File Added: gtk3clip.diff
2020-04-19 11:55 Juha Manninen Status assigned => resolved
2020-04-19 11:55 Juha Manninen Resolution open => fixed
2020-04-19 11:55 Juha Manninen Fixed in Revision r62426 => r62426, r63015
2020-04-19 11:55 Juha Manninen Widgetset GTK 3 => GTK 3
2020-04-19 11:55 Juha Manninen Note Added: 0122245
2020-04-20 13:28 Chris Rorden Note Added: 0122273
2020-04-20 13:28 Chris Rorden File Added: gtk3_clipboard.zip
2020-04-20 13:33 Zeljan Rikalo Note Added: 0122275
2020-04-21 16:57 Chris Rorden Note Added: 0122320