Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Cross-Platform-Entwicklung (https://www.delphipraxis.net/91-cross-platform-entwicklung/)
-   -   Text einer Internetseite in Memo einlesen (https://www.delphipraxis.net/216910-text-einer-internetseite-memo-einlesen.html)

Rued 21. Mär 2025 20:39

Text einer Internetseite in Memo einlesen
 
In meiner Android-App will ich eine Internetseite parsen, wie ich es in meinen PC-Anwendungen mache.

Leider funktioniert WebBrowser1.OleObject.document.body.innerText nicht.

Wie bekomme ich den Text einer Internetseite, die über JavaScript generiert wurde, in ein Memo-Feld - wenn möglich ohne die WebBrowser-Komponente?

jaenicke 21. Mär 2025 21:07

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von Rued (Beitrag 1547350)
Leider funktioniert WebBrowser1.OleObject.document.body.innerText nicht.

Das funktioniert nur mit dem alten Internet Explorer Control, das es auf anderen Plattformen logischerweise nicht gibt.

Zitat:

Zitat von Rued (Beitrag 1547350)
Wie bekomme ich den Text einer Internetseite, die über JavaScript generiert wurde, in ein Memo-Feld - wenn möglich ohne die WebBrowser-Komponente?

Du kannst TEdgeBrowser verwenden. Das sollte so ca. gehen:
Delphi-Quellcode:
EdgeBrowser.ExecuteScript('document.documentElement.outerHTML',
  ...
Ohne Browser kann es wegen JavaScript nicht gehen.

Sinnvoller ist aber, wenn du über eine API des Anbieters gehst bzw. diesen danach fragst.

Rued 21. Mär 2025 21:22

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von jaenicke (Beitrag 1547352)
...
Du kannst TEdgeBrowser verwenden.
...

TEdgeBrowser habe ich in der geräteübergreifenden Entwicklung nicht.

Christian Seehase 21. Mär 2025 21:34

AW: Text einer Internetseite in Memo einlesen
 
Moin Rüdiger,

vielleicht kannst Du hiermit Klasse HTMLDocument etwas anfangen.

jaenicke 21. Mär 2025 21:45

AW: Text einer Internetseite in Memo einlesen
 
Einfach herunterladen und parsen funktioniert aber mit JavaScript nicht.

Zum Browser:
Entschuldigung, es ist schon spät. Ich meinte FMX TWebBrowser und EvaluateJavaScript. Das sollte unter Android gehen.

Rued 21. Mär 2025 22:13

AW: Text einer Internetseite in Memo einlesen
 
Weiß nicht, wie es es umsetzbar ist, aber warum kann ich die Seite nicht im TWebBrowser laden, dort "alles markieren" und dann die Zwischenablage ins Memo laden?

Rued 22. Mär 2025 13:29

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von Christian Seehase (Beitrag 1547354)
Moin Rüdiger,

vielleicht kannst Du hiermit Klasse HTMLDocument etwas anfangen.

Da wird der Content aus der Zwischenablage bezogen. Wenn ich den Text der aufgerufenen Website erst einmal in der Zwischenablage habe, dann habe ich schon gewonnen. Denn dann habe ich ihn auch im Memo-Feld, in dem ich den Text durchsuchen kann. Mit irgendwelchen Tags habe ich dann nichts am Hut.

Daher noch einmal die Frage, wie komme ich an den Text einer im WebBrowser aufgerufenen Seite ohne OleObject, das ja im FMX.TWebBrowser nicht im Angebot ist?

jaenicke 22. Mär 2025 14:57

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von Rued (Beitrag 1547365)
Daher noch einmal die Frage, wie komme ich an den Text einer im WebBrowser aufgerufenen Seite ohne OleObject, das ja im FMX.TWebBrowser nicht im Angebot ist?

Funktioniert mit dem genannten EvaluateJavaScript etwas nicht?

Rued 22. Mär 2025 15:22

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von jaenicke (Beitrag 1547366)
Zitat:

Zitat von Rued (Beitrag 1547365)
Daher noch einmal die Frage, wie komme ich an den Text einer im WebBrowser aufgerufenen Seite ohne OleObject, das ja im FMX.TWebBrowser nicht im Angebot ist?

Funktioniert mit dem genannten EvaluateJavaScript etwas nicht?

Ich habe damit noch nicht gearbeitet:

Delphi-Quellcode:
var
  JS: string;
begin
   JS := 'var text = encodeURIComponent(document.body.innerText);' ;
  WebBrowser1.EvaluateJavaScript(JS);
Wie komme ich jetzt an text ?

Christian Seehase 22. Mär 2025 15:32

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von Rued (Beitrag 1547365)
Zitat:

Zitat von Christian Seehase (Beitrag 1547354)
Moin Rüdiger,

vielleicht kannst Du hiermit Klasse HTMLDocument etwas anfangen.

Da wird der Content aus der Zwischenablage bezogen. Wenn ich den Text der aufgerufenen Website erst einmal in der Zwischenablage habe, dann habe ich schon gewonnen. Denn dann habe ich ihn auch im Memo-Feld, in dem ich den Text durchsuchen kann. Mit irgendwelchen Tags habe ich dann nichts am Hut.

Daher noch einmal die Frage, wie komme ich an den Text einer im WebBrowser aufgerufenen Seite ohne OleObject, das ja im FMX.TWebBrowser nicht im Angebot ist?

Dann schau Dir mal das Beispiel im zweiten Beitrag von "Klasse HTMLDocument" an.
Da wird, u.a., der gesamte Content (Text) ausgelesen.

Rued 22. Mär 2025 16:59

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von Christian Seehase (Beitrag 1547368)
Zitat:

Zitat von Rued (Beitrag 1547365)
Zitat:

Zitat von Christian Seehase (Beitrag 1547354)
Moin Rüdiger,

vielleicht kannst Du hiermit Klasse HTMLDocument etwas anfangen.

Da wird der Content aus der Zwischenablage bezogen. Wenn ich den Text der aufgerufenen Website erst einmal in der Zwischenablage habe, dann habe ich schon gewonnen. Denn dann habe ich ihn auch im Memo-Feld, in dem ich den Text durchsuchen kann. Mit irgendwelchen Tags habe ich dann nichts am Hut.

Daher noch einmal die Frage, wie komme ich an den Text einer im WebBrowser aufgerufenen Seite ohne OleObject, das ja im FMX.TWebBrowser nicht im Angebot ist?

Dann schau Dir mal das Beispiel im zweiten Beitrag von "Klasse HTMLDocument" an.
Da wird, u.a., der gesamte Content (Text) ausgelesen.

Das hatte ich mir angesehen und vielleicht verstehe ich auch "LDOC.Content := Clipboard.AsText;" falsch. Das sieht für mich so aus, als würde der Code mit der Zwischenablage gefüttert, die für mich das Ziel der Bemühungen ist. Zudem muss ich keine tags identifizieren.

Ich bringe es mal auf den Punkt: Ich will den Text dieser Seite in ein Memo-Feld bekommen, um Spielergebnisse auslesen zu können.

Christian Seehase 22. Mär 2025 17:39

AW: Text einer Internetseite in Memo einlesen
 
Stimmt, mein Fehler. :oops:
Man braucht eine Datei mit dem gesamten HTML Dokument.
Der Download der Webadresse ist nicht enthalten.
Inwieweit die Indys plattformübergreifend funktionieren, weiss ich leider nicht.
Damit hatte ich schon Downloads gemacht.

jaenicke 22. Mär 2025 19:35

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von Rued (Beitrag 1547371)
Ich bringe es mal auf den Punkt: Ich will den Text dieser Seite in ein Memo-Feld bekommen, um Spielergebnisse auslesen zu können.

Aber du hast doch eingangs dies geschrieben:
Zitat:

Zitat von Rued (Beitrag 1547350)
Wie bekomme ich den Text einer Internetseite, die über JavaScript generiert wurde, in ein Memo-Feld - wenn möglich ohne die WebBrowser-Komponente?

Die genannte Webseite liefert aber den kompletten Inhalt ganz ohne Skripte aus. Da brauchst du keine Browserfunktionalität, sondern kannst die Webseite direkt herunterladen...

Also kannst du einfach TNetHTTPClient.Get verwenden:
https://docwiki.embarcadero.com/Libr...HTTPClient.Get

fisipjm 22. Mär 2025 21:21

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von jaenicke (Beitrag 1547373)
Zitat:

Zitat von Rued (Beitrag 1547371)
Ich bringe es mal auf den Punkt: Ich will den Text dieser Seite in ein Memo-Feld bekommen, um Spielergebnisse auslesen zu können.

Aber du hast doch eingangs dies geschrieben:
Zitat:

Zitat von Rued (Beitrag 1547350)
Wie bekomme ich den Text einer Internetseite, die über JavaScript generiert wurde, in ein Memo-Feld - wenn möglich ohne die WebBrowser-Komponente?

Die genannte Webseite liefert aber den kompletten Inhalt ganz ohne Skripte aus. Da brauchst du keine Browserfunktionalität, sondern kannst die Webseite direkt herunterladen...

Also kannst du einfach TNetHTTPClient.Get verwenden:
https://docwiki.embarcadero.com/Libr...HTTPClient.Get

Ich denke mal es geht ihm darum das er nur den Text bekommt, also nicht das HTML sondern nur den fertig geparsten Text.

Rued 22. Mär 2025 22:44

AW: Text einer Internetseite in Memo einlesen
 
Wenn ich
Delphi-Quellcode:
Memo4.text:= NetHTTPClient1.get('https://m.flashscore.de/?d=0').ContentAsString;
starte bekomme ich Html, ausschnittsweise...
Code:
<!DOCTYPE html>
<html lang="de">
    <head>
        <meta charset="utf-8">
        <title>Livescore Mobile - Fussball auf Flashscore.de Mobil</title>
        <meta name="description" content="Verfolge die akttuellen fussball Ergebnisse wenn du unterwegs bist mit der für Mobilgeräte optimierten Version von Flashscore.de.">
        <meta name="copyright" content="Copyright (c) 2006-2025 Livesport s.r.o.">
        <meta name="robots" content="noindex,nofollow" />
        <meta name="viewport" content="width=device-width, initial-scale=1">
       <meta property="og:title" content="Livescore Mobile - Fussball auf Flashscore.de Mobil">
       <meta property="og:description" content="Verfolge die akttuellen fussball Ergebnisse wenn du unterwegs bist mit der für Mobilgeräte optimierten Version von Flashscore.de.">
       <meta property="og:type" content="website">
       <meta property="og:url" content="http://www.flashscore.de/?d=0">
       <meta property="og:image" content="https://m.flashscore.de/">
            <link rel="shortcut icon" href="https://static.flashscore.com/res/_fs/image/4_favicons/_fs/favicon.ico?v=8">
            <link rel="apple-touch-icon" sizes="180x180" href="https://static.flashscore.com/res/_fs/image/4_favicons/_mobi/touch-icon-180x180.png?v=8">
            <link rel="icon" type="image/png" sizes="32x32" href="https://static.flashscore.com/res/_fs/image/4_favicons/_mobi/favicon-32x32.png?v=8">
            <link rel="icon" type="image/png" sizes="16x16" href="https://static.flashscore.com/res/_fs/image/4_favicons/_mobi/favicon-16x16.png?v=8">
        <link rel="manifest" href="/manifest/1/?v=7">
        <meta name="theme-color" content="#001e28">
        <link rel="stylesheet" href="https://static.flashscore.com/x/css/layout_304_1433000000.css">
        <link rel="stylesheet" href="https://static.flashscore.com/res/styles/container.304.css">
        <link rel="stylesheet" href="https://static.flashscore.com/res/styles/container.0.css">
        <script type="text/javascript" defer src="https://static.flashscore.com/res/_fs/build-mobi/programaticStrip.ba5d2c6.js"></script>
        <script type="text/javascript" src="https://static.flashscore.com/res/_fs/build-mobi/mobiRuntime.2d4cf7d.js"></script>
        <script type="text/javascript" src="https://static.flashscore.com/res/_fs/build-mobi/autorefresh.0b1d793.js"></script>
        <script type="text/javascript">
            // <![CDATA[
            // ]]>
        </script>
    </head>
<body class="m.Flashscore.de mobi brand--flashscore">
<div id="top"></div><div class="logo"><a href="/"><img src="https://static.flashscore.com/res/_mobi/image/logo/flashscore.png?v=2" alt="m.Flashscore.de" /></a></div>
<div id="main" class="soccer">
<p class="p-set menu"><a href="/" class="active">Fussball</a> | <a href="/eishockey/">Eishockey</a> | <a href="/tennis/">Tennis</a> | <a href="/basketball/">Basketball</a> | <a href="/handball/">Handball</a> | <a href="/volleyball/">Volleyball</a> | <a href="/baseball/">Baseball</a> | <a href="/football/">Am. Football</a> | <a href="/rugby/">Rugby</a> | <a href="/andere-sportarten/">Mehr&nbsp;&raquo;</a></p><p class="p-set menu">
...
Kopiere ich gleichzeitig den von mir gewünschten Text der Seite, erhalte ich ausschnittsweise...
Code:
Fussball | Eishockey | Tennis | Basketball | Handball | Volleyball | Baseball | Am. Football | Rugby | Mehr »

Heute | Gestern | Morgen | Weitere Tage »

Alle Spiele | LIVE | Beendete | Quoten

Auto-refresh (30s) | EINSCHALTEN | JETZT AKTUALISIEREN

Fussball » Heute » Alle Spiele
Sportwetten jetzt auch von Ihrem Mobiltelefon aus. Mit bet365!

AFRIKA: Weltmeisterschaft - Qualifikation Tabelle
15:00AbgesagtKongo - Sambia -:-
15:00AbgesagtNiger - Eritrea -:-
17:00Togo - Mauretanien 2:2
20:00Sudan - Senegal 0:0
EUROPA: Weltmeisterschaft - Qualifikation Tabelle
15:00Liechtenstein - Nordmazedonien 0:3
18:00Moldawien - Norwegen 0:5
18:00Montenegro - Gibraltar 3:1
88'Israel - Estland 2:1
90+'Tschechien - Färöer Inseln 2:1
90'Wales - Kasachstan 2:1
SÜDAMERIKA: Weltmeisterschaft - Qualifikation Tabelle
00:30Uruguay - Argentinien 0:1
ÄGYPTEN: Division 2 A Tabelle
20:30Abu Qir Semad - Al-Sekka 0:0
90+'Aswan SC - WE SC 1:0
90+'Dayrout - Asyut Petroleum 0:2
Warten auf
UpdatesEl Mansoura - Alexandria SC 1:0
90+'La Viena - Kahrabaa Ismailia 0:2
87'Proxy - Arab Contractors 0:2
90+'Suez SC - Baladiyat El Mahalla 0:1
90+'Tanta - Tersana 1:0
90+'Wadi Degla - Al Qanah 2:1
...

jaenicke 22. Mär 2025 22:53

AW: Text einer Internetseite in Memo einlesen
 
Zum Parsen der Seite kannst du Christians Klasse verwenden. Oder du nimmst einfach Regular Expressions, denn das Format ist ja sehr überschaubar.

Wenn du aus dem Browser markierst und kopierst, bekommst du ja nur den Text. Das ist zwar für einen Menschen gut lesbar, aber um es verarbeiten zu können, fehlen alle Elementdefinitionen. Darum kann man damit zum Verarbeiten wenig anfangen. Da musst du ja wissen, wo ein Element anfängt und wo es endet.

Rued 23. Mär 2025 01:13

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von jaenicke (Beitrag 1547377)
...Wenn du aus dem Browser markierst und kopierst, bekommst du ja nur den Text...

Sorry, ich weiß nicht, wie oft ich es sagen soll... ICH WILL NUR DEN TEXT - und den gibt mir keiner!

HolgerX 23. Mär 2025 06:35

AW: Text einer Internetseite in Memo einlesen
 
Liste der Anhänge anzeigen (Anzahl: 1)
Hmm..

Ich habe mal zum Test einfach mit D6 und dessem TWebBrowser (Ja, der URALT IE)!
den Link geöffnet und dann dessen Text in ein Memo geholt.

(Siehe ScreenShot.jpg)

Delphi-Quellcode:
procedure TForm1.Button1Click(Sender: TObject);
begin
  WebBrowser1.Silent := True; // Script-Fehlemeldunngen unterdrücken
  WebBrowser1.Navigate(Edit1.Text);

  // Warten das Browser fertig
  while not(WebBrowser1.ReadyState = READYSTATE_COMPLETE) do Application.ProcessMessages;

  // Text aus IE holen
  Memo1.Lines.Text := WebBrowser1.OleObject.Document.Body.InnerText // nur der Text;
end;
Auch wenn MS den IE nicht mehr weiter entwickelt, kann es noch im aktuellen W11 verwendet werden.
Eigentlich müsste dies doch im neuen Delphi und dem TEgeBrowser genau so gehen?

Optional könnte das auch im Hintergrund mit der MSHTML gemacht werden, hab ich nur noch nicht ausprobiert.
Diese soll lt. MS auch noch weiterhin in Windows verbleiben, selbst wenn der IE entfernt wird...

jaenicke 23. Mär 2025 08:52

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von Rued (Beitrag 1547378)
Sorry, ich weiß nicht, wie oft ich es sagen soll... ICH WILL NUR DEN TEXT - und den gibt mir keiner!

Ich hatte das so verstanden, dass du das danach automatisch auswerten wolltest. Das erschwert du dir damit unnötig.

Ich würde dir sehr raten, auf den umständlichen Weg über den Webbrowser und das umständliche Auswerten des reinen Textes zu verzichten und den Download der Seite und den direkten Zugriff auf die Elemente zu nutzen.

Aber dein Weg ist sehr einfach, was das Auslesen des Textes angeht, nur eben mit viel Overhead:
In Javascript bekommst du das mit document.body.innerText, das du oben ja schon verwendet hast. Das kannst du dann mit EvaluateJavaScript auswerten, musst das dann aber auch zurückgeben und nicht in eine Variable schreiben. Du kannst das auch direkt bekommen, aber das ist relativ umständlich und funktioniert dann nur unter Android, deshalb zeige ich lieber einen einfachen Weg, auch wenn der nicht optimal ist.

Beispiel:
Delphi-Quellcode:
procedure TForm287.Button1Click(Sender: TObject);
begin
  WebBrowser1.Navigate('https://www.with-is-bad.de');
end;

procedure TForm287.Button2Click(Sender: TObject);
begin
  WebBrowser1.EvaluateJavaScript('document.location = "source://" + encodeURIComponent(document.documentElement.outerHTML);');
end;

procedure TForm287.WebBrowser1ShouldStartLoadWithRequest(ASender: TObject;
  const URL: string);
begin
  if URL.StartsWith('source://') then
  begin
    ShowMessage(TNetEncoding.URL.Decode(URL.Substring(9)));
    WebBrowser1.Stop;
  end;
end;
Zitat:

Zitat von HolgerX (Beitrag 1547380)
Ich habe mal zum Test einfach mit D6 und dessem TWebBrowser (Ja, der URALT IE)!

Das hat leider nichts mit dem Thema zu tun. Es geht um Android. ;-)

jaenicke 23. Mär 2025 09:56

AW: Text einer Internetseite in Memo einlesen
 
Liste der Anhänge anzeigen (Anzahl: 1)
Hier mal ein komplettes Beispiel ohne Browser und ohne Parserklasse, einfach nur Strings und eine Regular Expression. Die Kategorie könnte man natürlich auch im RegEx direkt mit auswerten, aber so ist es vielleicht einfacher zu verstehen.

Du brauchst nur einen Button und ein Memo:
Delphi-Quellcode:
uses
  System.Generics.Collections, System.RegularExpressions, System.Net.HttpClientComponent;

type
  TGame = class
    Category: string;
    StartTime: string;
    Opponent1, Opponent2: string;
    URL: string;
    MatchResult1, MatchResult2: string;
  end;

function LoadHtml(const AUrl: string): string;
var
  NetHTTPClient: TNetHTTPClient;
begin
  NetHTTPClient := TNetHTTPClient.Create(nil);
  try
    Result := NetHTTPClient.get(AUrl).ContentAsString;
  finally
    NetHTTPClient.Free;
  end;
end;

function ParseGameLine(const AValue: string): TGame;
var
  RegEx: TRegEx;
  Match: TMatch;
begin
  RegEx := TRegEx.Create('<span>([0-9:]*)<\/span>([a-zA-Z]*) - ([a-zA-Z]*) ?<a href="([\/a-zA-Z0-9]*)" class="sched">([0-9\-]*):([0-9\-]*)<\/a>');
  Match := RegEx.Match(AValue);
  if Match.Success then
  begin
    Result := TGame.Create;
    Result.StartTime := Match.Groups[1].Value;
    Result.Opponent1 := Match.Groups[2].Value;
    Result.Opponent2 := Match.Groups[3].Value;
    Result.URL := Match.Groups[4].Value;
    Result.MatchResult1 := Match.Groups[5].Value;
    Result.MatchResult2 := Match.Groups[6].Value;
  end
  else
    Result := nil;
end;

procedure FindGames(const ATarget: TObjectList<TGame>);
const
  cContentsContainer = '<div id="score-data">';
  cHeaderStart = '<h4>';
  cHeaderEnd = '</h4>';
var
  HtmlContents, CurrentCategory, CurrentLine: string;
  Data: TArray<string>;
  CurrentGame: TGame;
  i: Integer;
begin
  HtmlContents := LoadHtml('https://m.flashscore.de/?d=0');
  HtmlContents := HtmlContents.Substring(HtmlContents.IndexOf(cContentsContainer) + Length(cContentsContainer));
  Data := HtmlContents.Split(['<br />']);
  for i := 0 to High(Data) do
  begin
    CurrentLine := Data[i];
    if CurrentLine.StartsWith(cHeaderStart) then
    begin
      CurrentCategory := CurrentLine.Substring(Length(cHeaderStart), CurrentLine.IndexOf(cHeaderEnd));
      if CurrentCategory.IndexOf('<') > 0 then
        CurrentCategory := CurrentCategory.Substring(0, CurrentCategory.IndexOf('<')).Trim;
      CurrentLine := CurrentLine.Substring(CurrentLine.IndexOf(cHeaderEnd) + Length(cHeaderEnd));
    end;
    CurrentGame := ParseGameLine(CurrentLine);
    if Assigned(CurrentGame) then
    begin
      CurrentGame.Category := CurrentCategory;
      ATarget.Add(CurrentGame);
    end;
  end;
end;

procedure TForm288.Button1Click(Sender: TObject);
var
  CurrentGame: TGame;
  Games: TObjectList<TGame>;
  i: Integer;
begin
  Games := TObjectList<TGame>.Create(True);
  try
    FindGames(Games);
    for i := 0 to Games.Count - 1 do
    begin
      CurrentGame := Games[i];
      Memo1.Lines.Add(CurrentGame.Category + sLineBreak
        + 'Start: ' + CurrentGame.StartTime + sLineBreak
        + 'Gegner: ' + CurrentGame.Opponent1 + ' gegen ' + CurrentGame.Opponent2 + sLineBreak
        + 'URL: ' + CurrentGame.URL + sLineBreak
        + 'Ergebnis: ' + CurrentGame.MatchResult1 + ' : ' + CurrentGame.MatchResult2 + sLineBreak + sLineBreak);
    end;
  finally
    Games.Free;
  end;
end;
Ergebnis:
Anhang 57450

Solltest du das nicht nur privat selbst nutzen, brauchst du natürlich auch die Genehmigung des Seiteninhabers, dass du die Daten nutzen darfst!

Rued 23. Mär 2025 14:09

AW: Text einer Internetseite in Memo einlesen
 
Sebastian, das ist für mich eine völlig fremde Welt. Wenn ich Deinen Code sehe, überlege ich, ob ich mir nicht ein neues Hobby suche, das Programmieren aufgebe.

Ganz herzlichen Dank für dieses Lehrstück! Das ist mein voller Ernst.

Darf ich trotzdem noch fragen, wie ich in Erfahrung bringe, welche Angaben "Data" noch so enthält? Zum Beispiel, ob das Spiel beendet ist, ob Halbzeit ist oder das Spiel verlegt wurde?
Habe ne Weile geschaut, ob ich da selbst hinterkomme, aber keine Chance in absehbarer Zeit.

jaenicke 23. Mär 2025 15:00

AW: Text einer Internetseite in Memo einlesen
 
Liste der Anhänge anzeigen (Anzahl: 1)
Zitat:

Zitat von Rued (Beitrag 1547385)
Sebastian, das ist für mich eine völlig fremde Welt. Wenn ich Deinen Code sehe, überlege ich, ob ich mir nicht ein neues Hobby suche, das Programmieren aufgebe.

Das kann man alles lernen. Wichtig ist nur, dass du wirklich lernst und verstehst, was solcher Code eigentlich macht. Nicht auswendig lernen, sondern wirklich verstehen wie der Code funktioniert, denn genau das ist der entscheidende Unterschied. Wenn du soweit bist, kannst du das dann auch in anderen Situationen anwenden.

Das ist am Anfang nicht einfach, aber es lohnt sich, die Zeit zu investieren, auch wenn es schon funktioniert. Und du kannst natürlich jederzeit konkret fragen, wenn du etwas nicht verstehst. Für uns ist das Problem immer, dass wir nicht wissen, wo ein Verständnisproblem liegt.

Zitat:

Zitat von Rued (Beitrag 1547385)
Darf ich trotzdem noch fragen, wie ich in Erfahrung bringe, welche Angaben "Data" noch so enthält? Zum Beispiel, ob das Spiel beendet ist, ob Halbzeit ist oder das Spiel verlegt wurde?

Am besten drückst du im normalen Chrome Browser einfach mal F12, falls du das noch nicht gemacht hast. Dann drückst du Strg + Shift + C. Dann kannst du die einzelnen Elemente anklicken und siehst, wie die im Quelltext aussehen.
Vorsicht: Das sieht im Browser nicht 1:1 so aus wie du es bekommst.
Aber daran kannst du sehen, wonach du im Quelltext, den du dir ja einfach in eine Textdatei zur Ansicht speichern kannst, suchen musst.

Anhang 57451

In diesem Fall ist wichtig, dass Zeilenumbrüche im HTML-Quelltext <br /> (so bekommst du es) bzw. <br> (so siehst du es in Chrome) sind. Dementsprechend habe ich die Zeilen so trennen können. Und sie stecken in einem div-Container, der so aussieht: <div id="score-data">
Also kann ich danach suchen.

Viel musst du dafür über HTML nicht unbedingt wissen. Da sollte es reichen, wenn du dir den Quelltext ein wenig anschaust.

Rued 23. Mär 2025 15:24

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von jaenicke (Beitrag 1547386)
Das kann man alles lernen. Wichtig ist nur, dass du wirklich lernst und verstehst, was solcher Code eigentlich macht.
...

Hast Du da einen Tipp für Literatur oder Tutorials?
Zitat:

Zitat von jaenicke (Beitrag 1547386)
...
Am besten drückst du im normalen Chrome Browser einfach mal F12, falls du das noch nicht gemacht hast. Dann drückst du Strg + Shift + C.
...

Interessant, Strg + Shift + C kannte ich noch nicht.

HolgerX 23. Mär 2025 16:39

AW: Text einer Internetseite in Memo einlesen
 
Hmmm...

Zitat:

Zitat von jaenicke (Beitrag 1547381)
nichts mit dem Thema zu tun. Es geht um Android. ;-)

Stimmt..

Aber hat dann doch zum Ergebnis geführt ;)

