qgis / QGIS

QGIS is a free, open source, cross platform (lin/win/mac) geographical information system (GIS)
https://qgis.org
GNU General Public License v2.0
10.65k stars 3.01k forks source link

Default values depending on other fields are not correctly applied when field not part of form made by Drag and Drop Designer #57411

Open mblesius opened 6 months ago

mblesius commented 6 months ago

What is the bug or the crash?

I have a vector layer with two fields: field_a and field_b and I have set up an attribute form using the Drag and Drop Designer. In my case, "field_a" is editable and has no default value. On the other hand, "field_b" is not editable, but has a default value definition in which "field_a" is used, e.g. like title("field_a").

Now, if "field_b" is not part of the attribute form set up using the drag and drop designer, it appears that the default value is not applied when adding or modifying features. In fact, the return value of "field_a" (as used in the default value expression) is always NULL. This does not happen if "field_b" is present in the form.

Steps to reproduce the issue

Download the sample_project.zip

  1. Open the sample project from the attached geopackage
  2. In the TOC select "test_layer_a" and digitize a new feature
  3. For "field_a" type in e.g. "london", hit OK
  4. Select "test_layer_b" repeat the prevvious steps

test_digit_form

Versions

QGIS version 3.36.2-Maidenhead QGIS code revision 6d250527
Qt version 5.15.13
Python version 3.12.3
GDAL/OGR version 3.8.5
PROJ version 9.4.0
EPSG Registry database version v11.004 (2024-02-24)
GEOS version 3.12.1-CAPI-1.18.1
SQLite version 3.45.1
PDAL version 2.6.3
PostgreSQL client version 16.2
SpatiaLite version 5.1.0
QWT version 6.2.0
QScintilla2 version 2.14.1
OS version Windows 11 Version 2009
       

Active Python plugins db_manager | 0.1.20 grassprovider | 2.12.99 MetaSearch | 0.3.6 processing | 2.12.99

Supported QGIS version

New profile

Additional context

No response

signedav commented 6 months ago

I can confirm this bug. The problem is that on adding a feature the default values are evaluated:

On updating a feature, they are updated as well after the form has been edited (on pressing ok)

That's why on this use case the value is evaluated on opening the form on adding new feature (where field_a still is empty, what leads to an empty field_b as well) and on updating the feature, but not - as you expect - on __adding a new feature after it has been edited (on pressing ok).

I see two approaches to fix it:

  1. Update realtime invisible widgets as well
  2. Update the default values after having entered all the values on adding a feature (on presing ok)

The first, is a little bit tricky, since we set the value not in the fields (attributes) but in the widget values (and on saving them we set the widget value to the attribute), and because those invisible fields do not have a widget, it's hard to achieve without rebuilding the whole logic.

The second one needs to be checked out. I'm a little bit afraid of an overkill and performance losses, but I not sure.

A *workaround would be to set the Hidden-Widget. Then it would update the value realtime.

image

(concern to unselect "showlabel" as well)

signedav commented 6 months ago

This would fix it, but really should be checked enough, to be sure that there are no bad effects:

+++ b/src/core/vector/qgsvectorlayer.cpp
@@ -1373,6 +1373,11 @@ bool QgsVectorLayer::addFeature( QgsFeature &feature, Flags )
       success = mJoinBuffer->addFeature( feature );
   }

+  if ( success && !mDefaultValueOnUpdateFields.isEmpty() )
+  {
+    updateDefaultValues( feature.id() );
+  }
+
   return success;
 }
mblesius commented 6 months ago

Thank you @signedav for investigating this!

The workaround you mentioned works fine for doing work in QGIS desktop, but does not work well with the current version of QField. Unfortunately, a "hidden" widget still takes up space in the form, and its label will be displayed regardless of whether "Show Label" is checked or not.

For QField, a container (e.g. a group box) can be used, which is then set to always be hidden:

image

signedav commented 6 months ago

Concerning QField it is well possible that it behaves differently, ain't it working there neither?

It's true that the hidden widget takes space. Not sure if this should be optimized.

Anyway I guess the workaround with the tab you proposed for QField works on QGIS as well, no?

mblesius commented 6 months ago

Concerning QField it is well possible that it behaves differently, ain't it working there neither?

I initially noticed this issue when using QField, and I tested it again and it behaved the same way.

Anyway I guess the workaround with the tab you proposed for QField works on QGIS as well, no?

Yes, this workaround also works for QGIS.