Skip to content

Commit d0a38f6

Browse files
authoredDec 15, 2020
Formspec: Allow to specify frame loop for model[] (#10679)
Add the ability to specify an animation frame loop range for the model[] formspec element.
1 parent 3ed940f commit d0a38f6

File tree

4 files changed

+31
-6
lines changed

4 files changed

+31
-6
lines changed
 

Diff for: ‎doc/lua_api.txt

+5-1
Original file line numberDiff line numberDiff line change
@@ -2277,7 +2277,7 @@ Elements
22772277
* `frame duration`: Milliseconds between each frame. `0` means the frames don't advance.
22782278
* `frame start` (Optional): The index of the frame to start on. Default `1`.
22792279

2280-
### `model[<X>,<Y>;<W>,<H>;<name>;<mesh>;<textures>;<rotation X,Y>;<continuous>;<mouse control>]`
2280+
### `model[<X>,<Y>;<W>,<H>;<name>;<mesh>;<textures>;<rotation X,Y>;<continuous>;<mouse control>;<frame loop range>]`
22812281

22822282
* Show a mesh model.
22832283
* `name`: Element name that can be used for styling
@@ -2288,6 +2288,9 @@ Elements
22882288
The axes are euler angles in degrees.
22892289
* `continuous` (Optional): Whether the rotation is continuous. Default `false`.
22902290
* `mouse control` (Optional): Whether the model can be controlled with the mouse. Default `true`.
2291+
* `frame loop range` (Optional): Range of the animation frames.
2292+
* Defaults to the full range of all available frames.
2293+
* Syntax: `<begin>,<end>`
22912294

22922295
### `item_image[<X>,<Y>;<W>,<H>;<item name>]`
22932296

@@ -2789,6 +2792,7 @@ Some types may inherit styles from parent types.
27892792
* image_button
27902793
* item_image_button
27912794
* label
2795+
* model
27922796
* pwdfield, inherits from field
27932797
* scrollbar
27942798
* tabheader

Diff for: ‎src/gui/guiFormSpecMenu.cpp

+16-5
Original file line numberDiff line numberDiff line change
@@ -70,15 +70,15 @@ with this program; if not, write to the Free Software Foundation, Inc.,
7070

7171
#define MY_CHECKPOS(a,b) \
7272
if (v_pos.size() != 2) { \
73-
errorstream<< "Invalid pos for element " << a << "specified: \"" \
73+
errorstream<< "Invalid pos for element " << a << " specified: \"" \
7474
<< parts[b] << "\"" << std::endl; \
7575
return; \
7676
}
7777

7878
#define MY_CHECKGEOM(a,b) \
7979
if (v_geom.size() != 2) { \
8080
errorstream<< "Invalid geometry for element " << a << \
81-
"specified: \"" << parts[b] << "\"" << std::endl; \
81+
" specified: \"" << parts[b] << "\"" << std::endl; \
8282
return; \
8383
}
8484
/*
@@ -2725,16 +2725,16 @@ void GUIFormSpecMenu::parseModel(parserData *data, const std::string &element)
27252725
{
27262726
std::vector<std::string> parts = split(element, ';');
27272727

2728-
if (parts.size() < 5 || (parts.size() > 8 &&
2728+
if (parts.size() < 5 || (parts.size() > 9 &&
27292729
m_formspec_version <= FORMSPEC_API_VERSION)) {
27302730
errorstream << "Invalid model element (" << parts.size() << "): '" << element
27312731
<< "'" << std::endl;
27322732
return;
27332733
}
27342734

27352735
// Avoid length checks by resizing
2736-
if (parts.size() < 8)
2737-
parts.resize(8);
2736+
if (parts.size() < 9)
2737+
parts.resize(9);
27382738

27392739
std::vector<std::string> v_pos = split(parts[0], ',');
27402740
std::vector<std::string> v_geom = split(parts[1], ',');
@@ -2744,6 +2744,7 @@ void GUIFormSpecMenu::parseModel(parserData *data, const std::string &element)
27442744
std::vector<std::string> vec_rot = split(parts[5], ',');
27452745
bool inf_rotation = is_yes(parts[6]);
27462746
bool mousectrl = is_yes(parts[7]) || parts[7].empty(); // default true
2747+
std::vector<std::string> frame_loop = split(parts[8], ',');
27472748

27482749
MY_CHECKPOS("model", 0);
27492750
MY_CHECKGEOM("model", 1);
@@ -2794,6 +2795,16 @@ void GUIFormSpecMenu::parseModel(parserData *data, const std::string &element)
27942795
e->enableContinuousRotation(inf_rotation);
27952796
e->enableMouseControl(mousectrl);
27962797

2798+
s32 frame_loop_begin = 0;
2799+
s32 frame_loop_end = 0x7FFFFFFF;
2800+
2801+
if (frame_loop.size() == 2) {
2802+
frame_loop_begin = stoi(frame_loop[0]);
2803+
frame_loop_end = stoi(frame_loop[1]);
2804+
}
2805+
2806+
e->setFrameLoop(frame_loop_begin, frame_loop_end);
2807+
27972808
auto style = getStyleForElement("model", spec.fname);
27982809
e->setStyles(style);
27992810
e->drop();

Diff for: ‎src/gui/guiScene.cpp

+9
Original file line numberDiff line numberDiff line change
@@ -152,6 +152,15 @@ void GUIScene::setStyles(const std::array<StyleSpec, StyleSpec::NUM_STATES> &sty
152152
setBackgroundColor(style.getColor(StyleSpec::BGCOLOR, m_bgcolor));
153153
}
154154

155+
/**
156+
* Sets the frame loop range for the mesh
157+
*/
158+
void GUIScene::setFrameLoop(s32 begin, s32 end)
159+
{
160+
if (m_mesh->getStartFrame() != begin || m_mesh->getEndFrame() != end)
161+
m_mesh->setFrameLoop(begin, end);
162+
}
163+
155164
/* Camera control functions */
156165

157166
inline void GUIScene::calcOptimalDistance()

Diff for: ‎src/gui/guiScene.h

+1
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@ class GUIScene : public gui::IGUIElement
3636
scene::IAnimatedMeshSceneNode *setMesh(scene::IAnimatedMesh *mesh = nullptr);
3737
void setTexture(u32 idx, video::ITexture *texture);
3838
void setBackgroundColor(const video::SColor &color) noexcept { m_bgcolor = color; };
39+
void setFrameLoop(s32 begin, s32 end);
3940
void enableMouseControl(bool enable) noexcept { m_mouse_ctrl = enable; };
4041
void setRotation(v2f rot) noexcept { m_custom_rot = rot; };
4142
void enableContinuousRotation(bool enable) noexcept { m_inf_rot = enable; };

0 commit comments

Comments
 (0)