Er hat u.a. nach einer Möglichkeit gesucht, das mit einem Browser in Delphi zu machen...
Mein Beispiel hat die Windows D6 Lösung gezeigt.

Dein Folgebeitrag dann die Lösung mit dem Aktuellen TWebBrowser unter Android..
Somit hat mein Beitrag einen kleinen Schubs gegeben ;)

Leider funktionieren diverse Seiten ohne Browser nicht, da deren Kontent erst im Browser per Java-Script zusammen gebaut wird und nicht im direkten HTML per Indy und Co zu bekommen ist.

Somit muss die Seite erst im Browser geladen werden, von diesem vollständig (teils mit Runterscrollen auf der Seite) gebaut werden, bevor alles da ist.


Wenn (habs erst gerade gesehen) wie hier bereits aller Kontent im HTML enthalten ist, dann sollte die Seite direkt herunter geladen und geparst werden.

Dies kann per RegExt oder mit einem vollwertigem HTML-Parser gemacht werden.

jaenicke 23. Mär 2025 16:58

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von Rued (Beitrag 1547387)
Hast Du da einen Tipp für Literatur oder Tutorials?

Keine spezielle für ein bestimmtes Thema in dem Zusammenhang. Lesenswert ist das Buch von Marco Cantú:
https://www.embarcadero.com/products...ascal-handbook

