Pondering too quickly

- Fixed idle instruction only idling for t-1
- Made keyframe skipping a little easier
- Added option to register keyframes as part of a text window builder
- PonderUI now stalls the scene briefly after skips
This commit is contained in:
simibubi 2021-03-12 20:42:37 +01:00
parent 678ddfa764
commit 841bba04bd
7 changed files with 188 additions and 135 deletions

View file

@ -5,150 +5,170 @@ import com.simibubi.create.foundation.gui.widgets.AbstractSimiWidget;
import com.simibubi.create.foundation.utility.AnimationTickHolder; import com.simibubi.create.foundation.utility.AnimationTickHolder;
import com.simibubi.create.foundation.utility.ColorHelper; import com.simibubi.create.foundation.utility.ColorHelper;
import com.simibubi.create.foundation.utility.LerpedFloat; import com.simibubi.create.foundation.utility.LerpedFloat;
import net.minecraft.client.Minecraft;
import net.minecraft.client.audio.SoundHandler; import net.minecraft.client.audio.SoundHandler;
import net.minecraft.client.gui.FontRenderer;
import net.minecraftforge.fml.client.gui.GuiUtils; import net.minecraftforge.fml.client.gui.GuiUtils;
import org.antlr.v4.runtime.misc.IntegerList; import org.antlr.v4.runtime.misc.IntegerList;
public class PonderProgressBar extends AbstractSimiWidget { public class PonderProgressBar extends AbstractSimiWidget {
LerpedFloat progress; LerpedFloat progress;
LerpedFloat flash; LerpedFloat flash;
PonderUI ponder; PonderUI ponder;
public PonderProgressBar(PonderUI ponder, int xIn, int yIn, int widthIn, int heightIn) { public PonderProgressBar(PonderUI ponder, int xIn, int yIn, int widthIn, int heightIn) {
super(xIn, yIn, widthIn, heightIn); super(xIn, yIn, widthIn, heightIn);
this.ponder = ponder; this.ponder = ponder;
progress = LerpedFloat.linear() progress = LerpedFloat.linear()
.startWithValue(0); .startWithValue(0);
flash = LerpedFloat.linear() flash = LerpedFloat.linear()
.startWithValue(0); .startWithValue(0);
} }
public void tick() { public void tick() {
progress.chase(ponder.getActiveScene().getSceneProgress(), .5f, LerpedFloat.Chaser.EXP); progress.chase(ponder.getActiveScene()
progress.tickChaser(); .getSceneProgress(), .5f, LerpedFloat.Chaser.EXP);
progress.tickChaser();
if (isHovered) if (isHovered)
flash(); flash();
} }
public void flash() { public void flash() {
float value = flash.getValue(); float value = flash.getValue();
flash.setValue(value + (1 - value) * .2f); flash.setValue(value + (1 - value) * .2f);
} }
public void dim() { public void dim() {
float value = flash.getValue(); float value = flash.getValue();
flash.setValue(value * .5f); flash.setValue(value * .5f);
} }
@Override @Override
protected boolean clicked(double mouseX, double mouseY) { protected boolean clicked(double mouseX, double mouseY) {
return this.active && this.visible && return this.active && this.visible && !ponder.getActiveScene().keyframeTimes.isEmpty()
!ponder.getActiveScene().keyframeTimes.isEmpty() && && mouseX >= (double) this.x && mouseX < (double) (this.x + this.width) && mouseY >= (double) this.y - 3
mouseX >= (double)this.x && && mouseY < (double) (this.y + this.height + 20);
mouseX < (double)(this.x + this.width) && }
mouseY >= (double)this.y - 3 &&
mouseY < (double)(this.y + this.height + 3);
}
@Override @Override
public void onClick(double mouseX, double mouseY) { public void onClick(double mouseX, double mouseY) {
PonderScene activeScene = ponder.getActiveScene(); PonderScene activeScene = ponder.getActiveScene();
int clickedAtTime = (int) ((mouseX - x) / ((double) width) * activeScene.totalTime); int clickedAtTime = (int) ((mouseX - x) / ((double) width) * activeScene.totalTime);
int seekTime = 0; int seekTime = 0;
IntegerList keyframeTimes = activeScene.keyframeTimes; IntegerList keyframeTimes = activeScene.keyframeTimes;
for (int i = 0; i < keyframeTimes.size(); i++) { for (int i = 0; i < keyframeTimes.size(); i++) {
int keyframeTime = keyframeTimes.get(i); int keyframeTime = keyframeTimes.get(i);
if (keyframeTime > clickedAtTime) if (keyframeTime > clickedAtTime)
break; break;
seekTime = keyframeTime; seekTime = keyframeTime;
} }
ponder.seekToTime(seekTime); ponder.seekToTime(seekTime);
} }
public int getHoveredKeyframeIndex(double mouseX) { public int getHoveredKeyframeIndex(double mouseX) {
PonderScene activeScene = ponder.getActiveScene(); PonderScene activeScene = ponder.getActiveScene();
int clickedAtTime = (int) ((mouseX - x) / ((double) width) * activeScene.totalTime); int clickedAtTime = (int) ((mouseX - x) / ((double) width) * activeScene.totalTime);
int index = -1; int index = -1;
IntegerList keyframeTimes = activeScene.keyframeTimes; IntegerList keyframeTimes = activeScene.keyframeTimes;
for (int i = 0; i < keyframeTimes.size(); i++) { for (int i = 0; i < keyframeTimes.size(); i++) {
int keyframeTime = keyframeTimes.get(i); int keyframeTime = keyframeTimes.get(i);
if (keyframeTime > clickedAtTime) if (keyframeTime > clickedAtTime)
break; break;
index = i; index = i;
} }
return index; return index;
} }
@Override @Override
public void renderButton(int mouseX, int mouseY, float partialTicks) { public void renderButton(int mouseX, int mouseY, float partialTicks) {
isHovered = clicked(mouseX, mouseY); isHovered = clicked(mouseX, mouseY);
RenderSystem.pushMatrix(); RenderSystem.pushMatrix();
RenderSystem.translated(0, 0, 400); RenderSystem.translated(0, 0, 400);
PonderUI.renderBox(x, y, width, height, false); PonderUI.renderBox(x, y, width, height, false);
RenderSystem.popMatrix(); RenderSystem.popMatrix();
RenderSystem.pushMatrix(); RenderSystem.pushMatrix();
RenderSystem.translated(x - 2, y - 2, 0); RenderSystem.translated(x - 2, y - 2, 0);
RenderSystem.pushMatrix(); RenderSystem.pushMatrix();
RenderSystem.scaled((width + 4) * progress.getValue(partialTicks), 1, 1); RenderSystem.scaled((width + 4) * progress.getValue(partialTicks), 1, 1);
GuiUtils.drawGradientRect(500, 0, 3, 1, 4, 0x60ffeedd, 0x60ffeedd); GuiUtils.drawGradientRect(500, 0, 3, 1, 4, 0x80ffeedd, 0x80ffeedd);
RenderSystem.popMatrix(); GuiUtils.drawGradientRect(500, 0, 4, 1, 5, 0x50ffeedd, 0x50ffeedd);
RenderSystem.popMatrix();
renderKeyframes(mouseX, partialTicks); renderKeyframes(mouseX, partialTicks);
RenderSystem.popMatrix(); RenderSystem.popMatrix();
} }
private void renderKeyframes(int mouseX, float partialTicks) { private void renderKeyframes(int mouseX, float partialTicks) {
PonderScene activeScene = ponder.getActiveScene(); PonderScene activeScene = ponder.getActiveScene();
int hoverStartColor; int hoverStartColor;
int hoverEndColor; int hoverEndColor;
int hoverIndex; int hoverIndex;
if (isHovered) {
hoverIndex = getHoveredKeyframeIndex(mouseX);
float flashValue = flash.getValue(partialTicks) * 3 + (float) Math.sin((AnimationTickHolder.getTicks() + partialTicks) / 6); if (isHovered) {
hoverIndex = getHoveredKeyframeIndex(mouseX);
float flashValue = flash.getValue(partialTicks) * 3
+ (float) Math.sin((AnimationTickHolder.getTicks() + partialTicks) / 6);
hoverEndColor = ColorHelper.applyAlpha(0x70ffffff, flashValue); hoverEndColor = ColorHelper.applyAlpha(0x70ffffff, flashValue);
hoverStartColor = ColorHelper.applyAlpha(0x30ffffff, flashValue); hoverStartColor = ColorHelper.applyAlpha(0x30ffffff, flashValue);
} } else {
else { hoverIndex = -1;
hoverIndex = -1; hoverEndColor = 0;
hoverEndColor = 0; hoverStartColor = 0;
hoverStartColor = 0; }
}
IntegerList keyframeTimes = activeScene.keyframeTimes; IntegerList keyframeTimes = activeScene.keyframeTimes;
for (int i = 0; i < keyframeTimes.size(); i++) { for (int i = 0; i < keyframeTimes.size(); i++) {
int keyframeTime = keyframeTimes.get(i); int keyframeTime = keyframeTimes.get(i);
int keyframePos = (int) (((float) keyframeTime) / ((float) activeScene.totalTime) * (width + 4));
int startColor = i == hoverIndex ? hoverStartColor : 0x60ffeedd; int startColor = i == hoverIndex ? hoverStartColor : 0x30ffeedd;
int endColor = i == hoverIndex ? hoverEndColor : 0x60ffeedd; int endColor = i == hoverIndex ? hoverEndColor : 0x60ffeedd;
int height = i == hoverIndex ? 8 : 4;
int keyframePos = (int) (((float) keyframeTime) / ((float) activeScene.totalTime) * (width + 4)); if (i == hoverIndex) {
GuiUtils.drawGradientRect(500, keyframePos, 1, keyframePos + 1, 4, startColor, endColor); FontRenderer font = Minecraft.getInstance().fontRenderer;
} GuiUtils.drawGradientRect(500, keyframePos, 10, keyframePos + 1, 10 + height, endColor, startColor);
} RenderSystem.pushMatrix();
RenderSystem.translated(0, 0, 400);
String text;
int offset;
if (activeScene.currentTime < keyframeTime) {
text = ">";
offset = -1 - font.getStringWidth(text);
} else {
text = "<";
offset = 3;
}
font.drawString(text, keyframePos + offset, 10, endColor);
RenderSystem.popMatrix();
}
GuiUtils.drawGradientRect(500, keyframePos, -1, keyframePos + 1, 2 + height, startColor, endColor);
}
}
@Override @Override
public void playDownSound(SoundHandler handler) { public void playDownSound(SoundHandler handler) {
} }
} }

