[WP7] Windows Phone Developer Tools RTM disponible !

Le 16 septembre 2010 à 18:25

Vu sur le blog de la team WP7, les Windows Phone Developer Tools en RTM viennent de sortir !
Pour rappel, la version RTM apporte plusieurs nouveautés, comme les contrôles Panorama, Pivot et Bing Maps.

windows-phone-logo-305x46-trans

Pour télécharger la version “web” (téléchargement des fichiers pendant l’installation), rendez-vous sur cette page. Pour la version ISO, c’est ici !

A bientôt !

[WP7/Silverlight] Une alternative à la classe System.Drawing.Bitmap

Le 14 septembre 2010 à 11:09

Sur Windows Phone 7, tout comme Silverlight d’ailleurs, la classe Bitmap n’existe pas (bon il faut être lucide, la classe Bitmap est une encapsulation d’une bitmap GDI+, donc ça parait logique que ce ne soit pas disponible sinon ce serait trop ancré avec Windows :)). Cela peut poser problème dans des plusieurs cas concrets, comme notre application TranslateIt présenté sur ce blog et pour le concours de Windows Phone 7 organisé par Microsoft. Dans notre cas, nous avons besoin de découper une image et avec la classe Bitmap, cela est très simple avec la méthode Clone().
Il a donc fallu trouver une alternative à cette classe. Nous sommes donc passer sur WriteableBitmap avec ses méthodes d’extensions disponibles dans le projet WriteableBitmapEx sur Codeplex.

La description du projet est très claire :

The WriteableBitmapEx library is a collection of extension methods for Silverlight's WriteableBitmap. The WriteableBitmap class that was added in Silverlight 3, allows the direct manipulation of a bitmap and could be used to generate fast procedural images by drawing directly to a bitmap. The WriteableBitmap API is very minimalistic and there's only the raw Pixels array for such operations. The WriteableBitmapEx library tries to compensate that with extensions methods that are easy to use like built in methods. The library extends the WriteableBitmap class with elementary and fast (2D drawing) functionality, supporting common shapes like point, line, ellipse, polyline, quad, rectangle, triangle. Conversion methods and functions to combine WriteableBitmaps (Blitting) are part of it too.

Comme on peut le constater, c’est très complet :).

Pour reprendre les exemples de Codeplex :

// Initialize the WriteableBitmap with size 512x512 and set it as source of an Image control
WriteableBitmap writeableBmp = new WriteableBitmap(512, 512);
ImageControl.Source = writeableBmp;

// Load an image from the calling Assembly's resources only by passing the relative path
writeableBmp = new WriteableBitmap(0, 0).FromResource("Data/flower2.png");

// Clear the WriteableBitmap with white color
writeableBmp.Clear(Colors.White);

// Set the pixel at P(10, 13) to black
writeableBmp.SetPixel(10, 13, Colors.Black);

// Get the color of the pixel at P(30, 43)
Color color = writeableBmp.GetPixel(30, 43);

// Green line from P1(1, 2) to P2(30, 40)
writeableBmp.DrawLine(1, 2, 30, 40, Colors.Green);

// Line from P1(1, 2) to P2(30, 40) using the fastest draw line method with the color as
// integer
int[] pixels = writeableBmp.Pixels;
int w = writeableBmp.PixelWidth;
int h = writeableBmp.PixelHeight;
WriteableBitmapExtensions.DrawLine(pixels, w, h, 1, 2, 30, 40, myIntColor);

// Black triangle with the points P1(10, 5), P2(20, 40) and P3(30, 10)
writeableBmp.DrawTriangle(10, 5, 20, 40, 30, 10, Colors.Black);

// Red rectangle from the point P1(2, 4) that is 10px wide and 6px high
writeableBmp.DrawRectangle(2, 4, 12, 10, Colors.Red);

// Filled blue ellipse with the center point P1(2, 2) that is 8px wide and 5px high
writeableBmp.FillEllipseCentered(2, 2, 8, 5, Colors.Blue);

// Closed green polyline with P1(10, 5), P2(20, 40), P3(30, 30) and P4(7, 8)
int[] p = new int[] { 10, 5, 20, 40, 30, 30, 7, 8, 10, 5 };
writeableBmp.DrawPolyline(p, Colors.Green);

// Cubic Beziér curve from P1(5, 5) to P4(20, 7) with the control points P2(10, 15)
// and P3(15, 0)
writeableBmp.DrawBezier(5, 5, 10, 15, 15, 0, 20, 7,  Colors.Purple);

