Changeset View
Changeset View
Standalone View
Standalone View
source/blender/editors/space_image/image_undo.c
| Show First 20 Lines • Show All 139 Lines • ▼ Show 20 Lines | for (PaintTile *ptile = paint_tiles->first, *ptile_next; ptile; ptile = ptile_next) { | ||||
| ptile_next = ptile->next; | ptile_next = ptile->next; | ||||
| ptile_free(ptile); | ptile_free(ptile); | ||||
| } | } | ||||
| BLI_listbase_clear(paint_tiles); | BLI_listbase_clear(paint_tiles); | ||||
| } | } | ||||
| static void ptile_invalidate_list(ListBase *paint_tiles) | static void ptile_invalidate_list(ListBase *paint_tiles) | ||||
| { | { | ||||
| for (PaintTile *ptile = paint_tiles->first; ptile; ptile = ptile->next) { | LISTBASE_FOREACH (PaintTile *, ptile, paint_tiles) { | ||||
| ptile->valid = false; | ptile->valid = false; | ||||
| } | } | ||||
| } | } | ||||
| void *ED_image_paint_tile_find(ListBase *paint_tiles, | void *ED_image_paint_tile_find(ListBase *paint_tiles, | ||||
| Image *image, | Image *image, | ||||
| ImBuf *ibuf, | ImBuf *ibuf, | ||||
| ImageUser *iuser, | ImageUser *iuser, | ||||
| int x_tile, | int x_tile, | ||||
| int y_tile, | int y_tile, | ||||
| ushort **r_mask, | ushort **r_mask, | ||||
| bool validate) | bool validate) | ||||
| { | { | ||||
| for (PaintTile *ptile = paint_tiles->first; ptile; ptile = ptile->next) { | LISTBASE_FOREACH (PaintTile *, ptile, paint_tiles) { | ||||
| if (ptile->x_tile == x_tile && ptile->y_tile == y_tile) { | if (ptile->x_tile == x_tile && ptile->y_tile == y_tile) { | ||||
| if (ptile->image == image && ptile->ibuf == ibuf && ptile->iuser.tile == iuser->tile) { | if (ptile->image == image && ptile->ibuf == ibuf && ptile->iuser.tile == iuser->tile) { | ||||
| if (r_mask) { | if (r_mask) { | ||||
| /* allocate mask if requested. */ | /* allocate mask if requested. */ | ||||
| if (!ptile->mask) { | if (!ptile->mask) { | ||||
| ptile->mask = MEM_callocN(sizeof(ushort) * square_i(ED_IMAGE_UNDO_TILE_SIZE), | ptile->mask = MEM_callocN(sizeof(ushort) * square_i(ED_IMAGE_UNDO_TILE_SIZE), | ||||
| "UndoImageTile.mask"); | "UndoImageTile.mask"); | ||||
| } | } | ||||
| ▲ Show 20 Lines • Show All 91 Lines • ▼ Show 20 Lines | void *ED_image_paint_tile_push(ListBase *paint_tiles, | ||||
| } | } | ||||
| return ptile->rect.pt; | return ptile->rect.pt; | ||||
| } | } | ||||
| static void ptile_restore_runtime_list(ListBase *paint_tiles) | static void ptile_restore_runtime_list(ListBase *paint_tiles) | ||||
| { | { | ||||
| ImBuf *tmpibuf = imbuf_alloc_temp_tile(); | ImBuf *tmpibuf = imbuf_alloc_temp_tile(); | ||||
| for (PaintTile *ptile = paint_tiles->first; ptile; ptile = ptile->next) { | LISTBASE_FOREACH (PaintTile *, ptile, paint_tiles) { | ||||
| Image *image = ptile->image; | Image *image = ptile->image; | ||||
| ImBuf *ibuf = BKE_image_acquire_ibuf(image, &ptile->iuser, NULL); | ImBuf *ibuf = BKE_image_acquire_ibuf(image, &ptile->iuser, NULL); | ||||
| const bool has_float = (ibuf->rect_float != NULL); | const bool has_float = (ibuf->rect_float != NULL); | ||||
| if (has_float) { | if (has_float) { | ||||
| SWAP(float *, ptile->rect.fp, tmpibuf->rect_float); | SWAP(float *, ptile->rect.fp, tmpibuf->rect_float); | ||||
| } | } | ||||
| else { | else { | ||||
| ▲ Show 20 Lines • Show All 258 Lines • ▼ Show 20 Lines | typedef struct UndoImageHandle { | ||||
| ListBase buffers; | ListBase buffers; | ||||
| } UndoImageHandle; | } UndoImageHandle; | ||||
| static void uhandle_restore_list(ListBase *undo_handles, bool use_init) | static void uhandle_restore_list(ListBase *undo_handles, bool use_init) | ||||
| { | { | ||||
| ImBuf *tmpibuf = imbuf_alloc_temp_tile(); | ImBuf *tmpibuf = imbuf_alloc_temp_tile(); | ||||
| for (UndoImageHandle *uh = undo_handles->first; uh; uh = uh->next) { | LISTBASE_FOREACH (UndoImageHandle *, uh, undo_handles) { | ||||
| /* Tiles only added to second set of tiles. */ | /* Tiles only added to second set of tiles. */ | ||||
| Image *image = uh->image_ref.ptr; | Image *image = uh->image_ref.ptr; | ||||
| ImBuf *ibuf = BKE_image_acquire_ibuf(image, &uh->iuser, NULL); | ImBuf *ibuf = BKE_image_acquire_ibuf(image, &uh->iuser, NULL); | ||||
| if (UNLIKELY(ibuf == NULL)) { | if (UNLIKELY(ibuf == NULL)) { | ||||
| CLOG_ERROR(&LOG, "Unable to get buffer for image '%s'", image->id.name + 2); | CLOG_ERROR(&LOG, "Unable to get buffer for image '%s'", image->id.name + 2); | ||||
| continue; | continue; | ||||
| } | } | ||||
| bool changed = false; | bool changed = false; | ||||
| for (UndoImageBuf *ubuf_iter = uh->buffers.first; ubuf_iter; ubuf_iter = ubuf_iter->next) { | LISTBASE_FOREACH (UndoImageBuf *, ubuf_iter, &uh->buffers) { | ||||
| UndoImageBuf *ubuf = use_init ? ubuf_iter : ubuf_iter->post; | UndoImageBuf *ubuf = use_init ? ubuf_iter : ubuf_iter->post; | ||||
| ubuf_ensure_compat_ibuf(ubuf, ibuf); | ubuf_ensure_compat_ibuf(ubuf, ibuf); | ||||
| int i = 0; | int i = 0; | ||||
| for (uint y_tile = 0; y_tile < ubuf->tiles_dims[1]; y_tile += 1) { | for (uint y_tile = 0; y_tile < ubuf->tiles_dims[1]; y_tile += 1) { | ||||
| uint y = y_tile << ED_IMAGE_UNDO_TILE_BITS; | uint y = y_tile << ED_IMAGE_UNDO_TILE_BITS; | ||||
| for (uint x_tile = 0; x_tile < ubuf->tiles_dims[0]; x_tile += 1) { | for (uint x_tile = 0; x_tile < ubuf->tiles_dims[0]; x_tile += 1) { | ||||
| uint x = x_tile << ED_IMAGE_UNDO_TILE_BITS; | uint x = x_tile << ED_IMAGE_UNDO_TILE_BITS; | ||||
| ▲ Show 20 Lines • Show All 42 Lines • ▼ Show 20 Lines | |||||
| * \{ */ | * \{ */ | ||||
| /** #UndoImageHandle utilities */ | /** #UndoImageHandle utilities */ | ||||
| static UndoImageBuf *uhandle_lookup_ubuf(UndoImageHandle *uh, | static UndoImageBuf *uhandle_lookup_ubuf(UndoImageHandle *uh, | ||||
| const Image *UNUSED(image), | const Image *UNUSED(image), | ||||
| const char *ibuf_name) | const char *ibuf_name) | ||||
| { | { | ||||
| for (UndoImageBuf *ubuf = uh->buffers.first; ubuf; ubuf = ubuf->next) { | LISTBASE_FOREACH (UndoImageBuf *, ubuf, &uh->buffers) { | ||||
| if (STREQ(ubuf->ibuf_name, ibuf_name)) { | if (STREQ(ubuf->ibuf_name, ibuf_name)) { | ||||
| return ubuf; | return ubuf; | ||||
| } | } | ||||
| } | } | ||||
| return NULL; | return NULL; | ||||
| } | } | ||||
| static UndoImageBuf *uhandle_add_ubuf(UndoImageHandle *uh, Image *image, ImBuf *ibuf) | static UndoImageBuf *uhandle_add_ubuf(UndoImageHandle *uh, Image *image, ImBuf *ibuf) | ||||
| Show All 15 Lines | static UndoImageBuf *uhandle_ensure_ubuf(UndoImageHandle *uh, Image *image, ImBuf *ibuf) | ||||
| } | } | ||||
| return ubuf; | return ubuf; | ||||
| } | } | ||||
| static UndoImageHandle *uhandle_lookup_by_name(ListBase *undo_handles, | static UndoImageHandle *uhandle_lookup_by_name(ListBase *undo_handles, | ||||
| const Image *image, | const Image *image, | ||||
| int tile_number) | int tile_number) | ||||
| { | { | ||||
| for (UndoImageHandle *uh = undo_handles->first; uh; uh = uh->next) { | LISTBASE_FOREACH (UndoImageHandle *, uh, undo_handles) { | ||||
| if (STREQ(image->id.name + 2, uh->image_ref.name + 2) && uh->iuser.tile == tile_number) { | if (STREQ(image->id.name + 2, uh->image_ref.name + 2) && uh->iuser.tile == tile_number) { | ||||
| return uh; | return uh; | ||||
| } | } | ||||
| } | } | ||||
| return NULL; | return NULL; | ||||
| } | } | ||||
| static UndoImageHandle *uhandle_lookup(ListBase *undo_handles, const Image *image, int tile_number) | static UndoImageHandle *uhandle_lookup(ListBase *undo_handles, const Image *image, int tile_number) | ||||
| { | { | ||||
| for (UndoImageHandle *uh = undo_handles->first; uh; uh = uh->next) { | LISTBASE_FOREACH (UndoImageHandle *, uh, undo_handles) { | ||||
| if (image == uh->image_ref.ptr && uh->iuser.tile == tile_number) { | if (image == uh->image_ref.ptr && uh->iuser.tile == tile_number) { | ||||
| return uh; | return uh; | ||||
| } | } | ||||
| } | } | ||||
| return NULL; | return NULL; | ||||
| } | } | ||||
| static UndoImageHandle *uhandle_add(ListBase *undo_handles, Image *image, ImageUser *iuser) | static UndoImageHandle *uhandle_add(ListBase *undo_handles, Image *image, ImageUser *iuser) | ||||
| ▲ Show 20 Lines • Show All 129 Lines • ▼ Show 20 Lines | for (PaintTile *ptile = us->paint_tiles.first, *ptile_next; ptile; ptile = ptile_next) { | ||||
| BLI_assert(ubuf_pre->tiles[tile_index] == NULL); | BLI_assert(ubuf_pre->tiles[tile_index] == NULL); | ||||
| ubuf_pre->tiles[tile_index] = utile; | ubuf_pre->tiles[tile_index] = utile; | ||||
| } | } | ||||
| ptile_next = ptile->next; | ptile_next = ptile->next; | ||||
| ptile_free(ptile); | ptile_free(ptile); | ||||
| } | } | ||||
| BLI_listbase_clear(&us->paint_tiles); | BLI_listbase_clear(&us->paint_tiles); | ||||
| for (UndoImageHandle *uh = us->handles.first; uh; uh = uh->next) { | LISTBASE_FOREACH (UndoImageHandle *, uh, &us->handles) { | ||||
| for (UndoImageBuf *ubuf_pre = uh->buffers.first; ubuf_pre; ubuf_pre = ubuf_pre->next) { | LISTBASE_FOREACH (UndoImageBuf *, ubuf_pre, &uh->buffers) { | ||||
| ImBuf *ibuf = BKE_image_acquire_ibuf(uh->image_ref.ptr, &uh->iuser, NULL); | ImBuf *ibuf = BKE_image_acquire_ibuf(uh->image_ref.ptr, &uh->iuser, NULL); | ||||
| const bool has_float = ibuf->rect_float; | const bool has_float = ibuf->rect_float; | ||||
| BLI_assert(ubuf_pre->post == NULL); | BLI_assert(ubuf_pre->post == NULL); | ||||
| ubuf_pre->post = ubuf_from_image_no_tiles(uh->image_ref.ptr, ibuf); | ubuf_pre->post = ubuf_from_image_no_tiles(uh->image_ref.ptr, ibuf); | ||||
| UndoImageBuf *ubuf_post = ubuf_pre->post; | UndoImageBuf *ubuf_post = ubuf_pre->post; | ||||
| ▲ Show 20 Lines • Show All 162 Lines • ▼ Show 20 Lines | static void image_undosys_step_free(UndoStep *us_p) | ||||
| ptile_free_list(&us->paint_tiles); | ptile_free_list(&us->paint_tiles); | ||||
| } | } | ||||
| static void image_undosys_foreach_ID_ref(UndoStep *us_p, | static void image_undosys_foreach_ID_ref(UndoStep *us_p, | ||||
| UndoTypeForEachIDRefFn foreach_ID_ref_fn, | UndoTypeForEachIDRefFn foreach_ID_ref_fn, | ||||
| void *user_data) | void *user_data) | ||||
| { | { | ||||
| ImageUndoStep *us = (ImageUndoStep *)us_p; | ImageUndoStep *us = (ImageUndoStep *)us_p; | ||||
| for (UndoImageHandle *uh = us->handles.first; uh; uh = uh->next) { | LISTBASE_FOREACH (UndoImageHandle *, uh, &us->handles) { | ||||
| foreach_ID_ref_fn(user_data, ((UndoRefID *)&uh->image_ref)); | foreach_ID_ref_fn(user_data, ((UndoRefID *)&uh->image_ref)); | ||||
| } | } | ||||
| } | } | ||||
| /* Export for ED_undo_sys. */ | /* Export for ED_undo_sys. */ | ||||
| void ED_image_undosys_type(UndoType *ut) | void ED_image_undosys_type(UndoType *ut) | ||||
| { | { | ||||
| ut->name = "Image"; | ut->name = "Image"; | ||||
| ▲ Show 20 Lines • Show All 99 Lines • Show Last 20 Lines | |||||