1. The generic type is constrained, but cannot be used for class references?
type
TBase = class
procedure NothingAbstractHere;
constructor Create; virtual;
end;
TGenericWrapper = class
type
TBaseClass = class of TB; <– [dcc32 Error]: E2021 Class type required
end;
Is there any logical reason for why this should not be possible?
2. Constructing an instance from a generic type does not flag construction of a class with unimplemented virtual abstract methods. This one I can understand, but it still is annoying. I guess I could factory functions to work around it.
It’s not always easy to pick a good color that will show well on displays with limited color depths.
If anyone knows if this exists – or have some time on their hands, it would be good to have a simple application that could render the System.UITypes TColors constants for lines/text/brushes on different color depths (8 bit, 16-bit, 32-bit). Showing the name of the color (or atleast the hex value) would be good and being able to copy it to the clipboard as a string would be great.
“We’ve got 3 jam-packed days of engaging content—for developers like you. Please note that Day 3 is by invitation only to Update subscribers. We’re offering a wide variety of topics that center around Embarcadero products, related technologies, Object Pascal, and C++.”
The code below shows something that is a bit of a mystery to me.
 TQuerySetToGrid = class(TQuerySet); // simplified
 TQuerySetXML = class(TQuerySetToGrid)
 public
  Id: TQuerySet.TFieldInteger;
  TimeStamp: TQuerySet.TFieldDateTime;
  PID: TQuerySet.TFieldInteger;
  TID: TQuerySet.TFieldInteger;
  Level: TQuerySet.TFieldEnum;
  Category: TQuerySet.TFieldEnum;
  App: TQuerySet.TFieldString;
  Client: TQuerySet.TFieldString;
  Title: TQuerySet.TFieldString;
  constructor Create; override;
 end;
Apart from “it works that way” – is there a reasonable explanation of why I have to qualify the TFieldxxxx types which all are public types declared inside TQuerySet, when referring the types inside a descendant class? I wonder!
/off-topic
FYI, this is actual code and part of a log viewer in our monitoring and maintenance tool, and to give you an idea of what I am trying to achieve…
This is the scaffolding code needed for link a grid and a query to display the results from a TDataSet.
Initialize and set up the look of the grid:
 XMLQueryLog := TQuerySetXML.Create;
 XMLQueryLog.Grid := sgLog;
sgLog is a TAdvStringGrid dropped on a frame, and there is some grid specific code to get the desired look, and ofcourse code to handle grid operations – but for the content, this is the only scaffolding needed.
Execute the query and fill the grid:
 XMLQueryLog.Refresh(SQLStatement);
The “real” scaffolding happens in that Create you saw in the initial class.
constructor TQuerySetXML.Create;
begin
 inherited;
 Id := Add(‘Id’, 64);
 TimeStamp := Add(‘TimeStamp’, ‘Dato og tid’, 120);
 PID := Add(‘ProcessId’, ‘PID’, 64);
 TID := Add(‘ThreadId’, ‘TID’, 64);
 Level := Add<TFieldEnum>(‘XLevel’, ‘NivÃ¥’, 70);
 Level.Formatter :=
  function (const Lvl: TLogEventLevel):String
  begin
   Result := LogEventLevelToString(Lvl);
  end;
 Category := Add<TFieldEnum>(‘XCategory’, ‘Kategori’, 70);
 Category.Formatter :=
  function (const Cat: TLogEventCategory):String
  begin
   Result := LogEventCategoryToString(Cat);
  end;
 App := Add(‘AppShortName’, ‘App’, 30);
 Client := Add(‘ClientName’, ‘Client’, 140);
 Client.HAlighment := taRightJustify;
 Title := Add(‘Title’, ‘Beskrivelse’, 800);
end;
which is a lot less code than I needed before.
Basically, I Add(‘sqlcolumn’, ‘Grid Col Title’, width in px);
If I don’t add any field specifications to the QuerySet, they will be generated based on the query results and the name/TFieldType of each column.
The old code also read individual log objects from the database and then moved them to the grid – while this uses SQL -> Grid – so it is quite a bit faster.
I could also use owner draw and a virtual grid to avoid duplicating the query results as strings in the grid – but that would rob me of some of the nice features of TAdvStringGrid.
Right now, there are only two conversions for each cell – first DB result to native, and then native to string – and there are no case statements 😉
Still work in progress, but I am reasonably happy so far – except from that internal type scope thing?
What is your favorite way of doing a dropdown with multiple checkboxes (3-15 items)? Must be able to check/uncheck multiple items without closing/reopening. Â Custom text when closed up would be nice too. Off-the shelf component suggestions also welcome.
Confession: My name is Lars Fosdal, and I am a writer of frameworks.
It’s just so hard not to do it!. I really dislike cut & paste code or having to rewrite the same code with just different types! Â Generics are really addictive, and I fear I have become a user.Â
You must be logged in to post a comment.