3 klitzekleine Fragen



  • Ich habe inzwischen Version 2 von nem Texteditor programmiert. Doch seit Version 0.9(Der Urversion) schon nervt mich die Fehlermeldung: "Datei kann nicht erstellt werden", wenn ich einen SaveDialog ausführe und auf "Abbrechen" klicke. Außerdem würde ich gerne, wie z.B. be Notepad üblich, eine Datei direkt per Drag ´n Drop aus dem Explorer in den Texteditor ziehen. Und wenn ich grade mal dabei bin: Wie kann ich ein Dokument per Doppelklick öffnen? Das müsste ja ungefähr das gleiche sein wie bei 2., oder? So, und jetzt kommen die Fragen:

    //------------------------------------------
    

    1. Fehlermeldung: "Datei kann nicht erstellt werden" bei Klick auf: Abbrechen im SaveDialog abfangen

    //-------------------------
    

    2. Drag ´n Drop aus dem Explorer in WriteSpeed

    //-------------------------
    

    3. Bei Doppelklick auf Datei sofort mit WriteSpeed öffnen

    //-------------------------
    

    Ich hoffe, dass das Thema wegen 2 Grundverschiedenen Fragen geschlossen wird. 😃



    1. Texteditor-Tutorial in der BCB-Hilfe durcharbeiten.

    2. Siehe FAQ unter 'Forms'.

    3. Siehe FAQ, erster Beitrag, sowie ParamStr().



  • 1. Im BCB-Tut Texteditor hab ich das nicht gefunden. Werd jetzt mal in das Beispiel gehen, was angegeben ist.(Das im Ordner $BCB5\examples\)

    2. Hab ich noch nicht ausgewertet.

    3. Die in der FAQ unter: ""Öffnen mit ..."-Dateiendung festlegen"
    angegebene Methode funktioniert nicht. WriteSpeed wird geöffnet, aber die Datei wird nicht geladen." Muss da noch irgendein Eintrag im Source gemacht werden?



  • du bistn held... woher sollen wir denn wissen was du in deinem SaveDialog verzapft hast, wenn du das nicht postest! was soll writespeed sein?

    zu 3. die eintragung zum starten, erfolgt in der registry dein programm muss den übergebenen parameter dann nur auswerten...

    schau mal hier (zu 3.):
    http://www.bytesandmore.de/rad/index.htm?http://www.bytesandmore.de/rad/cpp/snipp/sc03037.php



  • zu 1) Du hast Recht, das Tutorial ist da doch nicht so aussagekräftig. Das Beispiel aus der Hilfe zu TSaveDialog::Execute sollte aber alle Klarheiten beseitigen. 🙂

    zu 3) Wie gesagt: siehe auch ParamStr(), du musst den übergebenen Dateinamen auswerten.



    1. Da ist immer noch der ParameterString "%1", der den Anwendungen mit übergeben wird. Folgender Code mit GetCommandLine() funktioniert bei mir (und öffnet auch Quelltexte aus dem IE):
      [code type="C++"]
      void __fastcall TEditor::FormShow(TObject *Sender)
      {
      String ClickedFileName, FE;
      String CommandLine = GetCommandLine();
      int len = CommandLine.Length();
      String next = CommandLine.SubString(CommandLine.Pos(":") + 1,
      len - CommandLine.Pos(":"));
      //Prüfen, auf Command Line FileName
      if(next.Pos(":") != 0)
      {
      ClickedFileName = next.SubString(next.Pos(":") - 1,
      next.Length() - next.Pos(":") + 1);
      FE = ExtractFileExt(ClickedFileName).LowerCase();
      OpenDialog->FileName = ClickedFileName;
      OpenDialog->DefaultExt = FE;
      OpenDialog->InitialDir = OpenDialog->FileName;
      // Alles weitere (incl. der Zuweisungen an den SaveDialog)
      // dann gemeinsam mit der OpenDialog-Routine
      Open(Sender);
      }
      else
      // Wurde kein File geklickt, startet die MDI mit
      // einem neuen Child-Fenster
      FileNewClick(Sender);
      }[code]

    <edit>Ein ShowMessage(ClickedFileName); half beim richtigen Setzen der +1 und -1 (vorher hatte ich nur Erfolg bei in der Registry ohne "%1" selbsterstellten Dateitypen).



  • Hier ist der Code für die beiden SaveDialog-Aufrufe!

    void __fastcall TMainForm::FileSave(TObject *Sender)
    {
     if(SaveDialog->FileName != "")
      {
       RichEdit1->Lines->SaveToFile(SaveDialog->FileName); //Speichern des aktuellen Textes unter seinem aktuellen Namen
      }
     else
      {
       SaveDialog->Execute(); //Speichern-Dialog anzeigen
       RichEdit1->Lines->SaveToFile(SaveDialog->FileName); //Speichern des aktuellen Textes unter einem neuen Namem
      }
    }
    //----------------------------------------------------------------------------
    void __fastcall TMainForm::FileSaveAs(TObject *Sender)
    {
     if (SaveDialog->Execute())
      {
       RichEdit1->Lines->SaveToFile(SaveDialog->FileName); //Speichern des aktuellen Textes unter einem neuen Namem
      }
    }
    

    Danke erstmal an Omega-X. Gibt es auch ne Möglichkeit, die Datei direkt zu öffnen? Bei mir kommt, wenn ich auf ne Datei klicke, erstmal der OpenDialog!

    @Sunday: WriteSpeed ist der Name des Progs!
    @Jansen: Geht das auch über CmdLine?



  • Warum schreibst du in FileSave nur "SaveDialog->Execute()" ohne es auf den Rückgabewert zu prüfen, so wie du es in FileSaveAs machst?

    Wenn du dich also dann in FileSave befindest und du noch keinen Dateinamen angegeben hast, dann möchtest du mit Hilfe des Save-Dialogs ja einen neuen Namen angegeben und die Datei dann unter diesem Namen speichern.
    Wenn du allerdings während dieses Vorgangs auf Abbrechen klickst, dann hast du ja keinen Dateinamen angegeben, aber du rufst dann trotzdem die Speichermethode auf. Das kann ja nicht funktionieren!



  • Klar geht das auch über CmdLine (oder GetCommandLine), aber wozu, wenn ParamStr() soviel bequemer ist!?

    Den OpenDialog kannst du hier komplett weglassen.

    Beim FileSave solltest du als Alternative bei leerem Dateinamen einfach deine FileSaveAs-Funktion aufrufen, anstatt den Code doppelt zu schreiben.



  • Problem Nummer 1 ist vollständig gelöst! 🕶 Ich bedanke mich bei allen, die mir dabei geholfen haben 😉

    Nun brauch ich nur noch das:

    3. Bei Doppelklick auf Datei sofort mit WriteSpeed öffnen
    Aus der Broland-Hilfe werd ich zu ParamStr nicht schlau.

    Problem 2 werd ich demnächst mal euer Geschribsel anschauen!



  • @GordonWessel, such mal in der Hilfe nach FileExists. Bei der SaveAs Routine ist es in jeden Fall zu empfehlen. Eine Application->MessageBox sollte den User auf einen existierenden file hinweisen und ihn um eine Entscheidung bitten. (Dto. macht eine Meldung im OnCloseQuery sinn, wenn der file noch nicht gespeichert ist).

    Sorry, kleiner Schreibfehler (C++ läuft automatisch großgeschrieben aus der Hand 🙄 ), und ich kann den Beitrag nicht editieren. Bin angemeldet, aber das Login hat keinen Effekt. Wenn es einer der Mods editieren kann/mag, das wär super - aber ich will eigentlich niemandem Arbeit machen.

    Ohne Einrückungen schlecht lesbar, aber die Kommentare sagen, daß weder im FormShow noch in der OpenDialog-Routine die Datei geöffnet wird. An beiden Stellen laufen nur die Vorbereitungen. In Open(Sender) werden die Angaben für den SaveDialog gemacht, dann wird der file geöffnet.

    Der Vorteil, dadurch wird Code gespart und die Funktionen bleiben schön kompakt, was der Stabilität immer zugute kommt. Ganz nebenbei bietet dann die SaveAs Routine gleich das Verzeichnis an, in dem die Datei geöffnet wurde. Das klappt auch bei der MDI für mehrere Fenster.

    Kleiner Tip: Du kannst auch in der Save-Routine auf SaveAs verweisen, wenn der file nicht existiert. Also nur eine Tastenkombination für fast alle Save-Fälle. Wenn ich unter einem neuen Namen speichern will, steht ja trotzdem die Strg+U zur Verfügung.



  • Nachdem ich vorher schon recht aufwändigen Code um ParamStr() gesehen hatte... aber jetzt war ich doch neugierig :p . Kein Wunder, daß man keinen Code sieht. Das schreibt sich ja von allein und funzt UFB. - Also am besten den Codebeitrag weiter oben verbrennen. 🙄

    Aber warum nicht (mal einen Prototyp posten)? In der Anfangszeit steht man vielleicht ratlos vor Aufgabe und Syntax.

    // Im FormShow der Anwendung
        if (ParamCount() != 0)
        {
            OpenDialog->FileName = ParamStr(1);
            // Open-Routine ohne OpenDialog aufrufen
            Open(Sender);
        }
    


  • Ok!

    3. ist auch aus der Welt!

    Ich danke euch allen auch wieder für die Lösung!

    Ich hab den OpenDialog umgangen, indem ich das hier geschrieben hab:

    if (ParamCount() != 0)
        {
            OpenDialog->FileName = ParamStr(1);
            RichEdit1->Lines->LoadFromFile(OpenDialog->FileName);
        }
    


  • Warum den Umweg über OpenDialog??

    Geht doch auch kürzer:

    if (ParamCount() != 0)
    {
        RichEdit1->Lines->LoadFromFile(ParamStr(1);
    }
    


  • Für den Gelegenheitsfall ist einfach sicher das allerbeste. 'Ne User-Anwendung wie Editor, Viewer... wird aber von Handlingsvorteilen sehr profitieren. Mich nerven zB. die oft vielen unnötigen Handgriffe, die sich die App auch hätte merxen können. 'Ne Batterie files aus einem Verzeichnis laden, bearbeiten und speichern, und für jeden Vorgang muß man sich vom Desktop her durchhangeln - bei sowas denk ich mir mein Teil... und würde mich ärgern, wenn ich dafür auch noch Geld bezahlt hätte.



  • So. Jetzt hab ich mal angefangen, den Beitrag aus der FAQ zu meiner 2ten Frage zu verstehen(C/C++-Ecke » Unsere Archive » FAQ - C++ Builder (VCL/CLX) » Forms - Datei per Drag and Drop aus dem Explorer empfangen).

    Ich hab, glaub ich, alles richtig gemacht(wer glaubt das nicht von sich 😉 ).

    Nur dass ich die Datei aufs Form kriege, die aber nicht geladen wird. Ich denke, es liegt daran, dass ich sonst nirgends sehe: RichEdit1->Lines->LoadFromFile...

    Also muss ich die Variable, in der das dan drinsteht rausfinden, oder? 😕 😕 😕

    Danke schon im Voraus



  • Also das mit dem ParamStr() haut so nicht hin. Fragezeichen werden als Parametertrenner gewertet. Damit ist Quelltextöffnen sehr oft nicht möglich. Ich geh doch wieder reumütig auf GetCommandLine() zurück. So wild ist der Code nicht. Verglichen mit der sicher guten Lösung in der FAQ sogar geradezu schnukelig klein. :p

    <edit>Vielleicht den Codetag-Fehler korrigieren und den Code alternativ in die FAQ stellen? 🙄


Anmelden zum Antworten