Zitat:

Zitat von Rued (Beitrag 1547387)
Interessant, Strg + Shift + C kannte ich noch nicht.

Ich benutze normalerweise den linken oberen Button, aber bevor ich beschreibe, welcher das ist... :-D

Zitat:

Zitat von HolgerX (Beitrag 1547389)
Mein Beispiel hat die Windows D6 Lösung gezeigt.

Die hatte er in der ursprünglichen Frage oben geschrieben und gefragt, wie das unter Android geht, weil es dort WebBrowser1.OleObject.... nicht gibt. :wink:

Rued 23. Mär 2025 18:03

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von HolgerX (Beitrag 1547389)
Hmmm...

Zitat:

Zitat von jaenicke (Beitrag 1547381)
nichts mit dem Thema zu tun. Es geht um Android. ;-)

Stimmt..

Aber hat dann doch zum Ergebnis geführt ;)

Er hat u.a. nach einer Möglichkeit gesucht, das mit einem Browser in Delphi zu machen...
Mein Beispiel hat die Windows D6 Lösung gezeigt.
...

Tut mir leid, den Anstoß brauchte es nicht. Den Thread habe ich wie folgt eingeleitet:
Zitat:

In meiner Android-App will ich eine Internetseite parsen, wie ich es in meinen PC-Anwendungen mache.

