Microsoft MVP Visual C#

April 2, 2013 at 8:00 PMNathanael

Depuis le 1er avril (non ca n'était pas une blague), j'ai eu l'immense privilège d'être nommé Microsoft MVP Visual C#.
Cette distinction par Microsoft vient récompenser mes contributions pour la communauté.

Je tiens à remercier tous ceux qui m'ont aidé, ils se reconnaitront !

 

[Astuce] Hyperlink et lien absolu sur Windows Phone

February 1, 2013 at 12:32 PMNathanael

Il est bien souvent tentant d'utiliser des Hyperlink ou HyperlinkButton pour créer un lien de navigation.

Cependant, sur Windows Phone, la propriété NavigateUri n'accepte que des liens relatifs, par conséquent, il est impossible de rediriger quelqu'un sur une url de type http://www.natmarchand.fr

Une astuce existe cependant : en effet, lorsque l'on met une uri absolue on obtient une levée de l'évènement NavigationFailed sur l'instance du NavigationService. Cet évènement, il est possible (et d'ailleurs c'est le cas dans le Template par défaut) de s'y abonner. Dans le gestionnaire d'évènement, il suffit de dire qu'on a effectivement pris en compte cet évènement et que pour traiter cette uri, on va finalement le faire nous même avec un WebBrowserTask. C'est assez simple, ca tiens en quelques lignes :

private void RootFrame_NavigationFailed(object sender, NavigationFailedEventArgs e)
{
	if (e.Uri.IsAbsoluteUri && (e.Uri.Scheme == Uri.UriSchemeHttp || e.Uri.Scheme == Uri.UriSchemeHttps))
	{
		e.Handled = true;
		new WebBrowserTask { Uri = e.Uri }.Show();
	}
	else
	{
		if (Debugger.IsAttached)	//ceci est le code
		{							//par défaut
			Debugger.Break();		//dans le template
		}							//Windows Phone
	}
}

L'autre solution est d'utiliser la propriété Target de l'HyperlinkButton (et Hyperlink) de la définir à _blank 

Comprendre le Dispatcher

January 15, 2013 at 8:59 PMNathanael

Dans les technologies XAML (Silverlight, WPF, Windows 8, WP), il est nécessaire d'utiliser le Dispatcher dès lors qu'on veut mettre à jour l'interface utilisateur.

J'ai vu récemment sur le groupe des développeurs Windows Phone une question concernant judicieuse l'utilisation de BeginInvoke :

Si je suis déjà sur le thread de l'UI, est ce que cela sert de faire un BeginInvoke ?

Et par extension, y'a t il des conséquences fâcheuses, comment faire lorsqu'on ne sait pas où on est?

Il faut bien comprendre ce qu'est le Dispatcher: c'est une file d'action à exécuter sur le thread. Ainsi, ajouter une action au Dispatcher, la met à la file.

Ainsi, on peut avoir un comportement plutôt inattendu:

var myBool = false;
Dispatcher.CurrentDispatcher.BeginInvoke(new Action(() => myBool = true));
if(myBool==true)
	Console.WriteLine("content");
else
	Console.WriteLine("pas content");

Lors de l'exécution de ce code, si on est sur le Thread de l'UI, contrairement à ce qu'on pourrait penser, on va obtenir "pas content". En effet, le Dispatcher étant une file, lorsque l'on fait un BeginInvoke, l'action est empilée. Elle ne sera dépilée que lorsque le thread de l'UI n'aura plus rien à faire, or il est en train d'exécuter le code autour. L'action sera donc dépilée après le if/then.

Mais comment faire alors ?

Il existe une méthode pour savoir si le code s'exécute sur le thread de l'UI, c'est CheckAccess(). Il est donc possible de s'écrire un petit helper :

public static class DispatcherExtension
{
	public static void MyBeginInvoke(this Dispatcher dispatcher, Action action)
	{
		if(dispatcher.CheckAccess())
		{
			action();
		}
		else
		{
			dispatcher.BeginInvoke(action);
		}
	}
}

Si on modifie le code qu'on avait au début en remplaçant le BeginInvoke par le MyBeginInvoke, on obtient comme prévu : "content".

Astuce XAML: Colorer un champ de formulaire si la valeur est nécessaire

September 20, 2012 at 1:55 PMNathanael

Lorsque l'on développe des formulaires avec une techno XAML, il est très intéressant d'utiliser les mécanismes de validation via annotation. Par exemple, l'attribut RequiredAttribute permet de dire que le champ est nécessaire à la validation.
Cependant, il peut être intéressant de signaler à l'utilisateur que le champ est nécessaire AVANT qu'il soumette le formulaire (et que sa demande échoue).

J'ai donc créé un petit Behavior qui va vérifier via le Binding si le champ possède l'attribut Required et si oui, il le colore en mastic; si non en vert léger.

Voici ledit behavior :

public class ColorIfRequiredBehavior : Behavior<TextBox>
{
	public static readonly DependencyProperty RequiredBrushProperty =
		DependencyProperty.Register("RequiredBrush", typeof(Brush), typeof(ColorIfRequiredBehavior), new PropertyMetadata(default(Brush)));

	public static readonly DependencyProperty NotRequiredBrushProperty =
		DependencyProperty.Register("NotRequiredBrush", typeof(Brush), typeof(ColorIfRequiredBehavior), new PropertyMetadata(default(Brush)));

	public Brush NotRequiredBrush
	{
		get { return (Brush)GetValue(NotRequiredBrushProperty); }
		set { SetValue(NotRequiredBrushProperty, value); }
	}

	public Brush RequiredBrush
	{
		get { return (Brush)GetValue(RequiredBrushProperty); }
		set { SetValue(RequiredBrushProperty, value); }
	}

	protected override void OnAttached()
	{
		base.OnAttached();
		var be = AssociatedObject.GetBindingExpression(TextBox.TextProperty);
		var pi = be.ResolvedSource.GetType().GetProperty(be.ResolvedSourcePropertyName);
		AssociatedObject.Background = pi.GetCustomAttributes(typeof(RequiredAttribute), true).Length > 0 ? RequiredBrush : NotRequiredBrush;
	}
}

Et son utilisation:

<TextBox Grid.Row="0"
			Text="{Binding Path=MyRequiredField}"
			Margin="5">
	<i:Interaction.Behaviors>
		<WpfApplication1:ColorIfRequiredBehavior NotRequiredBrush="PaleGreen" RequiredBrush="PaleGoldenrod" />
	</i:Interaction.Behaviors>
</TextBox>
<TextBox Grid.Row="1"
			Text="{Binding Path=MyNotRequiredField}"
			Margin="5">
	<i:Interaction.Behaviors>
		<WpfApplication1:ColorIfRequiredBehavior NotRequiredBrush="PaleGreen" RequiredBrush="PaleGoldenrod" />
	</i:Interaction.Behaviors>
</TextBox>

Gérer efficacement les tuiles sous Windows 8

September 6, 2012 at 4:14 PMNathanael

J'ai eu la chance d'intervenir lors du Meet Up BeMyApp lundi 3 sept. avec mon collègue Cyril Cathala.
Le sujet était la gestion des tuiles sous Windows 8, vous pouvez retrouver ci-dessous les slides de ma présentation ainsi que le replay.

Astuce XAML: Un même bouton, plusieurs storyboards différents!

July 30, 2012 at 12:09 PMNathanael

Suite à une petite question sur le groupe des développeurs Windows Phone sur Facebook, voici une petite astuce qui permet, lors d'un clic sur un bouton d'alterner deux storyboards. Ici, le premier storyboard provoque la sortie du texte, un nouvel appui, le fait re-rentrer dans la scène.

Tout se passe dans les EventTriggers qui possèdent des conditions de déclenchement. Le premier trigger n'est déclenché que si le bloc de texte est en dehors de la scène, cela appelle le storyboard d'entrée et inversement pour le second.

Voici le code:

<UserControl.Resources>
	<Storyboard x:Name="HideText">
		<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateY)" Storyboard.TargetName="textBlock">
			<EasingDoubleKeyFrame KeyTime="0:0:2" Value="-100" />
		</DoubleAnimationUsingKeyFrames>
		<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateX)" Storyboard.TargetName="textBlock">
			<EasingDoubleKeyFrame KeyTime="0:0:2" Value="-100" />
		</DoubleAnimationUsingKeyFrames>
	</Storyboard>
	<Storyboard x:Name="ShowText">
		<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateX)" Storyboard.TargetName="textBlock">
			<EasingDoubleKeyFrame KeyTime="0:0:2" Value="100" />
		</DoubleAnimationUsingKeyFrames>
		<DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateY)" Storyboard.TargetName="textBlock">
			<EasingDoubleKeyFrame KeyTime="0:0:2" Value="100" />
		</DoubleAnimationUsingKeyFrames>
	</Storyboard>
</UserControl.Resources>
<!--LayoutRoot is the root grid where all page content is placed-->
<Grid x:Name="LayoutRoot" Background="Transparent">
	<Button Content="Button" HorizontalAlignment="Left" VerticalAlignment="Top" Margin="200,100,0,0">
		<i:Interaction.Triggers>
			<i:EventTrigger EventName="Click">
				<i:Interaction.Behaviors>
					<eic:ConditionBehavior>
						<eic:ConditionalExpression>
							<eic:ComparisonCondition LeftOperand="{Binding Path=RenderTransform.TranslateX, ElementName=textBlock}"	Operator="LessThan"	RightOperand="0" />
						</eic:ConditionalExpression>
					</eic:ConditionBehavior>
				</i:Interaction.Behaviors>
				<eim:ControlStoryboardAction Storyboard="{StaticResource HideText}" ControlStoryboardOption="Stop" />
				<eim:ControlStoryboardAction Storyboard="{StaticResource ShowText}" ControlStoryboardOption="Play" />
			</i:EventTrigger>
			<i:EventTrigger EventName="Click">
				<i:Interaction.Behaviors>
					<eic:ConditionBehavior>
						<eic:ConditionalExpression>
							<eic:ComparisonCondition LeftOperand="{Binding Path=RenderTransform.TranslateX, ElementName=textBlock}"	Operator="GreaterThanOrEqual" RightOperand="0" />
						</eic:ConditionalExpression>
					</eic:ConditionBehavior>
				</i:Interaction.Behaviors>
				<eim:ControlStoryboardAction Storyboard="{StaticResource HideText}" ControlStoryboardOption="Play" />
				<eim:ControlStoryboardAction Storyboard="{StaticResource ShowText}" ControlStoryboardOption="Stop" />
			</i:EventTrigger>
		</i:Interaction.Triggers>
	</Button>
	<TextBlock x:Name="textBlock" Text="Kikoulol" RenderTransformOrigin="0.5,0.5" HorizontalAlignment="Left" VerticalAlignment="Top">
		<TextBlock.RenderTransform>
			<CompositeTransform TranslateX="100" TranslateY="100" />
		</TextBlock.RenderTransform>
	</TextBlock>
