I'm trying to figure out what the expected action is in this scenario. Let's assume that there is currently no shift delay and we're at 20G. If we've got this position and the shift right command has been entered: Code: I XXX IIIXXX XXX XXX XX XXX XXX XXX XX XXXXXXXX Do we expect it to catch into the top notch or slide after it's at the bottom? This is assuming that the shift command was entered either during the spawn delay or the first frame of the fall, before the block has fallen any. Certainly any shift entered a frame later would be processed at the bottom of the fall. It seems to me that it should definitely be able to slide into the top notch if the user is able to press the keys fast enough. This question is actually a result of a completely different case, so if this seems unimportant in and of itself, try to answer anyway. Let me know what you think. Thanks again.
if you are refering to TGM, we know the game is running to a fixed framerate of 60 frames per seconds. The frame is the shortest time indice in the game. Here is the basic of the gameplay process instruction order in one frame : Code: Do { 1) Input read 2) Gameplay process: a. Rotation b. Shift (horizontal movement) c. Gravity d. Lock 3) Output Display update } Until top out or last level complete when the Gravity go up to 20G, there is no way you can expect what you described, because the only thing that the engine check is what is under the piece and presently represented by pound char : Code: I XXX XXX IIIXXX XXX XXX XXX XXX XXX XX ==> XX XXX XXX XXX XXX XXX I XXX XX III XX XX###XXX XX###XXX the shift on right side will only be processed on next frame !
As jago says, there is no point where the piece is at the same height as the top notch. There is no way for the player to be "fast enough" in this instance. Without wishing to sound condescending, it's the whole point of 20G...
I was under the impression that there was a frame of falling in 20g? The definition of 20g as I understand it is "falling the height of 20 rows in one frame", not "starting in a hard-dropped position". If that's true, then the question is whether we treat a falling block as jumping from frame to frame or if we try to simulate that it's moved through every pixel during that frame. Well, that's not necessarily true. It's certainly one way to do it. I've already implemented another where the loop looks something like this: Code: Do { 1) Input read 2) Gameplay process: a. Rotation b. Shift (horizontal movement) (making note if a shift was ordered but unable to be executed) c. Apply Gravity: for (1...total_pixels_this_gravity) { increment by a pixel; if we have an un-executed shift { try to shift, if we are able to, we no longer have an un-executed shift } } d. Lock 3) Output Display update } Until top out or last level complete In laymans terms this is saying "I'm going to try to apply your shift through this entire frame, not just at the top of it." Let me clarify how this problem came about in the first place. If we use your loop, when you're dealing with not so high gravity and realistic sideways collisions (where blocks can never overlap each other during a shift) and increments that aren't multiples of the block-size, you have the case where the block will be falling at normal gravity and you will be unable to slide it in sideways. Let me illustrate: Say this is our first frame: Code: # XXXX ##XXXX # XXX XXXX XXXX Now lets say we increment 3 pixels per frame, and that the user is holding down the right shift button. Let's also say our blocks are 16 pixels tall. First frame it's at pixel 0, second frame its at pixel 3, third it's at 6, fourth it's a 9, fifth it's at 12, sixth it's at 15. and now the seventh frame it's at the 18th pixel -- past the crevice -- and it hasn't been able to shift this entire time. If instead we use my algorithm, it will shift during the sixth frame as gravity is being incrementally applied. Of course if we use the shift algorithm from lockjaw, it will slide in during the second frame. But it's trivial to create a scenario with even this algorithm where the shift will be missed: Set the increment to 17 pixels. I'm pretty sure that theoretically we should be able to slide in sideways during 20G play, just that it's made impossible by the compounding of DAS with limited user-reaction time. And of course if the block starts in a hard-dropped position instead of at the top of the graph, it would be impossible to make this shift. I think I recall reading that some of the TGM games have this implemented in the higher levels.
TGM has an order: In each frame, all rotations are processed, then all shifts are processed, then gravity is processed. This is a nice idea that I haven't seen in any Tetris product. If you do add it, here's another suggestion: take DAS into account when calculating the ghost piece position. The New Tetris, the birthplace of square mode, used realistic sideways collisions, but it appeared to have a special rule that applied only when gravity was about to cause the piece to enter a new grid cell. It also never exceeded 1G. Once you're in >1G, the game rule is that you're supposed to change your strategy from lots of slides into cliffs into pyramid stacking. Tough shit if you're in square mode, which depends almost entirely on slides into cliffs. Correct. TGM does not process shifts during the initial frame of an active piece; it processes only rotation and gravity. Neither does LJ when you turn off "Initial sideways motion".
20G "theorically" means that a piece falls 20 rows per frame on a 60 fps game. In practice, it means the piece spawns and falls immediately. I believe this is so because the name appeared after the feature. To be correct, it should be named something like "instant spawn" or "instant gravity". So, to answer your question, the piece won't stack on that hole because it won't spawn on top. And that's the reason why you see several people claiming that the shadow and 20g spawning are essentially the same code or logic.
Alright. I think it's a nifty idea, but like everything else in my game I'll make it an option that can be turned on and off. No point in enforcing it when I can just let you decide.
with instant gravity it seems you would want the piece to reach bottom then slide (to give a solid foundation to stack on). i know this is an extreme example, but i can't imagine wanting a piece to block the center of the well with a big gap underneath, even if it fits best higher up. Code: I XXXX IIIXXXX XXXX XXX X XXXX XXXX XXXX XXX XXXXXXXXXX the situation where you would want it to work would nearly never happen, unless the game sped up from slow gravity to instant from one level to the next. anyway, even if you had this situation when the gravity is instant you could always clear out the 4 rows beneath the hole then fill it in. it seems like the player could play faster if the piece would hit bottom then slide if they were holding down the rightward movement key (or the piece would land on top of the stack on the right, as if it had spawned on that side). otherwise they would have to wait for it to land then slide it, taking a few extra frames to place the piece. if the gravity is anything short of instant, then it seems like the piece should slide into the J shaped hole.
This simply doesn't apply to any mainstream tetris game. The drop increment (I don't like that phrase but can't think of a better one right now) is almost always exactly the height of one block at gravities of 1G or less. Code: Do { 1) Input read 2) Gameplay process: a. Rotation b. Shift (horizontal movement) (making note if a shift was ordered but unable to be executed) c. Apply Gravity: for (1...total_pixels_this_gravity) { increment by a pixel; if we have an un-executed shift { try to shift, if we are able to, we no longer have an un-executed shift } } d. Lock 3) Output Display update } Until top out or last level complete This is an interesting concept, but I doubt it would ever be useful in practice (at least in 20G). In your first example, the starting position would have to be spawn, (you couldn't humanly move a piece left and right again 1 frame later) which makes the exact layout where this could be used extremely unlikely.
If the structure in question was on the right side of the playfield and was accompanied by a similarly sized structure on the left, one could move it right from where it spawned on the left structure and use DAS to slide it into the notch on the one on the right.
Not when you have smoothly scrolling blocks. The increment is usually some prime number like 1 or 2, but it could be something larger, and I wouldn't want to create restrictions. If someone wanted a level that incremented 7 pixels every N milliseconds, they should be able to create it. This particular problem is actually the bug that set me off to creating my own tetris clone. I was playing a low-speed tetris clone called "Tetrablocks", and when it got to the higher levels you weren't guaranteed that the block would be able to slide into niches; sometimes it would and sometimes it wouldn't. The behavior was erratic and incredbily irritating. So I decided to write my own. Then I discovered TGM. To clarify my original post: I don't think this behavior would ever actually be executed in 20G play. Like some posters have noted it would be near impossible to actually input as a user. However, it's theoretically possible if I implement shifts this way, so I wanted to see the reaction to it. Anyway, it's a check box. Actually, it's probably going to be better than a check box. I still haven't worked out my level paradigm, but I'm pretty sure I'm going to be allowing any game setting to be changed any time a level changes, so even if you had a game that started in slow drop (and required this behavior) once it accelerated to high-speed you could just turn it off.
It would work if you allow one to charge DAS and then initiate a firm drop (e.g. hold right and tap up). It would be sort of like a reverse Zangi move or something.
That's a good idea. I'll be sure to put that code in my firm drop function (but not my hard drop function).