RNA: add RNA_collection_is_empty & RNA_property_collection_is_empty

Some collections needed to be iterated over to count their length.
Provide a function to check if the collection is empty to avoid this.
This commit is contained in:
Campbell Barton 2022-02-15 20:07:54 +11:00
parent 4637e83990
commit 07ed869b94
7 changed files with 36 additions and 14 deletions

View File

@ -577,7 +577,7 @@ static bool curve_draw_init(bContext *C, wmOperator *op, bool is_invoke)
/* Using an empty stroke complicates logic later,
* it's simplest to disallow early on (see: T94085). */
if (RNA_collection_length(op->ptr, "stroke") == 0) {
if (RNA_collection_is_empty(op->ptr, "stroke")) {
MEM_freeN(cdd);
BKE_report(op->reports, RPT_ERROR, "The \"stroke\" cannot be empty");
return false;

View File

@ -186,7 +186,7 @@ static int open_exec(bContext *C, wmOperator *op)
MovieClip *clip = NULL;
char str[FILE_MAX];
if (RNA_collection_length(op->ptr, "files")) {
if (!RNA_collection_is_empty(op->ptr, "files")) {
PointerRNA fileptr;
PropertyRNA *prop;
char dir_only[FILE_MAX], file_only[FILE_MAX];

View File

@ -747,7 +747,8 @@ static int sequencer_add_movie_strip_invoke(bContext *C,
RNA_enum_set(op->ptr, "fit_method", SEQ_tool_settings_fit_method_get(scene));
/* This is for drag and drop. */
if ((RNA_struct_property_is_set(op->ptr, "files") && RNA_collection_length(op->ptr, "files")) ||
if ((RNA_struct_property_is_set(op->ptr, "files") &&
!RNA_collection_is_empty(op->ptr, "files")) ||
RNA_struct_property_is_set(op->ptr, "filepath")) {
sequencer_generic_invoke_xy__internal(C, op, SEQPROP_NOPATHS, SEQ_TYPE_MOVIE);
return sequencer_add_movie_strip_exec(C, op);
@ -901,7 +902,8 @@ static int sequencer_add_sound_strip_invoke(bContext *C,
const wmEvent *UNUSED(event))
{
/* This is for drag and drop. */
if ((RNA_struct_property_is_set(op->ptr, "files") && RNA_collection_length(op->ptr, "files")) ||
if ((RNA_struct_property_is_set(op->ptr, "files") &&
!RNA_collection_is_empty(op->ptr, "files")) ||
RNA_struct_property_is_set(op->ptr, "filepath")) {
sequencer_generic_invoke_xy__internal(C, op, SEQPROP_NOPATHS, SEQ_TYPE_SOUND_RAM);
return sequencer_add_sound_strip_exec(C, op);
@ -1094,7 +1096,7 @@ static int sequencer_add_image_strip_invoke(bContext *C,
RNA_enum_set(op->ptr, "fit_method", SEQ_tool_settings_fit_method_get(scene));
/* Name set already by drag and drop. */
if (RNA_struct_property_is_set(op->ptr, "files") && RNA_collection_length(op->ptr, "files")) {
if (RNA_struct_property_is_set(op->ptr, "files") && !RNA_collection_is_empty(op->ptr, "files")) {
sequencer_generic_invoke_xy__internal(
C, op, SEQPROP_ENDFRAME | SEQPROP_NOPATHS, SEQ_TYPE_IMAGE);
return sequencer_add_image_strip_exec(C, op);

View File

@ -1117,6 +1117,11 @@ void RNA_property_collection_next(CollectionPropertyIterator *iter);
void RNA_property_collection_skip(CollectionPropertyIterator *iter, int num);
void RNA_property_collection_end(CollectionPropertyIterator *iter);
int RNA_property_collection_length(PointerRNA *ptr, PropertyRNA *prop);
/**
* Return true when `RNA_property_collection_length(ptr, prop) == 0`,
* without having to iterate over items in the collection (needed for some kinds of collections).
*/
bool RNA_property_collection_is_empty(PointerRNA *ptr, PropertyRNA *prop);
int RNA_property_collection_lookup_index(PointerRNA *ptr, PropertyRNA *prop, PointerRNA *t_ptr);
int RNA_property_collection_lookup_int(PointerRNA *ptr,
PropertyRNA *prop,
@ -1445,6 +1450,7 @@ void RNA_pointer_add(PointerRNA *ptr, const char *name);
void RNA_collection_begin(PointerRNA *ptr, const char *name, CollectionPropertyIterator *iter);
int RNA_collection_length(PointerRNA *ptr, const char *name);
bool RNA_collection_is_empty(PointerRNA *ptr, const char *name);
void RNA_collection_add(PointerRNA *ptr, const char *name, PointerRNA *r_value);
void RNA_collection_clear(PointerRNA *ptr, const char *name);

View File

@ -3753,6 +3753,16 @@ int RNA_property_collection_length(PointerRNA *ptr, PropertyRNA *prop)
return length;
}
bool RNA_property_collection_is_empty(PointerRNA *ptr, PropertyRNA *prop)
{
BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
CollectionPropertyIterator iter;
RNA_property_collection_begin(ptr, prop, &iter);
bool test = iter.valid;
RNA_property_collection_end(&iter);
return !test;
}
/* This helper checks whether given collection property itself is editable (we only currently
* support a limited set of operations, insertion of new items, and re-ordering of those new items
* exclusively). */
@ -6417,6 +6427,17 @@ int RNA_collection_length(PointerRNA *ptr, const char *name)
return 0;
}
bool RNA_collection_is_empty(PointerRNA *ptr, const char *name)
{
PropertyRNA *prop = RNA_struct_find_property(ptr, name);
if (prop) {
return RNA_property_collection_is_empty(ptr, prop);
}
printf("%s: %s.%s not found.\n", __func__, ptr->type->identifier, name);
return false;
}
bool RNA_property_is_set_ex(PointerRNA *ptr, PropertyRNA *prop, bool use_ghost)
{
prop = rna_ensure_property(prop);

View File

@ -23,7 +23,7 @@ static void node_shader_buts_vertex_color(uiLayout *layout, bContext *C, Pointer
PointerRNA dataptr = RNA_pointer_get(&obptr, "data");
if (U.experimental.use_sculpt_vertex_colors &&
RNA_collection_length(&dataptr, "sculpt_vertex_colors")) {
!RNA_collection_is_empty(&dataptr, "sculpt_vertex_colors")) {
uiItemPointerR(
layout, ptr, "layer_name", &dataptr, "sculpt_vertex_colors", "", ICON_GROUP_VCOL);
}

View File

@ -2192,16 +2192,9 @@ static int pyrna_prop_array_bool(BPy_PropertyRNA *self)
static int pyrna_prop_collection_bool(BPy_PropertyRNA *self)
{
/* No callback defined, just iterate and find the nth item. */
CollectionPropertyIterator iter;
int test;
PYRNA_PROP_CHECK_INT(self);
RNA_property_collection_begin(&self->ptr, self->prop, &iter);
test = iter.valid;
RNA_property_collection_end(&iter);
return test;
return !RNA_property_collection_is_empty(&self->ptr, self->prop);
}
/* notice getting the length of the collection is avoided unless negative