Project

General

Profile

issue with live scatter line chart

Added by priyanka more almost 3 years ago

Hello,

I'm trying to create a live scatter chart on x-y axis. In which I want x-axis to be running continuously and on y-axis values to be updated. I'm able to do it to some point but, after some period of time the previous sample lines are getting reused to plot next samples on x-axis. (please look at the graph below to get clear idea). Please help to plot a live graph as x-axis should be running continuously and y-axis values to be plotted wrt x-axis and the previous values of y-axis should be vanished.

created a container Widget as:
GraphApp::GraphApp(const WEnvironment& env) : WApplication(env)
{
setTitle("xy graph");
setCssTheme("polished");

root()->setPadding(10);
root()->resize(WLength::Auto, WLength::Auto);

std::unique_ptr<ChartWidget> snr_widget = std::make_unique<ChartWidget>(WString("SNR"), 800, 300);

auto gridUser = root()->setLayout(Wt::cpp14::make_unique<Wt::WGridLayout>());

std::unique_ptr<Wt::WText> item = Wt::cpp14::make_unique<Wt::WText>("<b>Top Status</b>");
item->setStyleClass("green-box");
gridUser->addWidget(std::move(item), 0, 0, 1, 2);

this->m_chart_widget_snr = gridUser->addWidget(std::move(snr_widget), 2, 0);

this->x_axis = 0;
this->y_axis = -30;

Wt::WString footer_title = Wt::WString("<b>Bottom Status</b>");
auto footer_text = Wt::cpp14::make_unique<Wt::WText>(footer_title);
footer_text->setStyleClass("yellow-box");
gridUser->addWidget(std::move(footer_text), 4, 0, 1, 2);

useStyleSheet("charts.css");

auto timer = this->addChild(std::make_unique<Wt::WTimer>());
timer->setInterval(std::chrono::milliseconds(250));
timer->timeout().connect(this, &GraphApp::Timeout);
timer->start();

}

void GraphApp::Timeout()
{
double y_snr = this->y_axis++;
this->m_chart_widget_snr->Update2DGraph(this->x_axis, y_snr);

this->x_axis++;
if (this->y_axis > -10) {
    this->y_axis = -20;
}

}

ChartWidget::ChartWidget(WString graph_name, int pix_x, int pix_y) : WContainerWidget()
{
std::shared_ptr model = std::make_shared(40, 2);
std::unique_ptr prototype = std::make_unique();

model->setItemPrototype(std::move(prototype));
model->setHeaderData(0, WString("X"));
model->setHeaderData(1, WString("Y"));

this->chart = this->addWidget(std::make_unique<WCartesianChart>());
this->chart->setModel(model);
this->chart->setXSeriesColumn(0);
this->chart->setZoomEnabled(true);
this->chart->setPanEnabled(true);
this->chart->setCrosshairEnabled(true);
this->chart->setBackground(WColor(171,219,227));
this->chart->setType(ChartType::Line);

this->chart->axis(Axis::X).setLocation(AxisValue::Zero);
this->chart->axis(Axis::Y).setLocation(AxisValue::Both);
this->wptr = 0;

std::unique_ptr<WDataSeries> s = std::make_unique<WDataSeries>(1, SeriesType::Line);
s->setShadow(WShadow(0, 0, WColor(0, 0, 0, 127), 0));
this->chart->addSeries(std::move(s));

this->chart->resize(pix_x, pix_y); // WPaintedWidget must be given explicit size
this->chart->setMargin(1, Side::Top );            // add margin vertically
this->chart->setMargin(1, Side::Bottom);            // add margin vertically
this->chart->setMargin(100, Side::Left); // center horizontally
this->chart->setMargin(10, Side::Right); // center horizontally

}

void ChartWidget::Update2DGraph(double x, double y)
{
if (this->play_pause_flag == false) {
return;
}

std::shared_ptr<WAbstractItemModel> model = this->chart->itemModel();

  model->setData(this->wptr, 0, x);
  model->setData(this->wptr, 1, y);

  this->wptr++;
  if(this->wptr >= 40) {
 this->wptr = 0;
  } 

}


1.PNG (49 KB) 1.PNG
2.PNG (77.6 KB) 2.PNG
3.PNG (74.6 KB) 3.PNG

Replies (1)

RE: issue with live scatter line chart - Added by Plug Gulp over 2 years ago

Hi Priyanka,

I am noob with Wt graphs, but the code in the following method looks bit odd against the description you have given of the problem:

I want x-axis to be running continuously and on y-axis values to be updated.
help to plot a live graph as x-axis should be running continuously and y-axis values to be plotted wrt x-axis and the previous values of y-axis should be vanished.

void GraphApp::Timeout()
{
   double y_snr = this->y_axis++;
   this->m_chart_widget_snr->Update2DGraph(this->x_axis, y_snr);

   this->x_axis++;

   if (this->y_axis > -10) {
      this->y_axis = -20;
   }
}

From the code it looks like you are updating Y-axis continuously(as opposed to X-axis). Then update the graph. And then increment X-axis. And then bring the Y-axis, if required, between the range -10 to -30. Are you suppose to increment the X-axis first, then update the graph, and then adjust the Y-axis?

    (1-1/1)