简体   繁体   English

gtkmm应用程序内存使用量不断增加

[英]gtkmm applications memory usage keeps increasing

I have a client that updates its window when it gets data from a server. 我有一个客户端在从服务器获取数据时更新其窗口。 Because it is using ClearSilver templates the glade file needs to be loaded every time it receives an update from the server. 因为它使用的是ClearSilver模板,所以每次从服务器收到更新时都需要加载glade文件。 I'm trying to do this by replacing the windows first child with a newly generated child every time there is an update. 我试图通过每次更新时用新生成的子代替Windows第一个孩子来做到这一点。 This works fine apart from the fact that the memory usage keeps increasing, and since the client needs to be running continuously this will become a problem eventually. 除了内存使用量持续增加这一事实之外,这种方法还可以,并且由于客户端需要连续运行,这最终将成为一个问题。

This is how I build the window: 这就是我构建窗口的方式:

Glib::RefPtr<Gtk::Application> app = Gtk::Application::create(argc, argv, "mywindow");
HDF* hdf = NULL;
CSPARSE *parse = NULL;
STRING newLayout;

string_init(&newLayout);
hdf_init(&hdf);
cs_init(&parse, hdf);
cs_parse_file(parse, gladeFilePath);
cs_render(parse, &newLayout, Render);
cs_destroy(&parse);

hdf_destroy(&hdf);        

Glib::RefPtr<Gtk::Builder> builder = Gtk::Builder::create();
builder->add_from_string(newLayout.buf, newLayout.len);
gtk_builder_connect_signals_full(builder->gobj(), SignalConnect, NULL);

builder->get_widget("window", window);

string_clear(&newLayout);

app->run(*window);

The Render function that cs_render calls: cs_render调用的Render函数:

NEOERR* Render(void * ctx, char * data)
{
   STRING * layout = (STRING *)ctx;
   string_append(layout, data);

   return 0;
}

This is how I rebuild the window: 这是我重建窗口的方式:

HDF* hdf = NULL;
CSPARSE *parse = NULL;
STRING newLayout;
Gtk::Widget* widget = NULL;

string_init(&newLayout);
hdf_init(&hdf);
cs_init(&parse, hdf);
cs_parse_file(parse, gladeFilePath);
cs_render(parse, &newLayout, Render);
cs_destroy(&parse);

hdf_destroy(&hdf);

Glib::RefPtr<Gtk::Builder> builder = Gtk::Builder::create();
builder->add_from_string(newLayout.buf, newLayout.len);
gtk_builder_connect_signals_full(builder->gobj(), SignalConnect, NULL);

builder->get_widget("child1", widget);

// remove the old child
window->remove();

widget->reparent(*window);

string_clear(&newLayout);

The new window generated from another thread through a Glib::Dispatcher 新窗口是从另一个线程通过Glib :: Dispatcher生成的

You don't destroy previous widgets. 您不会破坏以前的小部件。 gtkmm-tutorial : gtkmm-tutorial

Note that if you never added the widget to any parent container, or you did but later Gtk::Container::remove()d it from said parent, gtkmm restores the widget's lifetime management to whatever state it had before manage() was called, which typically means that the responsibility for deleteing the widget returns to the user. 请注意,如果您从未将窗口小部件添加到任何父容器,或者您从稍后将Gtk :: Container :: remove()d添加到所述父容器中,则gtkmm会将窗口小部件的生命周期管理恢复到在调用manage()之前的状态。 ,这通常意味着删除小部件的责任将返回给用户。

So you need something like that: 所以你需要这样的东西:

Gtk::Widget* oldWidget = window->get_child(); //from Gtk::Bin
if(oldWidget) //I had errors when reparenting into an empty Gtk::Container
{
  widget->reparent(*window);
  delete oldWidget;
}
else
  window->add(*widget);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM