| 1 | // Aseprite Render Library |
| 2 | // Copyright (C) 2019 Igara Studio S.A. |
| 3 | // |
| 4 | // This file is released under the terms of the MIT license. |
| 5 | // Read LICENSE.txt for more information. |
| 6 | |
| 7 | #ifdef HAVE_CONFIG_H |
| 8 | #include "config.h" |
| 9 | #endif |
| 10 | |
| 11 | #include "render/rasterize.h" |
| 12 | |
| 13 | #include "base/debug.h" |
| 14 | #include "doc/blend_internals.h" |
| 15 | #include "doc/cel.h" |
| 16 | #include "doc/sprite.h" |
| 17 | #include "render/render.h" |
| 18 | |
| 19 | namespace render { |
| 20 | |
| 21 | void rasterize( |
| 22 | doc::Image* dst, |
| 23 | const doc::Cel* cel, |
| 24 | const int x, |
| 25 | const int y, |
| 26 | const bool clear) |
| 27 | { |
| 28 | ASSERT(dst); |
| 29 | ASSERT(dst->pixelFormat() != IMAGE_TILEMAP); |
| 30 | ASSERT(cel); |
| 31 | |
| 32 | const doc::Sprite* sprite = cel->sprite(); |
| 33 | ASSERT(sprite); |
| 34 | |
| 35 | if (clear) |
| 36 | dst->clear(sprite->transparentColor()); |
| 37 | |
| 38 | int t; |
| 39 | int opacity; |
| 40 | opacity = MUL_UN8(cel->opacity(), cel->layer()->opacity(), t); |
| 41 | |
| 42 | if (cel->image()->pixelFormat() == IMAGE_TILEMAP) { |
| 43 | render::Render render; |
| 44 | render.renderCel( |
| 45 | dst, |
| 46 | cel, |
| 47 | sprite, |
| 48 | cel->image(), |
| 49 | cel->layer(), |
| 50 | sprite->palette(cel->frame()), |
| 51 | gfx::RectF(cel->bounds()), |
| 52 | gfx::Clip(x, y, 0, 0, dst->width(), dst->height()), |
| 53 | clear ? 255: opacity, |
| 54 | clear ? BlendMode::NORMAL: cel->layer()->blendMode()); |
| 55 | } |
| 56 | else { |
| 57 | if (clear) |
| 58 | copy_image(dst, cel->image(), x+cel->x(), y+cel->y()); |
| 59 | else |
| 60 | composite_image( |
| 61 | dst, cel->image(), |
| 62 | sprite->palette(cel->frame()), |
| 63 | x+cel->x(), |
| 64 | y+cel->y(), |
| 65 | opacity, |
| 66 | cel->layer()->blendMode()); |
| 67 | } |
| 68 | } |
| 69 | |
| 70 | void rasterize_with_cel_bounds( |
| 71 | doc::Image* dst, |
| 72 | const doc::Cel* cel) |
| 73 | { |
| 74 | rasterize(dst, cel, -cel->x(), -cel->y(), true); |
| 75 | } |
| 76 | |
| 77 | void rasterize_with_sprite_bounds( |
| 78 | doc::Image* dst, |
| 79 | const doc::Cel* cel) |
| 80 | { |
| 81 | rasterize(dst, cel, 0, 0, true); |
| 82 | } |
| 83 | |
| 84 | doc::Image* rasterize_with_cel_bounds( |
| 85 | const doc::Cel* cel) |
| 86 | { |
| 87 | ASSERT(cel); |
| 88 | |
| 89 | const doc::Sprite* sprite = cel->sprite(); |
| 90 | ASSERT(sprite); |
| 91 | |
| 92 | doc::ImageSpec spec = sprite->spec(); |
| 93 | spec.setWidth(cel->bounds().w); |
| 94 | spec.setHeight(cel->bounds().h); |
| 95 | |
| 96 | std::unique_ptr<doc::Image> dst(doc::Image::create(spec)); |
| 97 | rasterize_with_cel_bounds(dst.get(), cel); |
| 98 | return dst.release(); |
| 99 | } |
| 100 | |
| 101 | doc::Image* rasterize_with_sprite_bounds( |
| 102 | const doc::Cel* cel) |
| 103 | { |
| 104 | ASSERT(cel); |
| 105 | |
| 106 | const doc::Sprite* sprite = cel->sprite(); |
| 107 | ASSERT(sprite); |
| 108 | |
| 109 | std::unique_ptr<doc::Image> dst(doc::Image::create(sprite->spec())); |
| 110 | rasterize_with_sprite_bounds(dst.get(), cel); |
| 111 | return dst.release(); |
| 112 | } |
| 113 | |
| 114 | } // namespace render |
| 115 | |