How to connect GTK4 application properly with the Apple Launch Service (solution to previous post)

Following my previous post, I found enlightening information from Apple’s Launch Services Concepts:

If the application is not already running, Launch Services starts it up (launches it) and sends it an 'oapp' (“open application”) Apple event. The application should respond to this event by performing its normal startup processing.
If the application is already running, Launch Services activates it (brings it to the front of the screen) and sends it an 'rapp' (“reopen application”) Apple event.

My hunch is that, on "Open with...", Apple Launch Service sends the file arguments to both 'oapp' and 'rapp' Apple events (at least this could be what happens in Big Sur).

To solve the problem in my previous post, all I used is the following assumptions:

  1. GTK4’s application.activate.connect() responds to Apple Launch Services 'oapp' Apple event.
  2. GTK4’s application.open.connect() responds to Apple Launch Services 'rapp' Apple event.

So, my solution is to allow application.activate.connect() to present the application window only when there are no file arguments.

If it sees file arguments, the file arguments are passed to application.open.connect(), by calling application.open({file},"") (see the code below).

The code is posted here. I added an optional code that makes sure there is only one application window — it tests for an existing application window and hijacks it.


using Gtk;
using Poppler;

int 
main (string[] argv)
{
    GLib.File gfile = null;
    
    Gtk.Application application =
        new Gtk.Application (
            "org.test.www",
            GLib.ApplicationFlags.HANDLES_OPEN);

    // register with OSX to open file from Finder
    // must be done here and
    // cannot be done under startup
    Value val = Value (GLib.Type.BOOLEAN);
    val.set_boolean (true);
    application.set_property ("register-session", val);
    val.unset ();

    application.activate.connect (()=>{
        Gtk.ApplicationWindow window = null;
        if (argv.length < 2){
            window = new Gtk.ApplicationWindow (application);
            window.set_default_size (480, 360);

            Gtk.Label label =
                new Gtk.Label ("This is activate");
            window.set_child (label);

            window.present ();
        } else {
            GLib.File file = 
                GLib.File.new_for_commandline_arg (argv[1]);
            application.open ({file},"");
        }
/*
        Gtk.ApplicationWindow window =
            new Gtk.ApplicationWindow (application);
        window.set_default_size (480, 360);

        Gtk.Label label =
            new Gtk.Label ("This is activate");
        window.set_child (label);

        window.present ();
*/

    });
    application.open.connect ((files, hint)=>{
        gfile = files[0];
        Gtk.ApplicationWindow window = null;
        if (application.get_active_window () != null) { 
            window = application.get_active_window () as Gtk.ApplicationWindow;
        } else {
            window = new Gtk.ApplicationWindow (application); 
        };
        window.set_default_size (480, 360);

        string formatted = "%s is Open.".printf (gfile.get_path ());
        Gtk.Label label =
            new Gtk.Label (formatted);
        window.set_child (label);

        window.present ();

/*
        Gtk.ApplicationWindow window =
            new Gtk.ApplicationWindow (application);
        window.set_default_size (480, 360);

        string formatted = "%s is Open.".printf (gfile.get_path ());
        Gtk.Label label =
            new Gtk.Label (formatted);
        window.set_child (label);

        window.present ();
*/

    });

    var status = application.run (argv);
    return status;
}

So, it was a problem with my code! Sorry it took me this long to post my solution — so long that replies are closed for my previous post.

A further reflection, I wonder whether it is better to restructure my code, so that application.open.connect() responds to Apple’s 'oapp' and application.open.activate() reponds to Apple’s 'rapp'

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.