-
Content Count
627 -
Joined
-
Last visited
-
Days Won
11
Everything posted by corneliusdavid
-
Delphi 12.2 available for download
corneliusdavid replied to pyscripter's topic in Delphi IDE and APIs
The feature matrix has been updated. -
Delphi 12.2 available for download
corneliusdavid replied to pyscripter's topic in Delphi IDE and APIs
Watch the webinar to find out what's new: https://blogs.embarcadero.com/save-your-seat-whats-coming-in-rad-studio-athens-12-2/ -
What are you using AI code-gen tools for that's working well?
corneliusdavid replied to David Schwartz's topic in General Help
You don't need AI for that, you just need GExperts! -
I've got a Delphi 12.1 VCL application where, by default, there is no style applied. If the user wants, they can switch to a dark mode at which point, I load a pre-selected .vsf file and all is good. If the user wants to switch back, I simply set the style to 'Windows' and it switches back to the default style. It all still works. Because there will be several programs with this same functionality and option, I don't store the style file in the application but load it dynamically at runtime. And if, down the road, I want to replace the style file with a different one, I can because it's named simply "DarkMode.vsf" even though the internal style name could be "CopperDark" or "Windows10 BlackPearl" for example. With the overloaded TStyleManager.SetStyle procedure that can take either a string (the style name) or a TStyleServicesHandle (returned from LoadFromFile), I figured I could use either one interchangeably; therefore, it's simplest in my code to refer to the loaded file by its handle and not it's name but when changing back to the default style, I simply use the standard 'Windows' string name, leading to these procedures: procedure TMainForm.LoadThemeFiles; begin // save handle to dark style for later FDarkStyleServicesHandle := TStyleManager.LoadFromFile(TPath.Combine(ThemePath, 'DarkMode.vsf')); end; procedure TsMainForm.SetDarkTheme; begin TStyleManager.SetStyle(FDarkStyleServicesHandle); end; procedure TcssMainForm.ClearTheme; begin TStyleManager.SetStyle('Windows'); end; However, I found that once SetDarkTheme has been called followed by ClearTheme, SetDarkTheme will no longer work (as in the case the user switches DarkMode off then tries to turn it back on). I've attached a small program to demonstrate this; I've tried it in both Delphi 11.3 and 12.1. I've submitted a bug report but also have a work-around. Since SetStyle(string-name) works consistently, I've changed the LoadThemeFiles procedure to get and save the name of the style. The TStyleManager has a list of all registered style names, including 'Windows' so if I load one style, TStyleManager should have two style names: procedure TsMainForm.LoadThemeFiles; var StyNames: TArray<string>; begin TStyleManager.LoadFromFile(TPath.Combine(ThemePath, 'DarkMode.vsf')); StyNames := TStyleManager.StyleNames; // reminder not to load any styles into the project if Length(StyNames) > 2 then raise EProgrammerNotFound.Create('Styles should not be defined in the project!'); for var sn in StyNames do begin if not SameText(sn, 'Windows') then begin // save the dark-mode style name FDarkStyleName := sn; Break; end; end; end; After that, the change to SetDarkMode procedure is pretty obvious: procedure TcssMainForm.SetDarkTheme; begin TStyleManager.SetStyle(FDarkStyleName); end; I looked at the VCL source for the two SetStyle procedures and the string version simply looks through the list of registered style names and calls the TStyleServicesHandle version. So why does the first method fail? VclStyleToggle.zip
-
What are you using AI code-gen tools for that's working well?
corneliusdavid replied to David Schwartz's topic in General Help
Last December, I blogged about how ChatGPT helped me write a DLL to call a SOAP web service where the header packet was already created (I had always used the wizard-created class and had a brain block). More recently, I've been using Claude to jump-start projects. For example, I needed to write a small WebBroker app but hadn't done that in a while and just needed a quick reminder of the structure. I was about to look up an old project when I decided to ask Claude and it built a simple example. AI isn't doing my work for me but it's increasing my productivity by either reminding me of techniques or helping me get something going quicker. It's sort of like a writer who sits down to type the next novel but just needs a shove of inspiration to get it started. -
Custom Managed Records and Default(T)
corneliusdavid replied to rgdawson's topic in Algorithms, Data Structures and Class Design
I suppose this is legal but if you need to create/free a TStringList, why not use a class instead of a record? I always thought of records as a collection of simple types--it never even dawned on me to add a field that required it to be created at runtime. -
"Death to WITH" in your Delphi Code
corneliusdavid replied to Darian Miller's topic in Tips / Blogs / Tutorials / Videos
This is good in that it eliminates scope confusion and is actually 2 lines shorter than using the nested with because there's no need for "end" statements. And, you could combine the first two var lines into one. Now, if refactoring and the debugger would just work well enough with inline vars that this won't cause frustration down the road if you ever need to change or debug it, then this is the perfect answer! -
"Death to WITH" in your Delphi Code
corneliusdavid replied to Darian Miller's topic in Tips / Blogs / Tutorials / Videos
Ah! So you did! I hadn't read down through all the links. That's a pretty comprehensive study of everyone's opinion! Good job! -
"Death to WITH" in your Delphi Code
corneliusdavid replied to Darian Miller's topic in Tips / Blogs / Tutorials / Videos
I agree with this in about 95% of the cases. In fact, I've inherited an old Delphi 7 project that I'm maintaining and upgrading for a customer and it is filled with WITH statements--even nested ones! It's a mess to untangle! A couple of years ago, during the "Delphi Debates" webinar series, I blogged my stance on this: Delphi Debates: With, Goto, & Label--and Exit. I've added a +1 comment to your QP ticket. -
You might want to check this recent topic:
-
Delphi 2007 and XE5 Crashes on Windows 11
corneliusdavid replied to CarGo's topic in Delphi IDE and APIs
Just to add my experience with Windows 11, I have an old laptop that originally came with Windows 10 and I upgraded it to Windows 11 several months back. It has the following versions of Delphi on it, all of which have multiple components and plug-ins installed and which I use to maintain various projects: Delphi 7 Delphi XE Delphi XE2 Delphi 10.1 Berlin Delphi 10.4 Sydney Delphi 11 Alexandria Delphi 12 Athens Make sure your path settings are right, all other apps and libraries are up-to-date (like Java libraries), you're not running out of memory or disk space, and all the other suggestions above. -
ifthen strange return value !
corneliusdavid replied to bravesofts's topic in Algorithms, Data Structures and Class Design
There are two allocations for memory you're dealing with: LObj is a pointer to an object. That pointer takes up space in memory and is allocated in your VAR declaration section as soon as that procedure is called. If it's not specifically initialized with either nil or a pointer to an actual object, the value of that pointer will contain whatever happened to be in that memory location. The second memory allocation happens when the statement LObj := TMyClass.Create; is called. That allocates memory for the object type TMyClass and the pointer to that memory space is stored in the LObj pointer variable. So when you say "LObj is just a variable..." you're right but you might be forgetting what that means: it's a variable at a memory location and in this case, it's a pointer variable that doesn't yet know what it's pointing at. Another way to look at it is if you declared this in your VAR section: var X: Integer X is a variable just like LObj is in that it's allocated when the procedure is called and similarly, if you don't assign X a value, you'll end up with whatever value happens to be in that memory space. Can you imagine testing the value of X without first assigning a number to it? -
ifthen strange return value !
corneliusdavid replied to bravesofts's topic in Algorithms, Data Structures and Class Design
When you compiled, you likely got the following warning: [dcc32 Warning] Main.View.pas(54): W1036 Variable 'LObj' might not have been initialized You should always take special notice to eliminate warnings in your code. -
ifthen strange return value !
corneliusdavid replied to bravesofts's topic in Algorithms, Data Structures and Class Design
Because LObj is not initialized to nil; therefore, it gets whatever happens to be in memory. Assigned() simply checks to see if the pointer is 0; when I ran it in Delphi 12.1, and put a break-point at the label assignment, LObj was -1 ($FFFFFFFF). -
WebUI framework: Technical preview. Part 1.
corneliusdavid replied to Alexander Sviridenkov's topic in I made this
It looks like this is similar to Elevate Web Builder. I think TMS has a product that does this also. Are you targeting a different or lower-cost market or is there something specific about this I missed that is really unique? -
Under HKEY_CURRENT_USER\SOFTWARE\Embarcadero\BDS\<Version> ... If you have any part of the BDE installed or used to be installed but not completely cleaned out, there will be a few entries. CodeInsight has some keys with the word Borland in it but that's not part of Delphi proper. I also found a several entries under the BDS Editor key in recent installs of Delphi that look like they deal with the IDE's editor such as a DefaultFileFilter, EditorEmulation, Known Editor Enhancements, and several Source Options keys. Under ToolForm|Mapping, it looks like there are several "new item" entries that have never been renamed from their original entry. Under HKEY_LOCAL_MACHINE\SOFTWARE\Classes, you'll find lots of objects registered that still have the Borland name. Some of these are only to support legacy components, like MIDAS or the BDE but some appear to still be active parts of product, like ToolsAPI and Refactoring. I'm guessing there's just too much tooling and/or third-party support built up around these original registry entries that changing them would break things. So, yes, the Borland name is still a part of Delphi, albeit quite hidden.
-
Good point; I often forget to look at which group the message is in.
-
Calling a Delphi DLL function from a C++ Builder application
corneliusdavid replied to Jean_D's topic in VCL
Either include the ShareMem unit in both Delphi and C++ so both sides understand Delphi's strings, or pass the string as a pointer (e.g. PAnsiChar) from the Delphi unit--which is what the C++ code is expecting.- 3 replies
-
- delphi
- c++ builder
-
(and 3 more)
Tagged with:
-
TButton is a wrapper around a Windows control so doesn't natively support a custom color. To accomplish this, you could use TRzButton (from KSVC) and disable the ThemeAware property, then set its Color property.
-
Delphi 12.1 Amnesty price isn’t what I thought it was…
corneliusdavid replied to Al T's topic in Delphi IDE and APIs
There is--it's called, email back and request to opt out of that unwanted support line. -
Delphi 12.1 Amnesty price isn’t what I thought it was…
corneliusdavid replied to Al T's topic in Delphi IDE and APIs
Check the renewal quote; if there are two lines, one is likely for "Platinum Support" which is totally unnecessary (at least in my opinion). On mine, that support cost adds $500 to the quote. I always respond and have them take that line off as I have NEVER requested it or needed it. That might help to bring the price back down to something reasonable. -
It looks like the only mention of Android support is in the Version 5.0 Release Notes; there are a couple of references to Android which link to source check-ins. I'd follow those and ask the authors. But it still appears so new that there would likely be a lot of bumps to get it deployed. You might consider using Interbase Embedded (IB Mobile), which has a similar structure and is free to distribute on mobile devices for any D12 edition.
-
Devin AI - Is it already happening?
corneliusdavid replied to FreeDelphiPascal's topic in General Help
Hmm... Yes, that is a serious consideration. Eye-opening article. True. Good point. -
GExperts Code Librarian is very handy--I have used that quite a bit.
-
Devin AI - Is it already happening?
corneliusdavid replied to FreeDelphiPascal's topic in General Help
I don't put data into the code repository--nor are there API keys. Those are always kept totally separate and private. THAT is what I consider top secret. True. And I can appreciate that. For the most part, keeping code in a private repository is good enough security for the projects I work on (small business database apps); the databases and API keys are what are always kept out. It may very well be a completely different scenario for others--and for many good reasons as you've stated. This is the part I guess could vary a lot for different developers/companies. Like I mentioned above, I mostly write small-business database desktop apps containing grids, edit forms, reports, and so forth. There's nothing terribly tricky about the code except the way the forms are designed or business rules that are implemented. Even embedded SQL statements won't reveal more than how the tables are structured. Now, if the customer databases or sales history were to get out, that is something that would be very bad. So for me, those are the "top secret" part of my projects. But if an AI were to train on my proprietary code, all it would get was how I implement logging or store configuration settings or create/destroy forms and show error messages and how data is accessed--but no usernames or passwords. I'm not at all arguing that no code should be private or even that trusting private online repositories or AI privacy policies should be fine for everyone--obviously not. But they're good enough for the micro-apps I build. And I was surprised to see the resistance to including AI in the IDE; but now I understand. (And I'd also like to see bugs fixed first, like @Vincent Parrett said.)