</Grid>

Il est bien entendu nécessaire de référencer les assemblies suivantes: System.Windows.Interactivity et Microsoft.Expression.Interactions, ce sont elles qui donnent les namespaces i et ei*

Victoire de Showrizo aux Dev Kings

June 6, 2012 at 10:01 PMNathanael

Showrizo, l'application sur laquelle je travaille avec Cyril Cathala dans le cadre de l'Accélérateur Windows 8 vient d'être désignée par l'équipe DPE de Microsoft, meilleure application Windows 8.

Pour un projet, certes qui nous tiens à coeur, mais développé sur notre temps libre, c'est une belle victoire :)

Cela montre également la qualité des So@t Experts puisque Smart Shopping, l'application de Nathalie était également dans le Top 10.

Des articles vont bien sûr suivre prochainement sur les points clés de Windows 8 (tuiles, gestion d'état, etc.).

L'application devrait bientôt être publiée sur le MarketPlace Release Preview et sera bien sûr au rendez-vous pour la sortie officielle de Windows 8.

Fonctionnement du binding en XAML (Silverlight, WPF, WP7 et WinRT)

May 3, 2012 at 7:21 PMNathanael

Bien que l'annonce sera uniquement publié la semaine prochaine, l'article est déjà en ligne!

Cet article dévlopper aborde la notion de Binding lorsqu'on utilise les technos se basant sur le XAML. Voici le résumé :

Avec l'arrivée de WPF et Silverlight, on a vu apparaître le XAML, nouvel élément pour construire des interfaces graphiques riches dans le monde de .Net. Avec l'essor de ces technologies ainsi que le renfort de Windows Phone 7 et WinRT, il devient essentiel de comprendre ce qui ce cache sous cette pierre angulaire du XAML qu'est le Binding afin d'avoir des applications à la fois riches et simples

Accéder à l'article

N'hésiter pas à commenter et à noter sur le topic dédié dans le forum developpez.com

       

Retour des commentaires

May 3, 2012 at 7:20 PMNathanael

Suite au changement de nom de domaine blog.ou-bien.net vers natmarchand.fr , les commentaires avaient cessé de fonctionner.

C'est désormais chose rétablie Cool

Tech'Days 2012: la session est en ligne!

March 12, 2012 at 9:54 PMNathanael

Comme promis, vous pouvez retrouver le webcast ainsi que les slides et le code source de notre session PAR305 aux Tech'Days 2012.

A bientôt pour de nouvelles aventures! :)