// Cardinal spline through the points P1(10, 5), P2(20, 40) and P3(30, 30) with a 
// tension of 0.5
int[] pts = new int[] { 10, 5, 20, 40, 30, 30};
writeableBmp.DrawCurve(pts, 0.5,  Colors.Yellow);

// A filled Cardinal spline through the points P1(10, 5), P2(20, 40) and P3(30, 30) 
// with a tension of 0.5
writeableBmp.FillCurveClosed(pts, 0.5,  Colors.Green);

// Blit a bitmap using the additive blend mode at P1(10, 10)
writeableBmp.Blit(new Point(10, 10), bitmap, sourceRect, Colors.White, 
                                              WriteableBitmapExtensions.BlendMode.Additive);

// Override all pixels with a function that changes the color based on the coordinate
writeableBmp.ForEach((x, y, color) => Color.FromArgb(color.A, (byte)(color.R / 2), 
                                                                       (byte)(x * y), 100));

// Present the WriteableBitmap!
writeableBmp.Invalidate();

// Take snapshot
var clone = writeableBmp.Clone();

// Save to a TGA image stream (file for example)
writeableBmp.WriteTga(stream);

// Crops the WriteableBitmap to a region starting at P1(5, 8) and 10px wide and 10px high
var cropped = writeableBmp.Crop(5, 8, 10, 10);

// Resizes the WriteableBitmap to 200px wide and 300px high using a bilinear
// interpolation method
var resized = writeableBmp.Resize(200, 300, 
                                          WriteableBitmapExtensions.Interpolation.Bilinear);

A bientôt !

[WP7] Mon application pour le concours Windows Phone 7 !

Le 23 août 2010 à 10:05

Microsoft organise une compétition pour les développeurs Windows Phone 7 pour rechercher les killers-apps de demain. Les 7 finalistes passeront devant un jury composé de 6 personnes : Steve Ballmer (CEO Microsoft), Pierre Olivier Carles (CEO de Kipost et co-fondateur de Labotec, business angel), Jacques Antoine Granjon (fondateur de Vente-privée.com), Ouril Ohayon (co-fondateur d’AppsFire et co-fondateur du fonds Isai), Marc Simoncini (fondateur et président de Meetic et du fonds Jaïna) et Bruno Vanryb (fondateur et Président d’Avanquest Software).

L’application que je présente pour le concours (avec Lionel Reichert) est un traducteur d’image (avec reconnaissance optique des caractères) et de textes en une vingtaine de langues. On a aussi la possibilité d’écouter le texte traduit.

Vidéo :


Pour voter pour cette application, vous pouvez vous rendre sur la page officiel du concours et cliquer sur “j’aime” ! Merci !

Edit : on ne peut plus cliquer sur “j’aime” sur la vidéo sur Facebook, c’est aussi le cas de nombreuses vidéos sur le groupe “Développeurs.net”, pour pouvoir cliquer sur “j’aime” il faudra se rendre à présent sur cette page ! Merci ! 

A bientôt !

[.NET] Impersonation : changer d’utilisateur (WindowsIdentity) à la volée

Le 6 août 2010 à 15:51

Pour les besoins d’un projet, j’ai besoin d’utiliser temporairement un compte avec d’autres privilèges (par exemple, même si c’est faisable autrement, si vous avez besoin d’accéder à des ressources réseaux ou tout simplement, comme il sera montré dans l’exemple, d’accéder à un répertoire où l’utilisateur courant n’a pas les droits). Pour simplifier l’utilisation, j’ai crée une (simple) classe qui sera présentée ici.

Tout d’abord, voici la classe Impersonation, qui permet de changer d’utilisateur :

public class Impersonation : IDisposable
{
    [DllImport("advapi32.dll", SetLastError = true)]
    private static extern bool 
        LogonUser(string lpszUsername, 
                  string lpszDomain, 
                  string lpszPassword, 
                  int dwLogonType, 
                  int dwLogonProvider, 
                  out IntPtr phToken);

    private const int LOGON32_PROVIDER_DEFAULT = 0;
    private const int LOGON32_LOGON_INTERACTIVE = 2;

    private WindowsImpersonationContext _impersonationContext;

