connect(ui->toolButtonSelectProject, SIGNAL(clicked()), this,
SLOT(selectDir()));
connect(ui->pushButtonOpen, SIGNAL(clicked()), this, SLOT(open()));
- connect(ui->pushButtonOpenLastFile, SIGNAL(clicked()), this,
- SLOT(openLastFile()));
- connect(ui->pushButtonOpenLastProject, SIGNAL(clicked()), this,
- SLOT(openLastProject()));
- connect(ui->lineEditFilterLastFile, SIGNAL(textChanged(QString))), this, SLOT(
- textChanged(QString));
+ connect(ui->lineEditFilterLastFile, SIGNAL(textChanged(QString)), this,
+ SLOT(textChangedFilterFiles(QString)));
+ connect(ui->tableWidgetFiles, SIGNAL(cellEntered(int,int)), this,
+ SLOT(cellEnteredFiles(int, int)));
+ connect(ui->tableWidgetProjects, SIGNAL(cellEntered(int,int)), this,
+ SLOT(cellEnteredProjects(int, int)));
Workspace* workspace = mainWindow->workspace();
buildTableInfo(workspace, Workspace::KEY_HISTORY_FILES, true, m_files);
buildTableInfo(workspace, Workspace::KEY_HISTORY_PROJECTS, false,
ProjectSelection::~ProjectSelection() {
delete ui;
}
-void ProjectSelection::textChangedFilterFiles(const QString& text) {
-
+/**
+ * Handles the event cellEntered for the last opened files.
+ *
+ * @param row the row of the entered cell
+ * @param col the column of the entered cell
+ */
+void ProjectSelection::cellEnteredFiles(int row, int col) {
+ ReUseParameter(col);
+ QString file = fileOfTable(ui->tableWidgetFiles, row);
+ ui->lineEditOpen->setText(file);
}
-void ProjectSelection::textChangedFilterProjects(const QString& text) {
+/**
+ * Handles the event cellEntered for the last opened projects.
+ *
+ * @param row the row of the entered cell
+ * @param col the column of the entered cell
+ */
+void ProjectSelection::cellEnteredProjects(int row, int col) {
+ ReUseParameter(col);
+ QString file = fileOfTable(ui->tableWidgetProjects, row);
+ ui->lineEditOpen->setText(file);
}
/**
* @param lines the full table info
* @param table OUT: will be filled with all lines matching the filter
*/
-void ProjectSelection::buildTable(const QString& filter, QStringList& lines,
- QTableWidget* table) {
+void ProjectSelection::buildTable(const QString& filter,
+ const QStringList& lines, QTableWidget* table) {
QStringList::const_iterator it;
int rowCount = 0;
+ ReMatcher matcher(filter, Qt::CaseInsensitive, true);
for (it = lines.cbegin(); it != lines.cend(); ++it) {
- bool matches = filter.isEmpty();
- if (!matches) {
- //@ToDo: coding
- if (filter.startsWith("*")) {
-
- } else {
-
- }
- }
- if (matches)
+ if (matcher.matches(*it))
rowCount++;
}
table->setRowCount(rowCount);
int row = -1;
for (it = lines.cbegin(); it != lines.cend(); ++it) {
- bool matches = filter.isEmpty();
- if (!matches) {
- //@ToDo: coding
- if (filter.startsWith("*")) {
-
- } else {
-
- }
- }
- if (matches) {
+ if (matcher.matches(*it)) {
row++;
QStringList cols = it->split('\t');
for (int col = 0; col < cols.size(); col++) {
dialog.exec();
}
+/**
+ * Extracts the full filename of a given table.
+ *
+ * The node is the first column, the path the last.
+ *
+ * @param table the table from which the filename is taken
+ * @param row the row where the filename is
+ * @return the full name of the file in the given row
+ */
+QString ProjectSelection::fileOfTable(QTableWidget* table, int row) {
+ int colPath = table->columnCount() - 1;
+ QString file = table->item(row, colPath)->text() + OS_SEPARATOR_STR
+ + table->item(row, 0)->text();
+ return file;
+}
/**
* Opens a file or a directory (project directory).
*/
}
}
-/**
- * Opens the selected recently opened file.
- */
-void ProjectSelection::openLastFile() {
- openSelectedItem(ui->tableWidgetFiles);
-}
-
-/**
- * Opens the selected recently opened project (project directory).
- */
-void ProjectSelection::openLastProject() {
- openSelectedItem(ui->tableWidgetProjects);
-}
-
-QString ProjectSelection::openSelectedItem(QTableWidget* table) {
- int row = max(0, table->currentRow());
- if (row < table->rowCount()) {
- QString file;
- int colPath = table->columnCount() - 1;
- file = table->item(row, colPath)->text() + OS_SEPARATOR_STR
- + table->item(row, 0)->text();
- ui->lineEditOpen->setText(file);
- open();
- }
-}
/**
* Selects a directory (project directory) with an open dialog.
*/
}
}
+/**
+ * Handles the filter text change for a given table.
+ *
+ * @param text the filter text
+ * @param table the table which will be filled
+ * @param lines the full (unfiltered) table info
+ */
+void ProjectSelection::textChanged(const QString& text, QTableWidget* table,
+ const QStringList& lines) {
+ buildTable(text, lines, table);
+ if (table->rowCount() > 0) {
+ QString file = fileOfTable(table, 0);
+ ui->lineEditOpen->setText(file);
+ }
+}
+
+/**
+ * Handles the event "text changed" of the last opened files.
+ *
+ * @param text the new text
+ */
+void ProjectSelection::textChangedFilterFiles(const QString& text) {
+ textChanged(text, ui->tableWidgetFiles, m_files);
+}
+
+/**
+ * Handles the event "text changed" of the last opened projects.
+ *
+ * @param text the new text
+ */
+void ProjectSelection::textChangedFilterProjects(const QString& text) {
+ textChanged(text, ui->tableWidgetProjects, m_projects);
+}
public slots:
void open();
- void openLastFile();
- void openLastProject();
void selectDir();
void selectFile();
protected:
- void buildTable(const QString& filter, QStringList& lines,
+ void buildTable(const QString& filter, const QStringList& lines,
QTableWidget* table);
void buildTableInfo(ReSettings* settings, const char* key, bool withDate,
QStringList& tableContent);
- QString openSelectedItem(QTableWidget* table);
+ QString fileOfTable(QTableWidget* table, int row);
+ void textChanged(const QString& text, QTableWidget* table,
+ const QStringList& lines);protected slots:
+ void cellEnteredFiles(int row, int col);
+ void cellEnteredProjects(int row, int col);
void textChangedFilterFiles(const QString& text);
- void textChangedFilterProjecs(const QString& text);
+ void textChangedFilterProjects(const QString& text);
private:
void error(const QString& message);
private:
<item>
<widget class="QTableWidget" name="tableWidgetFiles">
<property name="mouseTracking">
- <bool>false</bool>
+ <bool>true</bool>
</property>
<property name="editTriggers">
<set>QAbstractItemView::NoEditTriggers</set>
</widget>
</item>
<item>
- <layout class="QHBoxLayout" name="horizontalLayout_5" stretch="0,0,0">
- <item>
- <spacer name="horizontalSpacer_4">
- <property name="orientation">
- <enum>Qt::Horizontal</enum>
- </property>
- <property name="sizeHint" stdset="0">
- <size>
- <width>40</width>
- <height>20</height>
- </size>
- </property>
- </spacer>
- </item>
- <item>
- <widget class="QPushButton" name="pushButtonOpenLastFile">
- <property name="toolTip">
- <string>Opens the selected last opened file (Control-F)</string>
- </property>
- <property name="text">
- <string>Open File</string>
- </property>
- <property name="shortcut">
- <string>Ctrl+F</string>
- </property>
- </widget>
- </item>
- <item>
- <spacer name="horizontalSpacer_5">
- <property name="orientation">
- <enum>Qt::Horizontal</enum>
- </property>
- <property name="sizeHint" stdset="0">
- <size>
- <width>40</width>
- <height>20</height>
- </size>
- </property>
- </spacer>
- </item>
- </layout>
+ <layout class="QHBoxLayout" name="horizontalLayout_5" stretch=""/>
</item>
</layout>
</widget>
</item>
<item>
<widget class="QTableWidget" name="tableWidgetProjects">
+ <property name="mouseTracking">
+ <bool>true</bool>
+ </property>
<property name="columnCount">
<number>2</number>
</property>
</widget>
</item>
<item>
- <layout class="QHBoxLayout" name="horizontalLayout_7">
- <item>
- <spacer name="horizontalSpacer_6">
- <property name="orientation">
- <enum>Qt::Horizontal</enum>
- </property>
- <property name="sizeHint" stdset="0">
- <size>
- <width>40</width>
- <height>20</height>
- </size>
- </property>
- </spacer>
- </item>
- <item>
- <widget class="QPushButton" name="pushButtonOpenLastProject">
- <property name="toolTip">
- <string>Opens the selected last opened project (Control-P)</string>
- </property>
- <property name="text">
- <string>Open Project</string>
- </property>
- <property name="shortcut">
- <string>Ctrl+P</string>
- </property>
- </widget>
- </item>
- <item>
- <spacer name="horizontalSpacer_7">
- <property name="orientation">
- <enum>Qt::Horizontal</enum>
- </property>
- <property name="sizeHint" stdset="0">
- <size>
- <width>40</width>
- <height>20</height>
- </size>
- </property>
- </spacer>
- </item>
- </layout>
+ <layout class="QHBoxLayout" name="horizontalLayout_7"/>
</item>
</layout>
</widget>
* <code>false<code>: the pattern can start anywhere in the string<br>
*/
-ReMatcher::ReMatcher(const QString& pattern, bool anchored) :
- m_needles(pattern.split(QChar('*'))),
+ReMatcher::ReMatcher(const QString& pattern, Qt::CaseSensitivity caseSensivity,
+ bool anchored) :
+ m_needles(),
m_restLengths(),
- m_anchored(anchored) {
- for (int ix = 0; ix < m_needles.size(); ix++) {
- m_restLengths.append(0);
- }
- int sum = 0;
- for (int ix = m_needles.size() - 1; ix >= 0; ix--) {
- int size = m_needles.at(ix).size();
- m_restLengths.append(size + sum);
- sum += size;
- }
-}
-
-/**
- * Destructor.
- */
-ReMatcher::~ReMatcher() {
+ m_anchored(anchored),
+ m_caseSensivitiy(caseSensivity) {
+ setPattern(pattern);
}
/**
* @return <code>true</code>: the pattern matches
*/
bool ReMatcher::matches(const QString& text) {
- bool found = false;
- if (m_anchored)
- found = matches(text, 0, 0);
- else {
- found = text.startsWith(m_needles.at(0));
- if (found && m_needles.size() > 1)
- found = matches(text, m_needles.at(0).length(), 1);
+ bool found = m_needles.size() == 0;
+ if (!found) {
+ found =
+ m_anchored ?
+ text.startsWith(m_needles.at(0), m_caseSensivitiy) : true;
+ if (found) {
+ int startIx = m_anchored ? 1 : 0;
+ int textIndex = m_anchored ? m_needles.at(0).length() : 0;
+ for (int ix = startIx; found && ix < m_needles.size(); ix++) {
+ found = text.size() - textIndex >= m_restLengths.at(ix);
+ if (found)
+ found = (textIndex = text.indexOf(m_needles.at(ix),
+ textIndex, m_caseSensivitiy)) >= 0;
+ }
+ }
}
return found;
}
/**
- * Recursive matching test.
+ * Sets the search pattern.
*
- * @param text text to inspect
- * @param textIndex the first index in <code>text</code> to inspect
- * @param needleIndex the index of the pattern part to test
- * @return <code>true</code>: the needles from the given index
- * up to the last index matches
+ * @param pattern the search pattern, with wildcards '*' (any string)
*/
-bool ReMatcher::matches(const QString& text, int textIndex, int needleIndex) {
- int ix = textIndex;
- QString needle = m_needles.at(needleIndex);
- bool found = text.size() - textIndex >= m_restLengths.at(needleIndex);
- while (!found && (ix = text.indexOf(needle, textIndex)) >= 0) {
- textIndex = ix;
- if (needleIndex >= m_needles.size() - 1)
- found = true;
+void ReMatcher::setPattern(const QString& pattern) {
+ m_needles = pattern.split('*');
+ // Eliminate empty entries:
+ for (int ix = m_needles.size() - 1; ix >= 0; ix--) {
+ if (m_needles.at(ix).length() == 0)
+ m_needles.removeAt(ix);
else
- found = matches(text, ix + needle.length(), needleIndex);
+ m_restLengths.append(0);
}
- return found;
+ int sum = 0;
+ for (int ix = m_needles.size() - 1; ix >= 0; ix--) {
+ int size = m_needles.at(ix).size();
+ m_restLengths.append(size + sum);
+ sum += size;
+ }
+
}
+
class ReMatcher {
public:
- ReMatcher(const QString& pattern, bool anchored = false);
- virtual ~ReMatcher();
+ ReMatcher(const QString& pattern, Qt::CaseSensitivity caseSensitivty =
+ Qt::CaseSensitive, bool anchored = false);
public:
- virtual bool matches(const QString& text);
-protected:
- bool matches(const QString& text, int textIndex, int needleIndex);
+ bool matches(const QString& text);
+ void setPattern(const QString& pattern);
protected:
QStringList m_needles;
// m_restLengths[ix] = sum(m_needles[ix..last].size()
QList<int> m_restLengths;
bool m_anchored;
+ Qt::CaseSensitivity m_caseSensivitiy;
};
#endif // RPLQSTRING_HPP
checkEqu(QTime(1, 2, 9), time);
}
void testReMatcher() {
- ReMatcher m1("a*b*c", true);
+ ReMatcher m1("a*b*c", Qt::CaseSensitive, true);
checkT(m1.matches("a b c d"));
checkT(m1.matches("abc d"));
- checkF(m1.matches("ababc"));
- ReMatcher m2("a*b*c", false);
+ checkT(m1.matches("ababc"));
+ checkT(m1.matches("abc"));
+ checkF(m1.matches("aBc"));
+ ReMatcher m2("a*b*c", Qt::CaseSensitive, false);
checkT(m2.matches("a b c d"));
checkT(m2.matches("ababc"));
checkT(m2.matches("a b a b c"));
+ checkT(m2.matches(" abc"));
+ checkF(m2.matches(" ab"));
+
+ ReMatcher m3("a**B*C", Qt::CaseInsensitive, true);
+ checkT(m3.matches("a b c d"));
+ checkT(m3.matches("abc d"));
+ checkT(m3.matches("ababc"));
+ checkT(m3.matches("abc"));
+
+ ReMatcher m4("A*B*c", Qt::CaseInsensitive, false);
+ checkT(m4.matches("a b c d"));
+ checkT(m4.matches("ababc"));
+ checkT(m4.matches("a b a b c"));
+ checkT(m4.matches(" abc"));
+ checkF(m4.matches(" ab"));
+
+ m4.setPattern("*");
+ checkT(m4.matches("x"));
+ m4.setPattern("");
+ checkT(m4.matches("any"));
}
virtual void run(void) {