Leider funktioniert WebBrowser1.OleObject.document.body.innerText nicht.
Sehe gerade, dass auch Sebastian schon darauf hingewiesen hat.

Rued 23. Mär 2025 18:10

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von jaenicke (Beitrag 1547390)
Zitat:

Zitat von Rued (Beitrag 1547387)
Hast Du da einen Tipp für Literatur oder Tutorials?

Keine spezielle für ein bestimmtes Thema in dem Zusammenhang. Lesenswert ist das Buch von Marco Cantú:
https://www.embarcadero.com/products...ascal-handbook
...

Danke, habe ich mal heruntergeladen.

Rued 24. Mär 2025 16:31

AW: Text einer Internetseite in Memo einlesen
 
Was ich nicht verstehe ist, dass die Abfrage für die Seite https://m.flashscore.de/?d=0 funktioniert, nicht aber z.B. für https://m.flashscore.de/?d=-1 (gestrige Begegnungen) und über https://m.flashscore.de/?d=1 die morgigen Spiele nicht auswirft - obwohl die Seiten m. E. identisch aufgebaut sind.

Da hapert es jeweils schon daran, dass
Delphi-Quellcode:
HtmlContents := LoadHtml('https://m.flashscore.de/?d=-1');
nichts liefert.

Woran liegt das?

