Comment EventArgs Annuler le travail dans le FormClosing événement?
-
11-09-2019 - |
Question
Comment fonctionne l'événement e.Cancel en cas de FormClosing sur un WinForm? Je sais que vous définissez à True
pour annuler la fermeture, mais à quel moment le processus de forme cela? Y at-il une action secondaire prise par la propriété?
Comment pourrais-je mettre en œuvre une action similaire dans un contrôle personnalisé? (C # ou VB)
Remarque: Je l'ai regardé pendant environ 30 minutes maintenant et ne pouvait pas trouver de réponses dans Google ou la recherche SO, donc si c'est un double, mon mauvais
.La solution
Je pense que l'affiche originale peut se demander ce qui se passe lorsque certains abonnés mis Cancel = false
et certains abonnés mis Cancel = true
. Si tel est le cas, la question « Quand le processus de forme cette » prend plus d'importance.
Dans un premier temps je me suis demandé si le compositeur a été mis en œuvre pour OU ou ET chaque valeur. En utilisant réflecteur pour inspecter le poseur de CancelEventArgs.Cancel
montre qu'il définit simplement un champ privé:
public bool Cancel
{
get{ return this.cancel; }
set{ this.cancel = value; }
}
Alors je me suis dit jeter un oeil dans « Form.OnClosing (CancelEventArgs args) » montrerait lorsque la valeur est cochée, comme les réponses précédentes, mais ce n'est pas ce réflecteur montre:
[EditorBrowsable(EditorBrowsableState.Advanced)]
protected virtual void OnClosing(CancelEventArgs e)
{
CancelEventHandler handler = (CancelEventHandler) base.Events[EVENT_CLOSING];
if (handler != null)
{
handler(this, e);
}
}
Alors j'ai activé le débogage source et trouvé obtenir le délégué EVENT_CLOSING
de la collection Events
tombe profondément dans l'API de fenêtrage telle que handler
dans la première ligne de OnClosing
est null
lorsque la forme définit Cancel = true
, ce qui signifie le code managé teste jamais vraiment si CancelEventArgs.Cancel == true
. Si vous voulez le courage laid de ce qui se passe à l'intérieur du eventHandlerList, vous obtenez ceci:
get {
ListEntry e = null;
if (parent == null || parent.CanRaiseEventsInternal)
{
e = Find(key);
}
if (e != null) {
return e.handler;
}
else {
return null;
}
}
Alors que le débogage, parent.CanRaiseEventsInternal
est faux si la fermeture a été annulée.
Alors ... la mise en œuvre effective de l'annulation de la fermeture d'une forme est plus compliquée que les réponses précédentes, mais leurs suggestions sur la façon d'annuler vos propres événements montrent bien comment le faire en code managé. Appelez le CancelEventHandler puis tester la valeur de CancelEventArgs.Cancel
après que tous les abonnés ont eu la chance de mettre la valeur à true
. Cela ne répond toujours pas à ce qui se passe si certains abonnés mis Cancel = false
et un certain ensemble Cancel = true
. Est-ce que quelqu'un sait? Est-ce que quelque chose comme ce qui suit nécessaire?
public bool Cancel
{
get{ return this.cancel; }
set{ this.cancel = this.cancel || value; }
}
Autres conseils
Suite à l'événement standard modèle de génération utilisé dans Windows Forms:
public event CancelEventHandler MyEvent;
protected void OnMyEvent(CancelEventArgs e) {
CancelEventHandler handler = MyEvent;
if (handler != null) {
handler(this, e);
}
}
private void button1_Click(object sender, EventArgs e) {
CancelEventArgs args = new CancelEventArgs();
OnMyEvent(args);
if (!args.Cancel) {
// Client code didn't cancel, do your stuff
//...
}
}
function OnMyCancelableEvent()
{
var handler = CancelableEvent;
var args = new CancelEventArgs()
if(handler != null)
{
handler(this, args)
if(args.Canceled)
// do my cancel logic
else
// do stuff
}
}