Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations gkittelson on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Display text between brackets in an EditBox? 1

Status
Not open for further replies.

doctorjellybean

Programmer
May 5, 2003
145
The application should load the contents of a file into an invisible memo, and display the text between brackets in an EditBox so that a user can change it and save the file.

The file itself contains a number of lines, but the ones I'm interested in have the following format:

"integer displayinterval" [60]
"integer writeinterval" [600]
"string filename" ["E:/_DAZ Studio Content/_Renders/Three"]

and so on.

What is the best way to search and display, change the values and save the file?

Thanks in advance.

 
Assuming you don't want the brackets included in the edit:

Add two buttons to your form First that will put each line, one-by-one into your edit, the second to save the file.

Code:
unit bracketEdit;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, Buttons;

type
  TForm1 = class(TForm)
    Memo1: TMemo;
    Edit1: TEdit;
    BitBtn1: TBitBtn;
    BitBtn2: TBitBtn;
    procedure BitBtn1Click(Sender: TObject);
    procedure BitBtn2Click(Sender: TObject);
  private
    I:  integer;
    function GetSpecialFolderPath(folder:  integer):  string;
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

uses SHFolder;

{$R *.dfm}

procedure TForm1.BitBtn1Click(Sender: TObject);
var
   start_pos, length:  integer;
begin
   if I <= Memo1.Lines.Count - 1 then
   begin
      start_pos := pos('[', memo1.lines[I])+1;
      length := pos(']', memo1.lines[I]) - start_pos;
      Edit1.text := copy(memo1.lines[I], start_pos, length);
      //do your work here
      inc(I);
   end
   else
      MessageDlg('You Reached The End', mtInformation, [mbOK], 0);
end;

procedure TForm1.BitBtn2Click(Sender: TObject);
begin
   Memo1.Lines.SaveToFile(GetSpecialFolderPath(CSIDL_PERSONAL)+'\YourFileName.txt');
   MessageDlg('Your File was saved in '+
               GetSpecialFolderPath(CSIDL_PERSONAL)+'\YourFileName.txt',
               mtInformation, [mbok], 0);
end;

function TForm1.GetSpecialFolderPath(folder: integer): string;
const
   SHGFP_TYPE_CURRENT = 0;
var
   Path:  array[0..MAX_PATH]of char;
begin
   if SUCCEEDED(SHGetFolderPath(0,folder,0,SHGFP_TYPE_CURRENT,@path[0])) then
      Result := path
   else
      Result := '';
end;

end.
 
Forgot to add that in your formcreate method add:

Code:
procedure TForm1.FormCreate(Sender: TObject);
begin
   I := 0;
   ...
   ...
end;
 
Thanks!

However, I think I didn't explain myself very well. The original file that is being opened, has a number of entries:

"integer haltspp" [0]
"integer halttime" [0]
"integer displayinterval" [60]
"integer writeinterval" [600]
"bool write_png_gamutclamp" ["true"]
"string filename" ["E:/_DAZ Studio Content/_Renders/Three"]
"bool write_resume_flm" ["false"]

Now my application needs to search for e.g. integer displayinterval and display it's associated values in an EditBox. Same for the next search item. The values are changed and everything is then saved back into a file.
 
When you say it needs to search for a specific term, is this a choice the user makes? Please explain what mechanism are you using to know which term is relevant?
 
I'll pre-define in the application which terms are relevant. All I'm giving the user is a label with an editbox. The reason being that not all terms might be present in the original file, so I would like to do a search for a term, e.g. "integer halttime", and if present display it's values in the editbox. I hope that is clearer.
 
then all you need to do is add a check before extracting the value in brackets to see if it is a line you want to process
Code:
procedure TForm1.BitBtn1Click(Sender: TObject);
var
   start_pos, length:  integer;
begin
   if I <= Memo1.Lines.Count - 1 then
   begin
      if pos(<string your searching for>, memo1.lines[I]) <> 0 then //does the string exist in the current line
      begin //if so get the value
         start_pos := pos('[', memo1.lines[I])+1;
         length := pos(']', memo1.lines[I]) - start_pos;
         Edit1.text := copy(memo1.lines[I], start_pos, length);
      end;
      //do your work here
      //If there are changes to the value, then you'd need to write them back to the Memo
      inc(I); //increment counter
   end
   else
      MessageDlg('You Reached The End', mtInformation, [mbOK], 0);
end;
Make sure the search terms you're searching for can only match the relevant lines you are looking for. If you search for: 'integer' it will hit the first 4 lines of your example.
 
Thank you again.

The code seems to work (that is the app runs without any errors), but nothing appears in the editbox. I've uploaded the project and a sample file which contains the data the application looks for. This is a very simple project, just to test the search and display. As the application will be searching for quite a few strings and displaying the associated values in the corresponding editboxes, I assume that the search and display code will have to be put in a loop?

Thanks again for your help.
 
 http://www.it-utilities.co.uk/downloads/Lux.zip
Just opened the project, a few things:

1) you added opening the data file to the same action created to cycle through what's in the data file. That means the button used to fire going to each matching record will also execute this each time:

Code:
if opendialog1.Execute=false then exit;
memo1.Lines.LoadFromFile(opendialog1.FileName);

This needs to fired just once, not each time the button is clicked. Maybe with another button, or as something that happens when the application starts.

Also, the initial iteration of this, I thought you wanted the value of each line, one-by-one. So I didn't put the operation inside a loop. Since you are looking for a specific string, and need to cycle through the entire contents of the file, you need to enclose your code inside a loop. I've added a "repeat..until" loop. I assume there is just one instance of each search term in the file. If there's more than one, you'll need to test to see if what's here will work.

I also noticed this
Camera "perspective" "float fov" [30.137] "float screenwindow" [-1.7789699570815452 1.7789699570815452 -1 1]
in the file. There are two occurrences of [] in this line. If you need both to be parsed, then you'll need to change the code, since this code will only bring back the first occurrence. Do a lookup on the function posex rather than pos.

Code:
procedure TForm1.FormCreate(Sender: TObject);
begin
I := 0;
if opendialog1.Execute=false then exit;
memo1.Lines.LoadFromFile(opendialog1.FileName);
end;

procedure TForm1.Button1Click(Sender: TObject);
var start_pos, length:  integer;
    match:  Boolean;
begin
  Match := False;
  repeat
  if I <= Memo1.Lines.Count - 1 then
     begin
     if pos('integer haltspp', memo1.lines[I]) <> 0 then //does the string exist in the current line
        begin //if so get the value
           start_pos := pos('[', memo1.lines[I])+1;
           length := pos(']', memo1.lines[I]) - start_pos;
           Edit1.text := copy(memo1.lines[I], start_pos, length);
           match := True;
        end;
        //do your work here
        //If there are changes to the value, then you'd need to write them back to the Memo
        inc(I); //increment counter
     end
  until ((Match) or (I > Memo1.Lines.Count-1));
end;
 
Thank you, that works now. Now I just have to figure out the loop and to write it back to the memo.
 
You'll want to attach that action to another button, or something else...
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top