Canalblog
Suivre ce blog Administration + Créer mon blog

DineInformatique

27 mars 2012

Uploader une image depuis une url...

Comment récupérer une image sur le web et la sauvegarder sur un ordinateur depuis une application Windows Form (WPF) :

Il faut dans un premier temps créé une requête vers l'url de l'image : 
WebRequest requete = WebRequest.Create("http://images.com/image.jpg");

Puis, récupérer la réponse à cette requête et le flux de données :
WebResponse reponse = requete.GetResponse();
Stream streamImg = reponse.GetResponseStream();

On créé alors une image (System.Drawing.Image) depuis ce flux :
Image img = Image.FromStream(streamImg);

Il suffit ensuite de sauvegarder l'image à l'endroit souhaité sur son ordinateur :
img.Save("C:/Users/Pictures/image.jpg");

Attention, il ne faut pas oublier de "fermer" le flux de données, pour éviter de saturer la mémoire (en cas de nombreux uploads) : streamImg.Close();


Lorsque l'on utilise des chemins (ici C:/Users/Pictures), il est plus "propre" de définir un fichier de configuration pour l'application dans lequel on définit différentes constantes (dont par exemple le chemin du dossier dans lequel les images seront stockées).

Publicité
Publicité
26 mars 2012

Utilisation du WebBrowser (WPF)

Depuis quelques jours je travaille avec le composant WebBrowser (WPF). Je vais donc partager ici quelques infos sur son utilisation (ça ne m'a pas paru très instinctif, et il m'a fallu faire pas mal de recherches sur le net).

Premier point : indiquer une adresse html à mon webbrowser et ! ne pas afficher les erreurs de script que peut contenir le site... 


Indiquer le site à afficher est très simple  : wbSite.Source = new Uri("http://monUri.com");
Là où ça se complique, ce sont les erreurs de script. En effet, même si en naviguant cela reste relativement invisible à l'utilisateur, de nombreux sites contiennent de petites erreurs de script (qui n'empêchent pas leur fonctionnement pour autant). Le souci est que le webBrowser affiche une belle fenêtre popup à chaque erreur rendant la navigation très pénible. J'ai donc cherché (non sans mal de tête...) une solution pour éviter ces popups intempestives ! Et j'ai trouvé (merci google, je ne suis pas assez calée pour coder ça toute seule...) : je vous partage donc la solution :

On créé une méthode utilisant la reflexion (je n'ai pas encore saisi toutes les subtilités de la méthode, alors je ne m'étale pas trop...)

public void HideScriptErrors(WebBrowser wb, bool Hide)
{

FieldInfo fiComWebBrowser = typeof(WebBrowser).GetField("_axIWebBrowser2", BindingFlags.Instance | BindingFlags.NonPublic);

if (fiComWebBrowser == null) return;


object objComWebBrowser = fiComWebBrowser.GetValue(wb);


if (objComWebBrowser == null) return;

objComWebBrowser.GetType().InvokeMember("Silent", BindingFlags.SetProperty, null, objComWebBrowser, new object[] { Hide });

}


On appelle ensuite cette méthode dans l'évènement Navigated du WebBrowser

 

private void webBrowserExemple_Navigated(object sender, System.Windows.Navigation.NavigationEventArgs e)
{
    HideScriptErrors(wbSite, true);
}


Et voilà les popups d'erreurs javascript ne s'affichent plus ! Ouf !


Deuxième point : Récupérer le contenu web affiché par le webBrowser


Beaucoup plus simple ! Mais pas si intuitif non plus...Mon but est de récupérer le contenu de la page web affichée dans mon composant webBrowser et de parser le html pour y récupérer des informations.

Le contenu est accessible depuis la propriété Document du composant webBrowserExemple.Document.
Cependant le type de cette propriété est "inconnu". Tout ce que l'on peut voir par l'espion de Visual Studio est que c'est un objet de type System__ComObject...Ah ben oui on va aller loin. Mais pas de panique ! C'est tout bêtement une page web, ça je le sais puisque c'est moi qui le gère. Donc après quelques recherches, je trouve que c'est un HTMLDocument. Pour pouvoir utiliser ce type d'objet COM, il faut ajouter la dll Microsoft HTML (MSHTML).  