View file

@ -13,7 +13,6 @@ import java.util.function.Consumer;
import java.util.function.Function; import java.util.function.Function;
import java.util.function.Supplier; import java.util.function.Supplier;
import com.simibubi.create.foundation.ponder.instructions.KeyframeInstruction;
import org.antlr.v4.runtime.misc.IntegerList; import org.antlr.v4.runtime.misc.IntegerList;
import org.apache.commons.lang3.mutable.MutableDouble; import org.apache.commons.lang3.mutable.MutableDouble;
import org.apache.commons.lang3.mutable.MutableObject; import org.apache.commons.lang3.mutable.MutableObject;
@ -271,6 +270,8 @@ public class PonderScene {
instruction.tick(this); instruction.tick(this);
if (instruction.isComplete()) { if (instruction.isComplete()) {
iterator.remove(); iterator.remove();
if (instruction.isBlocking())
break;
continue; continue;
} }
if (instruction.isBlocking()) if (instruction.isBlocking())
@ -299,10 +300,9 @@ public class PonderScene {
stoppedCounting = true; stoppedCounting = true;
} }
public void markKeyframe() { public void markKeyframe(int offset) {
if (!stoppedCounting) { if (!stoppedCounting)
keyframeTimes.add(totalTime); keyframeTimes.add(totalTime + offset);
}
} }
public void addElement(PonderElement e) { public void addElement(PonderElement e) {

View file

@ -68,6 +68,7 @@ public class PonderUI extends AbstractSimiScreen {
private PonderButton left, right, scan, chap, userMode; private PonderButton left, right, scan, chap, userMode;
private PonderProgressBar progressBar; private PonderProgressBar progressBar;
private int skipCooling = 0;
public static PonderUI of(ResourceLocation id) { public static PonderUI of(ResourceLocation id) {
return new PonderUI(PonderRegistry.compile(id)); return new PonderUI(PonderRegistry.compile(id));
@ -200,6 +201,9 @@ public class PonderUI extends AbstractSimiScreen {
public void tick() { public void tick() {
super.tick(); super.tick();
if (skipCooling > 0)
skipCooling--;
if (referredToByTag != null) { if (referredToByTag != null) {
for (int i = 0; i < scenes.size(); i++) { for (int i = 0; i < scenes.size(); i++) {
PonderScene ponderScene = scenes.get(i); PonderScene ponderScene = scenes.get(i);
@ -222,7 +226,8 @@ public class PonderUI extends AbstractSimiScreen {
PonderScene activeScene = scenes.get(index); PonderScene activeScene = scenes.get(index);
if (!identifyMode) { if (!identifyMode) {
ponderTicks++; ponderTicks++;
activeScene.tick(); if (skipCooling == 0)
activeScene.tick();
} }
lazyIndex.tickChaser(); lazyIndex.tickChaser();
fadeIn.tickChaser(); fadeIn.tickChaser();
@ -247,6 +252,8 @@ public class PonderUI extends AbstractSimiScreen {
replay(); replay();
getActiveScene().seekToTime(time); getActiveScene().seekToTime(time);
if (time != 0)
coolDownAfterSkip();
} }
public void updateIdentifiedItem(PonderScene activeScene) { public void updateIdentifiedItem(PonderScene activeScene) {
@ -312,7 +319,8 @@ public class PonderUI extends AbstractSimiScreen {
@Override @Override
protected void renderWindow(int mouseX, int mouseY, float partialTicks) { protected void renderWindow(int mouseX, int mouseY, float partialTicks) {
RenderSystem.enableBlend(); RenderSystem.enableBlend();
renderVisibleScenes(mouseX, mouseY, identifyMode ? ponderPartialTicksPaused : partialTicks); renderVisibleScenes(mouseX, mouseY,
skipCooling > 0 ? 0 : identifyMode ? ponderPartialTicksPaused : partialTicks);
renderWidgets(mouseX, mouseY, identifyMode ? ponderPartialTicksPaused : partialTicks); renderWidgets(mouseX, mouseY, identifyMode ? ponderPartialTicksPaused : partialTicks);
} }
@ -362,7 +370,7 @@ public class PonderUI extends AbstractSimiScreen {
for (int f = 0; f < 4; f++) { for (int f = 0; f < 4; f++) {
RenderSystem.translated(story.basePlateSize, 0, 0); RenderSystem.translated(story.basePlateSize, 0, 0);
RenderSystem.pushMatrix(); RenderSystem.pushMatrix();
RenderSystem.translated(0, 0, 1/1024f); RenderSystem.translated(0, 0, 1 / 1024f);
GuiUtils.drawGradientRect(0, 0, 0, -story.basePlateSize, 4, 0x66_000000, 0x00_000000); GuiUtils.drawGradientRect(0, 0, 0, -story.basePlateSize, 4, 0x66_000000, 0x00_000000);
RenderSystem.popMatrix(); RenderSystem.popMatrix();
RenderSystem.rotatef(-90, 0, 1, 0); RenderSystem.rotatef(-90, 0, 1, 0);
@ -480,7 +488,7 @@ public class PonderUI extends AbstractSimiScreen {
} }
if (identifyMode) { if (identifyMode) {
if (noWidgetsHovered) { if (noWidgetsHovered && mouseY < height - 80) {
RenderSystem.pushMatrix(); RenderSystem.pushMatrix();
RenderSystem.translated(mouseX, mouseY, 100); RenderSystem.translated(mouseX, mouseY, 100);
if (hoveredTooltipItem.isEmpty()) { if (hoveredTooltipItem.isEmpty()) {
@ -518,11 +526,12 @@ public class PonderUI extends AbstractSimiScreen {
{ {
// Scene overlay // Scene overlay
float scenePT = skipCooling > 0 ? 0 : partialTicks;
RenderSystem.pushMatrix(); RenderSystem.pushMatrix();
RenderSystem.translated(0, 0, 100); RenderSystem.translated(0, 0, 100);
renderOverlay(index, partialTicks); renderOverlay(index, scenePT);
if (indexDiff > 1 / 512f) if (indexDiff > 1 / 512f)
renderOverlay(lazyIndexValue < index ? index - 1 : index + 1, partialTicks); renderOverlay(lazyIndexValue < index ? index - 1 : index + 1, scenePT);
RenderSystem.popMatrix(); RenderSystem.popMatrix();
} }
@ -841,4 +850,8 @@ public class PonderUI extends AbstractSimiScreen {
return true; return true;
} }
public void coolDownAfterSkip() {
skipCooling = 15;
}
} }

View file

@ -203,6 +203,22 @@ public class SceneBuilder {
addInstruction(new RotateSceneInstruction(0, degrees, true)); addInstruction(new RotateSceneInstruction(0, degrees, true));
} }
/**
* Adds a Key Frame at the end of the last delay() instruction for the users to
* skip to
*/
public void addKeyframe() {
addInstruction(KeyframeInstruction.IMMEDIATE);
}
/**
* Adds a Key Frame a couple ticks after the last delay() instruction for the
* users to skip to
*/
public void addLazyKeyframe() {
addInstruction(KeyframeInstruction.DELAYED);
}
public class EffectInstructions { public class EffectInstructions {
public void emitParticles(Vec3d location, Emitter emitter, float amountPerCycle, int cycles) { public void emitParticles(Vec3d location, Emitter emitter, float amountPerCycle, int cycles) {
@ -349,10 +365,6 @@ public class SceneBuilder {
addInstruction(AnimateParrotInstruction.move(link, offset, duration)); addInstruction(AnimateParrotInstruction.move(link, offset, duration));
} }
public void addKeyframe() {
addInstruction(KeyframeInstruction.INSTANCE);
}
} }
public class WorldInstructions { public class WorldInstructions {

View file

@ -27,7 +27,7 @@ public class GantryScenes {
String id = "gantry_" + (pinion ? "carriage" : "shaft"); String id = "gantry_" + (pinion ? "carriage" : "shaft");
String title = "Using Gantry " + (pinion ? "Carriages" : "Shafts"); String title = "Using Gantry " + (pinion ? "Carriages" : "Shafts");
scene.title(id, title); scene.title(id, title);
scene.world.modifyKineticSpeed(util.select.everywhere(), f -> -2 * f); scene.world.modifyKineticSpeed(util.select.everywhere(), f -> -2 * f);
scene.configureBasePlate(0, 0, 5); scene.configureBasePlate(0, 0, 5);
scene.world.showSection(util.select.layer(0), Direction.UP); scene.world.showSection(util.select.layer(0), Direction.UP);
@ -46,10 +46,9 @@ public class GantryScenes {
: "Gantry Shafts form the basis of a gantry setup. Attached Carriages will move along them."; : "Gantry Shafts form the basis of a gantry setup. Attached Carriages will move along them.";
scene.overlay.showText(80) scene.overlay.showText(80)
.attachKeyFrame()
.text(text) .text(text)
.pointAt(util.vector.centerOf(centralShaft)); .pointAt(util.vector.centerOf(centralShaft));
scene.special.addKeyframe();
scene.idle(80); scene.idle(80);
scene.world.hideIndependentSection(gantry, Direction.UP); scene.world.hideIndependentSection(gantry, Direction.UP);
@ -58,10 +57,10 @@ public class GantryScenes {
Vec3d gantryTop = util.vector.topOf(4, 2, 2); Vec3d gantryTop = util.vector.topOf(4, 2, 2);
scene.world.modifyKineticSpeed(util.select.everywhere(), f -> 0f); scene.world.modifyKineticSpeed(util.select.everywhere(), f -> 0f);
scene.overlay.showText(40) scene.overlay.showText(40)
.attachKeyFrame()
.text("Gantry setups can move attached Blocks.") .text("Gantry setups can move attached Blocks.")
.pointAt(gantryTop) .pointAt(gantryTop)
.placeNearTarget(); .placeNearTarget();
scene.special.addKeyframe();
scene.idle(30); scene.idle(30);
Selection planks = util.select.position(5, 3, 1); Selection planks = util.select.position(5, 3, 1);
@ -75,12 +74,11 @@ public class GantryScenes {
scene.idle(20); scene.idle(20);
scene.overlay.showText(80) scene.overlay.showText(80)
.attachKeyFrame()
.sharedText("movement_anchors") .sharedText("movement_anchors")
.pointAt(gantryTop) .pointAt(gantryTop)
.placeNearTarget(); .placeNearTarget();
scene.special.addKeyframe();
scene.idle(80); scene.idle(80);
scene.special.addKeyframe();
scene.world.modifyKineticSpeed(util.select.layer(0), f -> 32f); scene.world.modifyKineticSpeed(util.select.layer(0), f -> 32f);
scene.world.modifyKineticSpeed(util.select.layer(1), f -> -64f); scene.world.modifyKineticSpeed(util.select.layer(1), f -> -64f);
@ -122,12 +120,12 @@ public class GantryScenes {
BlockPos cogPos = util.grid.at(1, 2, 1); BlockPos cogPos = util.grid.at(1, 2, 1);
scene.overlay.showText(60) scene.overlay.showText(60)
.attachKeyFrame()
.colored(PonderPalette.RED) .colored(PonderPalette.RED)
.pointAt(util.vector.centerOf(cogPos.down() .pointAt(util.vector.centerOf(cogPos.down()
.south())) .south()))
.text("Redstone-powered gantry shafts stop moving their carriages") .text("Redstone-powered gantry shafts stop moving their carriages")
.placeNearTarget(); .placeNearTarget();
scene.special.addKeyframe();
scene.idle(70); scene.idle(70);
Selection cogSelection = util.select.position(cogPos); Selection cogSelection = util.select.position(cogPos);
@ -171,10 +169,10 @@ public class GantryScenes {
scene.world.moveSection(gantry2, util.vector.of(-1, 0, 0), 20); scene.world.moveSection(gantry2, util.vector.of(-1, 0, 0), 20);
scene.overlay.showText(80) scene.overlay.showText(80)
.attachKeyFrame()
.text("The movement direction of carriages depend on their shafts' orientation") .text("The movement direction of carriages depend on their shafts' orientation")
.pointAt(util.vector.topOf(1, 1, 3)) .pointAt(util.vector.topOf(1, 1, 3))
.placeNearTarget(); .placeNearTarget();
scene.special.addKeyframe();
scene.idle(80); scene.idle(80);
BlockPos lastShaft = util.grid.at(0, 1, 2); BlockPos lastShaft = util.grid.at(0, 1, 2);
@ -192,10 +190,10 @@ public class GantryScenes {
if (i == 0) { if (i == 0) {
scene.overlay.showText(80) scene.overlay.showText(80)
.attachKeyFrame()
.text("...as well as the rotation direction of the shaft") .text("...as well as the rotation direction of the shaft")
.pointAt(util.vector.blockSurface(lastShaft, Direction.WEST)) .pointAt(util.vector.blockSurface(lastShaft, Direction.WEST))
.placeNearTarget(); .placeNearTarget();
scene.special.addKeyframe();
} }
scene.idle(30); scene.idle(30);
@ -221,10 +219,10 @@ public class GantryScenes {
scene.idle(20); scene.idle(20);
scene.overlay.showText(120) scene.overlay.showText(120)
.attachKeyFrame()
.text("Same rules apply for the propagated rotation") .text("Same rules apply for the propagated rotation")
.pointAt(util.vector.topOf(0, 3, 3)) .pointAt(util.vector.topOf(0, 3, 3))
.placeNearTarget(); .placeNearTarget();
scene.special.addKeyframe();
scene.idle(20); scene.idle(20);
for (boolean flip2 : Iterate.trueAndFalse) { for (boolean flip2 : Iterate.trueAndFalse) {
@ -268,9 +266,9 @@ public class GantryScenes {
scene.world.moveSection(gantry, util.vector.of(0, 2, 0), 40); scene.world.moveSection(gantry, util.vector.of(0, 2, 0), 40);
scene.overlay.showText(60) scene.overlay.showText(60)
.attachKeyFrame()
.text("Gantry shafts attach to a carriage without the need of super glue") .text("Gantry shafts attach to a carriage without the need of super glue")
.independent(20); .independent(20);
scene.special.addKeyframe();
scene.idle(40); scene.idle(40);
scene.world.modifyKineticSpeed(util.select.everywhere(), f -> -f); scene.world.modifyKineticSpeed(util.select.everywhere(), f -> -f);
@ -281,9 +279,9 @@ public class GantryScenes {
scene.world.showIndependentSection(util.select.position(gantryPos2), Direction.DOWN); scene.world.showIndependentSection(util.select.position(gantryPos2), Direction.DOWN);
scene.idle(15); scene.idle(15);
scene.overlay.showText(60) scene.overlay.showText(60)
.attachKeyFrame()
.text("Same applies for carriages on moved Gantry Shafts") .text("Same applies for carriages on moved Gantry Shafts")
.independent(20); .independent(20);
scene.special.addKeyframe();
scene.idle(15); scene.idle(15);
scene.world.moveSection(gantry, util.vector.of(0, 2, 0), 40); scene.world.moveSection(gantry, util.vector.of(0, 2, 0), 40);

View file

@ -71,6 +71,11 @@ public class TextWindowElement extends AnimatedOverlayElement {
return this; return this;
} }
public Builder attachKeyFrame() {
scene.builder().addLazyKeyframe();
return this;
}
} }
@Override @Override

View file

@ -5,9 +5,14 @@ import com.simibubi.create.foundation.ponder.PonderScene;
public class KeyframeInstruction extends PonderInstruction { public class KeyframeInstruction extends PonderInstruction {
public static final KeyframeInstruction INSTANCE = new KeyframeInstruction(); public static final KeyframeInstruction IMMEDIATE = new KeyframeInstruction(false);
public static final KeyframeInstruction DELAYED = new KeyframeInstruction(true);
private boolean delayed;
private KeyframeInstruction() { } private KeyframeInstruction(boolean delayed) {
this.delayed = delayed;
}
@Override @Override
public boolean isComplete() { public boolean isComplete() {
@ -19,6 +24,6 @@ public class KeyframeInstruction extends PonderInstruction {
@Override @Override
public void onScheduled(PonderScene scene) { public void onScheduled(PonderScene scene) {
scene.markKeyframe(); scene.markKeyframe(delayed ? 6 : 0);
} }
} }