Progressively mounting delay on rendering TH2 with real-time data

TH2 real-time graph gets progressively delayed on rendering data, the visual effect is that the visualized data is way behind current transferred data.

I have checked my data pipeline and there is no significant delay on transfer / serializing / deserializing

I also have parallelized the histogram filling loop, just in case that was it. But it seems that the bottleneck lies on the rendering itself ?

I have tried to include and use TH2GL.h but I don’t have it, even tho in the build instructions it looks like OpenGL option is added by default and I had libglu installed on my system at the time of compiling.

How can I check the options added at ROOT compile time to check if I have OpenGL support ?

Besides this, if you have any other tip it’s very welcome !

EDIT: I have recompiled root and now there is OpenGL support. How can I now plot a TH2D via Opengl ? Thanks !

Before creating any canvas, you need: gStyle->SetCanvasPreferGL(kTRUE);
Then use any of the available histogram drawing options which use OpenGL.

See:
grep -r -l SetCanvasPreferGL ${ROOTSYS}/t[eu]*

thanks for the tip, it’s working … but unfortunately there is no suport for GLCOL on TH2 :frowning:

Do you know of any alternative ? Just testing it now and yes it’s blazing fast but I can’t use it

EDIT: I just realized, that this also happens with the GL histograms. When I cut off the pipe, no more messages are flowing, but ROOT is still processing the graphics. I thought this was a bottleneck on the graphics, but it seems that it’s not. When I restart the pipe, the plot is loading frames much faster to catch up with the train of incoming messages that are in the buffer. It’s after a while that it seems that a delay occurs. Could this be because of how I’m updating the histogram ?

    TApplication RootApp("App", 0, 0);

    gStyle->SetCanvasPreferGL(kTRUE);

    TCanvas *canvas = new TCanvas("canvas", "CWT", 200, 10, 800, 600);

    // canvas->cd(1);

    auto hist = new TH2D("hist", "hist", 49, 0, 49, 114, 0, 114);

    hist->SetStats(0);
    hist->SetFillColor(55);
    hist->SetTitle("CWT");
    canvas->cd(1);
    hist->Draw("GLSURF1");

    BS::thread_pool pool(10);
while (true)
{

    std::string message = cwtOutRootInSocket.receiveMessage();

    cwts = json.cwtScaleOfScalesJsonToStruct(message);

    std::reverse(cwts.eventOfEvents.begin(), cwts.eventOfEvents.end());


    pool.parallelize_loop(0, cwts.eventOfEvents.at(0).size(),
                          [&cwts, &hist](const int a, const int b)
                          {
                              for (int t = 0; t < cwts.eventOfEvents.size(); ++t)
                              {

                                  for (int i = a; i < b; ++i)
                                  {

                                      hist->Fill(i, t, cwts.eventOfEvents[t][i]);
                                  }
                              }
                          })
        .wait();

    canvas->Pad()->Draw();

    canvas->Modified();

    canvas->Update();

    gSystem->ProcessEvents();

    hist->Reset();
}

If I cut the pipe on the first few minutes, the graph is very responsive and stops plotting immediately. If I let it run for, let’s say 15 minutes, then it starts getting delayed and visibly sluggish on drawing. If I cut the pipe, there is still data being plotted.

Note that partial pararellization of the fill has no substantial effect on it, I just did this to test what was going on. It seems to be fine without partial parallelization. Any hints on this would be helpful, thanks.

Ok so what I’ve got here is a massive leak …

I have tested many things and changed the code to this, so each incoming message sets a new hist with the correct bin sizes, then delete it when a loop cycle ends :

while (true){

    TH2D *hist = new TH2D("hist", "CWTHist", timeSteps, 0, timeSteps, scaleSize, 0, scaleSize);

    hist->SetStats(0);
    hist->SetTitle("CWT");
    hist->Draw("GLSURF3");


    for (int t = 0; t < cwts->eventOfEvents.size(); ++t)
    {

        for (int i = 0; i < cwts->eventOfEvents[t].size(); ++i)
        {

            hist->Fill(i, t, cwts->eventOfEvents[t][i]);
        }
    }


    canvas->Draw();

    canvas->Modified();

    canvas->Update();

    gSystem->ProcessEvents();

    delete hist;

}

But to no avail, the leak persists …

Ok fixed it, I forgot to remove something I wrote for testing on the module sending the data and it was processing a larger and larger array every time, so not a problem with ROOT as expected :slight_smile:

Thank you very much

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