I have been using the D5 vanilla StringGrid for displaying data.
The data I am reading is from non database data files - I am reading
it in
myself using TFileStream.
From now on I want to be inputting and editing data in grids, but the
standard StringGrid does not have many embedded cell editors - the
one it
supplies seems pretty simple - it does not do even the things the
standard
editbox one does (move through a string one word at a time etc with
Ctrl/W
etc).
Can anyone who has an opinion on the options below kindly give a
recommendation!
(see below for a tiny reward)
As I see it my options are:
Option 1 - Add a few extra features to the standard stringgrid and
use that
for my stuff.
____________________________________________________________________________
______________
I would need:
-a enter cell event (to store the current contents of the cell to
check
for changes)
-a exit cell event (so I can call code to verify any cell changes)
-someway to know the position on the screen of the current cell
in case
I want to pop up a lookup window
If I could do all of these I would have all I need. Best way to get
these?
I could use the onDrawCell event?
Option 2 - DBGrid
_________________
I note the DBGrid seems to have a lot more data verification and cell
events
onColEnter and onColExit (are these meant to be called onCellEnter and
onCellExit?) The help says these are when a cell is entered and
exited. If
it is a colenter and not a cell enter, what happens if the user
arrows from
one cell to the one below it - does it fire?
I notice there is a LoadFromFile and a SavetoFile which looks like I
could
use to get the data into the grid.
To use the TDBGrid I could use these methods or a TClientDataSet.
Option 3 - use a third party grid control.
__________________________________________
So far I haven't needed to do this, but have been wondering about
some of
the 3rd party components like XStringGrid and AliGrid. I like having
everything vanilla and not having upgrade issues, but also don't wish to
reinvent the wheel all the time!
Option 4 - TClientDataSet and upgrade
_____________________________________
Now TClientDataSet is not in D5, and some friends (namely Gary B)
have been
long telling me this is the simplest way to display, edit and manipulate
data (using DBGrid), so it might be time to upgrade, hence look at D7 or
D2005. I think the stuff I have done so far is unlikely to break
D2005, so
happy to look at either. Best sources of an upgrade?
Reward
______
For reading this far here is a tiny reward: a little bit of code I
wrote to
sort a standard stringgrid. Very fast. Note it only does (case
insensitive)
alpha compares, but could easily be modified to do other orderings.
As I
already put in numbers right justified into grids it also works for
numbers
for me.
It makes a tag stringlist which is sorted in one step, then copies the
original data into a temporary array and then puts it back in the new
order
to the original stringgrid. While a bit more work, it is a lot
faster than
using a two record at a time exchange or a bubblesort. It also allows
sorting by two columns.
If there is anything I have done you would like to improve kindly
tell me!
procedure xcSortGrid(var
PGrid:TStringGrid;SortColumn1:Integer;SortColumn2:integer;AscDesc:char;CaseI
nSensitive:Boolean);
var
UnsortedList:TStringList;
olddefrow,newdefrow:integer; //keep same data row as default
oldrow,datalhs,ptr,colptr,rowptr:integer;
tempstr:string;
lAscDesc:char;
tempcells:array of array of string;
begin
if PGrid.rowcount < 2 then exit; //nothing to sort
UnsortedList:=TStringList.Create;
UnsortedList.sorted:=false;
olddefrow:=-1;
NewDefRow:=-1;
if PGrid.row>0 then oldDefRow:=PGrid.row;
for ptr:=0 to PGrid.rowcount-1 do
begin
//put sort col plus orig pointer into stringlist
tempstr:=PGrid.cells[SortColumn1,ptr]+PGrid.cells[SortColumn2,ptr];
if CaseInsensitive=true then uppercase(tempstr);
xcstrpad(tempstr,60); //make the string 60 chars long
tempstr:=tempstr+inttostr(ptr);
UnSortedList.Add(tempstr);
end;
//sort it
UnSortedList.sorted:=true;
//now copy original cells to tempcells dynamic array
setlength(tempcells,PGrid.colcount,PGrid.rowcount);
for rowptr:=0 to PGrid.rowcount-1 do
begin
for colptr:=0 to PGrid.colcount-1 do
begin
tempcells[colptr,rowptr]:=PGrid.cells[colptr,rowptr];
end;
end;
//now write back to grid
lAscDesc:=upcase(AscDesc);
if lAscDesc='A' then
begin
for ptr:=0 to PGrid.rowCount-1 do
begin
tempstr:=copy(UnSortedList[ptr],61,10);
oldrow:=strtoint(tempstr);
if oldrow=oldDefRow then NewDefRow:=ptr;
//oldptr is orig row number, ptr is new row number
for colptr:=0 to PGrid.colcount-1 do
begin
PGrid.cells[colptr,ptr]:=tempcells[colptr,oldrow];
end;
end;
end
else
begin
for ptr:=PGrid.rowcount-1 downto 0 do
begin
tempstr:=copy(UnSortedList[ptr],61,10);
oldrow:=strtoint(tempstr);
if oldrow=oldDefRow then NewDefRow:=ptr;
//oldptr is orig row number, ptr is new row number
for colptr:=0 to PGrid.colcount-1 do
begin
PGrid.cells[colptr,ptr]:=tempcells[colptr,oldrow];
end;
end;
end;
UnsortedList.free;
tempcells:=nil;
if (OldDefRow>0) and (NewDefRow >=0) then PGrid.row:=NewDefRow;
//note this means if the current row was 0 (the top) the new
default row
after sorting is still the top, //which is generally the best sense.
end;
John B
_______________________________________________
Delphi mailing list
[email protected]
http://ns3.123.co.nz/mailman/listinfo/delphi