Better factory icons & animations

This commit is contained in:
Nikita Lisitsa 2024-08-20 11:51:29 +03:00
parent 8a98bf3c21
commit b0628fbce6
2 changed files with 218 additions and 39 deletions

2
psemek

@ -1 +1 @@
Subproject commit a2c83633ae09f3db5c1e4d115a417021d38914ae
Subproject commit c16194c95cf627c14135db8b4da33fa4eb3b759f

View file

@ -697,37 +697,225 @@ namespace gmtk
}
}
float animation_factor(float animate)
{
static geom::gradient<float> const g
{
std::pair{0.5f, 0.f},
geom::easing_type::cubic,
std::pair{0.875f, 1.f},
geom::easing_type::cubic,
std::pair{1.f, 0.f},
};
return g(animate);
}
void draw_structure(geom::box<float, 2> const & bbox, transformer const & t, gfx::painter & painter)
{
auto box = geom::shrink(bbox, bbox[0].length() * 0.2f);
for (int i = 0; i < 2; ++i)
switch (t.type)
{
gfx::color_rgba color = {0, 0, 0, 255};
case transformer_type::mixer:
{
float an = animation_factor(t.animate);
if (i == 1)
auto box = geom::shrink(bbox, bbox[0].length() * 0.2f);
float r1 = std::sqrt(2.f) * (2.f + 2.f * an) / 16.f * box[0].length();
float r2 = std::sqrt(2.f) * (4.f + 2.f * an) / 16.f * box[0].length();
float s = bbox[0].length() * 0.025f;
float t = 0.6f * s;
box = geom::expand(box, an * box[0].length() * 0.125f);
geom::point<float, 2> points[]
{
color = {255, 255, 255, 255};
if (t.type == transformer_type::mixer)
box = geom::shrink(bbox, bbox[0].length() * (0.2f + 0.025f * std::sqrt(2.f)));
else
box = geom::shrink(bbox, bbox[0].length() * 0.225f);
box.corner(0.f, 0.75f),
box.corner(0.f, 0.25f),
box.corner(0.25f, 0.f),
box.corner(0.75f, 0.f),
box.corner(1.f, 0.25f),
box.corner(1.f, 0.75f),
box.corner(0.75f, 1.f),
box.corner(0.25f, 1.f),
};
static geom::triangle<std::uint32_t> const triangles[]
{
{0, 1, 2},
{0, 2, 3},
{0, 3, 4},
{0, 4, 5},
{0, 5, 6},
{0, 6, 7},
};
for (int i = 0; i < 2; ++i)
{
auto color = (i == 0) ? gfx::black : gfx::white;
if (i == 1)
{
points[0] += geom::vector{ s, -t};
points[1] += geom::vector{ s, t};
points[2] += geom::vector{ t, s};
points[3] += geom::vector{-t, s};
points[4] += geom::vector{-s, t};
points[5] += geom::vector{-s, -t};
points[6] += geom::vector{-t, -s};
points[7] += geom::vector{ t, -s};
}
for (auto const & t : triangles)
{
auto p0 = points[t[0]];
auto p1 = points[t[1]];
auto p2 = points[t[2]];
painter.triangle(p0, p1, p2, color);
}
}
switch (t.type)
auto c = bbox.center();
for (int i = 0; i < 4; ++i)
{
case transformer_type::mixer:
painter.triangle(box.corner(0.f, 0.5f), box.corner(1.f, 0.5f), box.corner(0.5f, 0.f), color);
painter.triangle(box.corner(0.f, 0.5f), box.corner(1.f, 0.5f), box.corner(0.5f, 1.f), color);
break;
case transformer_type::reshaper:
painter.rect(box, color);
break;
case transformer_type::hue_shifter:
painter.circle(box.center(), box[0].length() / 2.f, color, 72);
break;
auto d = geom::direction(geom::rad(45.f + 90.f * i));
painter.line(c + d * r1, c + d * r2, s, gfx::black, true);
}
}
break;
case transformer_type::reshaper:
{
auto box = geom::shrink(bbox, bbox[0].length() * 0.2f);
float s = bbox[0].length() * 0.025f;
for (int k = 0; k < 2; ++k)
{
geom::point<float, 2> points[]
{
box.corner(0.f, 1.f),
box.corner(0.f, 0.75f),
box.corner(0.25f, 0.5f),
box.corner(0.75f, 0.5f),
box.corner(1.f, 0.75f),
box.corner(1.f, 1.f),
};
static geom::triangle<std::uint32_t> const triangles[]
{
{0, 1, 2},
{0, 2, 3},
{0, 3, 4},
{0, 4, 5},
};
auto c = bbox.center();
for (int i = 0; i < 2; ++i)
{
auto color = (i == 0) ? gfx::black : gfx::white;
if (i == 1)
{
points[0] += geom::vector{s, -s};
points[1] += geom::vector{s, 0.6f * s};
points[2] += geom::vector{0.6f * s, s};
points[3] += geom::vector{- 0.6f * s, s};
points[4] += geom::vector{-s, 0.6f * s};
points[5] += geom::vector{-s, -s};
}
for (int j = 0; j < 2; ++j)
{
float d = 1.f - animation_factor(t.animate);
d *= box[0].length() * 0.125f;
if (j == 1)
d = -d;
for (auto const & t : triangles)
{
auto p0 = points[t[0]];
auto p1 = points[t[1]];
auto p2 = points[t[2]];
if (j == 1)
{
float m = box[1].min + box[1].max;
p0[1] = m - p0[1];
p1[1] = m - p1[1];
p2[1] = m - p2[1];
}
p0[1] += d;
p1[1] += d;
p2[1] += d;
if (k == 0)
{
p0 = c + geom::ort(p0 - c);
p1 = c + geom::ort(p1 - c);
p2 = c + geom::ort(p2 - c);
}
painter.triangle(p0, p1, p2, color);
}
}
}
}
break;
}
case transformer_type::hue_shifter:
{
float size = bbox[0].length();
float s = size * 0.025f;
float r1 = size * 0.33f - s / 2.f;
float r2 = r1 * 0.5f - s / 2.f;
auto c = bbox.center();
static geom::gradient<float> const g
{
std::pair{0.5f, 1.f},
geom::easing_type::cubic,
std::pair{1.f, 0.f},
};
float offset = - g(t.animate) * geom::pi / 3.f;
int n = 6;
for (int i = 0; i < n; ++i)
{
float a = (i * 2.f * geom::pi) / n + offset;
float b = ((i + 1) * 2.f * geom::pi) / n + offset;
auto da = geom::direction(a);
auto db = geom::direction(b);
painter.triangle(c + da * r2, c + db * r2, c + da * r1, gfx::white);
painter.triangle(c + db * r2, c + da * r1, c + db * r1, gfx::white);
}
for (int i = 0; i < n; ++i)
{
float a = (i * 2.f * geom::pi) / n + offset;
float b = ((i + 1) * 2.f * geom::pi) / n + offset;
auto da = geom::direction(a);
auto db = geom::direction(b);
painter.line(c + da * r1, c + db * r1, s, gfx::black, false);
painter.line(c + da * r2, c + db * r2, s, gfx::black, false);
if (i % (n / 6) == 0)
painter.line(c + da * r2, c + da * r1, s, gfx::black, true);
}
}
break;
}
}
void draw_structure(geom::box<float, 2> const & bbox, crossing const &, gfx::painter & painter)
@ -751,7 +939,12 @@ namespace gmtk
case card_type::mixer:
case card_type::reshaper:
case card_type::hue_shifter:
draw_structure(bbox, transformer{card_to_transformer(type).value()}, painter);
{
float animate = 0.f;
// if (type == card_type::reshaper)
// animate = 0.875f;
draw_structure(bbox, transformer{.type = card_to_transformer(type).value(), .animate = animate}, painter);
}
break;
case card_type::zoomer:
draw_grid(bbox, -1.f, painter, true);
@ -781,20 +974,6 @@ namespace gmtk
});
}
float animation_factor(float animate)
{
static geom::gradient<float> const g
{
std::pair{0.5f, 0.f},
geom::easing_type::cubic,
std::pair{0.875f, 1.f},
geom::easing_type::cubic,
std::pair{1.f, 0.f},
};
return g(animate);
}
void draw(map & map, gfx::painter & painter, float pixel_size)
{
map.world.apply<vertex const, crossing const>([&](vertex const & v, crossing const & c)
@ -864,7 +1043,7 @@ namespace gmtk
map.world.apply<vertex const, transformer const>([&](vertex const & v, transformer const & t)
{
auto box = v.location.bbox();
box = geom::expand(box, 0.125f * animation_factor(t.animate) * box[0].length());
// box = geom::expand(box, 0.125f * animation_factor(t.animate) * box[0].length());
draw_structure(box, t, painter);
});
@ -933,7 +1112,7 @@ namespace gmtk
case card_type::hue_shifter:
return {"Hue shifter", "Shifts the hue of", " input colors"};
case card_type::reshaper:
return {"Reshaper", "Turns circles into squares", " and squares into hexagons"};
return {"Reshaper", "Turns circles into squares"};
case card_type::crossing:
return {"Bridge", "Allows belts to cross", " without merging"};
case card_type::zoomer: