属性查询是GIS应用不可缺少的重要功能,尤其是在各种业务系统中,根据用户输入相应的查询条件,从属性要素中快速定位到用户感兴趣的要素,为业务应用提供了便利。本文就来聊一聊QGis二次开发中如何实现属性查询功能。
其实这个功能我在写属性表格功能的实现时就提到过相应的参考源码了,只不过当时没有给出具体的实现方案。
功能简介
还是简单描述一下功能的使用。
首先来看看通过属性来筛选属性表,打开属性表,见下图
在左下角分别点击 “Show All Features In Initial Canvas Extent” – “Column Filter”就能看到几个字段列表了。
选择要查询的一个字段,并输入这个字段的可查询的属性信息,如下图。
回车之后,属性表会变成下图这样。
这时候属性表已经查询到“cat”字段为“4”的要素。
留意到左下角的按钮变成了“Advanced Filter (Expression)”,点击这个按钮,就会打开表达式编辑器,也就是下图中的这个窗口。
这里输入相应的查询语句就行了。
源码分析
要实现这个功能,首先还是定位到QGis的属性表功能的源代码上来。
打开 qgsattributetabledialog.cpp 这个文件,找到 filterQueryChanged() 这个方法,代码如下
void QgsAttributeTableDialog::filterQueryChanged( const QString& query )
{
QString str; // 这个是最后完整的查询字符串
if ( mFilterButton->defaultAction() == mActionAdvancedFilter )
{
str = query;
}
else
{
QString fieldName = mFilterButton->defaultAction()->text();
const QgsFields& flds = mLayer->pendingFields();
int fldIndex = mLayer->fieldNameIndex( fieldName );
if ( fldIndex < 0 )
{
return;
}
// 判断属性字段是否为数字
QVariant::Type fldType = flds[fldIndex].type();
bool numeric = ( fldType == QVariant::Int || fldType == QVariant::Double || fldType == QVariant::LongLong );
// 如果属性是字符串,判断应该用“ILIKE”或者“LIKE”
QString sensString = "ILIKE";
if ( mCbxCaseSensitive->isChecked() )
{