I think you need to make lines form the points with z=0, offset them, find the intersections then put the original z back in. [CommandMethod("rw")]
public static void OffsetP3d()
{
Document doc = acadApp.DocumentManager.MdiActiveDocument;
Editor ed = doc.Editor;
Database db = doc.Database;
PromptEntityOptions peo = new PromptEntityOptions("P");
peo.SetRejectMessage("3dp");
peo.AddAllowedClass(typeof(Polyline3d),true);
PromptEntityResult per = ed.GetEntity(peo);
if (per.Status != PromptStatus.OK) return;
using (Transaction tr = db.TransactionManager.StartTransaction())
{
Polyline3d p3d = tr.GetObject(per.ObjectId, OpenMode.ForWrite) as Polyline3d;
BlockTableRecord space = tr.GetObject(db.CurrentSpaceId, OpenMode.ForWrite) as BlockTableRecord;
Point3d p1=Point3d.Origin;
int cnt = 0;
Line l1=new Line();
Line line=new Line();
Polyline3d P3dOffset = new Polyline3d();
space.AppendEntity(P3dOffset);
tr.AddNewlyCreatedDBObject(P3dOffset, true);
double z = 0;
foreach(ObjectId id in p3d)
{
PolylineVertex3d v = tr.GetObject(id, OpenMode.ForRead) as PolylineVertex3d;
if (cnt == 0)
{
p1 =new Point3d( v.Position.X,v.Position.Y,0);
cnt++;
continue;
}
Point3d p2 = new Point3d(v.Position.X, v.Position.Y, 0);
z = v.Position.Z;
Line l=new Line(p1,p2);
line = (Line)l.GetOffsetCurvesGivenPlaneNormal(Vector3d.ZAxis, 1)[0];
p1 = p2;
if (cnt == 1)
{
P3dOffset.AppendVertex(new PolylineVertex3d
(new Point3d(line.StartPoint.X, line.StartPoint.Y, z)));
}
if(cnt>1)
{
Point3dCollection pts=new Point3dCollection();
l1.IntersectWith(line, Intersect.ExtendBoth, pts, 1,0);
if (pts.Count==0) continue;
Point3d p = pts[0];
P3dOffset.AppendVertex(new PolylineVertex3d(new Point3d(p.X,p.Y,z)));
}
l1 = line;
cnt++;
}
P3dOffset.AppendVertex(new PolylineVertex3d(new Point3d(line.EndPoint.X, line.EndPoint.Y, z)));
tr.Commit();
}
}