48 description.width_tiles = dimensions.width_tiles;
49 description.height_tiles = dimensions.height_tiles;
50 description.footprint = FootprintLabel(dimensions);
58 description.wheel_hint =
"Wheel: grow / shrink. Shift + wheel: width.";
60 bool width_changes =
false;
61 bool height_changes =
false;
62 for (uint8_t size = 0; size < 16; ++size) {
63 const auto candidate = DimensionsAtSize(
object, size);
64 width_changes |= candidate.width_tiles != dimensions.width_tiles;
65 height_changes |= candidate.height_tiles != dimensions.height_tiles;
67 description.kind = width_changes != height_changes
70 description.length_horizontal = width_changes;
79 uint8_t* requested_size) {
80 if (!requested_size) {
83 uint8_t size =
object.size_;
87 for (
const bool horizontal : {
true,
false}) {
89 const int shift = horizontal ? 2 : 0;
90 const int current = (size >> shift) & 3;
91 const auto preview = absl::StrFormat(
94 ImGui::SetNextItemWidth(-1);
95 const bool open = ImGui::BeginCombo(
96 horizontal ?
"##SelObjWidth" :
"##SelObjHeight", preview.c_str());
98 for (
int value = 0; value < 4; ++value) {
99 const auto candidate =
100 static_cast<uint8_t
>((size & ~(3 << shift)) | (value << shift));
101 const auto label = absl::StrFormat(
103 object.id_, candidate, horizontal));
104 if (ImGui::Selectable(label.c_str(), value == current)) {
111 absl::StrFormat(
"object_%s_%d",
112 horizontal ?
"width" :
"height", value));
114 if (value == current) {
115 ImGui::SetItemDefaultFocus();
125 horizontal ?
"selected_object_width" :
"selected_object_height",
126 horizontal ?
"Selected object width in tiles"
127 :
"Selected object height in tiles");
134 ? std::min(manager.GetSubtypeCount(
object.id_), 16)
137 const auto variant_label = [&](
int subtype) {
142 const auto filename = manager.ResolveFilename(
object.id_, subtype);
143 return filename.empty()
144 ? absl::StrFormat(
"Variant %d (unmapped)", subtype)
145 : std::filesystem::path(filename).stem().string();
148 const auto preview = size < variants
149 ? variant_label(size)
150 : absl::StrFormat(
"Invalid variant %d", size);
151 ImGui::SetNextItemWidth(-1);
152 const bool open = ImGui::BeginCombo(
"##SelObjVariant", preview.c_str());
154 for (
int subtype = 0; subtype < variants; ++subtype) {
156 absl::StrFormat(
"%02X %s", subtype, variant_label(subtype));
158 !manager.ResolveFilename(
object.id_, subtype).empty();
159 ImGui::BeginDisabled(!mapped);
160 if (ImGui::Selectable(label.c_str(), size == subtype)) {
161 size =
static_cast<uint8_t
>(subtype);
166 "selectable", absl::StrFormat(
"object_variant_%d", subtype));
168 ImGui::EndDisabled();
175 "Selected custom object variant");
182 ImGui::TextDisabled(
"Fixed size");
186 const auto label_for_size = [&](uint8_t value) {
187 const auto dimensions = DimensionsAtSize(
object, value);
189 const int tiles = description.length_horizontal
190 ? dimensions.width_tiles
191 : dimensions.height_tiles;
192 return absl::StrFormat(
"%d tiles (%d px)", tiles, tiles * 8);
194 return absl::StrFormat(
"%d x %d tiles", dimensions.width_tiles,
195 dimensions.height_tiles);
197 ImGui::SetNextItemWidth(-1);
198 if (ImGui::BeginCombo(
"##SelObjSize", label_for_size(size).c_str())) {
199 std::array<uint8_t, 16> sizes{};
200 for (uint8_t value = 0; value < sizes.size(); ++value) {
201 sizes[value] = value;
206 std::stable_sort(sizes.begin(), sizes.end(),
207 [&](uint8_t left, uint8_t right) {
208 const auto a = DimensionsAtSize(object, left);
209 const auto b = DimensionsAtSize(object, right);
210 return description.length_horizontal
211 ? a.width_tiles < b.width_tiles
212 : a.height_tiles < b.height_tiles;
215 for (
const uint8_t value : sizes) {
216 ImGui::PushID(value);
217 if (ImGui::Selectable(label_for_size(value).c_str(),
224 "selectable", absl::StrFormat(
"object_size_%d", value));
227 ImGui::SetItemDefaultFocus();
236 is_length ?
"Object length in tiles"
237 :
"Object footprint in tiles");
243 const auto dimensions = DimensionsAtSize(
object, size);
244 ImGui::TextWrapped(
"%d x %d tiles", dimensions.width_tiles,
245 dimensions.height_tiles);
246 ImGui::TextDisabled(
"%d x %d px", dimensions.width_pixels(),
247 dimensions.height_pixels());
249 *requested_size = size;
250 return size !=
object.size_;