Hanoi Tower lazarus / 39-Graphics ---------------------------------------------------------------------- Dzandaa · 2024-03-12 14:47 Hi, This is a classical "Hanoi Towers" I wrote this morning for the fun B-> ---------------------------------------------------------------------- YiannisKam · 2024-03-12 15:57 Nice, thank you. ---------------------------------------------------------------------- Boleeman · 2024-03-13 07:31 Thanks Dzandaa for creating the game in Lazarus. I tried your version but was getting  errors when trying to move the disk with the mouse. The delphiforfun web site has a working version of the game for up to 10 disk, which has 2 modes (game mode and solution mode) and uses animated moves. It converts OK to Lazarus. I am playing with it to see how it works, so I can understand drag and drop better. http://delphiforfun.org/programs/towers_of_hanoi3.htm I did not want the animated moves, just drag and drop. The CSharp version that I found on github does it perfectly, but I had troubles converting it to Lazarus. Not sure if you could possibly try to convert the CSharp version to Lazarus? Would be nice to have it  working in Lazarus. As always, its nice playing with all those graphics programs. Great fun.  Take care Dzandaa. ---------------------------------------------------------------------- Dzandaa · 2024-03-13 10:01 Hi, @Boleeman: Hi, Thank you for the review. Effectively,  I found a crashes when you drag the mouse out of the board before releasing it. Modified I tested it on Windows 7 64 Bits, Windows 10 64 Bits, Linux Mint 64 Bits, MacOS Sierra with Lazarus 2.2.4 FPC Version 3.2.2. I'm interested to know if it still crashes (Lazarus version problem?)  In that version, you can change the number of disks Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i const  DiskCnt = 5;  But I think that 7 is the limit for that paintbox size B-> ---------------------------------------------------------------------- Boleeman · 2024-03-15 06:40 Hi Dzandaa, unfortunately still crashes after 2nd dis move. I can now move the smallest disk to 2nd pole, but when I move the next disk to the 3rd pole I get an access violation error (I am using Lazarus 32 bit on Win10). ---------------------------------------------------------------------- Dzandaa · 2024-03-15 09:36 Hi, @boleeman Strange, which version of Lazarus and fpc? I installed Lazarus 32 bits (with Linux Mint 19.3 Cinamon) on an old Netbook with Lazarus 2.2.6 and FPC 3.2.2 and The Hanoi Tower run fine. I tried Lazarus 3.2 with fpc 3.2.2, but I had problems with some libraries (Many Packages are marked as untested) So I stay to the old 2.2.6 and 3.2.2 B-> ---------------------------------------------------------------------- Boleeman · 2024-03-16 02:35 I am using Lazarus 2.24 32bit on Windows 10. I also tried 64bit Lazarus version 2.26 but still I get that error. Sorry for the hassles, but not sure what the problem is. Perhaps Win10 related? I was getting similar errors for items not initialized. Don't know why? Frustrating. I can drag to smallest disk to the 2nd peg with no error but when dragging the next disk to 3rd peg the program crashes. Also if I drag the smallest disk to 3rd peg for the first move it crashes. The solving works well. ---------------------------------------------------------------------- Dzandaa · 2024-03-16 10:52 Hi, @Boleeman: Strange that it works on my Windows 10 64 Bits without problem... I'm interested to know why, surely related to Windows 10 and mouse can you set up a breakpoint at line 163 in debug mode  and look at the values of TowOrig and TowDest, must be in the range 0..2. Thank you. B-> ---------------------------------------------------------------------- rvk · 2024-03-16 14:54 Works fine for me on Windows 10 64 bit with both 32 and 64 bit Lazarus 3.2 (fixes_3_2). Lazarus 3.2 (rev lazarus_3_2) FPC 3.2.3 i386-win32-win32/win64 Although there is some massive memory leak when exiting the program (detected by switching on heaptrc)  Can you let it break back to the IDE and see with Stack Watch what's the last actual code in the HanoiTowerU unit? O, and I hate those TABs in the source code. They throw off all the indenting !!! You can do a CTRL+D once in a while to make the indenting correct. (With the correct default setting it will also turn those tabs into spaces) You also might want to use FormDestroy instead of FormClose to clean up some things. (FormDestroy is the counter of FormCreate, not FormClose) ---------------------------------------------------------------------- rvk · 2024-03-16 15:18 Quote from: Dzandaa on March 16, 2024, 11:52:03 amcan you set up a breakpoint at line 163 in debug mode  and look at the values of TowOrig and TowDest, must be in the range 0..2. I had a looksie on an older laptop which I have set at DPI 150%. There on line 163 I have... PBHanoi.Width = 450 X = 375 (dragging the disk to the third peg). So... you use X and coordinates, both don't take into account the possible deformation of different DPI settings  You do a div 100 but that should be corrected for the DPI setting. ---------------------------------------------------------------------- Boleeman · 2024-03-17 05:53 Hi Dzandaa. With your two latest updates the Towers of Hanoi game works without crashing in WIndows 10. Posted the message here as I did not want it to be final after your last post. Thanks for the fixes. Much appreciated Dzandaa, for making the game. ---------------------------------------------------------------------- Dzandaa · 2024-03-17 11:45 Hi, @rvk I think I corrected the memory Leaks C# free automatically memory, sorry, bad habit; But I don't know how to correct the DPI, I thought it was done automatically. QuoteSo... you use X and coordinates, both don't take into account the possible deformation of different DPI settings  You do a div 100 but that should be corrected for the DPI setting. ---------------------------------------------------------------------- rvk · 2024-03-17 14:00 Quote from: Dzandaa on March 17, 2024, 12:45:03 pmBut I don't know how to correct the DPI, I thought it was done automatically. You could check Screen.PixelsPerInch. Normally this is 96. For 150% dpi this would be 144. You could use div (100 / 96) * Screen.PixelsPerInch to get the correct division for 150 dpi (and any other dpi setting). But... I would suggest going another route. If PaintBox is 300, your peg-room will be 100. If PaintBox is 450, your peg-room will be 150. So always make do "div (PaintBox1.Width div 3)" (because you have 3 pegs in PaintBox1). Even better... make the whole thing resizable. If the form resizes, the PaintBox will resize with it (use the Anchors). And because now the 100 is replaced with dynamic peg-room you don't get a crash. (Of course you need to implement this everywhere where you do that div 100 or depend on a hard number) Another possible improvement... change the destination peg in MouseMove to another color. Then you have a visible representation as to which peg the disc will be dropped if let go. ---------------------------------------------------------------------- Dzandaa · 2024-03-17 15:13 Hi, @rvk Thank you very much, Here is an improved version. B-> ---------------------------------------------------------------------- rvk · 2024-03-17 16:02 Quote from: Dzandaa on March 17, 2024, 04:13:12 pmHere is an improved version. Yep. That look nice. The destination peg lights up. And when resizing the spaces become bigger and it still works. One small point still. Although FormClose will work... FormDestroy is the counter procedure for FormCreate. You create objects in FormCreate, so I would also free them in FormDestroy, not in FormClose. (in some rare instances it could also be too soon to free them in FormClose) (O, and the tabs are still there    ) ---------------------------------------------------------------------- dseligo · 2024-03-17 17:47 Quote from: Boleeman on March 17, 2024, 06:53:36 amAt line 163 and line 165 I have the slightly differing checks, but the error happens on line 165  for TowDest].Count: line 163:    if(Towers[TowOrig].Count <> 0) then                 begin line 165:    if (Towers[TowDest].Count <> 0) then You have range check error. What is value of TowDest in row 165? What size is array Towers in line 165? QuoteI have an  AMD A9 Cpu on an old Dell computer. I don't think CPU and age of your computer has anything with error you got. ---------------------------------------------------------------------- rvk · 2024-03-17 17:49 Quote from: dseligo on March 17, 2024, 06:47:19 pmI don't think CPU and age of your computer has anything with error you got. It was probably a problem with dpi setting. This should be solved in the last version. ---------------------------------------------------------------------- Dzandaa · 2024-03-17 18:12 Hi, @rvk QuoteOne small point still. Although FormClose will work... FormDestroy is the counter procedure for FormCreate. You create objects in FormCreate, so I would also free them in FormDestroy, not in FormClose. I tried to replace OnClose with OnDestroy, but then, I have difficulties to close with the button, I don't know why... B-> ---------------------------------------------------------------------- rvk · 2024-03-17 18:40 Quote from: Dzandaa on March 17, 2024, 07:12:45 pmQuoteOne small point still. Although FormClose will work... FormDestroy is the counter procedure for FormCreate. You create objects in FormCreate, so I would also free them in FormDestroy, not in FormClose. I tried to replace OnClose with OnDestroy, but then, I have difficulties to close with the button, I don't know why... B-> Yikes. Yes, I see. That seems to be a problem with TPaintBox.Paint. It's called so often, that it blocks the program from ending. (And now you see why it's best to put it in Destroy because you see a problem surfacing) What you can do is this: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure THanoiTowerForm.FormClose(Sender: TObject;  var CloseAction: TCloseAction);begin  PBHanoi.Enabled := False; // CloseAction should already be acFreeend; And now put the release code in FormDestroy: Code: Pascal  [Select][+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i procedure THanoiTowerForm.FormDestroy(Sender: TObject);var  i, j: integer;  D1: PDisk;begin  for i := 0 to 2 do  begin    if (Towers[i] <> nil) then  begin      if (Towers[i].Count <> 0) then      begin        for j := 0 to Pred(Towers[i].Count) do        begin          D1 := Towers[i].Pop;          Dispose(D1);        end;      end;      Towers[i].Free;    end;  end;end; This should work. I'm not sure why the TPainbox.Paint blocks the exit when not disabled, but by disabling it before closing it works. (So only the TPaintbox.Enabled := false needs to be in the CloseForm proc) ---------------------------------------------------------------------- Dzandaa · 2024-03-18 09:49 Hi, It works now, many thanks. This is the final version B-> ---------------------------------------------------------------------- Boleeman · 2025-01-01 04:03 DZandaa, looked over your source and noticed Randomized; was missing from OnCreate. Also noticed that the colors of the disks were not changing as the colours array was being created in OnCreate, instead of when a new game is created. Made a few variations (using rectangles, TShapes and lines). Sent you some emails with attachments. I thought of a  few new features like having transparent disks, using TBgrabmp , timed games and a best times leader board and possibly fireworks when a game is finished correctly. ***  Finished the 8 disk game in 255 moves   *** Happy New Year to you DZandaa Regards Boleeman