Ergänzung: Mir fällt gerade auf, dass auch die Abfrage von https://m.flashscore.de/?d=0 nur neun Begegnungen listet, also nur einen Bruchteil der Liste auf der Seite.

jaenicke 25. Mär 2025 02:48

AW: Text einer Internetseite in Memo einlesen
 
Es gibt einfach noch viel mehr Informationen, die enthalten sein können...
Deshalb wäre es ja, wie ich schon schrieb, sinnvoll, den Betreiber nach einer richtigen Schnittstelle zu fragen, statt die Seite auszulesen.

Ich habe das mal angepasst. Es macht aber wohl Sinn, dass du die Zeile selbst als String untersuchst (ParseGameLine), da du vermutlich so bald nicht die Regular Expression selbst anpassen kannst. Auch würde es helfen, wenn du einen Parser verwendest und so die Möglichkeiten behandeln kannst.

So funktioniert es jedenfalls erst einmal:
Delphi-Quellcode:
uses
  System.Generics.Collections, System.RegularExpressions, System.Net.HttpClientComponent, System.StrUtils;

type
  TGame = class
    Category: string;
    GameTime: string;
    Status: string;
    Opponent1, Opponent2: string;
    RedCards1, RedCards2: string;
    URL: string;
    MatchResult1, MatchResult2: string;
    MatchResultInfo: string;
  end;

