|
36 | 36 | #include "ansi_scrubber.hh" |
37 | 37 | #include "auto_mem.hh" |
38 | 38 | #include "config.h" |
| 39 | +#include "intervaltree/IntervalTree.h" |
39 | 40 | #include "lnav_log.hh" |
40 | 41 | #include "pcrepp/pcre2pp.hh" |
41 | 42 |
|
@@ -399,13 +400,43 @@ attr_line_t::subline(size_t start, size_t len) const |
399 | 400 | void |
400 | 401 | attr_line_t::split_lines(std::vector<attr_line_t>& lines) const |
401 | 402 | { |
| 403 | + using line_type_t = interval_tree::Interval<size_t, attr_line_t>; |
| 404 | + using lines_tree_t = interval_tree::IntervalTree<size_t, attr_line_t>; |
| 405 | + |
| 406 | + auto eols = std::vector<line_type_t>{}; |
402 | 407 | size_t pos = 0, next_line; |
403 | 408 |
|
404 | 409 | while ((next_line = this->al_string.find('\n', pos)) != std::string::npos) { |
405 | | - lines.emplace_back(this->subline(pos, next_line - pos)); |
| 410 | + eols.emplace_back( |
| 411 | + pos, |
| 412 | + next_line > pos ? next_line - 1 : next_line, |
| 413 | + attr_line_t{this->al_string.substr(pos, next_line - pos)}); |
406 | 414 | pos = next_line + 1; |
407 | 415 | } |
408 | | - lines.emplace_back(this->subline(pos)); |
| 416 | + if (pos < this->al_string.length()) { |
| 417 | + eols.emplace_back(pos, |
| 418 | + this->al_string.length() - 1, |
| 419 | + attr_line_t{this->al_string.substr(pos)}); |
| 420 | + } |
| 421 | + auto lines_tree = lines_tree_t{std::move(eols)}; |
| 422 | + for (const auto& sa : this->al_attrs) { |
| 423 | + if (sa.sa_range.empty()) { |
| 424 | + continue; |
| 425 | + } |
| 426 | + auto range_end = sa.sa_range.end_for_string(this->al_string) - 1; |
| 427 | + lines_tree.visit_overlapping( |
| 428 | + sa.sa_range.lr_start, range_end, [&sa](const auto& cinterval) { |
| 429 | + auto& interval = const_cast<line_type_t&>(cinterval); |
| 430 | + auto lr = line_range(interval.start, interval.stop + 1); |
| 431 | + auto ilr = lr.intersection(sa.sa_range).shift(0, -lr.lr_start); |
| 432 | + interval.value.al_attrs.emplace_back( |
| 433 | + ilr, std::make_pair(sa.sa_type, sa.sa_value)); |
| 434 | + }); |
| 435 | + } |
| 436 | + lines_tree.visit_all([&lines](auto& cinterval) { |
| 437 | + auto& interval = const_cast<line_type_t&>(cinterval); |
| 438 | + lines.emplace_back(std::move(interval.value)); |
| 439 | + }); |
409 | 440 | } |
410 | 441 |
|
411 | 442 | attr_line_t& |
|
0 commit comments