1
fork

Configure Feed

Select the types of activity you want to include in your feed.

feat: improve slam

+64 -6
+34 -2
physics_engine.vhd
··· 52 52 -- Physics tuning 53 53 constant GRAVITY : std_logic_vector(9 downto 0) := CONV_STD_LOGIC_VECTOR(1, 10); 54 54 constant IMPULSE : std_logic_vector(9 downto 0) := CONV_STD_LOGIC_VECTOR(3, 10); 55 - constant SLAM_FORCE : std_logic_vector(9 downto 0) := CONV_STD_LOGIC_VECTOR(4, 10); 55 + constant SLAM_TAP_FORCE : std_logic_vector(9 downto 0) := CONV_STD_LOGIC_VECTOR(18, 10); 56 + constant SLAM_BOOST_CLOSE : std_logic_vector(9 downto 0) := CONV_STD_LOGIC_VECTOR(24, 10); 57 + constant SLAM_BOOST_MED : std_logic_vector(9 downto 0) := CONV_STD_LOGIC_VECTOR(16, 10); 58 + constant SLAM_BOOST_FAR : std_logic_vector(9 downto 0) := CONV_STD_LOGIC_VECTOR(8, 10); 59 + constant SLAM_CLOSE_THR : std_logic_vector(10 downto 0) := CONV_STD_LOGIC_VECTOR(270, 11); 60 + constant SLAM_MED_THR : std_logic_vector(10 downto 0) := CONV_STD_LOGIC_VECTOR(660, 11); 56 61 -- Initial jump: full force at zero velocity, tapers off as |vel_y| rises. 57 62 -- Piecewise lookup approximates: max(JUMP_MIN, JUMP_BASE*JUMP_SCALE/(JUMP_SCALE+|vy|)) 58 63 constant JUMP_BASE : integer := 14; -- force at zero velocity ··· 87 92 signal squish_h : std_logic := '0'; 88 93 signal on_ground : std_logic := '0'; 89 94 signal jump_pressed : std_logic := '0'; 95 + signal slam_held : std_logic := '0'; 96 + signal slam_start_y : std_logic_vector(10 downto 0) := (others => '0'); 97 + signal prev_key_s : std_logic := '0'; 90 98 91 99 signal abs_vel_x : std_logic_vector(9 downto 0); 92 100 signal abs_vel_y : std_logic_vector(9 downto 0); ··· 149 157 variable abs_vy_int : integer; 150 158 variable jforce_int : integer; 151 159 variable jforce_slv : std_logic_vector(9 downto 0); 160 + variable slam_dist : std_logic_vector(10 downto 0); 161 + variable slam_boost : std_logic_vector(9 downto 0); 152 162 begin 153 163 wait until vert_sync'event and vert_sync = '1'; 154 164 ··· 180 190 vy := vy - JUMP_BOUNCE; 181 191 end if; 182 192 183 - if key_s = '1' and on_ground = '0' then vy := vy + SLAM_FORCE; end if; 193 + -- S slam: rising edge in air = tap burst downward; hold to get landing boost 194 + if key_s = '1' and prev_key_s = '0' and on_ground = '0' then 195 + slam_start_y <= pos_y; 196 + slam_held <= '1'; 197 + vy := vy + SLAM_TAP_FORCE; 198 + end if; 199 + if key_s = '0' then slam_held <= '0'; end if; 200 + prev_key_s <= key_s; 184 201 185 202 if key_a = '1' then 186 203 if on_ground = '1' then vx := vx - IMPULSE; else vx := vx - 2; end if; ··· 346 363 end if; 347 364 end if; 348 365 end loop; 366 + 367 + -- == HOLD-SLAM LANDING BOOST == 368 + -- Bigger boost when slam started closer to the surface 369 + if grounded = '1' and slam_held = '1' then 370 + slam_dist := py - slam_start_y; 371 + if slam_dist < SLAM_CLOSE_THR then 372 + slam_boost := SLAM_BOOST_CLOSE; 373 + elsif slam_dist < SLAM_MED_THR then 374 + slam_boost := SLAM_BOOST_MED; 375 + else 376 + slam_boost := SLAM_BOOST_FAR; 377 + end if; 378 + vy := vy - slam_boost; 379 + slam_held <= '0'; 380 + end if; 349 381 350 382 -- == COMMIT == 351 383 vel_x <= vx;
+30 -4
visualizer.py
··· 23 23 # --- Physics constants (match VHDL exactly) --- 24 24 GRAVITY = 1 25 25 IMPULSE = 3 26 - SLAM_FORCE = 4 26 + SLAM_TAP_FORCE = 18 # instant downward burst on S press in air 27 + SLAM_BOOST_CLOSE = 24 # upward boost on hold-slam landing, close range 28 + SLAM_BOOST_MED = 16 # upward boost, medium range 29 + SLAM_BOOST_FAR = 8 # upward boost, far range 30 + SLAM_CLOSE_THR = 80 # pixels: "close to surface" threshold 31 + SLAM_MED_THR = 200 # pixels: "medium distance" threshold 27 32 AIR_CONTROL = 2 28 33 JUMP_FORCE = 14 # initial jump force at zero velocity (scales down with |vel_y|) 29 34 JUMP_VEL_SCALE = 12 # velocity magnitude at which initial jump force is halved ··· 85 90 squish_h = False # False = vertical squish (floor/ceil), True = horizontal squish (walls) 86 91 on_ground = False 87 92 jump_pressed = False 93 + slam_held = False 94 + slam_start_y = 0 95 + prev_key_s = False 88 96 89 97 keys_held = {'w': False, 'a': False, 's': False, 'd': False} 90 98 trail = [] ··· 108 116 char_x, char_y = 100, 200 109 117 vel_x = vel_y = to_unsigned(0) 110 118 squish = 0; squish_h = False; on_ground = False; jump_pressed = False 119 + slam_held = False; slam_start_y = 0; prev_key_s = False 111 120 trail.clear() 112 121 elif event.type == pygame.KEYUP: 113 122 if event.key == pygame.K_w: keys_held['w'] = False ··· 143 152 # Holding W while bouncing: fixed boost so trampoline accumulates each contact 144 153 vy = (vy - JUMP_BOUNCE) & MASK 145 154 146 - # S: slam (air only) 147 - if keys_held['s'] and not on_ground: 148 - vy = (vy + SLAM_FORCE) & MASK 155 + # S slam: rising edge in air = tap burst downward; hold to get landing boost 156 + if keys_held['s'] and not prev_key_s and not on_ground: 157 + slam_start_y = char_y 158 + slam_held = True 159 + vy = (vy + SLAM_TAP_FORCE) & MASK 160 + if not keys_held['s']: 161 + slam_held = False 162 + prev_key_s = keys_held['s'] 149 163 150 164 # A/D 151 165 if keys_held['a']: ··· 311 325 loss = abs(svy) >> BOUNCE_SHIFT 312 326 svy = svy - loss if svy > 0 else svy + loss 313 327 vy = to_unsigned(svy) 328 + 329 + # Hold-slam landing boost: bigger boost when slam started closer to the surface 330 + if grounded and slam_held: 331 + dist = py - slam_start_y 332 + if dist < SLAM_CLOSE_THR: 333 + slam_boost_val = SLAM_BOOST_CLOSE 334 + elif dist < SLAM_MED_THR: 335 + slam_boost_val = SLAM_BOOST_MED 336 + else: 337 + slam_boost_val = SLAM_BOOST_FAR 338 + vy = (vy - slam_boost_val) & MASK 339 + slam_held = False 314 340 315 341 # Commit 316 342 char_x = px