function LoadHtml(const AUrl: string): string;
var
  NetHTTPClient: TNetHTTPClient;
begin
  NetHTTPClient := TNetHTTPClient.Create(nil);
  try
    Result := NetHTTPClient.get(AUrl).ContentAsString;
  finally
    NetHTTPClient.Free;
  end;
end;

function ParseGameLine(const AValue: string): TGame;
var
  RegEx: TRegEx;
  Match: TMatch;
begin
  RegEx := TRegEx.Create('<span(?: class="live")?>([0-9:+'']+)(?:<span[^>]*>(.*?)<\/span>)?<\/span>\s*([^<]+)(?:<img[^>]*class="rcard-(\d+)"[^>]*>)?\s*- ([^<]+)(?:<img[^>]*class="rcard-(\d+)"[^>]*>)?\s*<a href="([^"]+)" class="[^"]*">([0-9\-]+):([0-9\-]+)(.*?)<\/a>');
  Match := RegEx.Match(AValue);
  if Match.Success then
  begin
    Result := TGame.Create;
    Result.GameTime := Match.Groups[1].Value;
    if Match.Groups[2].Success then
      Result.Status := Match.Groups[2].Value;
    Result.Opponent1 := Match.Groups[3].Value;
    if Match.Groups[4].Success then
      Result.RedCards1 := Match.Groups[4].Value;
    Result.Opponent2 := Match.Groups[5].Value;
    if Match.Groups[6].Success then
      Result.RedCards2 := Match.Groups[6].Value;
    Result.URL := Match.Groups[7].Value;
    Result.MatchResult1 := Match.Groups[8].Value;
    Result.MatchResult2 := Match.Groups[9].Value;
    if Match.Groups[10].Success then
      Result.MatchResultInfo := Match.Groups[10].Value;
  end
  else
    Result := nil;
