1 | // Aseprite Document Library |
2 | // Copyright (c) 2022 Igara Studio S.A. |
3 | // Copyright (c) 2001-2018 David Capello |
4 | // |
5 | // This file is released under the terms of the MIT license. |
6 | // Read LICENSE.txt for more information. |
7 | |
8 | #ifdef HAVE_CONFIG_H |
9 | #include "config.h" |
10 | #endif |
11 | |
12 | #include "doc/cel_data_io.h" |
13 | |
14 | #include "base/serialization.h" |
15 | #include "doc/cel_data.h" |
16 | #include "doc/subobjects_io.h" |
17 | #include "doc/user_data_io.h" |
18 | #include "fixmath/fixmath.h" |
19 | |
20 | #include <iostream> |
21 | #include <memory> |
22 | |
23 | namespace doc { |
24 | |
25 | #define HAS_BOUNDS_F 1 |
26 | |
27 | using namespace base::serialization; |
28 | using namespace base::serialization::little_endian; |
29 | |
30 | void write_celdata(std::ostream& os, const CelData* celdata) |
31 | { |
32 | write32(os, celdata->id()); |
33 | write32(os, celdata->bounds().x); |
34 | write32(os, celdata->bounds().y); |
35 | write32(os, celdata->bounds().w); |
36 | write32(os, celdata->bounds().h); |
37 | write8(os, celdata->opacity()); |
38 | write32(os, celdata->image()->id()); |
39 | write_user_data(os, celdata->userData()); |
40 | |
41 | if (celdata->hasBoundsF()) { // Reference layer |
42 | write32(os, HAS_BOUNDS_F); |
43 | write32(os, fixmath::ftofix(celdata->boundsF().x)); |
44 | write32(os, fixmath::ftofix(celdata->boundsF().y)); |
45 | write32(os, fixmath::ftofix(celdata->boundsF().w)); |
46 | write32(os, fixmath::ftofix(celdata->boundsF().h)); |
47 | } |
48 | else { |
49 | write32(os, 0); |
50 | } |
51 | } |
52 | |
53 | CelData* read_celdata(std::istream& is, SubObjectsIO* subObjects, bool setId) |
54 | { |
55 | ObjectId id = read32(is); |
56 | int x = read32(is); |
57 | int y = read32(is); |
58 | int w = read32(is); |
59 | int h = read32(is); |
60 | int opacity = read8(is); |
61 | ObjectId imageId = read32(is); |
62 | UserData userData = read_user_data(is); |
63 | gfx::RectF boundsF; |
64 | |
65 | // Extra fields |
66 | int flags = read32(is); |
67 | if (flags & HAS_BOUNDS_F) { |
68 | fixmath::fixed x = read32(is); |
69 | fixmath::fixed y = read32(is); |
70 | fixmath::fixed w = read32(is); |
71 | fixmath::fixed h = read32(is); |
72 | if (w && h) { |
73 | boundsF = gfx::RectF(fixmath::fixtof(x), |
74 | fixmath::fixtof(y), |
75 | fixmath::fixtof(w), |
76 | fixmath::fixtof(h)); |
77 | } |
78 | } |
79 | |
80 | ImageRef image(subObjects->getImageRef(imageId)); |
81 | if (!image) |
82 | return nullptr; |
83 | |
84 | std::unique_ptr<CelData> celdata(new CelData(image)); |
85 | celdata->setBounds(gfx::Rect(x, y, w, h)); |
86 | celdata->setOpacity(opacity); |
87 | celdata->setUserData(userData); |
88 | if (setId) |
89 | celdata->setId(id); |
90 | if (!boundsF.isEmpty()) |
91 | celdata->setBoundsF(boundsF); |
92 | return celdata.release(); |
93 | } |
94 | |
95 | } |
96 | |