Recent

Author Topic: TStringGrid sort indicator  (Read 7344 times)

dbannon

  • Hero Member
  • *****
  • Posts: 2786
    • tomboy-ng, a rewrite of the classic Tomboy
TStringGrid sort indicator
« on: January 31, 2020, 03:09:19 am »
TStringGrid can have its top row set as a heading and if the user clicks one of its (button like) cells the grid is sorted according to that column. We get nice little green triangles indicating its sorted on that column.

You can also sort programmatically, eg StringGrid1.SortColRow(True, 1);   But that does not set the green triangles or even cancel green triangles that may be there from previous user interaction.

Is there some way we can, programmatically, turn the green triangles off or ideally, move them to the now relevant column ?

David
Lazarus 3, Linux (and reluctantly Win10/11, OSX Monterey)
My Project - https://github.com/tomboy-notes/tomboy-ng and my github - https://github.com/davidbannon

GAN

  • Sr. Member
  • ****
  • Posts: 370
Re: TStringGrid sort indicator
« Reply #1 on: January 31, 2020, 03:50:39 am »
Yes, to delete the arrow:

Code: Pascal  [Select][+][-]
  1. StringGrid1.Columns[0].Title.ImageIndex:=-1;

then you can use a TImageList in  the property TitleImageList.
Lazarus 2.0.8 FPC 3.0.4 Linux Mint Mate 19.3
Zeos 7̶.̶2̶.̶6̶ 7.1.3a-stable - Sqlite 3.32.3 - LazReport

dbannon

  • Hero Member
  • *****
  • Posts: 2786
    • tomboy-ng, a rewrite of the classic Tomboy
Re: TStringGrid sort indicator
« Reply #2 on: January 31, 2020, 06:02:38 am »

Thanks GAN but I don't seem to be able to access the columns property. My (test) grid has two visible columns containing data but there are zero columns and an attempt to call what you suggested gives an error.  My code eg -

Code: Pascal  [Select][+][-]
  1.     Grid.Clear;
  2.     Grid.FixedRows := 0;
  3.     Grid.FixedCols := 0;
  4.     Grid.InsertRowWithValues(0, ['Title', 'Last Change']);
  5.     Grid.FixedRows := 1;
  6.     Grid.InsertRowWithValues(Grid.RowCount, ['A Item', 'Z Item']);
  7.     Grid.InsertRowWithValues(Grid.RowCount, ['B Item', 'X Item']);
  8.     DebugLn('Column count is ' + inttostr(Grid.Columns.Count));
  9.     // Above line prints 'Column count is 0'    
     

I don't understand how Grid.Columns.Count is zero but I can see two columns ....

Davo
             
Lazarus 3, Linux (and reluctantly Win10/11, OSX Monterey)
My Project - https://github.com/tomboy-notes/tomboy-ng and my github - https://github.com/davidbannon

HeavyUser

  • Sr. Member
  • ****
  • Posts: 397
Re: TStringGrid sort indicator
« Reply #3 on: January 31, 2020, 06:16:42 am »
there are two different mechanisms that support columns
1) the colCount property and friends for delphi/backward compatibility
2) columns property and friends a newer never cought up construct.

Probably they should be seperated to two controls to avoid confusion or at least sync them in to a single mechanism.

dbannon

  • Hero Member
  • *****
  • Posts: 2786
    • tomboy-ng, a rewrite of the classic Tomboy
Re: TStringGrid sort indicator
« Reply #4 on: January 31, 2020, 07:44:09 am »
Thanks HeavyUser, thats explains a lot for me.  What I was finding was seriously confusing.

I think this is the Lazarus style -
Code: Pascal  [Select][+][-]
  1.     Grid.Clear;
  2.     Grid.FixedCols := 0;
  3.     Grid.Columns.Add;
  4.     Grid.Columns[0].Title.Caption := 'Name';
  5.     Grid.Columns.Add;
  6.     Grid.Columns[1].Title.Caption := 'Last Change';
  7.     Grid.FixedRows:=1;
  8.     Grid.InsertRowWithValues(Grid.RowCount, ['A Item', 'Z Item']);
  9.     Grid.InsertRowWithValues(Grid.RowCount, ['B Item', 'X Item']);
           

And I can get the result on screen that I expect.  And calling StringGrid1.Columns[0].Title.ImageIndex:=-1; as suggested by GAN does not crash it like the way I was doing it did. 

However, GAN's call does not make any difference to the little green triangle, it won't turn it off.  Nor will setting the value to 0 (as suggested by the help files) turn it off.  Setting a positive value such as 1 won't turn it on either.

Hmm....

Davo

 
Lazarus 3, Linux (and reluctantly Win10/11, OSX Monterey)
My Project - https://github.com/tomboy-notes/tomboy-ng and my github - https://github.com/davidbannon