end;

procedure FindGames(const ATarget: TObjectList<TGame>);
const
  cContentsContainer = '<div id="score-data">';
  cHeaderStart = '<h4>';
  cHeaderEnd = '</h4>';
var
  HtmlContents, CurrentCategory, CurrentLine: string;
  Data: TArray<string>;
  CurrentGame: TGame;
  i: Integer;
begin
  HtmlContents := LoadHtml('https://m.flashscore.de/?d=-1');
  HtmlContents := HtmlContents.Substring(HtmlContents.IndexOf(cContentsContainer) + Length(cContentsContainer));
  Data := HtmlContents.Split(['<br />']);
  for i := 0 to High(Data) do
  begin
    CurrentLine := Data[i];
    if CurrentLine.StartsWith(cHeaderStart) then
    begin
      CurrentCategory := CurrentLine.Substring(Length(cHeaderStart), CurrentLine.IndexOf(cHeaderEnd));
      if CurrentCategory.IndexOf('<') > 0 then
        CurrentCategory := CurrentCategory.Substring(0, CurrentCategory.IndexOf('<')).Trim;
      CurrentLine := CurrentLine.Substring(CurrentLine.IndexOf(cHeaderEnd) + Length(cHeaderEnd));
    end;
    CurrentGame := ParseGameLine(CurrentLine);
    if Assigned(CurrentGame) then
    begin
      CurrentGame.Category := CurrentCategory;
      ATarget.Add(CurrentGame);
    end;
  end;
