Bloqueia no Swift (animateWithDuration: animations: Completation :)

102

Estou tendo problemas para fazer os blocos funcionarem no Swift. Aqui está um exemplo que funcionou (sem bloco de conclusão):

UIView.animateWithDuration(0.07) {
    self.someButton.alpha = 1
}

ou, alternativamente, sem o fechamento final:

UIView.animateWithDuration(0.2, animations: {
    self.someButton.alpha = 1
})

mas depois que tento adicionar o bloco de conclusão, ele simplesmente não funciona:

UIView.animateWithDuration(0.2, animations: {
    self.blurBg.alpha = 1
}, completion: {
    self.blurBg.hidden = true
})

O autocomplete me dá, completion: ((Bool) -> Void)?mas não tenho certeza de como fazê-lo funcionar. Também tentei com o fechamento à direita, mas obteve o mesmo erro:

! Could not find an overload for 'animateWithDuration that accepts the supplied arguments

Atualização para Swift 3/4:

// This is how I do regular animation blocks
UIView.animate(withDuration: 0.2) {
    <#code#>
}

// Or with a completion block
UIView.animate(withDuration: 0.2, animations: {
    <#code#>
}, completion: { _ in
    <#code#>
})

Não uso o fechamento à direita para o bloco de conclusão porque acho que falta clareza, mas se você gostar, poderá ver a resposta de Trevor abaixo .

Manolosavi
fonte
1
"O autocomplete me dá a conclusão: ((Bool) -> Void)? Mas não tenho certeza de como fazê-lo funcionar" Exatamente o que diz. Deve ser um bloco que recebe um Bool e retorna um Void.
matt de
Como você sabe o que é ((Bool) -> Void)? é para? Já que eu usei isso no ObjC antes de saber que o BOOL terminou. Mas como um programador rápido saberia?
malhal

Respostas:

202

o parâmetro de conclusão em animateWithDuration leva um bloco que leva um parâmetro booleano. Em swift, como nos blocos Obj C, você deve especificar os parâmetros que um fechamento leva:

UIView.animateWithDuration(0.2, animations: {
    self.blurBg.alpha = 1
}, completion: {
    (value: Bool) in
    self.blurBg.hidden = true
})

A parte importante aqui é o (value: Bool) in. Isso informa ao compilador que esse encerramento recebe um Bool rotulado como 'valor' e retorna void.

Para referência, se você quisesse escrever um encerramento que retornasse um bool, a sintaxe seria

{(value: Bool) -> bool in
    //your stuff
}
Zaksoup
fonte
Também pode ser resolvido usando $0para o primeiro argumento, apenas usando a variável dentro do bloco, o compilador descobre que seu bloco aceita um argumento.
Can
1
sintaxe de bloco de conclusão dat :(
Chris Allinson
41

A conclusão é correta, o fechamento deve aceitar um Boolparâmetro: (Bool) -> (). Experimentar

UIView.animate(withDuration: 0.2, animations: {
    self.blurBg.alpha = 1
}, completion: { finished in
    self.blurBg.hidden = true
})
Nicholas H.
fonte
2
É importante notar que esta versão está correta. Você não precisa escrever o tipo completo, pois pode ser inferido, portanto, tudo o que você precisa é apenas mencionar o parâmetro de fechamento conforme mencionado aqui.
Chuck
29

O sublinhado por si só ao lado da inpalavra - chave irá ignorar a entrada

Swift 2

UIView.animateWithDuration(0.2, animations: {
    self.blurBg.alpha = 1
}, completion: { _ in
    self.blurBg.hidden = true
})

Swift 3, 4, 5

UIView.animate(withDuration: 0.2, animations: {
    self.blurBg.alpha = 1
}, completion: { _ in
    self.blurBg.isHidden = true
})
Dan Greenfield
fonte
8

Esta é a minha solução acima com base na resposta aceita acima. Ele esmaece uma visão e a esconde, antes quase invisível.

Swift 2

func animateOut(view:UIView) {

    UIView.animateWithDuration (0.25, delay: 0.0, options: UIViewAnimationOptions.CurveLinear ,animations: {
        view.layer.opacity = 0.1
        }, completion: { _ in
            view.hidden = true
    })   
}

Swift 3, 4, 5

func animateOut(view: UIView) {

    UIView.animate(withDuration: 0.25, delay: 0.0, options: UIView.AnimationOptions.curveLinear ,animations: {
        view.layer.opacity = 0.1
    }, completion: { _ in
        view.isHidden = true
    })
}
Jaro
fonte
4

Aqui está, isso irá compilar

Swift 2

UIView.animateWithDuration(0.3, animations: {
    self.blurBg.alpha = 1
}, completion: {(_) -> Void in
    self.blurBg.hidden = true
})

Swift 3, 4, 5

UIView.animate(withDuration: 0.3, animations: {
    self.blurBg.alpha = 1
}, completion: {(_) -> Void in
    self.blurBg.isHidden = true
})

A razão de eu ter tornado a área do Bool um sublinhado é porque você não está usando esse valor, se precisar, pode substituir o (_) por (valor: Bool)

Kris Gellci
fonte
1

Às vezes, você deseja lançar isso em uma variável para animar de maneiras diferentes, dependendo da situação. Para isso você precisa

 let completionBlock : (Bool) -> () = { _ in 
 }

Ou você pode usar o igualmente prolixo:

 let completionBlock = { (_:Bool) in 
 }

Mas em qualquer caso, você deve indicar o Boollugar.

Dan Rosenstark
fonte
0

SWIFT 3.x + 4.x

Gostaria de fazer uma atualização e simplificar as coisas.

O exemplo abaixo é implementado em qualquer viewum está se escondendo lentamente e quando está completamente transparente; remove-se dos paisview

okvariável sempre retornará truecom o término da animação.

    alpha = 1
    UIView.animate(withDuration: 0.5, animations: {
        self.alpha = 0
    }) { (ok) in
        print("Ended \(ok)")
        self.removeFromSuperview()
    }
Trevor
fonte