GAN

  • Sr. Member
  • ****
  • Posts: 370
Re: TStringGrid sort indicator
« Reply #5 on: January 31, 2020, 08:48:25 pm »
Code: Pascal  [Select][+][-]
  1. procedure TForm1.StringGrid1HeaderClick(Sender: TObject; IsColumn: Boolean; Index: Integer);
  2. begin
  3.   StringGrid1.Columns[Index].Title.ImageIndex:=-1;
  4. end;    

Works fine for me. Green triangles are never displayed.
Lazarus 2.0.8 FPC 3.0.4 Linux Mint Mate 19.3
Zeos 7̶.̶2̶.̶6̶ 7.1.3a-stable - Sqlite 3.32.3 - LazReport

GAN

  • Sr. Member
  • ****
  • Posts: 370
Re: TStringGrid sort indicator
« Reply #6 on: January 31, 2020, 11:54:25 pm »
Hi Dbannon sees the attachment, it can be helpful.
Lazarus 2.0.8 FPC 3.0.4 Linux Mint Mate 19.3
Zeos 7̶.̶2̶.̶6̶ 7.1.3a-stable - Sqlite 3.32.3 - LazReport

dbannon

  • Hero Member
  • *****
  • Posts: 2786
    • tomboy-ng, a rewrite of the classic Tomboy
Re: TStringGrid sort indicator
« Reply #7 on: February 01, 2020, 12:46:34 am »
Thanks for that Gan, but I see both green and black triangles. your code only controls the black one, the green triangle changes because the click is to the header, not because of the code.

If you move the code out of the StringGrid1HeaderClick() into, say, a Button1Click(), it only controls the black triangle you have added via the image list, it has no effect on the green triangle that is "Built In" to TStringGrid. See -

Code: Pascal  [Select][+][-]
  1. procedure TForm1.StringGrid1HeaderClick(Sender: TObject; IsColumn: Boolean; Index: Integer);
  2. begin
  3.  // StringGrid1.Columns[Index].Title.ImageIndex:=-1;
  4. {  if StringGrid1.SortOrder=soAscending then
  5.     StringGrid1.Columns[Index].Title.ImageIndex:=0
  6.   else
  7.     StringGrid1.Columns[Index].Title.ImageIndex:=1; }
  8. end;
  9.  
  10. procedure TForm1.Button1Click(Sender: TObject);
  11. begin
  12.    if (StringGrid1.Columns[0].Title.ImageIndex = 0) then
  13.         StringGrid1.Columns[0].Title.ImageIndex:=1
  14.    else
  15.         StringGrid1.Columns[0].Title.ImageIndex:=0;
  16. end;  
                 

With that code, clicking the button, we can toggle the black triangle up and down but the green one is not affected.  In this image I have clicked the header (to sort the column and display the green triangle) and then clicked the button multiple times. Each click inverts the black triangle but not the green.

I am on Linux (U18.04 Mate) running a GTK2 app. Are you using Qt5 perhaps or Win/Mac ? 

Davo
                             
Lazarus 3, Linux (and reluctantly Win10/11, OSX Monterey)
My Project - https://github.com/tomboy-notes/tomboy-ng and my github - https://github.com/davidbannon

GAN

  • Sr. Member
  • ****
  • Posts: 370
Re: TStringGrid sort indicator
« Reply #8 on: February 01, 2020, 01:00:43 am »
I use Linux Mint 17.2 MATE Gtk-2

Please watch the attached video.
Lazarus 2.0.8 FPC 3.0.4 Linux Mint Mate 19.3
Zeos 7̶.̶2̶.̶6̶ 7.1.3a-stable - Sqlite 3.32.3 - LazReport

GAN

  • Sr. Member
  • ****
  • Posts: 370
Re: TStringGrid sort indicator
« Reply #9 on: February 01, 2020, 01:37:00 am »
And works fine adding a button too.