end;

procedure TForm288.Button1Click(Sender: TObject);
var
  CurrentGame: TGame;
  Games: TObjectList<TGame>;
  i: Integer;
begin
  Games := TObjectList<TGame>.Create(True);
  try
    FindGames(Games);
    for i := 0 to Games.Count - 1 do
    begin
      CurrentGame := Games[i];
      Memo1.Lines.Add(CurrentGame.Category + sLineBreak
        + 'Spielzeit: ' + CurrentGame.GameTime + ' ' + CurrentGame.Status + sLineBreak
        + 'Gegner: ' + CurrentGame.Opponent1 + IfThen(CurrentGame.RedCards1 <> '', ' (' + CurrentGame.RedCards1 + ' rote Karte(n))', '')
          + ' gegen ' + CurrentGame.Opponent2 + IfThen(CurrentGame.RedCards2 <> '', ' (' + CurrentGame.RedCards2 + ' rote Karte(n))', '') + sLineBreak
        + 'URL: ' + CurrentGame.URL + sLineBreak
        + 'Ergebnis: ' + CurrentGame.MatchResult1 + ' : ' + CurrentGame.MatchResult2 + ' ' + CurrentGame.MatchResultInfo + sLineBreak + sLineBreak);
    end;
  finally
    Games.Free;
  end;
end;

Rued 25. Mär 2025 14:09

AW: Text einer Internetseite in Memo einlesen
 
Danke Dir Sebastian für die Anpassung. Das Ergebnis ermuntert, sich selbst mit der Thematik zu befassen, irritiert mich aber auch, da die Funktion, die HtmlContents liefert und zuvor ein unvollständiges Ergebnis lieferte, unverändert blieb, jetzt aber alle Zeilen erfasst.

jaenicke 25. Mär 2025 15:39

AW: Text einer Internetseite in Memo einlesen
 
Bist du da wirklich sicher? Das Problem war, dass die Zeilen zwar vorhanden waren, aber ein unerwartetes Aussehen hatten. Dadurch konnten die nicht mit dem Regex zerlegt werden und sie wurden ignoriert.

Ob solche Einträge da sind, findest du einfach heraus, indem du einen Haltepunkt im else in ParseGameLine setzt. Dort sollten keine Spieldaten gefunden werden. Einmal läuft das korrekt dort durch, weil ich das Ende der Liste nicht suche und daher dort nicht abbreche. Daher versucht es den Inhalt nach der Liste zu analysieren.

Rued 25. Mär 2025 17:33

AW: Text einer Internetseite in Memo einlesen
 
Zitat:

Zitat von jaenicke (Beitrag 1547462)
Bist du da wirklich sicher? Das Problem war, dass die Zeilen zwar vorhanden waren, aber ein unerwartetes Aussehen hatten. Dadurch konnten die nicht mit dem Regex zerlegt werden und sie wurden ignoriert.

Ob solche Einträge da sind, findest du einfach heraus, indem du einen Haltepunkt im else in ParseGameLine setzt. Dort sollten keine Spieldaten gefunden werden. Einmal läuft das korrekt dort durch, weil ich das Ende der Liste nicht suche und daher dort nicht abbreche. Daher versucht es den Inhalt nach der Liste zu analysieren.

Zu 100 % bin ich mir nicht sicher, zumal es unlogisch wäre. Ich dachte, ich hätte mir den ungeparsten HtmlContents angeschaut und wesentliche Seitenteile vermisst.

DANKE jedenfalls!


Alle Zeitangaben in WEZ +1. Es ist jetzt 12:11 Uhr.

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz