1bb02e0acSNicolas Bonnefon /*
28e788202SNicolas Bonnefon * Copyright (C) 2009, 2010, 2011, 2012, 2013, 2017 Nicolas Bonnefon and other contributors
3bb02e0acSNicolas Bonnefon *
4bb02e0acSNicolas Bonnefon * This file is part of glogg.
5bb02e0acSNicolas Bonnefon *
6bb02e0acSNicolas Bonnefon * glogg is free software: you can redistribute it and/or modify
7bb02e0acSNicolas Bonnefon * it under the terms of the GNU General Public License as published by
8bb02e0acSNicolas Bonnefon * the Free Software Foundation, either version 3 of the License, or
9bb02e0acSNicolas Bonnefon * (at your option) any later version.
10bb02e0acSNicolas Bonnefon *
11bb02e0acSNicolas Bonnefon * glogg is distributed in the hope that it will be useful,
12bb02e0acSNicolas Bonnefon * but WITHOUT ANY WARRANTY; without even the implied warranty of
13bb02e0acSNicolas Bonnefon * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14bb02e0acSNicolas Bonnefon * GNU General Public License for more details.
15bb02e0acSNicolas Bonnefon *
16bb02e0acSNicolas Bonnefon * You should have received a copy of the GNU General Public License
17bb02e0acSNicolas Bonnefon * along with glogg. If not, see <http://www.gnu.org/licenses/>.
18bb02e0acSNicolas Bonnefon */
19bb02e0acSNicolas Bonnefon
20bb02e0acSNicolas Bonnefon // This file implements LogFilteredData
21bb02e0acSNicolas Bonnefon // It stores a pointer to the LogData that created it,
22bb02e0acSNicolas Bonnefon // so should always be destroyed before the LogData.
23bb02e0acSNicolas Bonnefon
24bb02e0acSNicolas Bonnefon #include "log.h"
25bb02e0acSNicolas Bonnefon
26bb02e0acSNicolas Bonnefon #include <QString>
27bb02e0acSNicolas Bonnefon #include <cassert>
28bb02e0acSNicolas Bonnefon #include <limits>
29bb02e0acSNicolas Bonnefon
30bb02e0acSNicolas Bonnefon #include "utils.h"
31bb02e0acSNicolas Bonnefon #include "logdata.h"
32bb02e0acSNicolas Bonnefon #include "marks.h"
33bb02e0acSNicolas Bonnefon #include "logfiltereddata.h"
34bb02e0acSNicolas Bonnefon
35bb02e0acSNicolas Bonnefon // Creates an empty set. It must be possible to display it without error.
36bb02e0acSNicolas Bonnefon // FIXME
LogFilteredData()37bb02e0acSNicolas Bonnefon LogFilteredData::LogFilteredData() : AbstractLogData(),
38ced968a9SNicolas Bonnefon matching_lines_(),
39bb02e0acSNicolas Bonnefon currentRegExp_(),
40bb02e0acSNicolas Bonnefon visibility_(),
41ef13a493SNicolas Bonnefon filteredItemsCache_(),
42ef13a493SNicolas Bonnefon workerThread_( nullptr ),
43ced968a9SNicolas Bonnefon marks_()
44bb02e0acSNicolas Bonnefon {
45bb02e0acSNicolas Bonnefon /* Prevent any more searching */
46bb02e0acSNicolas Bonnefon maxLength_ = 0;
47bb02e0acSNicolas Bonnefon maxLengthMarks_ = 0;
48bb02e0acSNicolas Bonnefon searchDone_ = true;
49bb02e0acSNicolas Bonnefon visibility_ = MarksAndMatches;
50bb02e0acSNicolas Bonnefon
51bb02e0acSNicolas Bonnefon filteredItemsCacheDirty_ = true;
52bb02e0acSNicolas Bonnefon }
53bb02e0acSNicolas Bonnefon
54bb02e0acSNicolas Bonnefon // Usual constructor: just copy the data, the search is started by runSearch()
LogFilteredData(const LogData * logData)55bb02e0acSNicolas Bonnefon LogFilteredData::LogFilteredData( const LogData* logData )
56bb02e0acSNicolas Bonnefon : AbstractLogData(),
57ced968a9SNicolas Bonnefon matching_lines_( SearchResultArray() ),
58bb02e0acSNicolas Bonnefon currentRegExp_(),
59bb02e0acSNicolas Bonnefon visibility_(),
60ef13a493SNicolas Bonnefon filteredItemsCache_(),
61ef13a493SNicolas Bonnefon workerThread_( logData ),
62ced968a9SNicolas Bonnefon marks_()
63bb02e0acSNicolas Bonnefon {
64bb02e0acSNicolas Bonnefon // Starts with an empty result list
65bb02e0acSNicolas Bonnefon maxLength_ = 0;
66bb02e0acSNicolas Bonnefon maxLengthMarks_ = 0;
67bb02e0acSNicolas Bonnefon nbLinesProcessed_ = 0;
68bb02e0acSNicolas Bonnefon
69bb02e0acSNicolas Bonnefon sourceLogData_ = logData;
70bb02e0acSNicolas Bonnefon
71bb02e0acSNicolas Bonnefon searchDone_ = false;
72bb02e0acSNicolas Bonnefon
73bb02e0acSNicolas Bonnefon visibility_ = MarksAndMatches;
74bb02e0acSNicolas Bonnefon
75bb02e0acSNicolas Bonnefon filteredItemsCacheDirty_ = true;
76bb02e0acSNicolas Bonnefon
77bb02e0acSNicolas Bonnefon // Forward the update signal
78*c59cadb3SNicolas Bonnefon connect( &workerThread_, SIGNAL( searchProgressed( int, int, qint64 ) ),
79*c59cadb3SNicolas Bonnefon this, SLOT( handleSearchProgressed( int, int, qint64 ) ) );
80bb02e0acSNicolas Bonnefon
81bb02e0acSNicolas Bonnefon // Starts the worker thread
82ef13a493SNicolas Bonnefon workerThread_.start();
83ef13a493SNicolas Bonnefon }
84ef13a493SNicolas Bonnefon
~LogFilteredData()85ef13a493SNicolas Bonnefon LogFilteredData::~LogFilteredData()
86ef13a493SNicolas Bonnefon {
87ef13a493SNicolas Bonnefon // FIXME
88ef13a493SNicolas Bonnefon // workerThread_.stop();
89bb02e0acSNicolas Bonnefon }
90bb02e0acSNicolas Bonnefon
91bb02e0acSNicolas Bonnefon //
92bb02e0acSNicolas Bonnefon // Public functions
93bb02e0acSNicolas Bonnefon //
94bb02e0acSNicolas Bonnefon
95bb02e0acSNicolas Bonnefon // Run the search and send newDataAvailable() signals.
runSearch(const QRegularExpression & regExp)964fb0346eSAnton Filimonov void LogFilteredData::runSearch( const QRegularExpression& regExp )
97bb02e0acSNicolas Bonnefon {
98bb02e0acSNicolas Bonnefon LOG(logDEBUG) << "Entering runSearch";
99bb02e0acSNicolas Bonnefon
100721a2433SNicolas Bonnefon clearSearch();
101bb02e0acSNicolas Bonnefon currentRegExp_ = regExp;
102bb02e0acSNicolas Bonnefon
103ef13a493SNicolas Bonnefon workerThread_.search( currentRegExp_ );
104bb02e0acSNicolas Bonnefon }
105bb02e0acSNicolas Bonnefon
updateSearch()106bb02e0acSNicolas Bonnefon void LogFilteredData::updateSearch()
107bb02e0acSNicolas Bonnefon {
108bb02e0acSNicolas Bonnefon LOG(logDEBUG) << "Entering updateSearch";
109bb02e0acSNicolas Bonnefon
110ef13a493SNicolas Bonnefon workerThread_.updateSearch( currentRegExp_, nbLinesProcessed_ );
111bb02e0acSNicolas Bonnefon }
112bb02e0acSNicolas Bonnefon
interruptSearch()113bb02e0acSNicolas Bonnefon void LogFilteredData::interruptSearch()
114bb02e0acSNicolas Bonnefon {
115bb02e0acSNicolas Bonnefon LOG(logDEBUG) << "Entering interruptSearch";
116bb02e0acSNicolas Bonnefon
117ef13a493SNicolas Bonnefon workerThread_.interrupt();
118bb02e0acSNicolas Bonnefon }
119bb02e0acSNicolas Bonnefon
clearSearch()120bb02e0acSNicolas Bonnefon void LogFilteredData::clearSearch()
121bb02e0acSNicolas Bonnefon {
1224fb0346eSAnton Filimonov currentRegExp_ = QRegularExpression();
123ced968a9SNicolas Bonnefon matching_lines_.clear();
124bb02e0acSNicolas Bonnefon maxLength_ = 0;
125721a2433SNicolas Bonnefon nbLinesProcessed_ = 0;
126bb02e0acSNicolas Bonnefon filteredItemsCacheDirty_ = true;
127bb02e0acSNicolas Bonnefon }
128bb02e0acSNicolas Bonnefon
getMatchingLineNumber(int matchNum) const129bb02e0acSNicolas Bonnefon qint64 LogFilteredData::getMatchingLineNumber( int matchNum ) const
130bb02e0acSNicolas Bonnefon {
131bb02e0acSNicolas Bonnefon qint64 matchingLine = findLogDataLine( matchNum );
132bb02e0acSNicolas Bonnefon
133bb02e0acSNicolas Bonnefon return matchingLine;
134bb02e0acSNicolas Bonnefon }
135bb02e0acSNicolas Bonnefon
136bb02e0acSNicolas Bonnefon // Scan the list for the 'lineNumber' passed
isLineInMatchingList(qint64 lineNumber)137bb02e0acSNicolas Bonnefon bool LogFilteredData::isLineInMatchingList( qint64 lineNumber )
138bb02e0acSNicolas Bonnefon {
139bb02e0acSNicolas Bonnefon int index; // Not used
140bb02e0acSNicolas Bonnefon return lookupLineNumber<SearchResultArray>(
141ced968a9SNicolas Bonnefon matching_lines_, lineNumber, &index);
142bb02e0acSNicolas Bonnefon }
143bb02e0acSNicolas Bonnefon
getLineIndexNumber(quint64 lineNumber) const1443ff6c941SAnton Filimonov int LogFilteredData::getLineIndexNumber( quint64 lineNumber ) const
1453ff6c941SAnton Filimonov {
1463ff6c941SAnton Filimonov int lineIndex = findFilteredLine( lineNumber );
1473ff6c941SAnton Filimonov return lineIndex;
1483ff6c941SAnton Filimonov }
149bb02e0acSNicolas Bonnefon
getNbTotalLines() const150ced968a9SNicolas Bonnefon LineNumber LogFilteredData::getNbTotalLines() const
151bb02e0acSNicolas Bonnefon {
152bb02e0acSNicolas Bonnefon return sourceLogData_->getNbLine();
153bb02e0acSNicolas Bonnefon }
154bb02e0acSNicolas Bonnefon
getNbMatches() const155ced968a9SNicolas Bonnefon LineNumber LogFilteredData::getNbMatches() const
156bb02e0acSNicolas Bonnefon {
157ced968a9SNicolas Bonnefon return matching_lines_.size();
158bb02e0acSNicolas Bonnefon }
159bb02e0acSNicolas Bonnefon
getNbMarks() const160ced968a9SNicolas Bonnefon LineNumber LogFilteredData::getNbMarks() const
161bb02e0acSNicolas Bonnefon {
162ced968a9SNicolas Bonnefon return marks_.size();
163bb02e0acSNicolas Bonnefon }
164bb02e0acSNicolas Bonnefon
165bb02e0acSNicolas Bonnefon LogFilteredData::FilteredLineType
filteredLineTypeByIndex(int index) const166bb02e0acSNicolas Bonnefon LogFilteredData::filteredLineTypeByIndex( int index ) const
167bb02e0acSNicolas Bonnefon {
168bb02e0acSNicolas Bonnefon // If we are only showing one type, the line is there because
169bb02e0acSNicolas Bonnefon // it is of this type.
170bb02e0acSNicolas Bonnefon if ( visibility_ == MatchesOnly )
171bb02e0acSNicolas Bonnefon return Match;
172bb02e0acSNicolas Bonnefon else if ( visibility_ == MarksOnly )
173bb02e0acSNicolas Bonnefon return Mark;
174bb02e0acSNicolas Bonnefon else {
175bb02e0acSNicolas Bonnefon // If it is MarksAndMatches, we have to look.
176bb02e0acSNicolas Bonnefon // Regenerate the cache if needed
177bb02e0acSNicolas Bonnefon if ( filteredItemsCacheDirty_ )
178bb02e0acSNicolas Bonnefon regenerateFilteredItemsCache();
179bb02e0acSNicolas Bonnefon
180bb02e0acSNicolas Bonnefon return filteredItemsCache_[ index ].type();
181bb02e0acSNicolas Bonnefon }
182bb02e0acSNicolas Bonnefon }
183bb02e0acSNicolas Bonnefon
184bb02e0acSNicolas Bonnefon // Delegation to our Marks object
185bb02e0acSNicolas Bonnefon
addMark(qint64 line,QChar mark)186bb02e0acSNicolas Bonnefon void LogFilteredData::addMark( qint64 line, QChar mark )
187bb02e0acSNicolas Bonnefon {
188bb02e0acSNicolas Bonnefon if ( ( line >= 0 ) && ( line < sourceLogData_->getNbLine() ) ) {
189ced968a9SNicolas Bonnefon marks_.addMark( line, mark );
190bb02e0acSNicolas Bonnefon maxLengthMarks_ = qMax( maxLengthMarks_,
191bb02e0acSNicolas Bonnefon sourceLogData_->getLineLength( line ) );
192bb02e0acSNicolas Bonnefon filteredItemsCacheDirty_ = true;
193bb02e0acSNicolas Bonnefon }
194bb02e0acSNicolas Bonnefon else
195bb02e0acSNicolas Bonnefon LOG(logERROR) << "LogFilteredData::addMark\
196bb02e0acSNicolas Bonnefon trying to create a mark outside of the file.";
197bb02e0acSNicolas Bonnefon }
198bb02e0acSNicolas Bonnefon
getMark(QChar mark) const199bb02e0acSNicolas Bonnefon qint64 LogFilteredData::getMark( QChar mark ) const
200bb02e0acSNicolas Bonnefon {
201ced968a9SNicolas Bonnefon return marks_.getMark( mark );
202bb02e0acSNicolas Bonnefon }
203bb02e0acSNicolas Bonnefon
isLineMarked(qint64 line) const204bb02e0acSNicolas Bonnefon bool LogFilteredData::isLineMarked( qint64 line ) const
205bb02e0acSNicolas Bonnefon {
206ced968a9SNicolas Bonnefon return marks_.isLineMarked( line );
207bb02e0acSNicolas Bonnefon }
208bb02e0acSNicolas Bonnefon
getMarkAfter(qint64 line) const2098e788202SNicolas Bonnefon qint64 LogFilteredData::getMarkAfter( qint64 line ) const
2108e788202SNicolas Bonnefon {
2118e788202SNicolas Bonnefon qint64 marked_line = -1;
2128e788202SNicolas Bonnefon
2138e788202SNicolas Bonnefon for ( auto i = marks_.begin(); i != marks_.end(); ++i ) {
2148e788202SNicolas Bonnefon if ( i->lineNumber() > line ) {
2158e788202SNicolas Bonnefon marked_line = i->lineNumber();
2168e788202SNicolas Bonnefon break;
2178e788202SNicolas Bonnefon }
2188e788202SNicolas Bonnefon }
2198e788202SNicolas Bonnefon
2208e788202SNicolas Bonnefon return marked_line;
2218e788202SNicolas Bonnefon }
2228e788202SNicolas Bonnefon
getMarkBefore(qint64 line) const2238e788202SNicolas Bonnefon qint64 LogFilteredData::getMarkBefore( qint64 line ) const
2248e788202SNicolas Bonnefon {
2258e788202SNicolas Bonnefon qint64 marked_line = -1;
2268e788202SNicolas Bonnefon
2278e788202SNicolas Bonnefon for ( auto i = marks_.begin(); i != marks_.end(); ++i ) {
2288e788202SNicolas Bonnefon if ( i->lineNumber() >= line ) {
2298e788202SNicolas Bonnefon break;
2308e788202SNicolas Bonnefon }
2318e788202SNicolas Bonnefon marked_line = i->lineNumber();
2328e788202SNicolas Bonnefon }
2338e788202SNicolas Bonnefon
2348e788202SNicolas Bonnefon return marked_line;
2358e788202SNicolas Bonnefon }
2368e788202SNicolas Bonnefon
deleteMark(QChar mark)237bb02e0acSNicolas Bonnefon void LogFilteredData::deleteMark( QChar mark )
238bb02e0acSNicolas Bonnefon {
239ced968a9SNicolas Bonnefon marks_.deleteMark( mark );
240bb02e0acSNicolas Bonnefon filteredItemsCacheDirty_ = true;
241bb02e0acSNicolas Bonnefon
242bb02e0acSNicolas Bonnefon // FIXME: maxLengthMarks_
243bb02e0acSNicolas Bonnefon }
244bb02e0acSNicolas Bonnefon
deleteMark(qint64 line)245bb02e0acSNicolas Bonnefon void LogFilteredData::deleteMark( qint64 line )
246bb02e0acSNicolas Bonnefon {
247ced968a9SNicolas Bonnefon marks_.deleteMark( line );
248bb02e0acSNicolas Bonnefon filteredItemsCacheDirty_ = true;
249bb02e0acSNicolas Bonnefon
250bb02e0acSNicolas Bonnefon // Now update the max length if needed
251bb02e0acSNicolas Bonnefon if ( sourceLogData_->getLineLength( line ) >= maxLengthMarks_ ) {
252bb02e0acSNicolas Bonnefon LOG(logDEBUG) << "deleteMark recalculating longest mark";
253bb02e0acSNicolas Bonnefon maxLengthMarks_ = 0;
254ced968a9SNicolas Bonnefon for ( Marks::const_iterator i = marks_.begin();
255ced968a9SNicolas Bonnefon i != marks_.end(); ++i ) {
256bb02e0acSNicolas Bonnefon LOG(logDEBUG) << "line " << i->lineNumber();
257bb02e0acSNicolas Bonnefon maxLengthMarks_ = qMax( maxLengthMarks_,
258bb02e0acSNicolas Bonnefon sourceLogData_->getLineLength( i->lineNumber() ) );
259bb02e0acSNicolas Bonnefon }
260bb02e0acSNicolas Bonnefon }
261bb02e0acSNicolas Bonnefon }
262bb02e0acSNicolas Bonnefon
clearMarks()263bb02e0acSNicolas Bonnefon void LogFilteredData::clearMarks()
264bb02e0acSNicolas Bonnefon {
265ced968a9SNicolas Bonnefon marks_.clear();
266bb02e0acSNicolas Bonnefon filteredItemsCacheDirty_ = true;
267bb02e0acSNicolas Bonnefon maxLengthMarks_ = 0;
268bb02e0acSNicolas Bonnefon }
269bb02e0acSNicolas Bonnefon
setVisibility(Visibility visi)270bb02e0acSNicolas Bonnefon void LogFilteredData::setVisibility( Visibility visi )
271bb02e0acSNicolas Bonnefon {
272bb02e0acSNicolas Bonnefon visibility_ = visi;
273bb02e0acSNicolas Bonnefon }
274bb02e0acSNicolas Bonnefon
275bb02e0acSNicolas Bonnefon //
276bb02e0acSNicolas Bonnefon // Slots
277bb02e0acSNicolas Bonnefon //
handleSearchProgressed(int nbMatches,int progress,qint64 initial_position)278*c59cadb3SNicolas Bonnefon void LogFilteredData::handleSearchProgressed( int nbMatches, int progress, qint64 initial_position )
279bb02e0acSNicolas Bonnefon {
280bb02e0acSNicolas Bonnefon LOG(logDEBUG) << "LogFilteredData::handleSearchProgressed matches="
281bb02e0acSNicolas Bonnefon << nbMatches << " progress=" << progress;
282bb02e0acSNicolas Bonnefon
283bb02e0acSNicolas Bonnefon // searchDone_ = true;
284ced968a9SNicolas Bonnefon workerThread_.getSearchResult( &maxLength_, &matching_lines_, &nbLinesProcessed_ );
285bb02e0acSNicolas Bonnefon filteredItemsCacheDirty_ = true;
286bb02e0acSNicolas Bonnefon
287*c59cadb3SNicolas Bonnefon emit searchProgressed( nbMatches, progress, initial_position );
288bb02e0acSNicolas Bonnefon }
289bb02e0acSNicolas Bonnefon
findLogDataLine(LineNumber lineNum) const290ced968a9SNicolas Bonnefon LineNumber LogFilteredData::findLogDataLine( LineNumber lineNum ) const
291bb02e0acSNicolas Bonnefon {
2922493b508SNicolas Bonnefon LineNumber line = std::numeric_limits<LineNumber>::max();
293bb02e0acSNicolas Bonnefon if ( visibility_ == MatchesOnly ) {
294ced968a9SNicolas Bonnefon if ( lineNum < matching_lines_.size() ) {
295ced968a9SNicolas Bonnefon line = matching_lines_[lineNum].lineNumber();
296bb02e0acSNicolas Bonnefon }
297bb02e0acSNicolas Bonnefon else {
298bb02e0acSNicolas Bonnefon LOG(logERROR) << "Index too big in LogFilteredData: " << lineNum;
299bb02e0acSNicolas Bonnefon }
300bb02e0acSNicolas Bonnefon }
301bb02e0acSNicolas Bonnefon else if ( visibility_ == MarksOnly ) {
302ced968a9SNicolas Bonnefon if ( lineNum < marks_.size() )
303ced968a9SNicolas Bonnefon line = marks_.getLineMarkedByIndex( lineNum );
304bb02e0acSNicolas Bonnefon else
305bb02e0acSNicolas Bonnefon LOG(logERROR) << "Index too big in LogFilteredData: " << lineNum;
306bb02e0acSNicolas Bonnefon }
307bb02e0acSNicolas Bonnefon else {
308bb02e0acSNicolas Bonnefon // Regenerate the cache if needed
309bb02e0acSNicolas Bonnefon if ( filteredItemsCacheDirty_ )
310bb02e0acSNicolas Bonnefon regenerateFilteredItemsCache();
311bb02e0acSNicolas Bonnefon
312bb02e0acSNicolas Bonnefon if ( lineNum < filteredItemsCache_.size() )
313bb02e0acSNicolas Bonnefon line = filteredItemsCache_[ lineNum ].lineNumber();
314bb02e0acSNicolas Bonnefon else
315bb02e0acSNicolas Bonnefon LOG(logERROR) << "Index too big in LogFilteredData: " << lineNum;
316bb02e0acSNicolas Bonnefon }
317bb02e0acSNicolas Bonnefon
318bb02e0acSNicolas Bonnefon return line;
319bb02e0acSNicolas Bonnefon }
320bb02e0acSNicolas Bonnefon
findFilteredLine(LineNumber lineNum) const3213ff6c941SAnton Filimonov LineNumber LogFilteredData::findFilteredLine( LineNumber lineNum ) const
3223ff6c941SAnton Filimonov {
3233ff6c941SAnton Filimonov LineNumber lineIndex = std::numeric_limits<LineNumber>::max();
3243ff6c941SAnton Filimonov
3253ff6c941SAnton Filimonov if ( visibility_ == MatchesOnly ) {
3263ff6c941SAnton Filimonov lineIndex = lookupLineNumber( matching_lines_.begin(),
3273ff6c941SAnton Filimonov matching_lines_.end(),
3283ff6c941SAnton Filimonov lineNum );
3293ff6c941SAnton Filimonov }
3303ff6c941SAnton Filimonov else if ( visibility_ == MarksOnly ) {
3313ff6c941SAnton Filimonov lineIndex = lookupLineNumber( marks_.begin(),
3323ff6c941SAnton Filimonov marks_.end(),
3333ff6c941SAnton Filimonov lineNum );
3343ff6c941SAnton Filimonov }
3353ff6c941SAnton Filimonov else {
3363ff6c941SAnton Filimonov // Regenerate the cache if needed
3373ff6c941SAnton Filimonov if ( filteredItemsCacheDirty_ ) {
3383ff6c941SAnton Filimonov regenerateFilteredItemsCache();
3393ff6c941SAnton Filimonov }
3403ff6c941SAnton Filimonov
3413ff6c941SAnton Filimonov lineIndex = lookupLineNumber( filteredItemsCache_.begin(),
3423ff6c941SAnton Filimonov filteredItemsCache_.end(),
3433ff6c941SAnton Filimonov lineNum );
3443ff6c941SAnton Filimonov }
3453ff6c941SAnton Filimonov
3463ff6c941SAnton Filimonov return lineIndex;
3473ff6c941SAnton Filimonov }
3483ff6c941SAnton Filimonov
349bb02e0acSNicolas Bonnefon // Implementation of the virtual function.
doGetLineString(qint64 lineNum) const350bb02e0acSNicolas Bonnefon QString LogFilteredData::doGetLineString( qint64 lineNum ) const
351bb02e0acSNicolas Bonnefon {
352bb02e0acSNicolas Bonnefon qint64 line = findLogDataLine( lineNum );
353bb02e0acSNicolas Bonnefon
354bb02e0acSNicolas Bonnefon QString string = sourceLogData_->getLineString( line );
355bb02e0acSNicolas Bonnefon return string;
356bb02e0acSNicolas Bonnefon }
357bb02e0acSNicolas Bonnefon
358bb02e0acSNicolas Bonnefon // Implementation of the virtual function.
doGetExpandedLineString(qint64 lineNum) const359bb02e0acSNicolas Bonnefon QString LogFilteredData::doGetExpandedLineString( qint64 lineNum ) const
360bb02e0acSNicolas Bonnefon {
361bb02e0acSNicolas Bonnefon qint64 line = findLogDataLine( lineNum );
362bb02e0acSNicolas Bonnefon
363bb02e0acSNicolas Bonnefon QString string = sourceLogData_->getExpandedLineString( line );
364bb02e0acSNicolas Bonnefon return string;
365bb02e0acSNicolas Bonnefon }
366bb02e0acSNicolas Bonnefon
367bb02e0acSNicolas Bonnefon // Implementation of the virtual function.
doGetLines(qint64 first_line,int number) const368bb02e0acSNicolas Bonnefon QStringList LogFilteredData::doGetLines( qint64 first_line, int number ) const
369bb02e0acSNicolas Bonnefon {
370bb02e0acSNicolas Bonnefon QStringList list;
371bb02e0acSNicolas Bonnefon
372bb02e0acSNicolas Bonnefon for ( int i = first_line; i < first_line + number; i++ ) {
373bb02e0acSNicolas Bonnefon list.append( doGetLineString( i ) );
374bb02e0acSNicolas Bonnefon }
375bb02e0acSNicolas Bonnefon
376bb02e0acSNicolas Bonnefon return list;
377bb02e0acSNicolas Bonnefon }
378bb02e0acSNicolas Bonnefon
379bb02e0acSNicolas Bonnefon // Implementation of the virtual function.
doGetExpandedLines(qint64 first_line,int number) const380bb02e0acSNicolas Bonnefon QStringList LogFilteredData::doGetExpandedLines( qint64 first_line, int number ) const
381bb02e0acSNicolas Bonnefon {
382bb02e0acSNicolas Bonnefon QStringList list;
383bb02e0acSNicolas Bonnefon
384bb02e0acSNicolas Bonnefon for ( int i = first_line; i < first_line + number; i++ ) {
385bb02e0acSNicolas Bonnefon list.append( doGetExpandedLineString( i ) );
386bb02e0acSNicolas Bonnefon }
387bb02e0acSNicolas Bonnefon
388bb02e0acSNicolas Bonnefon return list;
389bb02e0acSNicolas Bonnefon }
390bb02e0acSNicolas Bonnefon
391bb02e0acSNicolas Bonnefon // Implementation of the virtual function.
doGetNbLine() const392bb02e0acSNicolas Bonnefon qint64 LogFilteredData::doGetNbLine() const
393bb02e0acSNicolas Bonnefon {
394bb02e0acSNicolas Bonnefon qint64 nbLines;
395bb02e0acSNicolas Bonnefon
396bb02e0acSNicolas Bonnefon if ( visibility_ == MatchesOnly )
397ced968a9SNicolas Bonnefon nbLines = matching_lines_.size();
398bb02e0acSNicolas Bonnefon else if ( visibility_ == MarksOnly )
399ced968a9SNicolas Bonnefon nbLines = marks_.size();
400bb02e0acSNicolas Bonnefon else {
401bb02e0acSNicolas Bonnefon // Regenerate the cache if needed (hopefully most of the time
402bb02e0acSNicolas Bonnefon // it won't be necessarily)
403bb02e0acSNicolas Bonnefon if ( filteredItemsCacheDirty_ )
404bb02e0acSNicolas Bonnefon regenerateFilteredItemsCache();
405bb02e0acSNicolas Bonnefon nbLines = filteredItemsCache_.size();
406bb02e0acSNicolas Bonnefon }
407bb02e0acSNicolas Bonnefon
408bb02e0acSNicolas Bonnefon return nbLines;
409bb02e0acSNicolas Bonnefon }
410bb02e0acSNicolas Bonnefon
411bb02e0acSNicolas Bonnefon // Implementation of the virtual function.
doGetMaxLength() const412bb02e0acSNicolas Bonnefon int LogFilteredData::doGetMaxLength() const
413bb02e0acSNicolas Bonnefon {
414bb02e0acSNicolas Bonnefon int max_length;
415bb02e0acSNicolas Bonnefon
416bb02e0acSNicolas Bonnefon if ( visibility_ == MatchesOnly )
417bb02e0acSNicolas Bonnefon max_length = maxLength_;
418bb02e0acSNicolas Bonnefon else if ( visibility_ == MarksOnly )
419bb02e0acSNicolas Bonnefon max_length = maxLengthMarks_;
420bb02e0acSNicolas Bonnefon else
421bb02e0acSNicolas Bonnefon max_length = qMax( maxLength_, maxLengthMarks_ );
422bb02e0acSNicolas Bonnefon
423bb02e0acSNicolas Bonnefon return max_length;
424bb02e0acSNicolas Bonnefon }
425bb02e0acSNicolas Bonnefon
426bb02e0acSNicolas Bonnefon // Implementation of the virtual function.
doGetLineLength(qint64 lineNum) const427bb02e0acSNicolas Bonnefon int LogFilteredData::doGetLineLength( qint64 lineNum ) const
428bb02e0acSNicolas Bonnefon {
429bb02e0acSNicolas Bonnefon qint64 line = findLogDataLine( lineNum );
430bb02e0acSNicolas Bonnefon return sourceLogData_->getExpandedLineString( line ).length();
431bb02e0acSNicolas Bonnefon }
432bb02e0acSNicolas Bonnefon
doSetDisplayEncoding(Encoding encoding)433209000a6SNicolas Bonnefon void LogFilteredData::doSetDisplayEncoding( Encoding encoding )
4345fa25391SNicolas Bonnefon {
435209000a6SNicolas Bonnefon LOG(logDEBUG) << "AbstractLogData::setDisplayEncoding: " << static_cast<int>( encoding );
4365fa25391SNicolas Bonnefon }
4375fa25391SNicolas Bonnefon
doSetMultibyteEncodingOffsets(int,int)438481c483cSSergei Dyshel void LogFilteredData::doSetMultibyteEncodingOffsets( int, int )
4394a4a124eSNicolas Bonnefon {
4404a4a124eSNicolas Bonnefon }
4414a4a124eSNicolas Bonnefon
442bb02e0acSNicolas Bonnefon // TODO: We might be a bit smarter and not regenerate the whole thing when
443bb02e0acSNicolas Bonnefon // e.g. stuff is added at the end of the search.
regenerateFilteredItemsCache() const444bb02e0acSNicolas Bonnefon void LogFilteredData::regenerateFilteredItemsCache() const
445bb02e0acSNicolas Bonnefon {
446bb02e0acSNicolas Bonnefon LOG(logDEBUG) << "regenerateFilteredItemsCache";
447bb02e0acSNicolas Bonnefon
448bb02e0acSNicolas Bonnefon filteredItemsCache_.clear();
449ced968a9SNicolas Bonnefon filteredItemsCache_.reserve( matching_lines_.size() + marks_.size() );
450bb02e0acSNicolas Bonnefon // (it's an overestimate but probably not by much so it's fine)
451bb02e0acSNicolas Bonnefon
452ced968a9SNicolas Bonnefon auto i = matching_lines_.cbegin();
453ced968a9SNicolas Bonnefon Marks::const_iterator j = marks_.begin();
454bb02e0acSNicolas Bonnefon
455ced968a9SNicolas Bonnefon while ( ( i != matching_lines_.cend() ) || ( j != marks_.end() ) ) {
456bb02e0acSNicolas Bonnefon qint64 next_mark =
457ced968a9SNicolas Bonnefon ( j != marks_.end() ) ? j->lineNumber() : std::numeric_limits<qint64>::max();
458bb02e0acSNicolas Bonnefon qint64 next_match =
459ced968a9SNicolas Bonnefon ( i != matching_lines_.cend() ) ? i->lineNumber() : std::numeric_limits<qint64>::max();
460bb02e0acSNicolas Bonnefon // We choose a Mark over a Match if a line is both, just an arbitrary choice really.
461bb02e0acSNicolas Bonnefon if ( next_mark <= next_match ) {
462bb02e0acSNicolas Bonnefon // LOG(logDEBUG) << "Add mark at " << next_mark;
463ced968a9SNicolas Bonnefon filteredItemsCache_.push_back( FilteredItem( next_mark, Mark ) );
464ced968a9SNicolas Bonnefon if ( j != marks_.end() )
465bb02e0acSNicolas Bonnefon ++j;
466ced968a9SNicolas Bonnefon if ( ( next_mark == next_match ) && ( i != matching_lines_.cend() ) )
467bb02e0acSNicolas Bonnefon ++i; // Case when it's both match and mark.
468bb02e0acSNicolas Bonnefon }
469bb02e0acSNicolas Bonnefon else {
470bb02e0acSNicolas Bonnefon // LOG(logDEBUG) << "Add match at " << next_match;
471ced968a9SNicolas Bonnefon filteredItemsCache_.push_back( FilteredItem( next_match, Match ) );
472ced968a9SNicolas Bonnefon if ( i != matching_lines_.cend() )
473bb02e0acSNicolas Bonnefon ++i;
474bb02e0acSNicolas Bonnefon }
475bb02e0acSNicolas Bonnefon }
476bb02e0acSNicolas Bonnefon
477bb02e0acSNicolas Bonnefon filteredItemsCacheDirty_ = false;
478bb02e0acSNicolas Bonnefon
479bb02e0acSNicolas Bonnefon LOG(logDEBUG) << "finished regenerateFilteredItemsCache";
480bb02e0acSNicolas Bonnefon }
481