Почему мое столкновение больше не распознается, когда я все еще сталкиваюсь со спрайтом?

#sprite-kit #collision #contacts #skphysicsbody

Вопрос:

Мы пытаемся создать зарядную станцию для игры, которую мы создаем, с полосой здоровья, которая увеличивается, когда игрок сталкивается с зарядным устройством. Для этого мы создали категорию для плеера, а также категорию для зарядного устройства. В нашей функции didBegin, которая активируется при столкновении, что видно ниже, здоровье(которое является глобальной переменной) увеличивается, а зарядка устанавливается в значение true. Чтобы убедиться, что здоровье не просто продолжает увеличиваться после того, как игрок перестанет сталкиваться с зарядным устройством, у нас есть функция didEnd, которая появляется только тогда, когда столкновения больше не происходит. Это устанавливает переменную зарядки в значение false. В нашей функции обновления у нас есть условные операторы для того, что должно произойти в нашем коде, если зарядка истинна или ложна. Когда это правда, здоровье немного увеличивается и не поднимается выше 1 или ниже нуля, чтобы держать его в рамках. Когда оно ложно, здоровье немного уменьшается, а также не поднимается выше 1 или ниже нуля, чтобы держать его в рамках. Проблема, с которой мы сталкиваемся, заключается в том, что при первом столкновении плеера с зарядным устройством переменная зарядки устанавливается в значение true, но как только она немного сдвинется, даже если она все еще сталкивается с зарядным устройством, переменная устанавливается в значение false, и она больше не заряжается. Есть ли что-то, чего нам не хватает/есть ли лучший способ настроить зарядную станцию?

 let chargerCategory: UInt32 = 0b1000 //6 if charge is in contact with player, then increase


func didBegin(_ contact: SKPhysicsContact) {
        var body1 = SKPhysicsBody()
        var body2 = SKPhysicsBody()
        
        if contact.bodyA.categoryBitMask < contact.bodyB.categoryBitMask{
            body1 = contact.bodyA
            body2 = contact.bodyB
        }
        else{
            body1 = contact.bodyB
            body2 = contact.bodyA
        }
               
        if body1.categoryBitMask == playerCategory amp;amp; body2.categoryBitMask == chargerCategory{
            //if player hit charger
            //health  = 0.001
            //HealthBar.xScale = health
            print("CHARGING...", health)
            charging = true
        }

func didEnd(_ contact: SKPhysicsContact) {
        var body1 = SKPhysicsBody()
        var body2 = SKPhysicsBody()
        
        if contact.bodyA.categoryBitMask < contact.bodyB.categoryBitMask{
            body1 = contact.bodyA
            body2 = contact.bodyB
        }
        else{
            body1 = contact.bodyB
            body2 = contact.bodyA
        }
        
        if body1.categoryBitMask == playerCategory amp;amp; body2.categoryBitMask == chargerCategory{
            charging = false
        }
        

    }


override func update(_ currentTime: TimeInterval) {
        if charging == false{
            health -= 0.0001
            HealthBar.xScale = health
            if health < 0 {
                health = 0
            }
            if health > 1.0{
                health = 1.0
            }
        }
        if charging == true{
            health  = 0.001
            HealthBar.xScale = health
//            print("CHARGING...", health)
            
            if health < 0 {
                health = 0
            }
            if health > 1.0{
                health = 1.0
            }
        }
        print(health)
        print(charging)
    }
 

Комментарии:

1. Вы использовали view.showsPhysics = true, чтобы увидеть сами физические тела? Затем вы можете определить, действительно ли это код столкновения или проблема в самих физических телах.

2. Да, я использовал это, чтобы увидеть сами физические тела. Физические тела — это не проблема.

3. ОК. Ваш код и логика, лежащая в его основе, кажутся разумными. Найдите «зарядка = ложь» в своем коде, есть ли где-нибудь еще, где устанавливается флаг?

4. Изначально он установлен в значение false, но это единственное другое место, где он установлен в значение false.

5. У вас есть много других категорий физического тела? Вы показываете только 1. Возможно, разверните свой код, покажите все категории физики. Каковы разрядные маски категорий/столкновений/контактов, установленные на проигрывателе и станции? Покажите, как вы устанавливаете физическое тело как игрока, так и станции.