IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Web & réseau Delphi Discussion :

Convertir "Dispatch" en "OleStr"?


Sujet :

Web & réseau Delphi

  1. #1
    Membre averti
    Profil pro
    Inscrit en
    Avril 2010
    Messages
    22
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 22
    Par défaut Convertir "Dispatch" en "OleStr"?
    Bonjour,

    J'essaye de coder une fonction qui va me permettre de récuperer un lien en particulier (vers un .zip) dans une page, et j'ai une erreur avec le code de la faq (ici)
    Voila le code tout entier:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    function VerifVersion(MemoTest: TMemo; Browser: TWebBrowser): String;
    var
      i: Integer;
      der_version: String;
    begin
      Browser.Navigate('http://lien');
      for i:=0 to 29 do
        if Not AnsiPos('zip', Browser.OleObject.Document.Links.Item(i)) = 0 then //J'ai transformé le Memo.Add pour pouvoir filtrer directement, mais j'avais la même erreur
        begin
          MemoTest.Lines.Add(Browser.OleObject.Document.Links.Item(i));
          //+ d'autres traitements à faire ici
        end;
     
      Result:= der_version;
    end;
    Voici l'erreur:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Could not convert variant of type (Dispatch) into type (OleStr)
    Merci d'avance

  2. #2
    Membre éclairé Avatar de delagoutte
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    42
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Pyrénées Atlantiques (Aquitaine)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 42
    Par défaut
    première chose :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    for i := 0 to Browser.OleObject.Document.Links.Item(i).Length -1 do
    begin
    .....
    cela t'évitera des erreurs si il y a moins de 30 liens.

    Deuxième chose :
    ton webbrowser n'a peut être pas fini de charger la page quand tu attaques la boucle.

    de tête et pas sans risque de boucle infini:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
     
    variable global
    DocComplete : boolean;
     
    onBeforenavigate2WebBrowser()
    begin
    docComplete := false;
    end;
     
    OnDocumentCompleteWebBrowser()
    begin
    docComplete := true;
    end;
     
    Browser.Navigate('http://lien');
    While not DocComplete do
      Application .Processmessage;
    For i:= 0 to .....
    A tester pour voir si ça te débloque

  3. #3
    Membre averti
    Profil pro
    Inscrit en
    Avril 2010
    Messages
    22
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 22
    Par défaut
    J'ai rajouté le code, mais j'ai toujours la même erreur sur
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    if Not AnsiPos('zip', Browser.OleObject.Document.Links.Item(i)) = 0 then
    Edit: Et j'ai aussi une erreur avec Browser.OleObject.Document.Links.Item(i).Length -1 das le for:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Method 'Length' not supported by automation object

  4. #4
    Membre Expert

    Profil pro
    Leader Technique
    Inscrit en
    Juin 2005
    Messages
    1 756
    Détails du profil
    Informations personnelles :
    Âge : 47
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Leader Technique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2005
    Messages : 1 756
    Par défaut
    Edit: Et j'ai aussi une erreur avec Browser.OleObject.Document.Links.Item(i).Length -1 das le for:
    Non, il fallait comprendre :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
      for i:=0 to Browser.OleObject.Document.Links.Length-1 do
    Ensuite, je dois dire que je suis étonné si l'exemple de la FAQ fonctionne.
    Links.Item(i) retourne normalement une interface IDispatch qui décrit un objet de type Link. Ce n'est pas une chaîne de caractère. Comme j'imagine que tu cherches en fait la cible du lien, essaie avec :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    if Not AnsiPos('zip', Browser.OleObject.Document.Links.Item(i).href) = 0 then

  5. #5
    Membre éclairé Avatar de delagoutte
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    42
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Pyrénées Atlantiques (Aquitaine)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 42
    Par défaut
    j'ai utilisé par le passé le code de la faq sans problème.(winxp+delphi7+IE8)
    vérifie que tu as ces unité dans tes uses :
    SHDocVw, SHDocVw_TLB,mshtml_tlb,variants,activex,ComObj


    Sinon, ci dessous tu trouveras une adaption d'une partie du code que j'utilise maintenant (renvoi tous les liens même ceux des frames si il y en a de manière récursive) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
     
    function ViewAllLink(MyWebBrowser : TEmbeddedWB):string;
    var
      UNum: Variant;
      s: string;
      ResList: TStringList;
      OleObject: Variant;
     
      procedure RecurseLinks(htmlDoc: Variant);
      var
        BodyElement, ElementCo,ElementClick, HTMLFrames, HTMLWnd, doc: OleVariant;
        k,j, i: Integer;
      begin
        if VarIsEmpty(htmlDoc) then Exit;
        BodyElement := htmlDoc.body;
        if BodyElement.tagName = 'BODY' then
        begin
          ElementCo := htmlDoc.links;
          j := ElementCo.Length - 1;
          for i := 0 to j do
          begin
            UNum := ElementCo.item(i);
            try
            s := UNum.href;
            except
              s:='';
            end;
            if j = 0 then
              s := ''
            else
              ResList.Add(s);
          end;
        end;
        HTMLFrames := htmlDoc.Frames;
        j := HTMLFrames.Length - 1;
        for i := 0 to j do
        begin
          HTMLWnd := HTMLFrames.Item(i);
          try
            doc := HTMLWnd.Document;
            RecurseLinks(doc);
          except
            Continue;
          end;
        end;
      end;
    begin
      try
      ResList := TStringList.Create;
      OleObject := Mywebbrowser.OleObject ;
      if not DocumentLoaded(OleObject.Document) then
        Exit;
      RecurseLinks(OleObject.Document);
      result := ResList.text;
      finally
      ResList.Free;
      end;
    end;
    Comme tu peux le voire j'utilise principalement un autre compo que le TWebbrowser classique mais le principe reste le même. et cela devrait marcher avec un TWebbrowser classique au lieu d'un TEmbeddedWB.

  6. #6
    Membre averti
    Profil pro
    Inscrit en
    Avril 2010
    Messages
    22
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 22
    Par défaut
    J'ai été un peu occupé ces derniers temps, j'ai pas trop pu m'occuper de ce projet.

    Mais voila, j'ai continué de coder et j'ai fini par avoir ça:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    function TLauncherForm.VerifVersion(): String;
    var
      tableau_adresse: TExplodeArray;
      i: Integer;
    begin
      StatusBar1.SimpleText := 'Connexion au site';
      MajBrowser.Navigate(EditDLPage.Text);
     
      while not docComplete do
        Application.Processmessages;
     
      StatusBar1.SimpleText := 'Analyse de la page';
      for i:=0 to MajBrowser.OleObject.Document.Links.Length-1 do
        if Not AnsiPos('zip', MajBrowser.OleObject.Document.Links.Item(i).href) = 0 then
          tableau_adresse := Explode('/', MajBrowser.OleObject.Document.Links.Item(i).href);
     
      StatusBar1.SimpleText := 'Vérification terminée';
      Result:= tableau_adresse[Length(tableau_adresse)-1];
    end;
    Voila le soucis:
    Access violation at adress 004BEF 16 in module 'Launch.exe'. Read of address FFFFFFFC
    Merci bien

  7. #7
    Expert éminent
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    14 124
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14 124
    Par défaut
    Tu devrais vérifier si Explode renvoi un tableau avec des éléments !
    j'ai l'impression que tableau_adresse est vide, nil = 00000000, et comme tu récupère l'item -1 d'un TExplodeArray (je ne connais pas, cela semble être un array of string), donc comme un string c'est un pointeur (4 octets) et que 00000000-4 = FFFFFFFC

    Est-ce que hRef contient au moins quelque chose !
    Est-ce Explode est vraiment appelé ?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    if Not AnsiPos('zip', MajBrowser.OleObject.Document.Links.Item(i).href) = 0 then
    Hum, c'est délicat à comprendre : Règles de priorité des opérateurs

    Le but est bien de vérifier que Zip est contenu dans la chaine ?

    donc le mieux serait
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    if AnsiPos('zip', MajBrowser.OleObject.Document.Links.Item(i).href) > 0 then
    car j'ai peur qu'en réalité tu as écrit

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    if (Not AnsiPos('zip', MajBrowser.OleObject.Document.Links.Item(i).href)) = 0 then
    Comme c'est un not binaire sur un nombre signé, cela ne doit pas être terrible, le seul moyen d'avoir 0 serait que AnsiPos renvoit -1 ce qui est impossible !

    Et donc tu n'entres jamais dans le then !
    tu pourrais tout de même exécuter pas-à-pas avant de balancer tes messages d'excetions
    De plus, tu notes qu'avec un peu d'effort, ce message était interprétable !


    Tel que tu as écrit la boucle, elle est étrange, cela revient à faire


    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
      for i:= MajBrowser.OleObject.Document.Links.Length - 1 downto 0 do
        if Not AnsiPos('zip', MajBrowser.OleObject.Document.Links.Item(i).href) = 0 then
        begin
          tableau_adresse := Explode('/', MajBrowser.OleObject.Document.Links.Item(i).href);
          break;
        end;
    ne serait pas plutôt
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
     
      StatusBar1.SimpleText := 'Analyse de la page';
      for i:=0 to MajBrowser.OleObject.Document.Links.Length-1 do
      begin
        if AnsiPos('zip', MajBrowser.OleObject.Document.Links.Item(i).href) > 0 then
        begin
          tableau_adresse := Explode('/', MajBrowser.OleObject.Document.Links.Item(i).href);
          if Length(tableau_adresse) > 0 then
          begin
            StatusBar1.SimpleText := 'Vérification terminée avec succès';
            Result:= tableau_adresse[Length(tableau_adresse)-1];
            Exit;
          end;
        end;
      end;
     
      StatusBar1.SimpleText := 'Vérification terminée';
    end;
    Aide via F1 - FAQ - Guide du développeur Delphi devant un problème - Pensez-y !
    Attention Troll Méchant !
    "Quand un homme a faim, mieux vaut lui apprendre à pêcher que de lui donner un poisson" Confucius
    Mieux vaut se taire et paraître idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la médiocrité !

    L'expérience, c'est le nom que chacun donne à ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

  8. #8
    Membre averti
    Profil pro
    Inscrit en
    Avril 2010
    Messages
    22
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Avril 2010
    Messages : 22
    Par défaut
    Ton code corrigé marche, merci beaucoup.

    Cela dit, j'ai compris que je devrais user du debug-mode et des break-points plus souvent pour vérifier le contenu des variables et le code qui est exécuté.

    Merci pour ça, j'en tirerais de bonnes leçons.

    Edit: et merci aux autres aussi

  9. #9
    Expert éminent
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    14 124
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 14 124
    Par défaut
    Je te conseille aussi ceci

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
      while not docComplete do
      begin
        Sleep(0);
        Application.ProcessMessages();
      end;
    Navigate étant asynchrone, tu dois attendre effectivement, mais ProcessMessages est chronophage (regarde le processeur qui doit consommer massivement), Sleep permet que le thread qui attend laisse plus temps au autres thread pour travailler donc celui du TWebBrowser
    Aide via F1 - FAQ - Guide du développeur Delphi devant un problème - Pensez-y !
    Attention Troll Méchant !
    "Quand un homme a faim, mieux vaut lui apprendre à pêcher que de lui donner un poisson" Confucius
    Mieux vaut se taire et paraître idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la médiocrité !

    L'expérience, c'est le nom que chacun donne à ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

+ Répondre à la discussion
Cette discussion est résolue.

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo