@blnmrk0101 (blnmrk0101) posted a new topic, subject "Tetris-like game - General help & suggestions". It read:

   Hello, I am trying to build a tetris-like / tetris-based game. What I have so far is this (sorry but I couldn't find how to show the gif here):http://imgur.com/a/njJd5
    
    As you can see, the player can select a piece and then he can move the piece to the selected square. He can repeat by selecting other pieces. First issue here is the green piece, when you choose it and place it on a square it shrinks to cover only one block and not three blocks (its base is three blocks wide).
    
    What I want to achieve in my game is something like that: http://imgur.com/a/uaS1M
    
    Player should be able to choose a piece and place it on the selected square, then other pieces should fill the line where the chosen piece is. Like the red piece is placed and then the blue piece comes next to it and so on until the line is filled. I don't want the pieces go outside the borders or the barriers. Then the procedure should continue like the green piece, which is placed (in three blocks) on the next, downwards line (here I made a little mistake, I missed the two squared line because the piece was larger, normally it should be placed just in the next line).
    
    Here is my blend file also t1.blend (3.46 MB)
    
    Is that possible with the bge or should I stay in animation? Am I going in the right direction with my script or seems like wrong?
    
    Thanks for your time.

So @HG1 (HG1) replied

    Line 50
    [code] 
        piece.worldTransform = tile_obj.worldTransform --&gt; piece.worldPosition = tile_obj.worldPosition
        
    [/code]
    
    I think it would be to complex to move the bricks with a F-Curve, there are to many possible positions. It is better to do the animate it with a python script.  
    With lerp or slerp you can interpolate between start and end vector. So you can move the brick smoothly to his end position.  
    https://docs.blender.org/api/current/mathutils.html?highlight=lerp#mathutils.Vector.lerp  
    https://docs.blender.org/api/current/mathutils.html?highlight=slerp#mathutils.Vector.slerp

@JustinBarrett (JustinBarrett) replied

    The green block…you need to apply scale. ctrl + a> below ‘apply' choose ‘scale'
    
    it is also a god idea to turn off automatic keyFraming…in the time line window header.

So @blnmrk0101 (blnmrk0101) replied

    HG1:
    
    > Line 50
    [code] 
    >     piece.worldTransform = tile_obj.worldTransform --&gt; piece.worldPosition = tile_obj.worldPosition
    >     
    [/code]
    > 
    > I think it would be to complex to move the bricks with a F-Curve, there are to many possible positions. It is better to do the animate it with a python script.  
    >  With lerp or slerp you can interpolate between start and end vector. So you can move the brick smoothly to his end position.  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=lerp#mathutils.Vector.lerp  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=slerp#mathutils.Vector.slerp
    
    Can I build the algorithm for my game through the animation? Would it be possible after to be dynamic? Like the player can choose a random first block and then my algorithm will run for any case.
    
    Also lerp or slerp will help me not having interpolations between objects and barriers?
    
    JustinBarrett:
    
    > The green block…you need to apply scale. ctrl + a> below ‘apply' choose ‘scale'
    > 
    > it is also a god idea to turn off automatic keyFraming…in the time line window header.
    
    I made the scale and I had forgotten the automatic keyFramming on when I captured the gifs I have posted, thanks.

After which, @blnmrk0101 (blnmrk0101) added

    HG1:
    
    > Line 50
    [code] 
    >     piece.worldTransform = tile_obj.worldTransform --&gt; piece.worldPosition = tile_obj.worldPosition
    >     
    [/code]
    > 
    > I think it would be to complex to move the bricks with a F-Curve, there are to many possible positions. It is better to do the animate it with a python script.  
    >  With lerp or slerp you can interpolate between start and end vector. So you can move the brick smoothly to his end position.  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=lerp#mathutils.Vector.lerp  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=slerp#mathutils.Vector.slerp
    
    Can I build the algorithm for my game through the animation? Would it be possible after to be dynamic? Like the player can choose a random first block and then my algorithm will run for any case.
    
    Also lerp or slerp will help me not having interpolations between objects and barriers?
    
    JustinBarrett:
    
    > The green block…you need to apply scale. ctrl + a> below ‘apply' choose ‘scale'
    > 
    > it is also a god idea to turn off automatic keyFraming…in the time line window header.
    
    I made the scale and I had forgotten the automatic keyFramming on when I captured the gifs I have posted, thanks.

After which, @blnmrk0101 (blnmrk0101) added

    HG1:
    
    > Line 50
    [code] 
    >     piece.worldTransform = tile_obj.worldTransform --&gt; piece.worldPosition = tile_obj.worldPosition
    >     
    [/code]
    > 
    > I think it would be to complex to move the bricks with a F-Curve, there are to many possible positions. It is better to do the animate it with a python script.  
    >  With lerp or slerp you can interpolate between start and end vector. So you can move the brick smoothly to his end position.  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=lerp#mathutils.Vector.lerp  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=slerp#mathutils.Vector.slerp
    
    Can I build the algorithm for my game through the animation? Would it be possible after to be dynamic? Like the player can choose a random first block and then my algorithm will run for any case.
    
    Also lerp or slerp will help me not having interpolations between objects and barriers?
    
    JustinBarrett:
    
    > The green block…you need to apply scale. ctrl + a> below ‘apply' choose ‘scale'
    > 
    > it is also a god idea to turn off automatic keyFraming…in the time line window header.
    
    I made the scale and I had forgotten the automatic keyFramming on when I captured the gifs I have posted, thanks.

Then @blnmrk0101 (blnmrk0101) said

    HG1:
    
    > Line 50
    [code] 
    >     piece.worldTransform = tile_obj.worldTransform --&gt; piece.worldPosition = tile_obj.worldPosition
    >     
    [/code]
    > 
    > I think it would be to complex to move the bricks with a F-Curve, there are to many possible positions. It is better to do the animate it with a python script.  
    >  With lerp or slerp you can interpolate between start and end vector. So you can move the brick smoothly to his end position.  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=lerp#mathutils.Vector.lerp  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=slerp#mathutils.Vector.slerp
    
    Can I build the algorithm for my game through the animation? Would it be possible after to be dynamic? Like the player can choose a random first block and then my algorithm will run for any case.
    
    Also lerp or slerp will help me not having interpolations between objects and barriers?
    
    JustinBarrett:
    
    > The green block…you need to apply scale. ctrl + a> below ‘apply' choose ‘scale'
    > 
    > it is also a god idea to turn off automatic keyFraming…in the time line window header.
    
    I made the scale and I had forgotten the automatic keyFramming on when I captured the gifs I have posted, thanks.

To which @blnmrk0101 (blnmrk0101) replied

    HG1:
    
    > Line 50
    [code] 
    >     piece.worldTransform = tile_obj.worldTransform --&gt; piece.worldPosition = tile_obj.worldPosition
    >     
    [/code]
    > 
    > I think it would be to complex to move the bricks with a F-Curve, there are to many possible positions. It is better to do the animate it with a python script.  
    >  With lerp or slerp you can interpolate between start and end vector. So you can move the brick smoothly to his end position.  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=lerp#mathutils.Vector.lerp  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=slerp#mathutils.Vector.slerp
    
    Can I build the algorithm for my game through the animation? Would it be possible after to be dynamic? Like the player can choose a random first block and then my algorithm will run for any case.
    
    Also lerp or slerp will help me not having interpolations between objects and barriers?
    
    JustinBarrett:
    
    > The green block…you need to apply scale. ctrl + a> below ‘apply' choose ‘scale'
    > 
    > it is also a god idea to turn off automatic keyFraming…in the time line window header.
    
    I made the scale and I had forgotten the automatic keyFramming on when I captured the gifs I have posted, thanks.

To which @blnmrk0101 (blnmrk0101) replied

    HG1:
    
    > Line 50
    [code] 
    >     piece.worldTransform = tile_obj.worldTransform --&gt; piece.worldPosition = tile_obj.worldPosition
    >     
    [/code]
    > 
    > I think it would be to complex to move the bricks with a F-Curve, there are to many possible positions. It is better to do the animate it with a python script.  
    >  With lerp or slerp you can interpolate between start and end vector. So you can move the brick smoothly to his end position.  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=lerp#mathutils.Vector.lerp  
    >  https://docs.blender.org/api/current/mathutils.html?highlight=slerp#mathutils.Vector.slerp
    
    Can I build the algorithm for my game through the animation? Would it be possible after to be dynamic? Like the player can choose a random first block and then my algorithm will run for any case.
    
    Also lerp or slerp will help me not having interpolations between objects and barriers?

So @blnmrk0101 (blnmrk0101) replied

    Any ideas how can I improve the current situation of my game? The only way is a python script for the animation?  
    Seems like too hard what I want to achieve?

@HG1 (HG1) replied

    > Player should be able to choose a piece and place it on the selected square, then other pieces should fill the line where the chosen piece is. Like the red piece is placed and then the blue piece comes next to it and so on until the line is filled. I don't want the pieces go outside the borders or the barriers. Then the procedure should continue like the green piece, which is placed (in three blocks) on the next, downwards line (here I made a little mistake, I missed the two squared line because the piece was larger, normally it should be placed just in the next line).
    
    Actually I don't understand how the game play should be (like 3D Tetris).
    
    For collision detection you can use a virtual map (python list) which stores the actual game filed (empty = 0, boarders = 1) and blocked fields (block = 2). This way you can also check if enough space in the row move the object in.  
    Or you can use raycat to detect the boarders and other blocks. But you need to change the raylength for bigger blocks.
    
    > Can I build the algorithm for my game through the animation?
    
    It is possible but you need one for every possible position. For your game grid 7x7 you need 49 - 9 = 40 different animations, to move the bricks from the outside the boarder to the grid (second video).
    
    So it is much easier to do this animation in code with lerp. For lerp the positioning need to be called every frame until the block has reach his end position. The result of lerp can be used to update the piece.worldPosition. So it will start fast and slows down to the end.
    [code] 
        piece.worldPosition = tile_obj.worldPosition.lerp(piece.worldPosition, 0.9)
        
    [/code]
    
    If you only want to have a continuous speed you only need to add a small value to the movement vector until the block has reached his end position. If the last movement step is bigger then the difference to the end position you need to set the block to the end position.
    
    Here is a Youtube video which shows how to do a normal 2D Tetris. Maybe it will help you a bit.

So @blnmrk0101 (blnmrk0101) replied

    > Actually I don't understand how the game play should be (like 3D Tetris).
    
    It's not really tetris-like, just uses the block of Tetris. It's much difficult at the moment the representation in absolute Tetris style, although I would love to do it.
    
    > For collision detection you can use a virtual map (python list) which stores the actual game filed (empty = 0, boarders = 1) and blocked fields (block = 2). This way you can also check if enough space in the row move the object in.  
    >  Or you can use raycat to detect the boarders and other blocks. But you need to change the raylength for bigger blocks.
    
    I cannot say I had much success with either virtual map or raycat, although the piece will detect the border or the barrier, then it will move in a physical way that doesn't offer me what I want. So, I think maybe it's unnecessary to include that detection if I proceed with the animation way and not in absolute gaming terms.
    
    > It is possible but you need one for every possible position. For your game grid 7x7 you need 49 - 9 = 40 different animations, to move the bricks from the outside the boarder to the grid (second video).
    > 
    > So it is much easier to do this animation in code with lerp. For lerp the positioning need to be called every frame until the block has reach his end position. The result of lerp can be used to update the piece.worldPosition. So it will start fast and slows down to the end.
    [code] 
    >     piece.worldPosition = tile_obj.worldPosition.lerp(piece.worldPosition, 0.9)
    >     
    [/code]
    > 
    > If you only want to have a continuous speed you only need to add a small value to the movement vector until the block has reached his end position. If the last movement step is bigger then the difference to the end position you need to set the block to the end position.
    
    Lerp looks like tricky for me. If I am understanding well what you suggest me to do is to animate the positioning of every piece from start to possible end positions, and then lerp will call the frame that is needed every time in order to run the animation in the right way. Am I correct or totally missing the concept?
    
    A working example would be much appreciated, if there is one, because I couldn't find something to clear me how the things should work with lerp.

After which, @HG1 (HG1) added

    > Lerp looks like tricky for me. If I am understanding well what you suggest me to do is to animate the positioning of every piece from start to possible end positions, and then lerp will call the frame that is needed every time in order to run the animation in the right way. Am I correct or totally missing the concept?
    
    No you calculate the position directly. Not the frame of a F-Curve animation.
    
    Only for animation (linear motion) nothing else.
    [code] 
        import bge
         
        PIECE_PROPERTY = 'PIECE'
        TILE_PROPERTY = 'TILE'
         
        PIECE_SELECT_COLOR = [1, 1, 1, 1]
        PIECE_DESELECT_COLOR = [0.5, 0.5, 0.5, 1]
         
        TILE_SELECT_COLOR = [1, 1, 1, 1]
        TILE_DESELECT_COLOR = [0.5, 0.5, 0.5, 1]
         
        ALIGN_TO_FACE_NORMAL = True  # Aligns to face normal of a random vertex in the hit object
         
        
        bge.render.showMouse(True)
         
        def init(cont):
            '''Deselect all pieces'''
            for obj in cont.owner.scene.objects:
                if PIECE_PROPERTY in obj:
                    obj.color = PIECE_DESELECT_COLOR
                elif TILE_PROPERTY in obj:
                    obj.color = TILE_DESELECT_COLOR
            cont.owner['activePiece'] = None
            cont.owner['activeTile'] = None
            cont.owner["move"] = False
            cont.script = __name__ + '.run'
         
        def run(cont):
            # Get teh object the mouse is over by casting a ray from the camera:
            cam = cont.owner.scene.active_camera
            pos = bge.logic.mouse.position
            hit_obj = cam.getScreenRay(pos[0], pos[1], 100)
           
            if bge.logic.mouse.events[bge.events.LEFTMOUSE] == bge.logic.KX_INPUT_JUST_ACTIVATED:
                if hit_obj is not None:
                    # Select the piece
                    if PIECE_PROPERTY in hit_obj:
                        select_piece(cont, hit_obj)
                       
                    elif TILE_PROPERTY in hit_obj and cont.owner['activePiece'] is not None:
                        cont.owner["move"] = True
         
                else:
                    deselect_piece(cont)
                    
            if cont.owner["move"]:
                move_piece_to_tile(cont, cont.owner['activePiece'], cont.owner['activeTile'])
           
            hover(cont, hit_obj)
         
        def move_piece_to_tile(cont, piece, tile_obj):
            vect = tile_obj.worldPosition - piece.worldPosition
            piece.worldPosition += vect.normalized() * 0.2 
            #print(vect.length)
            if  abs(vect.length) &lt; 0.11:
                piece.worldPosition = tile_obj.worldPosition
                cont.owner["move"] = False
        
            if ALIGN_TO_FACE_NORMAL:
                # Align the tile to the direction of tile (using a random vertex - I hope the tiles are flat)
                mesh = tile_obj.meshes[0]
                vertex = mesh.getVertex(0, 0)
                normal = vertex.normal  # Vertex's normal direction
                up = tile_obj.worldOrientation * normal  # Rotate normal by tile objects orientation
                piece.alignAxisToVect(up, 2, 1)
           
         
        def deselect_piece(cont):
            '''Deselects the currently selected piece'''
            if cont.owner['activePiece'] is not None:
                cont.owner['activePiece'].color = PIECE_DESELECT_COLOR
                cont.owner['activePiece'] = None
         
        def select_piece(cont, hit_obj):
            '''Deselect current piece and select the newpiece the mouse is over '''
            #Deselect old piece
            deselect_piece(cont)
         
            #Select the new piece
            hit_obj.color = PIECE_SELECT_COLOR
            cont.owner['activePiece'] = hit_obj
               
               
        def hover(cont, hit_obj):
            '''Does tile highlighting/hovering'''
            if cont.owner["move"] == False:
                if hit_obj is not None:
                    #Remove highlighting of existing tile
                    if cont.owner['activeTile'] is not None:
                        cont.owner['activeTile'].color = TILE_DESELECT_COLOR
                        
                    #If we're hovering over a tile, highlight it
                    if TILE_PROPERTY in hit_obj:
                        cont.owner['activeTile'] = hit_obj
                        hit_obj.color = TILE_SELECT_COLOR
                else:
                    # If we're not hovering over a tile, remove the highlighting and deselect the tile
                    if cont.owner['activeTile'] is not None:
                        cont.owner['activeTile'].color = TILE_DESELECT_COLOR
                    else:
                        cont.owner['activeTile'] = None
        
        
    [/code]

@blnmrk0101 (blnmrk0101) replied

    Thanks for your help. I am sorry but I am really struggling to understand what you are doing here and what you mean to animate with lerp. I am going through many tutorials but I am getting more confused.
    
    From what I see I think the best way will be the player to choose where to place the first object and then the animation will run to complete the algorithm. Maybe you are trying to tell me the same and that I should do it with lerp, but I cannot understand how to use it.

So @HG1 (HG1) replied

    Lerp don't place any object, don't make any collision check nor is it an algorithm for automatically placement.  
    Lerp is only if you want to slow down the moving animation on the end. Like the standard F-Curve animation it will do, if you don't change it to linear. My example don't use lerp because I thought the animation looks nicer without.
    
    For the automatic placement you need to write an algorithm which select and set the target position for your other blocks.

After which, @blnmrk0101 (blnmrk0101) added

    Okay, I not totally out of this, I got it. But in your example what you are actually doing?

To which @HG1 (HG1) replied

    Instead of just let the brick jump to the end target field, it slowly moving (animated with code instead of a fix F-Curve) the brick from outside the boarder to the target field. Like in the second video.


{'source': 'discourse', 'url': 'https://blenderartists.org/t/tetris-like-game-general-help-suggestions/694882', 'title': 'Tetris-like game - General help & suggestions', 'views': 860, 'has_accepted_answer': False, 'word_count': 3163, 'like_count': 0, 'reply_count': 8, 'participant_count': 3, 'posts': 17, 'tags': '', 'author': '@blnmrk0101 (blnmrk0101)', 'participants': '@blnmrk0101 (blnmrk0101), @HG1 (HG1), @JustinBarrett (JustinBarrett)', 'image_url': [None], 'created_at': '2017-08-26T07:09:04.000Z', 'last_posted_at': '2017-09-01T08:15:00.000Z'}