Turn spell tool into multimode spell/wild/regexp
This commit is contained in:
parent
72aca22c7e
commit
1ab0a31c41
@ -1,5 +1,5 @@
|
|||||||
#ifndef lint
|
#ifndef lint
|
||||||
static char rcsid[] = "@(#$Id: guiutils.cpp,v 1.21 2006-09-23 07:39:55 dockes Exp $ (C) 2005 Jean-Francois Dockes";
|
static char rcsid[] = "@(#$Id: guiutils.cpp,v 1.22 2006-10-30 12:59:44 dockes Exp $ (C) 2005 Jean-Francois Dockes";
|
||||||
#endif
|
#endif
|
||||||
/*
|
/*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
@ -173,6 +173,8 @@ void rwSettings(bool writing)
|
|||||||
Num, 100);
|
Num, 100);
|
||||||
SETTING_RW(prefs.sortSpec, "/Recoll/prefs/query/sortSpec",
|
SETTING_RW(prefs.sortSpec, "/Recoll/prefs/query/sortSpec",
|
||||||
Num, 0);
|
Num, 0);
|
||||||
|
SETTING_RW(prefs.termMatchType, "/Recoll/prefs/query/termMatchType",
|
||||||
|
Num, 0);
|
||||||
|
|
||||||
// Ssearch combobox history list
|
// Ssearch combobox history list
|
||||||
if (writing) {
|
if (writing) {
|
||||||
|
|||||||
@ -17,7 +17,7 @@
|
|||||||
#ifndef _GUIUTILS_H_INCLUDED_
|
#ifndef _GUIUTILS_H_INCLUDED_
|
||||||
#define _GUIUTILS_H_INCLUDED_
|
#define _GUIUTILS_H_INCLUDED_
|
||||||
/*
|
/*
|
||||||
* @(#$Id: guiutils.h,v 1.13 2006-09-23 07:39:55 dockes Exp $ (C) 2005 Jean-Francois Dockes
|
* @(#$Id: guiutils.h,v 1.14 2006-10-30 12:59:44 dockes Exp $ (C) 2005 Jean-Francois Dockes
|
||||||
* jean-francois.dockes@wanadoo.fr
|
* jean-francois.dockes@wanadoo.fr
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
@ -91,6 +91,9 @@ class PrefsPack {
|
|||||||
int sortWidth;
|
int sortWidth;
|
||||||
int sortSpec;
|
int sortSpec;
|
||||||
|
|
||||||
|
// Remembered term match mode
|
||||||
|
int termMatchType;
|
||||||
|
|
||||||
PrefsPack() :
|
PrefsPack() :
|
||||||
showicons(true),
|
showicons(true),
|
||||||
respagesize(8),
|
respagesize(8),
|
||||||
@ -99,7 +102,8 @@ class PrefsPack {
|
|||||||
queryBuildAbstract(true),
|
queryBuildAbstract(true),
|
||||||
queryReplaceAbstract(false),
|
queryReplaceAbstract(false),
|
||||||
startWithAdvSearchOpen(false),
|
startWithAdvSearchOpen(false),
|
||||||
startWithSortToolOpen(false)
|
startWithSortToolOpen(false),
|
||||||
|
termMatchType(0)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
#ifndef lint
|
#ifndef lint
|
||||||
static char rcsid[] = "@(#$Id: rclmain_w.cpp,v 1.3 2006-10-15 13:07:45 dockes Exp $ (C) 2005 J.F.Dockes";
|
static char rcsid[] = "@(#$Id: rclmain_w.cpp,v 1.4 2006-10-30 12:59:44 dockes Exp $ (C) 2005 J.F.Dockes";
|
||||||
#endif
|
#endif
|
||||||
/*
|
/*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
@ -83,6 +83,7 @@ void RclMain::init()
|
|||||||
asearchform = 0;
|
asearchform = 0;
|
||||||
sortform = 0;
|
sortform = 0;
|
||||||
uiprefs = 0;
|
uiprefs = 0;
|
||||||
|
spellform = 0;
|
||||||
m_searchId = 0;
|
m_searchId = 0;
|
||||||
// Set the focus to the search terms entry:
|
// Set the focus to the search terms entry:
|
||||||
sSearch->queryText->setFocus();
|
sSearch->queryText->setFocus();
|
||||||
|
|||||||
@ -8,8 +8,8 @@
|
|||||||
<rect>
|
<rect>
|
||||||
<x>0</x>
|
<x>0</x>
|
||||||
<y>0</y>
|
<y>0</y>
|
||||||
<width>0</width>
|
<width>796</width>
|
||||||
<height>0</height>
|
<height>351</height>
|
||||||
</rect>
|
</rect>
|
||||||
</property>
|
</property>
|
||||||
<property name="sizePolicy">
|
<property name="sizePolicy">
|
||||||
@ -27,7 +27,7 @@
|
|||||||
</size>
|
</size>
|
||||||
</property>
|
</property>
|
||||||
<property name="caption">
|
<property name="caption">
|
||||||
<string>Spelling Explorer</string>
|
<string>Term Explorer</string>
|
||||||
</property>
|
</property>
|
||||||
<vbox>
|
<vbox>
|
||||||
<property name="name">
|
<property name="name">
|
||||||
@ -35,7 +35,7 @@
|
|||||||
</property>
|
</property>
|
||||||
<widget class="QLayoutWidget">
|
<widget class="QLayoutWidget">
|
||||||
<property name="name">
|
<property name="name">
|
||||||
<cstring>layout3</cstring>
|
<cstring>layout5</cstring>
|
||||||
</property>
|
</property>
|
||||||
<vbox>
|
<vbox>
|
||||||
<property name="name">
|
<property name="name">
|
||||||
@ -45,97 +45,78 @@
|
|||||||
<property name="name">
|
<property name="name">
|
||||||
<cstring>layout4</cstring>
|
<cstring>layout4</cstring>
|
||||||
</property>
|
</property>
|
||||||
<vbox>
|
<hbox>
|
||||||
<property name="name">
|
<property name="name">
|
||||||
<cstring>unnamed</cstring>
|
<cstring>unnamed</cstring>
|
||||||
</property>
|
</property>
|
||||||
<widget class="QLayoutWidget">
|
<widget class="QLabel">
|
||||||
<property name="name">
|
<property name="name">
|
||||||
<cstring>layout3</cstring>
|
<cstring>Label1</cstring>
|
||||||
|
</property>
|
||||||
|
<property name="frameShape">
|
||||||
|
<enum>NoFrame</enum>
|
||||||
|
</property>
|
||||||
|
<property name="frameShadow">
|
||||||
|
<enum>Plain</enum>
|
||||||
|
</property>
|
||||||
|
<property name="text">
|
||||||
|
<string>Enter word to expand</string>
|
||||||
|
</property>
|
||||||
|
<property name="buddy" stdset="0">
|
||||||
|
<cstring>baseWordLE</cstring>
|
||||||
</property>
|
</property>
|
||||||
<hbox>
|
|
||||||
<property name="name">
|
|
||||||
<cstring>unnamed</cstring>
|
|
||||||
</property>
|
|
||||||
<widget class="QLabel">
|
|
||||||
<property name="name">
|
|
||||||
<cstring>Label1</cstring>
|
|
||||||
</property>
|
|
||||||
<property name="frameShape">
|
|
||||||
<enum>NoFrame</enum>
|
|
||||||
</property>
|
|
||||||
<property name="frameShadow">
|
|
||||||
<enum>Plain</enum>
|
|
||||||
</property>
|
|
||||||
<property name="text">
|
|
||||||
<string>Enter word</string>
|
|
||||||
</property>
|
|
||||||
<property name="buddy" stdset="0">
|
|
||||||
<cstring>baseWordLE</cstring>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
<widget class="QLineEdit">
|
|
||||||
<property name="name">
|
|
||||||
<cstring>baseWordLE</cstring>
|
|
||||||
</property>
|
|
||||||
<property name="minimumSize">
|
|
||||||
<size>
|
|
||||||
<width>200</width>
|
|
||||||
<height>0</height>
|
|
||||||
</size>
|
|
||||||
</property>
|
|
||||||
<property name="frameShape">
|
|
||||||
<enum>LineEditPanel</enum>
|
|
||||||
</property>
|
|
||||||
<property name="frameShadow">
|
|
||||||
<enum>Sunken</enum>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
<widget class="QPushButton">
|
|
||||||
<property name="name">
|
|
||||||
<cstring>expandPB</cstring>
|
|
||||||
</property>
|
|
||||||
<property name="enabled">
|
|
||||||
<bool>false</bool>
|
|
||||||
</property>
|
|
||||||
<property name="text">
|
|
||||||
<string>&Expand </string>
|
|
||||||
</property>
|
|
||||||
<property name="accel">
|
|
||||||
<string>Alt+E</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
<widget class="QPushButton">
|
|
||||||
<property name="name">
|
|
||||||
<cstring>clearPB</cstring>
|
|
||||||
</property>
|
|
||||||
<property name="enabled">
|
|
||||||
<bool>false</bool>
|
|
||||||
</property>
|
|
||||||
<property name="text">
|
|
||||||
<string>&Clear</string>
|
|
||||||
</property>
|
|
||||||
<property name="accel">
|
|
||||||
<string>Alt+C</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
<widget class="QPushButton">
|
|
||||||
<property name="name">
|
|
||||||
<cstring>dismissPB</cstring>
|
|
||||||
</property>
|
|
||||||
<property name="enabled">
|
|
||||||
<bool>true</bool>
|
|
||||||
</property>
|
|
||||||
<property name="text">
|
|
||||||
<string>&Close</string>
|
|
||||||
</property>
|
|
||||||
<property name="accel">
|
|
||||||
<string>Alt+C</string>
|
|
||||||
</property>
|
|
||||||
</widget>
|
|
||||||
</hbox>
|
|
||||||
</widget>
|
</widget>
|
||||||
</vbox>
|
<widget class="QLineEdit">
|
||||||
|
<property name="name">
|
||||||
|
<cstring>baseWordLE</cstring>
|
||||||
|
</property>
|
||||||
|
<property name="minimumSize">
|
||||||
|
<size>
|
||||||
|
<width>200</width>
|
||||||
|
<height>0</height>
|
||||||
|
</size>
|
||||||
|
</property>
|
||||||
|
<property name="frameShape">
|
||||||
|
<enum>LineEditPanel</enum>
|
||||||
|
</property>
|
||||||
|
<property name="frameShadow">
|
||||||
|
<enum>Sunken</enum>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
<widget class="QComboBox">
|
||||||
|
<property name="name">
|
||||||
|
<cstring>expTypeCMB</cstring>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
<widget class="QPushButton">
|
||||||
|
<property name="name">
|
||||||
|
<cstring>expandPB</cstring>
|
||||||
|
</property>
|
||||||
|
<property name="enabled">
|
||||||
|
<bool>false</bool>
|
||||||
|
</property>
|
||||||
|
<property name="text">
|
||||||
|
<string>&Expand </string>
|
||||||
|
</property>
|
||||||
|
<property name="accel">
|
||||||
|
<string>Alt+E</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
<widget class="QPushButton">
|
||||||
|
<property name="name">
|
||||||
|
<cstring>dismissPB</cstring>
|
||||||
|
</property>
|
||||||
|
<property name="enabled">
|
||||||
|
<bool>true</bool>
|
||||||
|
</property>
|
||||||
|
<property name="text">
|
||||||
|
<string>&Close</string>
|
||||||
|
</property>
|
||||||
|
<property name="accel">
|
||||||
|
<string>Alt+C</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</hbox>
|
||||||
</widget>
|
</widget>
|
||||||
<widget class="QTextEdit">
|
<widget class="QTextEdit">
|
||||||
<property name="name">
|
<property name="name">
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
#ifndef lint
|
#ifndef lint
|
||||||
static char rcsid[] = "@(#$Id: spell_w.cpp,v 1.2 2006-10-15 13:07:45 dockes Exp $ (C) 2005 J.F.Dockes";
|
static char rcsid[] = "@(#$Id: spell_w.cpp,v 1.3 2006-10-30 12:59:44 dockes Exp $ (C) 2005 J.F.Dockes";
|
||||||
#endif
|
#endif
|
||||||
/*
|
/*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
@ -30,10 +30,12 @@ static char rcsid[] = "@(#$Id: spell_w.cpp,v 1.2 2006-10-15 13:07:45 dockes Exp
|
|||||||
#include <qlineedit.h>
|
#include <qlineedit.h>
|
||||||
#include <qlayout.h>
|
#include <qlayout.h>
|
||||||
#include <qtooltip.h>
|
#include <qtooltip.h>
|
||||||
|
#include <qcombobox.h>
|
||||||
|
|
||||||
#include "debuglog.h"
|
#include "debuglog.h"
|
||||||
#include "recoll.h"
|
#include "recoll.h"
|
||||||
#include "spell_w.h"
|
#include "spell_w.h"
|
||||||
|
#include "guiutils.h"
|
||||||
|
|
||||||
#ifdef RCL_USE_ASPELL
|
#ifdef RCL_USE_ASPELL
|
||||||
#include "rclaspell.h"
|
#include "rclaspell.h"
|
||||||
@ -41,62 +43,95 @@ static char rcsid[] = "@(#$Id: spell_w.cpp,v 1.2 2006-10-15 13:07:45 dockes Exp
|
|||||||
|
|
||||||
void SpellW::init()
|
void SpellW::init()
|
||||||
{
|
{
|
||||||
|
expTypeCMB->insertItem(tr("Wildcards"));
|
||||||
|
expTypeCMB->insertItem(tr("Regexp"));
|
||||||
|
int maxtyp = 1;
|
||||||
|
#ifdef RCL_USE_ASPELL
|
||||||
|
expTypeCMB->insertItem(tr("Spelling/Phonetic"));
|
||||||
|
maxtyp = 2;
|
||||||
|
#endif
|
||||||
|
int typ = prefs.termMatchType;
|
||||||
|
if (typ < 0 || typ > maxtyp)
|
||||||
|
typ = 0;
|
||||||
|
expTypeCMB->setCurrentItem(typ);
|
||||||
|
|
||||||
// signals and slots connections
|
// signals and slots connections
|
||||||
connect(baseWordLE, SIGNAL(textChanged(const QString&)),
|
connect(baseWordLE, SIGNAL(textChanged(const QString&)),
|
||||||
this, SLOT(wordChanged(const QString&)));
|
this, SLOT(wordChanged(const QString&)));
|
||||||
connect(baseWordLE, SIGNAL(returnPressed()), this, SLOT(doExpand()));
|
connect(baseWordLE, SIGNAL(returnPressed()), this, SLOT(doExpand()));
|
||||||
connect(expandPB, SIGNAL(clicked()), this, SLOT(doExpand()));
|
connect(expandPB, SIGNAL(clicked()), this, SLOT(doExpand()));
|
||||||
connect(clearPB, SIGNAL(clicked()), baseWordLE, SLOT(clear()));
|
|
||||||
connect(dismissPB, SIGNAL(clicked()), this, SLOT(close()));
|
connect(dismissPB, SIGNAL(clicked()), this, SLOT(close()));
|
||||||
connect(suggsTE, SIGNAL(doubleClicked(int, int)),
|
connect(suggsTE, SIGNAL(doubleClicked(int, int)),
|
||||||
this, SLOT(textDoubleClicked(int, int)));
|
this, SLOT(textDoubleClicked(int, int)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Expand term according to current mode */
|
||||||
void SpellW::doExpand()
|
void SpellW::doExpand()
|
||||||
{
|
{
|
||||||
#ifdef RCL_USE_ASPELL
|
if (baseWordLE->text().isEmpty())
|
||||||
|
return;
|
||||||
|
|
||||||
string reason;
|
string reason;
|
||||||
if (!aspell || !maybeOpenDb(reason)) {
|
if (!maybeOpenDb(reason)) {
|
||||||
LOGDEB(("SpellW::doExpand: error aspell %p db: %s\n", aspell,
|
LOGDEB(("SpellW::doExpand: db error: %s\n", reason.c_str()));
|
||||||
reason.c_str()));
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (!baseWordLE->text().isEmpty()) {
|
|
||||||
list<string> suggs;
|
string expr = string((const char *)baseWordLE->text().utf8());
|
||||||
string word = string((const char *)baseWordLE->text().utf8());
|
list<string> suggs;
|
||||||
if (!aspell->suggest(*rcldb, word, suggs, reason)) {
|
prefs.termMatchType = expTypeCMB->currentItem();
|
||||||
|
Rcl::Db::MatchType mt = Rcl::Db::ET_WILD;
|
||||||
|
switch (expTypeCMB->currentItem()) {
|
||||||
|
case 1: mt = Rcl::Db::ET_REGEXP;
|
||||||
|
/* FALLTHROUGH */
|
||||||
|
case 0:
|
||||||
|
if (!rcldb->termMatch(mt, expr, suggs, prefs.queryStemLang.ascii(),
|
||||||
|
200)) {
|
||||||
|
LOGERR(("SpellW::doExpand:rcldb::termMatch failed\n"));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
#ifdef RCL_USE_ASPELL
|
||||||
|
case 2: {
|
||||||
|
if (!aspell) {
|
||||||
|
LOGDEB(("SpellW::doExpand: aspell init error\n"));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!aspell->suggest(*rcldb, expr, suggs, reason)) {
|
||||||
LOGERR(("SpellW::doExpand:suggest failed: %s\n", reason.c_str()));
|
LOGERR(("SpellW::doExpand:suggest failed: %s\n", reason.c_str()));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
suggsTE->clear();
|
return;
|
||||||
if (suggs.empty()) {
|
|
||||||
suggsTE->append(tr("No spelling expansion found"));
|
|
||||||
} else {
|
|
||||||
for (list<string>::iterator it = suggs.begin();
|
|
||||||
it != suggs.end(); it++) {
|
|
||||||
suggsTE->append(QString::fromUtf8(it->c_str()));
|
|
||||||
}
|
|
||||||
suggsTE->setCursorPosition(0,0);
|
|
||||||
suggsTE->ensureCursorVisible();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
suggsTE->clear();
|
||||||
|
if (suggs.empty()) {
|
||||||
|
suggsTE->append(tr("No spelling expansion found"));
|
||||||
|
} else {
|
||||||
|
for (list<string>::iterator it = suggs.begin();
|
||||||
|
it != suggs.end(); it++) {
|
||||||
|
suggsTE->append(QString::fromUtf8(it->c_str()));
|
||||||
|
}
|
||||||
|
suggsTE->setCursorPosition(0,0);
|
||||||
|
suggsTE->ensureCursorVisible();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void SpellW::wordChanged(const QString &text)
|
void SpellW::wordChanged(const QString &text)
|
||||||
{
|
{
|
||||||
if (text.isEmpty()) {
|
if (text.isEmpty()) {
|
||||||
expandPB->setEnabled(false);
|
expandPB->setEnabled(false);
|
||||||
clearPB->setEnabled(false);
|
|
||||||
suggsTE->clear();
|
suggsTE->clear();
|
||||||
} else {
|
} else {
|
||||||
expandPB->setEnabled(true);
|
expandPB->setEnabled(true);
|
||||||
clearPB->setEnabled(true);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void SpellW::textDoubleClicked(int, int)
|
void SpellW::textDoubleClicked(int para, int)
|
||||||
{
|
{
|
||||||
|
suggsTE->setSelection(para, 0, para+1, 0);
|
||||||
if (suggsTE->hasSelectedText())
|
if (suggsTE->hasSelectedText())
|
||||||
emit(wordSelect(suggsTE->selectedText()));
|
emit(wordSelect(suggsTE->selectedText()));
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
#ifndef lint
|
#ifndef lint
|
||||||
static char rcsid[] = "@(#$Id: ssearch_w.cpp,v 1.8 2006-10-24 11:42:13 dockes Exp $ (C) 2006 J.F.Dockes";
|
static char rcsid[] = "@(#$Id: ssearch_w.cpp,v 1.9 2006-10-30 12:59:44 dockes Exp $ (C) 2006 J.F.Dockes";
|
||||||
#endif
|
#endif
|
||||||
/*
|
/*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
@ -158,13 +158,16 @@ void SSearch::completion()
|
|||||||
QApplication::beep();
|
QApplication::beep();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
string s = txt.substr(cs);
|
string s = txt.substr(cs) + "*";
|
||||||
LOGDEB(("Completing: [%s]\n", s.c_str()));
|
LOGDEB(("Completing: [%s]\n", s.c_str()));
|
||||||
|
|
||||||
// Query database
|
// Query database
|
||||||
const int max = 100;
|
const int max = 100;
|
||||||
list<string> strs = rcldb->completions(s, prefs.queryStemLang.ascii(),max);
|
list<string> strs;
|
||||||
if (strs.size() == 0) {
|
|
||||||
|
if (!rcldb->termMatch(Rcl::Db::ET_WILD, s, strs,
|
||||||
|
prefs.queryStemLang.ascii(),max)
|
||||||
|
|| strs.size() == 0) {
|
||||||
QApplication::beep();
|
QApplication::beep();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
#ifndef lint
|
#ifndef lint
|
||||||
static char rcsid[] = "@(#$Id: rcldb.cpp,v 1.84 2006-10-25 10:52:02 dockes Exp $ (C) 2004 J.F.Dockes";
|
static char rcsid[] = "@(#$Id: rcldb.cpp,v 1.85 2006-10-30 12:59:44 dockes Exp $ (C) 2004 J.F.Dockes";
|
||||||
#endif
|
#endif
|
||||||
/*
|
/*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
@ -21,6 +21,7 @@ static char rcsid[] = "@(#$Id: rcldb.cpp,v 1.84 2006-10-25 10:52:02 dockes Exp $
|
|||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
#include <fnmatch.h>
|
#include <fnmatch.h>
|
||||||
|
#include <regex.h>
|
||||||
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <string>
|
#include <string>
|
||||||
@ -1173,20 +1174,63 @@ bool Db::setQuery(AdvSearchData &sdata, int opts, const string& stemlang)
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
list<string> Db::completions(const string &root, const string &lang, int max)
|
// Characters that can begin a wildcard or regexp expression. We use skipto
|
||||||
|
// to begin the allterms search with terms that begin with the portion of
|
||||||
|
// the input string prior to these chars.
|
||||||
|
const string wildSpecChars = "*?[";
|
||||||
|
const string regSpecChars = "(.[{^";
|
||||||
|
|
||||||
|
// Find all index terms that match a wildcard or regular expression
|
||||||
|
bool Db::termMatch(MatchType typ, const string &root, list<string>& res,
|
||||||
|
const string &lang, int max)
|
||||||
{
|
{
|
||||||
Xapian::Database db;
|
|
||||||
list<string> res;
|
|
||||||
if (!m_ndb || !m_ndb->m_isopen)
|
if (!m_ndb || !m_ndb->m_isopen)
|
||||||
return res;
|
return false;
|
||||||
|
Xapian::Database db = m_ndb->m_iswritable ? m_ndb->wdb: m_ndb->db;
|
||||||
|
res.clear();
|
||||||
|
// Get rid of capitals and accents
|
||||||
string droot;
|
string droot;
|
||||||
dumb_string(root, droot);
|
dumb_string(root, droot);
|
||||||
db = m_ndb->m_iswritable ? m_ndb->wdb: m_ndb->db;
|
string nochars = typ == ET_WILD ? wildSpecChars : regSpecChars;
|
||||||
|
|
||||||
|
regex_t reg;
|
||||||
|
int errcode;
|
||||||
|
if (typ == ET_REGEXP && (errcode=regcomp(®, droot.c_str(), 0))) {
|
||||||
|
char errbuf[200];
|
||||||
|
regerror(errcode, ®, errbuf, 199);
|
||||||
|
LOGERR(("termMatch: regcomp failed: %s\n", errbuf));
|
||||||
|
res.push_back(errbuf);
|
||||||
|
regfree(®);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Find the initial section before any special char
|
||||||
|
string::size_type es = droot.find_first_of(nochars);
|
||||||
|
string is;
|
||||||
|
switch (es) {
|
||||||
|
case string::npos: is = droot;break;
|
||||||
|
case 0: break;
|
||||||
|
default: is = droot.substr(0, es);break;
|
||||||
|
}
|
||||||
|
LOGDEB(("termMatch: initsec: [%s]\n", is.c_str()));
|
||||||
|
|
||||||
Xapian::TermIterator it = db.allterms_begin();
|
Xapian::TermIterator it = db.allterms_begin();
|
||||||
it.skip_to(droot.c_str());
|
if (!is.empty())
|
||||||
|
it.skip_to(is.c_str());
|
||||||
for (int n = 0;it != db.allterms_end(); it++) {
|
for (int n = 0;it != db.allterms_end(); it++) {
|
||||||
if ((*it).find(droot) != 0)
|
// If we're beyond the terms matching the initial string, end
|
||||||
|
if (!is.empty() && (*it).find(is) != 0)
|
||||||
break;
|
break;
|
||||||
|
// Don't match special internal terms beginning with uppercase ascii
|
||||||
|
if ((*it).at(0) >= 'A' && (*it).at(0) <= 'Z')
|
||||||
|
continue;
|
||||||
|
if (typ == ET_WILD) {
|
||||||
|
if (fnmatch(droot.c_str(), (*it).c_str(), 0) == FNM_NOMATCH)
|
||||||
|
continue;
|
||||||
|
} else {
|
||||||
|
if (regexec(®, (*it).c_str(), 0, 0, 0))
|
||||||
|
continue;
|
||||||
|
}
|
||||||
if (lang.empty()) {
|
if (lang.empty()) {
|
||||||
res.push_back(*it);
|
res.push_back(*it);
|
||||||
++n;
|
++n;
|
||||||
@ -1205,7 +1249,10 @@ list<string> Db::completions(const string &root, const string &lang, int max)
|
|||||||
}
|
}
|
||||||
res.sort();
|
res.sort();
|
||||||
res.unique();
|
res.unique();
|
||||||
return res;
|
if (typ == ET_REGEXP) {
|
||||||
|
regfree(®);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Term list walking. */
|
/** Term list walking. */
|
||||||
|
|||||||
@ -16,7 +16,7 @@
|
|||||||
*/
|
*/
|
||||||
#ifndef _DB_H_INCLUDED_
|
#ifndef _DB_H_INCLUDED_
|
||||||
#define _DB_H_INCLUDED_
|
#define _DB_H_INCLUDED_
|
||||||
/* @(#$Id: rcldb.h,v 1.39 2006-10-24 09:28:31 dockes Exp $ (C) 2004 J.F.Dockes */
|
/* @(#$Id: rcldb.h,v 1.40 2006-10-30 12:59:44 dockes Exp $ (C) 2004 J.F.Dockes */
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <list>
|
#include <list>
|
||||||
@ -160,9 +160,12 @@ class Db {
|
|||||||
bool getQueryTerms(list<string>& terms);
|
bool getQueryTerms(list<string>& terms);
|
||||||
bool getMatchTerms(const Doc& doc, list<string>& terms);
|
bool getMatchTerms(const Doc& doc, list<string>& terms);
|
||||||
|
|
||||||
// Return a list of database terms that begin with the input string
|
/** Return a list of index terms that match the input string
|
||||||
// Stem expansion is performed if lang is not empty
|
* Expansion is performed either with either wildcard or regexp processing
|
||||||
list<string> completions(const string &s, const string &lang, int max=20);
|
* Stem expansion is performed if lang is not empty */
|
||||||
|
enum MatchType {ET_WILD, ET_REGEXP};
|
||||||
|
bool termMatch(MatchType typ, const string &s, list<string>& result,
|
||||||
|
const string &lang, int max=20);
|
||||||
|
|
||||||
/** Add extra database for querying */
|
/** Add extra database for querying */
|
||||||
bool addQueryDb(const string &dir);
|
bool addQueryDb(const string &dir);
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user