On peut donc ainsi travailler avec le type HTMLDocument 
MSHTML.HTMLDocument pageWeb =(MSHTML.HTMLDocument) webBrowserExemple.Document;
Pour récupérer les éléments de la page Html, on peut utiliser différentes méthodes, comme getElementById, qui retourne l'élément correspondant à l'id passé en paramètre: exemple.Titre = pageWeb.getElementById("grand_titre").innerHTML; 

Pour récupérer les éléments par Classe, on utilise la méthode getElementsByClass. Or cette méthode retourne une collection particulière : IHTMLElementCollection liste = page.getElementsByClassName("NomDeClasse"); 

Si l'on souhaite alors récupérer le premier élément de la liste et son contenu :
IHTMLElement elem = (IHTMLElement)liste.item(0, null); 
return elem.innerText;

Je n'ai pas encore fini d'explorer le type HTMLDocument, mais c'est un début :-)


 

20 mars 2012

WPF-Datagrid : Changer la couleur de la ligne sélectionnée

Je ne connaissais pas WPF, je suis donc en pleine découverte. Du coup je partage les infos que je trouve bien utiles :-)

J'ai recherché comment modifier la couleur d'une ligne lorsqu'elle est sélectionnée (oui parce que le bleu "EDF" bof :p)

En fait, ce n'est pas très compliqué : il faut créer un style pour la ligne ou plutôt la cellule (oui...quand j'ai créé le style pour la ligne ça ne fonctionnait pas très bien...bref)

Dans mon exemple, je créé dans un premier temps le dégradé de couleur comme une ressource de ma page :

<Grid.Resources>
            <LinearGradientBrush x:Key="DegradeSelectedRow" StartPoint="0,0" EndPoint="0,1">
                <GradientStop Color="#fff" Offset="0" />
                <GradientStop Color="#FFCAF288" Offset="1" />
            </LinearGradientBrush>

(c'est un dégradé blanc->vert que j'ai appelé "DegradeSelectedRow")


Ensuite au niveau de mon datagrid, je créé un style pour les cellules (DataGridCell)

 <DataGrid.CellStyle>
       <Style TargetType="{x:Type DataGridCell}">
                <Style.Triggers>
                       <Trigger Property="IsSelected" Value="True">
                               <Setter Property="Background" Value="{DynamicResource ResourceKey=DegradeSelectedRow}"/>
                               <Setter Property="Foreground" Value="Black" />
                       </Trigger>
                </Style.Triggers>
                <Setter Property="Cursor" Value="Hand" />
         </Style>
 </DataGrid.CellStyle>

Explication : 
- TargetType comme son nom l'indique définit l'élément de la grid pour lequel le style est appliqué (ici une cellule donc DataGridCell)
- Je créé un "trigger" qui va me permettre de définir "quand" appliquer le style : dans le cas présent, le style est appliqué lorsque la valeur "IsSelected" de la cellule est à "True" (donc que ma cellule est sélectionnée)
- Je définit alors le style : le fond de la cellule (Property="Background") sera le dégradé que j'ai défini précédemment dans les ressources (appelé DegradeSelectedRow)
- Je précise également que la couleur du texte (Property="Foreground") sera noire.

Enfin je rajoute que lorsque l'utilisateur passe la souris sur une cellule de ma grid, le curseur est une main (Property="Cursor" Value="Hand"). Ce style est appliqué tout le temps, c'est pourquoi il n'est pas défini dans le trigger.

 

CouleurLigneSelectionne

 

20 mars 2012

Création d'une nouvelle appli : Le carnet de recettes

Et voilà, je me suis lancée : en plein développement d'un logiciel. 

J'en suis au début (j'avance au rythme de bébé) :

- Pour le moment c'est une application qui tournera sous Windows 

- Mais j'espère la mettre en place sur le web, les smartphones etc...

-C'est un logiciel qui permet de retrouver toutes ses recettes, avec un petit (gros) plus dont je ne dis rien pour le moment (hhi top secret !)

 

Je chercherai bientôt des testeurs :p

Publicité
Publicité
DineInformatique
Publicité
Archives
Publicité