Jump to content

Leaderboard


Popular Content

Showing content with the highest reputation on 02/28/19 in Posts

  1. Original post: https://www.thedelphigeek.com/2019/02/design-patterns-with-delphi-book.html Hurrah, hurray, my third book is here! It’s called Hands-On Design Patterns with Delphi and (just like my first book) I wrote it for Packt Publishing. (The second book was self-published and I expect the fourth one to be, too.) As the name says, “Design Patterns with Delphi” deals with design patterns. It is a bit different from most of design pattern books and websites you will find on the Internet. Case in point A: There are no UML diagrams. I don‘t speak UML. Tried to learn it few times but for some reason the whole concept doesn‘t agree with me. If you like diagrams, don’t fear though. Any book on design patterns - and most websites covering that topic - will gladly show how any design pattern can be diagrammed. That, however, is not important and should not govern your decision to buy the book. More important is case in point B: This book speaks Delphi. All the examples are written in Delphi and language features are used to the full. I also covered few less known Delphi idioms in separate sections. You’ll still be able to follow the discussion even though you may program in a different Pascal dialect. There’s also case in point 😄 Examples make sense. I deeply dislike classical design pattern examples of the “And then we want to write this program for different toolkits and it should also be able to draw circles, not only squares” kind. Euch! I tried to find a good example for each design pattern. Admittedly, I ended with few examples that draw triangles and squares on screen (mostly because some patterns were designed specifically for solving such problems), but most of them are of a more practical nature. This book covers all three classical design pattern categories - Creational patterns, Structural patterns, and Behavioral patterns. It also discusses patterns from the newer Concurrency patterns category. At the end I threw in some borderline-pattern(ish) topics and ended with a discussion of few patterns that cannot be strictly classified as “design” patterns. In this book you’ll find: Chapter 1 An introduction to patterns. Exploration of design principles, design patterns, and idioms. A mention of anti-patterns. A short description of most important design principles. Delphi idioms: creating and destroying objects. Chapter 2 Creation patterns part 1. Singleton. Dependency injection. Lazy initialization. Object pool. Chapter 3 Creation patterns part 2. Factory method, Abstract factory, Prototype, Builder. Delphi idioms: Assign and AssignTo. Chapter 4 Structural patterns part 1. Composite. Flyweight. Marker interface. Bridge. Delphi idioms: comparers and hashers. Chapter 5 Structure patterns part 2. Adapter. Proxy. Decorator. Facade. Delphi idioms: replacing components in runtime. Also: helpers. Chapter 6 Behavioral patterns part 1. Null object. Template method. Command. State. Chapter 7 Behavioral patterns part 2. Iterator. Visitor. Observer. Memento. Delphi idioms: for .. in. Chapter 8 Concurrency patterns part 1. Locking. Lock striping. Double-checked locking. Optimistic locking. Readers-writers lock. Delphi idioms: tasks and threads. Also: bitwise operators. Chapter 9 Concurrency patterns part 2. Thread pool. Messaging. Future. Pipeline. Chapter 10 Writing Delphi programs. Event-driven programming. Actions. LiveBindings. Form inheritance. Frames. Data modules. Chapter 11 Wrapping it up. Exceptions. Debugging. Functional programming. I hope you will like this book and learn a lot from it. I know I did during the nine months I spent writing it. And if you find any bug in the code, let me know so I can correct it in the second release!
  2. @Uwe RaabeIf you ever come to São Paulo, please let me know. Ifeel like I have to, at the very least, buy you dinner. Thank you very much for all the problems your input has put me back in business. -- Carlos Tré
  3. David Heffernan

    operator overloding Equal vs Multiply

    An array can be thought of as a single entity. Consider vector arithmetic. Take two vectors of length N and sum them. That's one operator, two operands, each operand a vector with N scalar components. My entire livelihood is based on such a form of mathematics. Are you saying I've been doing it wrong?
  4. Hi, I've had lots of enquiries recently about when Bookmarks and Navigator will have a version available for 10.3 - they've been updated and new features added for every release until now. I'm please to say they will be available with the upcoming version of RAD Studio (10.3.1) which is coming out soon. The reason for for being included, and for the lack of news about a 10.3-compatible release in the past month, is that the plugins have been acquired by Embarcadero and so will now ship with the IDE itself. This is great news. I wrote the plugins originally to add features I wanted to the IDE, and hundreds (thousands, actually!) of developers have given great feedback. It's great to know the features will be available to everyone. In addition, due to the pressures of work, I haven't had much time to maintain or extend them recently, and so having them under Embarcadero's wing means they'll live on and be developed as part of Delphi and C++Builder itself. More info in the linked post! - David
  5. RonaldK

    Communication between processes (IPC)

    Shared Memory: https://stackoverflow.com/questions/5646202/sharing-data-array-between-two-applications-in-delphi
  6. Primož Gabrijelčič

    Hands-On Design Patterns with Delphi

    A convenient timespace coordinate to get a copy of my book signed (or to buy a fresh new one 😉 ) Bergamo on 17th and 18th of April (https://conf.spring4d.com).
  7. Andrea Magni

    Error in LAction.Target := nil

    Hi @Ruslan, if you are freeing (closing) the frame (frameinfo) within an event handler of an UI element you may need to wait some amount of time in order to let the UI finish its activities related to the event itself (i.e. if it's a button, there might be some animations going on and/or similar things). Sincerely, Andrea
  8. Remy Lebeau

    CreateProcess[A] only returns Chinese

    Typically, a fixed AnsiChar[] array can be passed to a PAnsiChar pointer, but apparently that only works when the low index is 0, whereas yours is 1 instead. From the documentation: Yes, that will work, and is what you need to do, unless you change your Buf array to use 0-based indexing.
  9. David Heffernan

    CreateProcess[A] only returns Chinese

    There are only two functions, the A and the W version. The A version converts the input text arguments to Unicode and calls the W version. That's always the case with Windows. The A function is just a time and memory consuming wrapper around the W function. Note that this implies it makes no difference to the output of the created process since the W version is always going the work in the end. Basic rule is always call the W version. It's more efficient, the system is Unicode natively, and the W version means your code can be used by non English users.
  10. Remy Lebeau

    CreateProcess[A] only returns Chinese

    The problem is not with CreateProcess[A] itself, but in how the output of the spawned process is [mis]interpreted by TRedirectedConsole when converted to a string format. What you describe is commonly known as "mojibake", and it can happen when 7/8-bit ANSI character data is mis-interpreted as 16/32-bit Unicode data, thus producing bad "characters" that fall within, in this case, the Chinese language, for instance. If you look at TRedirectedConsole's internal logic more carefully (specifically, in its ReadHandle() method), you will see that it reads the spawned process's output using the Win32 API ReadFile() function (which has no concept of string characters), stores the raw bytes as-is into a Char[] array, and then copies that array into a native String. That worked just fine in 2004 when Delphi's native String type was still AnsiString, and the native Char type was still AnsiChar. But remember that in Delphi 2009, the native String type was changed to UnicodeString, and the native Char type was changed to WideChar. As such, TRedirectedConsole's current reading logic is no longer valid under a Unicode environment. It needs to be updated to account for the fact that the 8-bit ANSI encoding of the spawned process's output is now different than the 16-bit Unicode encoding of Delphi's native String type. One way to handle this would be to tweak TRedirectedConsole to make it explicitly use AnsiString and AnsiChar everywhere, instead of using String and Char, respectively. This is commonly known as "Ansifying" your code, which is generally shunned upon, but this is a common use case for it. Also, note that AnsiString is now codepage-aware, so you would have to use the RTL's SetCodePage() function to assign a proper codepage identifier to any AnsiString you give to the user, so the ANSI data will be converted properly when assigned to other strings, such as a UnicodeString when adding to the TMemo (since the entire VCL uses UnicodeString now). Unless the spawned process is manipulating its output to use a specific encoding (like UTF-8), you can generally use the Win32 API GetACP() function for the codepage identifier, or the RTL's global DefaultSystemCodePage . For example: //============================================================== function TRedirectedConsole.ReadHandle(h: THandle; var s: AnsiString): integer; //============================================================== var BytesWaiting: DWORD; Buf: Array[1..BufSize] of AnsiChar; BytesRead: {$IFDEF VER100}Integer{$ELSE}DWORD{$ENDIF}; begin Result := 0; PeekNamedPipe(h, nil, 0, nil, @BytesWaiting, nil); if BytesWaiting > 0 then begin if BytesWaiting > BufSize then BytesWaiting := BufSize; ReadFile(h, Buf[1], BytesWaiting, BytesRead, nil); SetString(s, Buf, BytesRead); {$IFDEF CONDITIONALEXPRESSIONS} {$IF CompilerVersion >= 12} // D2009+ SetCodePage(PRawByteString(@s)^, GetACP(), False); {$IFEND} {$ENDIF} Result := BytesRead; end; end; ... //============================================================== procedure TRedirectedConsole.Run( working_dir : string ); //============================================================== var s: AnsiString; // not String! ... begin ... end; However, other areas of TRedirectedConsole would also have to be ansified, and I can see some issues with doing that, so I would suggest instead to have TRedirectedConsole continue to use the native String type everywhere, and just re-write the ReadHandle() method to explicitly convert the spawned process's output from ANSI to UTF-16, such as with the RTL's UnicodeFromLocaleChars() function (using the same codepage as above): {$IFDEF CONDITIONALEXPRESSIONS} {$IF CompilerVersion >= 12} {$DEFINE STRING_IS_UNICODESTRING} {$IFEND} {$ENDIF} //============================================================== function TRedirectedConsole.ReadHandle(h: THandle; var s: String): integer; //============================================================== var BytesWaiting: DWORD; Buf: Array[1..BufSize] of AnsiChar; BytesRead: {$IFDEF VER100}Integer{$ELSE}DWORD{$ENDIF}; begin Result := 0; if PeekNamedPipe(h, nil, 0, nil, @BytesWaiting, nil) then begin if BytesWaiting > 0 then begin if BytesWaiting > BufSize then BytesWaiting := BufSize; ReadFile(h, Buf[1], BytesWaiting, BytesRead, nil); {$IFDEF STRING_IS_UNICODESTRING} SetLength(s, UnicodeFromLocaleChars(GetACP(), 0, Buf, BytesRead, nil, 0)); UnicodeFromLocaleChars(GetACP(), 0, Buf, BytesRead, PChar(s), Length(s))); {$ELSE} SetString(s, Buf, BytesRead); {$IFEND} Result := BytesRead; end; end; end; //============================================================== procedure TRedirectedConsole.Run( working_dir : string ); //============================================================== var ... begin ... {$IFDEF UNICODE} // this is important to prevent a crash in CreateProcessW()... UniqueString(fCmdLine); {$ENDIF} // this raises an exception if anything happens Win32Check(CreateProcess(nil, PChar(fCmdLine), nil, nil, True, NORMAL_PRIORITY_CLASS, nil, wd, fSI, fPI)); ... end;
  11. Clément

    ICS V8.60 adds several new components

    Great news!! ICS is amazing Clément Brazil
  12. Uwe Raabe

    operator overloding Equal vs Multiply

    I am inclined to see this as the compiler barfing at the language designer who came up with this ambiguous set/array thing in the first place.
  13. I got it working now! First I changed the path setting back to the old value (on my machine it is "c:\Users\Uwe\AppData\Roaming\Parnassus OU\Common"). Then I copied the new DLL into that folder and renamed it to ParnassusCoreEditor_XRio.dll It seems that the DLL loader logic first looks for the "XRio" DLL and has a fallback to the original name. That way the different DLLs can coexist in the same folder and the XRio renaming allows for future version, too.
  14. Markus Kinzler

    10.3.1 has been released

    This was postponed to 10.3.2 (planned) https://www.delphipraxis.net/1425561-post6.html
×