Code: Pascal  [Select][+][-]
  1. unit Unit1;
  2.  
  3. {$mode objfpc}{$H+}
  4.  
  5. interface
  6.  
  7. uses
  8.   Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, Grids,
  9.   Buttons, StdCtrls;
  10.  
  11. type
  12.  
  13.   { TForm1 }
  14.  
  15.   TForm1 = class(TForm)
  16.     Button1: TButton;
  17.     ImageList1: TImageList;
  18.     StringGrid1: TStringGrid;
  19.     procedure Button1Click(Sender: TObject);
  20.     procedure StringGrid1HeaderClick(Sender: TObject; IsColumn: Boolean;
  21.       Index: Integer);
  22.   private
  23.     procedure CleanHeaders(selCol:Integer);
  24.   public
  25.  
  26.   end;
  27.  
  28. var
  29.   Form1: TForm1;
  30.  
  31. implementation
  32.  
  33. {$R *.lfm}
  34.  
  35. { TForm1 }
  36.  
  37. procedure TForm1.StringGrid1HeaderClick(Sender: TObject; IsColumn: Boolean; Index: Integer);
  38. begin
  39.  // StringGrid1.Columns[Index].Title.ImageIndex:=-1;
  40.   if StringGrid1.SortOrder=soAscending then
  41.     StringGrid1.Columns[Index].Title.ImageIndex:=0
  42.   else
  43.     StringGrid1.Columns[Index].Title.ImageIndex:=1;
  44. end;
  45.  
  46. procedure TForm1.CleanHeaders(selCol: Integer);
  47. var
  48.   i:Integer;
  49. begin
  50.   for i:=0 to StringGrid1.ColCount-1 do
  51.     if i<>selCol then
  52.       StringGrid1.Columns[i].Title.ImageIndex:=-1;
  53. end;
  54.  
  55. procedure TForm1.Button1Click(Sender: TObject);
  56. begin
  57.   if StringGrid1.SortOrder=soAscending then
  58.     begin
  59.       StringGrid1.SortOrder:=soDescending;
  60.       StringGrid1.SortColRow(True,StringGrid1.SelectedColumn.Index);
  61.       StringGrid1.Columns[StringGrid1.SelectedColumn.Index].Title.ImageIndex:=1
  62.     end
  63.   else
  64.     begin
  65.       StringGrid1.SortOrder:=soAscending;
  66.       StringGrid1.SortColRow(True,StringGrid1.SelectedColumn.Index);
  67.       StringGrid1.Columns[StringGrid1.SelectedColumn.Index].Title.ImageIndex:=0;
  68.     end;
  69.     CleanHeaders(StringGrid1.SelectedColumn.Index);
  70. end;
  71.  
  72. end.  
Lazarus 2.0.8 FPC 3.0.4 Linux Mint Mate 19.3
Zeos 7̶.̶2̶.̶6̶ 7.1.3a-stable - Sqlite 3.32.3 - LazReport

dbannon

  • Hero Member
  • *****
  • Posts: 2786
    • tomboy-ng, a rewrite of the classic Tomboy
Re: TStringGrid sort indicator
« Reply #10 on: February 02, 2020, 12:41:58 am »
Stranger and stranger.
Firstly, I cannot view your Video GAN, can see something in there but nothing I can identify.

I note your tag mentions that you are using Lazarus 1.8.4, I guess thats not accurate but what version of Lazarus are you using ??

I am using fixes_2_0, the oldest one I have installed is 2.0.4 so I might try that. 

Perhaps the issue for me is that the default small green triangle is not being hidden when I  install your black indicators from the imagelist. What do you see if you don't use the imagelist ?  Do you then see the default green triagles show in my attached picture above ? And if you can see the green triangles, can you turn them on and off in the same manner that you can control your own black ones ?

I'll fire up my 2.0.4 and see how that behaves.

Davo
Lazarus 3, Linux (and reluctantly Win10/11, OSX Monterey)
My Project - https://github.com/tomboy-notes/tomboy-ng and my github - https://github.com/davidbannon

dbannon

  • Hero Member
  • *****
  • Posts: 2786
    • tomboy-ng, a rewrite of the classic Tomboy
Re: TStringGrid sort indicator
« Reply #11 on: February 02, 2020, 01:27:13 am »
OK, I found a copy of Lazarus 2.0.0 and that behaves, for me, just like Lazarus 2.0.7.

GAN, just to be clear, can you please try the attached version of your demo.  In my case, with Lazarus 2.0.0 to 2.0.7 it treats the default green triangle as a completely different thing from the black triangle you add with the image list.

If you click the grid header the green one shows. Click the toggle button and the black one shows and the green one remains visible.  I can see both the green AND the black triangle. Continued clicking of the toggle button makes the black triangle point up or down, it does not do anything to the green triangle.

Click the Black Off button, the black triangle hidss, the green one remains visible. 

The only way to interact with the green triangle is by clicking the grid heading.

GAN, it sounds like your experiences here are different to mine, why ?

Davo

Lazarus 3, Linux (and reluctantly Win10/11, OSX Monterey)
My Project - https://github.com/tomboy-notes/tomboy-ng and my github - https://github.com/davidbannon

GAN

  • Sr. Member
  • ****
  • Posts: 370
Re: TStringGrid sort indicator
« Reply #12 on: February 02, 2020, 05:44:15 am »
Stranger and stranger.
Firstly, I cannot view your Video GAN, can see something in there but nothing I can identify.

