-
Content Count
1089 -
Joined
-
Last visited
-
Days Won
23
Everything posted by aehimself
-
Cross-platform solution to forcefully end a thread
aehimself replied to aehimself's topic in Cross-platform
https://i.imgur.com/sqZE6sS.jpg I hope some will get it 🙂 -
Cross-platform solution to forcefully end a thread
aehimself replied to aehimself's topic in Cross-platform
It does. But we all know the phrase - you cook with what you have 😞 -
Cross-platform solution to forcefully end a thread
aehimself replied to aehimself's topic in Cross-platform
I strongly, strongly disagree. They introduce more problems that they solve in some implementations, true; but with correct usage they can make a sluggish UI fluent, a long running calculation finish in a fraction, or simply making the application do several calculations in parallel instead of serial. One word for all: they make a better experience and happier end-users. Threads are dangerous. Not evil. -
What to do when Commuunity Edition expires?
aehimself replied to Silver Black's topic in General Help
As far as I remember (I am not allowed to use CE anymore, unfortunately) you can request a new license for CE somewhere on the website after logging in. -
Cross-platform solution to forcefully end a thread
aehimself replied to aehimself's topic in Cross-platform
There is no cycle and - as I mentioned earlier - CallStuffThatMightBlockForever might never return, therefore the break will never trigger. If the application terminates I'm perfectly fine with that. Before reaching this point there will be 25 thousand nagging confirmation messages. If the user says yes, and accepts that the program might quit or become unstable, I did what I could. Unfortunately it does block resources. However leaving it to run also can be a solution. If it's needed again I can launch an other instance, this will only cause problems during shutdown. Unless I can detach them from the process... -
Cross-platform solution to forcefully end a thread
aehimself replied to aehimself's topic in Cross-platform
Edited to library 🙂 Sorry for not using the correct terminology, since this is my first multi-platform solution I'm not familiar on how these modules are called elsewhere. The original question is still valid, though. -
Cross-platform solution to forcefully end a thread
aehimself replied to aehimself's topic in Cross-platform
There's no cycle, no serial commands in my thread. It calls one method in a blackbox library (blackbox = not written by me, closed source) which can freeze or take way too long to execute. My code will not regain control for hours to be able to quit, or won't regain it at all. This leaves me no options but to expect leaks and misbehavior and kill it with fire. -
is there any "currency to words" routine for Delphi?
aehimself replied to Attila Kovacs's topic in Algorithms, Data Structures and Class Design
Well, I'd say one language = one set of of rules = one helper unit. You'll not reach 100 files, but can get close if you are ambitious enough 🙂 Plus, you need a fluent speaker of that language to help you out. I personally do not speak French, but I hear they have quite messed up way of saying numbers (like 92 is "76 and 16" or something). -
However I have 0 experience in cross-platform, this sounds perfectly reasonable. My 2 cents are that if any object (TMyThread) need to live and be accessible throughout a method, define it's variable in the parent (TForm1), worst-case-scenario unit global. It makes sense to me like this and it seems the garbage collector thinks the same way. @David Heffernan My guess is that there is a reason for suspended creation, it is just not included in the example code above. What I try to say is, I always create TThreads suspended myself but mostly because I want to do stuff with them before the actual execution (e.g. .NameThreadForDebugging, etc.).
-
Load a String from a file - returns strange char set
aehimself replied to bernhard_LA's topic in Algorithms, Data Structures and Class Design
...and this is from an era when I was already using Try ... Finally blocks! Seriously, most of my first codes make me want to give up development and be a baker instead. -
Load a String from a file - returns strange char set
aehimself replied to bernhard_LA's topic in Algorithms, Data Structures and Class Design
Code is from D7-era. Maybe it worked different back then...? In 10.2 .LoadFromFile effectively does the same (only without the .BeginUpdate and .EndUpdate). But I remember that I had to change due to insanely long loading times. -
Load a String from a file - returns strange char set
aehimself replied to bernhard_LA's topic in Algorithms, Data Structures and Class Design
Memo.Lines.LoadFromFile suffers from performance issues if the file is n x 10 MB, especially if it is on a network location. I changed most of my sensitive methods to use Streams instead: fs := TFileStream.Create('filename.txt', fmOpenRead + fmShareDenyNone); Try Memo.Lines.BeginUpdate; Memo.Lines.LoadFromStream(fs); Finally FreeAndNil(fs); Memo.Lines.EndUpdate; End; -
Afaik ShellExecute returns nothing, it does not even confirm if the command line was executed or not. By sticking to it you have no other options but command line parameters, best case scenario is to encrypt the password and decrypt it from the second app. You can check the running processes after ShellExecute and grab it's handle for data transfer but this introduces a lot of unnecessary checks, like timeout (don't wait for the second process until you can find it, what if it did not even launch), did it already initialize and ready to accept data? If you use CreateProcess and map the stdin and stdout, you can make your first application to "type in" the user name and password to the second one and read back the output to verify if authentication was successful. However if both applications are written and managed by you, move the worker method to a .DLL and make the first and the second application to load and use it. You also have to validate the legitimacy of the library, though. Or to a helper unit, and do not even include a secondary file. However, external files will always pose a major security risk, especially if they need to share sensitive information. It's really easy to put a malicious .EXE file in place of yours (even if it's running) just to steal the credentials.
-
You don't need a component for this. I'd proceed this way: - have a strict private DateTime variable. Upon form creation, set it to zero. - OnKeyDown / OnKeyPress handler of the ComboBox. If the key was pressed, and it's not a comma, set the above DateTime to zero. If it is, check if the value of the DateTime variable: - If the value equals zero, set it to Now - If it's not, check the seconds passed between that and Now (DateUtils.SecondsBetween): - If the difference is greater than 1 or 2, set the variable to Now - If the difference is less, execute your custom action. If you need more help let me know, I can make a quick demo, but my theory would be this.
-
This is a really important piece of information. Thank you!
-
Wish you a quick recovery!
-
I wish I would be. I'd buy you a beer for closing the military industrial takeover topic 🙂 Seriously though, my company is not paying for (or don't know about) these and it's a bit pricy for a simple person. There are people in my country who earn the price (or a fraction!) of a 1-day ticket per month.
-
...ooooor the focus actually stays on the button, it's just not redrawn properly. ActiveX controls work in strange ways (I still have active / not active issues with embedded MSTSC controls up to this day...) You can verify this by comparing form..ActiveControl with your button.
-
You can actually reproduce the issue (on 10.2) by dialog.Visible := Not dialog.Visible. I suppose the issue is that since the window object is not actually closing (default closing action is to hide only), the preview is not getting refreshed automatically. If you really would like to keep it this way, use the MainFormOnTaskbar or the .Handle workaround which you discovered. I suspect this is only an other bug though. I agree with everyone else though - do not auto-create windows. If you want to load data only once, load it into an object in your main form (like a DataSet or a TStringList) and send that to your dialog form with a reintroduced .Create or an additional .Init method. As all forms of your application are running in the same thread, passing any object should be safe - if you are 100% sure that only one form is using them, at least, a time.
-
Hello, I already used WM_SETREDRAW to disable flickering when resizing / loading components successfully, however today I faced an interesting issue. I created a TForm descendant (DoubleBuffered, if it makes any difference) with .BeginUpdate and .EndUpdate methods as follows: Procedure TMyForm.BeginUpdate; Begin SendMessage(Self.Handle, WM_SETREDRAW, Ord(False), 0); // LockWindowUpdate(Self.Handle); End; Procedure TMyForm.EndUpdate; Begin SendMessage(Self.Handle, WM_SETREDRAW, Ord(True), 0); Self.Repaint; // LockWindowUpdate(0); End; I am trying to create an "expandable" dialog box, where there is a button to show additional information about the message (if available). It looks like this: It contains three elements: a top panel with alTop (with the alLeft picture and a alClient caption), a bottom panel for buttons with alBottom and an alClient memo. Expanding / collapsing logic is: ExpandCollapseButton.Glyph.Assign(nil); If _expanded Then Begin ImageList.GetBitmap(1, ExpandCollapseButton.Glyph); Self.Constraints.MaxHeight := 0; Self.Height := _savedheight; Self.Constraints.MinHeight := Self.Height - ExtendedMessageMemo.Height + 21; End Else Begin ImageList.GetBitmap(0, ExpandCollapseButton.Glyph); _savedheight := Self.Height; Self.Constraints.MinHeight := 0; Self.ClientHeight := TopMessagePanel.Height + ButtonsPanel.Height; Self.Constraints.MinHeight := Self.Height; Self.Constraints.MaxHeight := Self.Height; End; Everything works like a charm until I try to wrap this block in the .BeginUpdate / .EndUpdate method. The form is alive (reacts to keypresses; even expands itself if I assign the expand method to a keypress), but unclickable, unmovable... like if the ending WM_SETREDRAW would have never been called. Both SendMessage functions returns with success. Extra: if I swap the ending SendMessage with PostMessage, the form works normally, only the moving parts are not repainted (in my case the memo and the button panel); guess this is because the .Repaint is performed before the message is processed. I already tried sending a WM_PAINT, a simple .Invalidate instead of .Repaint, even repainting the whole screen without success. The question is obvious. What am I overlooking, why WM_SETREDRAW is working fine with everything else, but a form? 🙂 Cheers!
-
Agreed, this is why I decided not to go with this route after all. But, you also have to admit that this was a funny little thing and it might help others later on!
-
I do not envy AV programmers. Most of us love to blame them for everything 😄
-
WM_SETREDRAW adds the WS_VISIBLE style, but this does not trigger the .Visible property to change. Since according to Delphi the window is not visible it does not even try to hide it - this is why the form stays visible forever. This is why I love to code, we always learn something new: During the OnCreate event the form is invisible. Forcing it visible without being fully created (property loading takes place in a later stage) seems to render it in an unusable state... like it does receive the enable redraw message, but omits it without processing... or something. Removing these calls from the OnCreate and OnClose method solves the issue completely. Verdict: do not use WM_SETREDRAW in any form during construction or destruction. I'll just stick to hiding it before the final expansion to eliminate the flicker, but it's good to know what we can and cannot do with WM_SETREDRAW.
-
No, I did not, as caHide is the default value of Action. The reason why the form pops back up can be found on MSDN: "If the application sends the WM_SETREDRAW message to a hidden window, the window becomes visible (that is, the operating system adds the WS_VISIBLE style to the window)." Maybe this is the reason why it fails to initialize in Modal...?
-
Ooooooookay. Progress. I'm calling the expand logic upon creating and closing the form to set / reset the dimensions. Procedure TForm2.FormClose(Sender: TObject; Var Action: TCloseAction); Begin Self.Visible := False; SendMessage(Self.Handle, WM_SETREDRAW, Ord(False), 0); SendMessage(Self.Handle, WM_SETREDRAW, Ord(True), 0); End; procedure TForm2.FormCreate(Sender: TObject); begin SendMessage(Self.Handle, WM_SETREDRAW, Ord(False), 0); SendMessage(Self.Handle, WM_SETREDRAW, Ord(True), 0); end; If you execute this window with ShowModal, it will freeze upon opening. If you execute it with .Show, it will never disappear (despite having it's .Visible property at false) but remain unpainted for it's lifetime. The problem is calling these upon creating and closing the form. I just don't know why. Yet. Edit: The flicker is there because of the OnClose logic, as I was expanding the window and it popped full-size for a moment before disappearing. The whole story started there, and however it can be done by hiding it before the logic, it disturbs me A LOT on why this method is not working 🙂