    public Impersonation(string domain, string login, string password)
    {
        try
        {
            IntPtr tokenHdle = IntPtr.Zero;

            bool ret = LogonUser(login, domain, password, LOGON32_LOGON_INTERACTIVE, 
                                 LOGON32_PROVIDER_DEFAULT, out tokenHdle);

            Trace.WriteLine("Current user : " + WindowsIdentity.GetCurrent().Name);

            WindowsIdentity newIdentity = new WindowsIdentity(tokenHdle);
            _impersonationContext = newIdentity.Impersonate();

            Trace.WriteLine("Current user : " + WindowsIdentity.GetCurrent().Name);
        }
        catch (Exception e)
        {
            Console.WriteLine(e.ToString());
        }
    }

    #region IDisposable Membres

    public void Dispose()
    {
         _impersonationContext.Undo();
         Trace.WriteLine("Current user : " + WindowsIdentity.GetCurrent().Name);
    }

    #endregion
}

Dans l’exemple qui va suivre, j’ai crée un dossier Test où j’ai enlever tous les droits pour ne laisser qu’un compte temporaire (juste pour mon exemple) :

image


Donc bien entendu, si avec mon compte par défaut, je souhaite y accéder :


image

Maintenant nous allons essayer de créer un fichier dans ce dossier avec l’utilisateur où je n’ai pas les droits, puis tout de suite derrière on va utiliser la classe Impersonation pour pouvoir basculer vers l’utilisateur “MathieuTest” afin d’avoir l’autorisation de créer le fichier :

static void Main(string[] args)
{
    string userName, password;

    Console.WriteLine("Impersonation Sample");
    Console.WriteLine("--------------------");
    Console.WriteLine(@"Pour cet exemple, 
                        nous allons essayer de créer le fichier 
                        E:\Test\File.txt dont le dossier n'est accessible 
                        que pour un utilisateur");
    Console.Write("Essai n°1 : ");
    Console.WriteLine(Test());
    Console.WriteLine("Donc on va utiliser l'impersonation pour pouvoir 
                       utiliser temporairement \"son compte\" afin de pouvoir 
                       créer le fichier");
    Console.Write("Username : ");
    userName = Console.ReadLine();
    Console.Write("Password : ");
    password = Console.ReadLine();
    Console.Write("Essai n°2 : ");

    // On tente avec l'impersonation
    Impersonation impersonation = new Impersonation(string.Empty, userName, password);

    Console.WriteLine(Test());

    // On revient à l'utilisateur "en cours"
    impersonation.Dispose();



    Console.Read();
}

static string Test()
{
    try
    {
        File.Create(@"E:\Test\File.txt");
        return "Fichier crée";
    }
    catch (Exception e)
    {
        return @"/!\ Impossible de créer le fichier";
    }
}

Voici le résultat dans la console :

image

Pour télécharger les sources, c’est ici.

A bientôt !

[WPF] Personnaliser le curseur

Le 4 août 2010 à 19:12

L'un des gros avantages de WPF c’est la personnalisation complète de notre application. Dans le même style que mon article sur la personnalisation de la sélection de texte et du curseur d’insertion, voici comment changer le curseur de la souris.

Tout cela est très simple à faire, pour commencer je vais ajouter le fichier du curseur dans mon application :

image

Ensuite, il faut définir le App.ani comme “Resource” (de base il est défini sur “Aucun”, ce qui fera qu’à la compilation notre application risque de ne pas trouver le curseur) :

image

Ensuite, sur nos éléments de l’interface, il existe la propriété “Cursor”, pour exemple, je vais le définir sur l’ensemble de la fenêtre :

<Window x:Class="Curseur.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="350" Width="525"
        Cursor="pack://application:,,,/Resources/Cursor/App.ani">
    <Grid>
        
    </Grid>
</Window>

Ce qui va donner à l’exécution :

image

Je peux bien sûr définir le curseur sur d’autres éléments tels que sur Textbox, ListBox… etc :).

Pour télécharger les sources, c’est ici.


A bientôt !

A propos de l'auteur

Mathieu Perrein est Software Solutions Architect, Microsoft Student Partner de 2010 à 2012.

 

MSP

 

MSP

MSP

 MSPD

MCT

 

Facebook

 

Ce blog est strictement personnel et les opinions exprimées ici n'engagent donc que moi, et pas mon employeur.

Tags

Vous avez désactivé JavaScript ou bien vous possédez une ancienne version d'Adobe Flash Player. Téléchargez la dernière version de Flash Player.