Search code examples
c++linuxgtkglibgio

how can I synchronize a gtk::label with the creation or suppression of a file in a directory?


I have a program who lists all files in the working directory (I use glib for doing this), then I screen this list in a GtkWindow trough a Gtk::Label. I screen the window by using run(),

  Glib::RefPtr<Gtk::Application> app = Gtk::Application::create(argc, argv, "Zombie-Shadowchaser SixSixSix");
app->run(*pMainWindow);

I know how to change the label with set_label() I can synchronize the list of files in the directory with the list screened trough the click of a button. So if I delete or create a file, it will remove or add to the label the file. But how can I make my program to synchronize every second without clicking ?


Solution

  • here a full example, is also good to study if you are looking to understand how to use g_signal_connect()

    #include <gtkmm.h>
    
    Gtk::Label *plabel; // because I"m lazzy...
    
    /**
     ** everytime a file is created in the current directory, toCallbackFunction()
     ** will be called. The paramaters are the same of signal see signal here :
     ** http://www.freedesktop.org/software/gstreamer-sdk/data/docs/latest/gio/GFileMonitor.html#GFileMonitor-changed
     **/
    void
    toCallbackFunction(GFileMonitor      *monitor
                      ,GFile             *file
                      ,GFile             *other_file
                      ,GFileMonitorEvent event_type
                      ,gpointer          user_data
                      ) 
    {
      plabel->set_label( g_file_get_path(file) );
    }
    
    
    
    int 
    main(int  argc 
        ,char *argv[]
        )
    {
      Glib::RefPtr<Gtk::Application> app = Gtk::Application::create(argc, argv, "org.gtkmm.examples.base");
      Gtk::Window window;
      Gtk::Label label;
      window.set_default_size(800, 200);
    
      label.set_label("test");
    
      window.add(label);
      label.show();
      plabel = &label;
    
      /* 
       * g_file_monitor() requires a file, not a path. So we use g_file_new_for_path()
       * to convert the directory (this is for demonstration)
       */   
      GFile *file = g_file_new_for_path("."); 
      GFileMonitor *monitor;
      /*
       * http://www.freedesktop.org/software/gstreamer-sdk/data/docs/latest/gio/GFile.html#g-file-monitor
       */
      monitor = g_file_monitor_directory(file, G_FILE_MONITOR_NONE, nullptr, nullptr);
      /* 
       * the next line, is how to connect the monitor to a callback function when
       * the signal changed has been triggered.
       */
      g_signal_connect(monitor, "changed", G_CALLBACK (toCallbackFunction), nullptr);
    
    
      return app->run(window);
    }
    

    compile on linux :

     g++ main.cc -o simple `pkg-config gtkmm-3.0 --cflags --libs` -std=c++11
    

    for MS Windows users, I'm not racist, but I don't know how to compile on windows. Any comment would be apreciate, I made this piece of code by my own. Thx to report any error.

    How to use it :

    when you start the program, go with your console in the same directory and create a new file, for example,

     $ echo "stack" > overflow
    

    you should get something like :

    enter image description here

    Thx to nemequ