I note your tag mentions that you are using Lazarus 1.8.4, I guess thats not accurate but what version of Lazarus are you using ??
Lazarus 1.8.4 - Free Pascal 3.0.4
Quote
I am using fixes_2_0, the oldest one I have installed is 2.0.4 so I might try that.
Maybe.

Quote
Perhaps the issue for me is that the default small green triangle is not being hidden when I  install your black indicators from the imagelist. What do you see if you don't use the imagelist ?
I don't see any triangles.

Quote
Perhaps the issue for me is that the default small green triangle is not being hidden when I  install your black indicators from the imagelist. What do you see if you don't use the imagelist ?  Do you then see the default green triagles show in my attached picture above ? And if you can see the green triangles, can you turn them on and off in the same manner that you can control your own black ones ?
Yes, I see your attached image, but in my evidence, I never saw both triangles in the same column. And yes, I can turn them off.

I'll fire up my 2.0.4 and see how that behaves.

Davo
[/quote]
Lazarus 2.0.8 FPC 3.0.4 Linux Mint Mate 19.3
Zeos 7̶.̶2̶.̶6̶ 7.1.3a-stable - Sqlite 3.32.3 - LazReport

GAN

  • Sr. Member
  • ****
  • Posts: 370
Re: TStringGrid sort indicator
« Reply #13 on: February 02, 2020, 06:01:53 am »
OK, I found a copy of Lazarus 2.0.0 and that behaves, for me, just like Lazarus 2.0.7.

GAN, just to be clear, can you please try the attached version of your demo.  In my case, with Lazarus 2.0.0 to 2.0.7 it treats the default green triangle as a completely different thing from the black triangle you add with the image list.

If you click the grid header the green one shows. Click the toggle button and the black one shows and the green one remains visible.
Quote
I'm running the project you've attached and.. . no, green is not visible.

Quote
I can see both the green AND the black triangle. Continued clicking of the toggle button makes the black triangle point up or down, it does not do anything to the green triangle.
Clicking Black Off all triangles disapear, in case there are one black on one column and one green in the other, both of them disapear.

Quote
Click the Black Off button, the black triangle hidss, the green one remains visible. 

The only way to interact with the green triangle is by clicking the grid heading.

GAN, it sounds like your experiences here are different to mine, why ?

Davo

Here: https://drive.google.com/open?id=1QD9ncbeQsk0RJeTJRMN0_vnH4kz1ziUp you have the video and the project working OK.
Please compile this project and tells me what happend?

GAN.
Lazarus 2.0.8 FPC 3.0.4 Linux Mint Mate 19.3
Zeos 7̶.̶2̶.̶6̶ 7.1.3a-stable - Sqlite 3.32.3 - LazReport

dbannon

  • Hero Member
  • *****
  • Posts: 2786
    • tomboy-ng, a rewrite of the classic Tomboy
Re: TStringGrid sort indicator
« Reply #14 on: February 02, 2020, 12:41:42 pm »
Lazarus 1.8.4 - Free Pascal 3.0.4
......
Clicking Black Off all triangles disapear, in case there are one black on one column and one green in the other, both of them disapear.
OK, that seems to be the key difference then.  In my case, that Black Off button turns only the Black one off. So, wonder if its the version of Lazarus ?  I have tested both 2.0.0 and 2.0.7 and in both of them the "Black Off" button only turns off the black triangle (the triangle from the imagelist).

Just to be clear, what I want to do is move the triangle (either green or black but not both!) from one column to the other. And turn it on for a grid that the user has not yet clicked the heading in.

Its seems those green triangles have been there for some time, Juha and WP mention them here https://forum.lazarus.freepascal.org/index.php/topic,36664.msg244630.html#msg244630
WP mentions "icons cannot be changed" but Juha says they can but he cannot remember. I assume he is refering to your trick.

I followed your link to google drive but the video there has same problem, I assume I don't have the right codec installed, It downloads and plays but is unintelligible.  I downloaded and compiled (2.0.7) the project there. It shows me the green triangles when I click the grid headers and the black ones if I click button1.    Button1 reverses the sort direction but does not alter the column being sorted (and its not intended to).

With another couple of buttons and a bit of code I can turn off the black triangles easily, but I cannot turn off the green ones, I cannot for example, turn off the green one in column 0 and turn it on in column 1. Once the user has clicked a column header, the green triangle appears (even if the black one is already there) and it cannot be removed.

Maybe I need to go back to 1.8.4 and see if that works for me as expected ?  "Something" has gone wrong since then !

GAN, I really appreciate the effort you are putting in here, thanks !

Davo





Davo
Lazarus 3, Linux (and reluctantly Win10/11, OSX Monterey)
My Project - https://github.com/tomboy-notes/tomboy-ng and my github - https://github.com/davidbannon

 

TinyPortal © 2005-2018