This is VBA, which while not .Net, it at least shows you and example. I think Bryco wrote this code
Option Explicit
Public Declare Function GetAsyncKeyState Lib "user32" _
(ByVal vKey As Long) As Integer
Public Const VK_ESCAPE = &H1B
Public Const VK_LBUTTON = &H1
Public Function GetPointEX(Optional vPoint As Variant, _
Optional strPrmt As Variant = vbCrLf & "Select point: ") As Variant
Dim objTemp As AcadEntity
Dim objUtil As AcadUtility
Dim varPnt As Variant
Dim UcsPt As Variant
Dim varCancel As Variant
On Error GoTo Err_Control
Set objUtil = ThisDrawing.Utility
If IsMissing(vPoint) Then
varPnt = objUtil.GetPoint(Prompt:=strPrmt)
Else
UcsPt = ThisDrawing.Utility.TranslateCoordinates(vPoint, acWorld, acUCS, False)
varPnt = objUtil.GetPoint(UcsPt, strPrmt)
End If
GetPointEX = varPnt
Exit_Here:
Exit Function
Err_Control:
Select Case Err.Number
Case -2147352567
If GetAsyncKeyState(VK_ESCAPE) > 0 Then
Err.Clear
Resume Exit_Here
ElseIf GetAsyncKeyState(VK_LBUTTON) > 0 Then
Err.Clear
Resume
Else
Err.Clear
Resume Exit_Here
End If
Case -2145320928
'Right click or 'Enter'
'You could use InitializeUserInput to allow
'Keywords, but in this example we just exit
Err.Clear
Resume Exit_Here
Case "13", "-2147024809" 'Invalid argument Point in GetPoint
Err.Clear
Resume Exit_Here
Case Else
'MsgBox Err.Description
'Debug.Print Err.Description, Err.Number
Resume Exit_Here
End Select
End Function
Sub PolyArc3d()
Dim P1, P2, P3
Dim MidP(2) As Double
Dim dHt As Double, dBulge As Double '
Dim dist As Double
Dim oPline As AcadLWPolyline
Dim N As Variant
Dim dElev As Double
Dim Pts(3) As Double
Dim util As AcadUtility
Set util = ThisDrawing.Utility
P1 = GetPointEX
P2 = GetPointEX(P1)
dHt = ThisDrawing.Utility.GetDistance(, vbCrLf + "Type the height:")
MidP(0) = P1(0) + 0.5 * (P2(0) - P1(0))
MidP(1) = P1(1) + 0.5 * (P2(1) - P1(1))
MidP(2) = P1(2) + 0.5 * (P2(2) - P1(2))
dist = Length(P1, MidP)
MidP(2) = MidP(2) + dHt
P3 = MidP
N = NormalFromPoints(P1, P2, P3)
P1 = util.TranslateCoordinates(P1, acWorld, acOCS, False, N)
P2 = util.TranslateCoordinates(P2, acWorld, acOCS, False, N)
P3 = util.TranslateCoordinates(P3, acWorld, acOCS, False, N)
dElev = P1(2)
dBulge = Tan(dHt / dist)
Pts(0) = P1(0): Pts(1) = P1(1)
Pts(2) = P2(0): Pts(3) = P2(1)
Set oPline = ThisDrawing.ModelSpace.AddLightWeightPolyline(Pts)
oPline.SetBulge 0, -dBulge
oPline.Elevation = dElev
oPline.Normal = N
oPline.ConstantWidth = 0
End Sub
Public Function Length(Startpoint As Variant, Endpoint As Variant) As Double
Dim Stx As Double, Sty As Double, Stz As Double
Dim Enx As Double, Eny As Double, Enz As Double
Dim dX As Double, dY As Double, dZ As Double
Dim i As Integer
If IsEmpty(Startpoint) Then Err.Raise 13
i = UBound(Startpoint)
If UBound(Endpoint) = i Then
If i > 0 Then
Stx = Startpoint(0): Sty = Startpoint(1)
Enx = Endpoint(0): Eny = Endpoint(1)
dX = Stx - Enx
dY = Sty - Eny
If i = 1 Then
Length = Sqr(dX * dX + dY * dY)
Else
Stz = Startpoint(2): Enz = Endpoint(2)
dZ = Stz - Enz
Length = Sqr((dX * dX) + (dY * dY) + (dZ * dZ))
End If
Else
Exit Function
End If
Else
Exit Function
End If
End Function
Function NormalFromPoints(P0, P1, P2) As Variant
'n = u×v = (V1-V0)×(V2-V0)
Dim X1 As Double, X2 As Double
Dim Y1 As Double, Y2 As Double
Dim Z1 As Double, Z2 As Double
Dim Unit As Double
Dim x(2) As Double
Dim y(2) As Double
Dim N(2) As Double
'Get distance from zero
x(0) = P1(0) - P0(0): y(0) = P2(0) - P0(0)
x(1) = P1(1) - P0(1): y(1) = P2(1) - P0(1)
x(2) = P1(2) - P0(2): y(2) = P2(2) - P0(2)
'get CrossProduct
N(0) = x(1) * y(2) - x(2) * y(1)
N(1) = x(2) * y(0) - x(0) * y(2)
N(2) = x(0) * y(1) - x(1) * y(0)
'Convert to unit normal
Unit = Sqr(N(0) * N(0) + N(1) * N(1) + N(2) * N(2))
N(0) = N(0) / Unit: N(1) = N(1) / Unit: N(2) = N(2) / Unit
NormalFromPoints = N
End Function