Recent

Author Topic: TDbf component  (Read 4371 times)

criki

  • Newbie
  • Posts: 2
TDbf component
« on: January 18, 2017, 06:01:11 pm »
Hello,

I 'm trying to create a database throught the TDbf component BUT i got a 'Identifier not found' for the ftString that I use in a FieldDefs.Add( 'toto', ftString, 8, True) ???

Any idea

Thaddy

  • Hero Member
  • *****
  • Posts: 14213
  • Probably until I exterminate Putin.
Re: TDbf component
« Reply #1 on: January 18, 2017, 06:13:38 pm »
I recall you have to add the db unit to the uses clause by hand for that to work, ftString is defined in the db unit.
There is an old and unresolved bug report by me about that....( http://bugs.freepascal.org/view.php?id=29733>:D >:D Fix that guys...
So look at your code. If the db unit isn't in the uses, add it.
Plz report back if it works.
« Last Edit: January 18, 2017, 06:19:19 pm by Thaddy »
Specialize a type, not a var.

Handoko

  • Hero Member
  • *****
  • Posts: 5131
  • My goal: build my own game engine using Lazarus
Re: TDbf component
« Reply #2 on: January 18, 2017, 07:00:42 pm »
I used TDbf. I've just checked my project files, not sure they are required or not but in my project I put these units in the uses clause:

- dbf
- dbf_fields
- db

Thaddy

  • Hero Member
  • *****
  • Posts: 14213
  • Probably until I exterminate Putin.
Re: TDbf component
« Reply #3 on: January 18, 2017, 07:58:15 pm »
I used TDbf. I've just checked my project files, not sure they are required or not but in my project I put these units in the uses clause:

- dbf
- dbf_fields
- db

Yes, I did something like that. But it should be done automatically ;) Delphi does that  >:D

Hence people are at a loss when they do not use the fields editor at design time and add fields in code.
IMNSHO this is a BIG bug and an OLD bug. But once you add those by hand, it works.
« Last Edit: January 18, 2017, 08:00:29 pm by Thaddy »
Specialize a type, not a var.

criki

  • Newbie
  • Posts: 2
Re: TDbf component
« Reply #4 on: January 18, 2017, 09:12:37 pm »
Well thank's a lot guys .. in fact the db in uses seems mandatory ... but you are right it should be included automaticaly ...

But until know the database create ends with a unable to open on the dfb1.createtable ... I need to check more ..

Good night

wp

  • Hero Member
  • *****
  • Posts: 11858
Re: TDbf component
« Reply #5 on: January 18, 2017, 10:01:40 pm »
You must be careful with the paths. If you enter a relative path in the property "Filepath" in the ObjectInspector then the IDE expands it to be relative the Lazarus binary folder. Enter the full path in the property FilePathFull. And after you completed all design works delete the filepath properties again and set the path at runtime.

Handoko

  • Hero Member
  • *****
  • Posts: 5131
  • My goal: build my own game engine using Lazarus
Re: TDbf component
« Reply #6 on: January 19, 2017, 03:32:13 am »
@criki
Can you show us your code? Below is part of mine which works correcly on both Win32 and Linux.

Code: Pascal  [Select][+][-]
  1. {$mode objfpc}{$H+}
  2.  
  3. interface
  4.  
  5. uses
  6.   Classes, SysUtils, dbf, dbf_fields, db, FileUtil
  7.   // add yours here
  8.   ;
  9.  
  10. var
  11.   dbfMain: TDbf;
  12.  
  13. const
  14.   DbfFileName = 'MyNote.dbf';
  15.  
  16. procedure OpenDatabase;
  17. begin
  18.  
  19.   dbfMain := TDbf.Create(nil);
  20.   dbfMain.FilePathFull := ExtractFileDir(ParamStr(0));
  21.   dbfMain.TableName := DbfFileName;
  22.  
  23.   with dbfMain do begin
  24.  
  25.     // Create table and field if the table isn't existed
  26.     if (not(FileExists(FilePathFull+DirectorySeparator+TableName))) then begin
  27.       FieldDefs.Add('ID', ftInteger, 0, True);
  28.       CreateTable;
  29.     end;
  30.      
  31.     Open;
  32.     // Do something here
  33.  
  34.     Close;
  35.     Free;    
  36.  
  37.   end;
  38. end;
  39.  

Thaddy

  • Hero Member
  • *****
  • Posts: 14213
  • Probably until I exterminate Putin.
Re: TDbf component
« Reply #7 on: January 19, 2017, 01:41:19 pm »
@Handoko
Excellent example.
I have reduced it somewhat and can confirm your code works:
Code: Pascal  [Select][+][-]
  1. program dbftest;
  2. {$ifdef fpc}{$mode delphi}{$H+}{$endif}
  3. uses
  4.   Classes, SysUtils, dbf, db;  
  5. var
  6.   dbfMain: TDbf;
  7.  
  8. const
  9.   DbfFileName = 'MyNote.dbf';
  10.  
  11. procedure OpenDatabase;
  12. begin
  13.   dbfMain := TDbf.Create(nil);
  14.   with dbfMain do
  15.   try
  16.     FilePathFull := ExtractFileDir(ParamStr(0));
  17.     TableName := DbfFileName;
  18.     // Create table and field if the table isn't existed
  19.     if (not(FileExists(FilePathFull+DirectorySeparator+TableName))) then
  20.     begin
  21.       FieldDefs.Add('ID', ftInteger, 0, True);
  22.       CreateTable;
  23.     end;
  24.     Open;
  25.     // Do something here
  26.     Close;
  27.    finally
  28.     Free;    
  29.   end;
  30. end;
  31. begin
  32.   OpenDataBase;
  33. end.
Result is:
Code: [Select]
pi@raspberrypi:~ $ ls -l *.dbf
-rw-r--r-- 1 pi pi 66 Jan 19 13:36 MyNote.dbf
And that is a valid dbf.

Anyway, somebody should finally fix that db omission from the uses clause (when using Lazarus and creating TDataset and fields in code). It is hard to know and find for average users.
 
« Last Edit: January 19, 2017, 03:48:50 pm by Thaddy »
Specialize a type, not a var.

Michl

  • Full Member
  • ***
  • Posts: 226
Re: TDbf component
« Reply #8 on: March 05, 2017, 01:40:24 pm »
Anyway, somebody should finally fix that db omission from the uses clause (when using Lazarus and creating TDataset and fields in code). It is hard to know and find for average users.
I read your bug report. Just as hint. It works semi automatic with package Cody (this is that one, I never miss to install on a new Lazarus installation).

Try to compile your code without "db" in the uses clause:
-> a error is shown in the message window "project1.lpr(21,27) Error: Identifier not found "ftInteger" "
-> now right-click on it and click on "Show Cody Dictionary for "ftInteger" "
-> select the first entry
Thats it.

Cody is learning identifiers by programming. For me, it saves a lot of time!
Code: [Select]
type
  TLiveSelection = (lsMoney, lsChilds, lsTime);
  TLive = Array[0..1] of TLiveSelection;

 

TinyPortal © 2005-2018