Commit: e167140e5d8c3d29432d7a8cabd87160082c2738 Author: Jeroen Bakker Date: Tue Nov 16 12:59:19 2021 +0100 Branches: temp-gpu-texture-partial-updates https://developer.blender.org/rBe167140e5d8c3d29432d7a8cabd87160082c2738
WIP: partial update image. Differential Revision: https://developer.blender.org/D13238 =================================================================== M source/blender/blenkernel/intern/image_partial_update.cc M source/blender/blenkernel/intern/image_partial_update_test.cc =================================================================== diff --git a/source/blender/blenkernel/intern/image_partial_update.cc b/source/blender/blenkernel/intern/image_partial_update.cc index 1eb054018b7..4dfbd4fa093 100644 --- a/source/blender/blenkernel/intern/image_partial_update.cc +++ b/source/blender/blenkernel/intern/image_partial_update.cc @@ -108,7 +108,7 @@ struct TileChangeset { bool has_dirty_tiles() const { - return has_dirty_tiles(); + return has_dirty_tiles_; } void init_tiles(int tile_x_len, int tile_y_len) @@ -167,15 +167,24 @@ struct TileChangeset { } }; -/** \brief Partial update data that is stored inside the image. */ +/** + * \brief Partial update changes stored inside the image runtime. + * + * The PartialUpdateRegisterImpl will keep track of changes over time. Changes are groups inside + * TileChangesets. + */ struct PartialUpdateRegisterImpl { /* Changes are tracked in tiles. */ static constexpr int TILE_SIZE = 256; + /** \brief changeset id of the first changeset kept in #history. */ ChangesetID first_changeset_id; - ChangesetID current_changeset_id; - Vector<TileChangeset> history; + /** \brief changeset id of the top changeset kept in #history. */ + ChangesetID last_changeset_id; + /** \brief history of changesets. */ + Vector<TileChangeset> history; + /** \brief The current changeset. New changes will be added to this changeset only. */ TileChangeset current_changeset; int image_width; @@ -198,9 +207,9 @@ struct PartialUpdateRegisterImpl { void mark_full_update() { history.clear(); - current_changeset_id++; + last_changeset_id++; current_changeset.reset(); - first_changeset_id = current_changeset_id; + first_changeset_id = last_changeset_id; } /** @@ -261,7 +270,7 @@ struct PartialUpdateRegisterImpl { { history.append_as(std::move(current_changeset)); current_changeset.reset(); - current_changeset_id++; + last_changeset_id++; } /** @@ -320,12 +329,12 @@ ePartialUpdateCollectResult BKE_image_partial_update_collect_tiles(Image *image, partial_updater->ensure_empty_changeset(); if (!partial_updater->can_construct(user_impl->last_changeset_id)) { - user_impl->last_changeset_id = partial_updater->current_changeset_id; + user_impl->last_changeset_id = partial_updater->last_changeset_id; return PARTIAL_UPDATE_NEED_FULL_UPDATE; } /* Check if there are changes since last invocation for the user. */ - if (user_impl->last_changeset_id == partial_updater->current_changeset_id) { + if (user_impl->last_changeset_id == partial_updater->last_changeset_id) { return PARTIAL_UPDATE_NO_CHANGES; } @@ -336,19 +345,21 @@ ePartialUpdateCollectResult BKE_image_partial_update_collect_tiles(Image *image, /* Convert tiles in the changeset to rectangles that are dirty. */ for (int tile_y = 0; tile_y < changed_tiles->tile_y_len_; tile_y++) { for (int tile_x = 0; tile_x < changed_tiles->tile_x_len_; tile_x++) { - if (changed_tiles->is_tile_dirty(tile_x, tile_y)) { - PartialUpdateTile tile; - BLI_rcti_init(&tile.region, - tile_x * PartialUpdateRegisterImpl::TILE_SIZE, - (tile_x + 1) * PartialUpdateRegisterImpl::TILE_SIZE, - tile_y * PartialUpdateRegisterImpl::TILE_SIZE, - (tile_y + 1) * PartialUpdateRegisterImpl::TILE_SIZE); - user_impl->updated_tiles.append_as(tile); + if (!changed_tiles->is_tile_dirty(tile_x, tile_y)) { + continue; } + + PartialUpdateTile tile; + BLI_rcti_init(&tile.region, + tile_x * PartialUpdateRegisterImpl::TILE_SIZE, + (tile_x + 1) * PartialUpdateRegisterImpl::TILE_SIZE, + tile_y * PartialUpdateRegisterImpl::TILE_SIZE, + (tile_y + 1) * PartialUpdateRegisterImpl::TILE_SIZE); + user_impl->updated_tiles.append_as(tile); } } - user_impl->last_changeset_id = partial_updater->current_changeset_id; + user_impl->last_changeset_id = partial_updater->last_changeset_id; return PARTIAL_UPDATE_CHANGES_AVAILABLE; } diff --git a/source/blender/blenkernel/intern/image_partial_update_test.cc b/source/blender/blenkernel/intern/image_partial_update_test.cc index 84cf3454d2f..91a74b8107e 100644 --- a/source/blender/blenkernel/intern/image_partial_update_test.cc +++ b/source/blender/blenkernel/intern/image_partial_update_test.cc @@ -326,4 +326,34 @@ TEST_F(ImagePartialUpdateTest, sequential_mark_region) } } +TEST_F(ImagePartialUpdateTest, mark_multiple_tiles) +{ + ePartialUpdateCollectResult result; + /* First tile should always return a full update. */ + result = BKE_image_partial_update_collect_tiles(image, image_buffer, partial_update_user); + EXPECT_EQ(result, PARTIAL_UPDATE_NEED_FULL_UPDATE); + /* Second invoke should now detect no changes. */ + result = BKE_image_partial_update_collect_tiles(image, image_buffer, partial_update_user); + EXPECT_EQ(result, PARTIAL_UPDATE_NO_CHANGES); + + /* Mark region. */ + rcti region; + BLI_rcti_init(®ion, 300, 700, 300, 700); + BKE_image_partial_update_register_mark_region(image, image_buffer, ®ion); + + /* Partial Update should be available. */ + result = BKE_image_partial_update_collect_tiles(image, image_buffer, partial_update_user); + EXPECT_EQ(result, PARTIAL_UPDATE_CHANGES_AVAILABLE); + + /* Check tiles. */ + PartialUpdateTile changed_tile; + int num_tiles_found = 0; + while (BKE_image_partial_update_next_tile(partial_update_user, &changed_tile) == + PARTIAL_UPDATE_ITER_TILE_LOADED) { + BLI_rcti_isect(&changed_tile.region, ®ion, nullptr); + num_tiles_found++; + } + EXPECT_EQ(num_tiles_found, 4); +} + } // namespace blender::bke::image _______________________________________________ Bf-blender-cvs mailing list [email protected] List details, subscription details or unsubscribe: https://lists.blender.org/mailman/listinfo/bf-blender-cvs
