function enemy_move_and_collide() { var _y_spd_total = (y_spd + y_spd_kb) * global.time_scale; var _x_spd_total = (x_spd + x_spd_kb) * global.time_scale; if place_meeting(x, y + _y_spd_total, oParentSolid) { while !place_meeting(x, y + sign(_y_spd_total), oParentSolid) y += sign(_y_spd_total); _y_spd_total = 0; y_spd = 0; y_spd_kb = 0; } y += _y_spd_total; if place_meeting(x + _x_spd_total, y, oParentSolid) { while !place_meeting(x + sign(_x_spd_total), y, oParentSolid) x += sign(_x_spd_total); _x_spd_total = 0; x_spd = 0; x_spd_kb = 0; } x += _x_spd_total; } function enemy_check_hitstun() { if hitstun_timer > 0 { hitstun_timer -= global.time_scale; x_spd_kb = lerp(x_spd_kb, 0, 0.2); y_spd_kb = lerp(y_spd_kb, 0, 0.2); x_spd = 0; y_spd = 0; image_blend = c_orange; } else { x_spd_kb = 0; y_spd_kb = 0; image_blend = c_white; } } function enemy_get_hit(_damage, _kb_x, _kb_y) { hp -= _damage; hitstun_timer = hitstun_max; x_spd_kb = _kb_x * kb_factor; y_spd_kb = _kb_y * kb_factor; if hp <= 0 { is_dead = true; instance_destroy(); } } /// @desc 优雅地以该实例为原点,给定宽高、偏移与持续时间为参数,生成敌人碰撞箱 /// @param {real} _x 碰撞箱宽度 /// @param {real} _y 碰撞箱高度 /// @param {real} _x_offset 碰撞箱与该实例在x轴上的偏移量,默认为0 /// @param {real} _y_offset 碰撞箱与该实例在y轴上的偏移量,默认为0 /// @param {real} _duration 碰撞箱持续时间,默认为0,即无限 function enemy_create_hitbox(_x, _y, _x_offset = 0, _y_offset = 0, _duration = 0) { var _hb = icd(oEnemyHitbox, x + _x_offset, y + _y_offset); _hb.owner = id; _hb.sprite_index = sEnemyHitboxRec; _hb.x_offset = _x_offset; _hb.y_offset = _y_offset; var _base = 2; _hb.image_xscale = _x / _base; _hb.image_yscale = _y / _base; /* oEnemyHitbox的基础大小为2*2 因为gml的1*1sprite无法将重心放在middle/center 此处定义后续用于缩放 */ if _duration != 0 { _hb.persist = false; _hb.duration = _duration; } return _hb; }