Jump to content

Leaderboard


Popular Content

Showing content with the highest reputation on 07/17/22 in all areas

  1. Brian Evans

    Clientdataset's delta becomes empty

    I would suggest switching to using cached updates on the TFDQuery instead of using ClientDataSet. https://docwiki.embarcadero.com/RADStudio/Sydney/en/Caching_Updates_(FireDAC)
  2. pyscripter

    Strange memory leak with checkbox

    This was due to a bug (TPyDelphiObject.SetAttrO causes memory leak · Issue #368 · pyscripter/python4delphi (github.com)) which is now fixed. It may take some time for the fix to be reflected in the pip installable delphivcl, but you can always compile your own delphivcl.pyd from the github sources. @shineworldThanks for discovering the issue.
  3. Sherlock

    iPhoneOS15.X.sdk

    I'm afraid that is a waste of time. It's not just the SDK that is needed here. Code signing by a specific XCode release is checked by Apple as well.
  4. dummzeuch

    Format source with tabs

    Yes. I never even thought about using tabs because they usually are a pain in the lower back everywhere.
  5. angusj

    Rounded polygon

    Here's my GetSmoothPath() routine. It requires no specific graphics library to use, just a few extra functions (also included below). This function generates an array of control points that's very easily converted into a flattened cubic bezier path using just about any 2D graphics library. (nb: The code below has been written with simplicity as the focus rather than performance.) uses SysUtils, Math; type TPointD = record X, Y: double; end; TPathD = array of TPointD; TArrayOfDouble = array of double; function DistanceSqrd(const pt1, pt2: TPointD): double; begin result := Sqr(pt1.X - pt2.X) + Sqr(pt1.Y - pt2.Y); end; function Distance(const pt1, pt2: TPointD): double; begin Result := Sqrt(DistanceSqrd(pt1, pt2)); end; function OffsetPoint(const pt: TPointD; dx, dy: double): TPointD; begin result.x := pt.x + dx; result.y := pt.y + dy; end; function GetAvgUnitVector(const vec1, vec2: TPointD): TPointD; var inverseHypot: Double; begin Result.X := (vec1.X + vec2.X) * 0.5; Result.y := (vec1.Y + vec2.Y) * 0.5; inverseHypot := 1 / Hypot(Result.X, Result.Y); Result.X := Result.X * inverseHypot; Result.Y := Result.Y * inverseHypot; end; procedure MakeSymmetric(var val1, val2: double); begin val1 := (val1 + val2) * 0.5; val2 := val1; end; function GetUnitVector(const pt1, pt2: TPointD): TPointD; var dx, dy, inverseHypot: Double; begin if (pt1.x = pt2.x) and (pt1.y = pt2.y) then begin Result.X := 0; Result.Y := 0; Exit; end; dx := (pt2.X - pt1.X); dy := (pt2.Y - pt1.Y); inverseHypot := 1 / Hypot(dx, dy); dx := dx * inverseHypot; dy := dy * inverseHypot; Result.X := dx; Result.Y := dy; end; // GetSmoothPath - returns cubic bezier control points // parameters: 1. path for smoothing // 2. whether or not the smoothed path will closed // 3. percent smoothness (0..100) // 4. maximum dist control pts from path pts (0 = no limit) // 5. symmetric vs asymmmetric control pts function GetSmoothPath(const path: TPathD; pathIsClosed: Boolean; percentOffset, maxCtrlOffset: double; symmetric: Boolean): TPathD; var i, len, prev: integer; vec: TPointD; pl: TArrayOfDouble; unitVecs: TPathD; d, d1,d2: double; begin Result := nil; len := Length(path); if len < 3 then Exit; d := Max(0, Min(100, percentOffset))/200; if maxCtrlOffset <= 0 then maxCtrlOffset := MaxDouble; SetLength(Result, len *3 +1); prev := len-1; SetLength(pl, len); SetLength(unitVecs, len); for i := 0 to len -1 do begin pl[i] := Distance(path[prev], path[i]); unitVecs[i] := GetUnitVector(path[prev], path[i]); prev := i; end; Result[len*3] := path[0]; for i := 0 to len -1 do begin if i = len -1 then begin vec := GetAvgUnitVector(unitVecs[i], unitVecs[0]); d2 := pl[0]*d; end else begin vec := GetAvgUnitVector(unitVecs[i], unitVecs[i+1]); d2 := pl[i+1]*d; end; d1 := pl[i]*d; if symmetric then MakeSymmetric(d1, d2); if i = 0 then Result[len*3-1] := OffsetPoint(path[i], -vec.X * Min(maxCtrlOffset, d1), -vec.Y * Min(maxCtrlOffset, d1)) else Result[i*3-1] := OffsetPoint(path[i], -vec.X * Min(maxCtrlOffset, d1), -vec.Y * Min(maxCtrlOffset, d1)); Result[i*3] := path[i]; Result[i*3+1] := OffsetPoint(path[i], vec.X * Min(maxCtrlOffset, d2), vec.Y * Min(maxCtrlOffset, d2)); end; if not pathIsClosed then begin Result[1] := Result[0]; dec(len); Result[len*3-1] := Result[len*3]; SetLength(Result, Len*3 +1); end; end; And here's what it produces ... the path to smooth (black), the cubic bezier control path produced by GetSmoothPath() (blue) and the flattened cubic bezier path (2D graphics library of you choice required) (red). var TPathD path; begin path := MakePath([190,120, 260,270, 560,120, 190,490]); path := GetSmoothPath(path, true, 20, 0, false); path := ThirdParty2DGraphicsLibrary.FlattenCBezier(path); end; var TPathD path; begin path := MakePath([190,120, 260,270, 560,120, 190,490]); path := GetSmoothPath(path, true, 80, 0, false); path := ThirdParty2DGraphicsLibrary.FlattenCBezier(path); end; Edit: The best way to avoid intersections is to make sure you have enough data points before generating your curves.
  6. Perhaps "terse" can be understood as rudeness. But for me personally, the words "keep your advice to yourself" mean unambiguously rudeness. I don't know, maybe I was brought up wrong.
  7. To be fair: David also tends to be - lets say "terse" - in his answers. That can also be interpreted as rude, in particular by people for whom English is a foreign language.
  8. @de la Mancha- you asked and got a relevant answer from someone known for doing heavy math with Delphi. No reason to be rude.
  9. No problem, I wanted to save time. It's not hard for me R. The program is free. I know the author. Good luck and keep your advice to yourself.
  10. Here's what to do. First of all you need to understand the R code. You need to know what it's purpose is, and how it achieves it. You will need a clear understanding of what data types are expected to be passed to, and returned from the function. You may need to talk to the author of the code, or learn enough R to work it out yourself. Once you have a clear understanding then you will be in a good place to write an equivalent function in Delphi. Good luck.
×