明经CAD社区

 找回密码
 注册

QQ登录

只需一步,快速开始

搜索
查看: 11235|回复: 21

[事件] [飞马系列] AUTOCAD中的"愤怒的小鸟"游戏,需BOX2DX引擎支持

  [复制链接]
发表于 2013-1-28 20:19:47 | 显示全部楼层 |阅读模式
本帖最后由 qjchen 于 2013-10-20 19:28 编辑

AutoCAD版的愤怒的小鸟 代码


其实两三年前就有这个想法了,当时学flex编程的时候,找到了BOX2D库,觉得很有趣

那时只是简单测试了一下flash的box2d库,没有仔细学习。愤怒的小鸟也还没有出来。后来有了,知道它也是用了这个库,但是和box2d库的作者弄的不可开交。

由于个人比较喜欢autocad,所以比较想在cad中实现。但当时的BOX2D库还只有c++版,不大懂。这几天稍有空,随手找了几个物理引擎库,发现已经有人port到了.net版,于是重燃了此番昔日思路。花了2天时间,利用box2d引擎,撰写了如下这个多线程版本的 Autocad 版的 愤怒的小鸟。可以一边玩,一边画图。纯属自娱自乐。
此.NET引擎似乎还有一些小问题,比如圆形似乎就没有rotation特性(或者是我还没有发现),时间间隔亦宜小些,否则会出现一些侵蚀现象(当然,后期会调整过来)。

本文只提供cad部分的代码,BOX2DX的由于不是我编的,自然不能放上来
如有兴趣的,请到http://code.google.com/p/box2dx/ 处,根据其协议,相应下载和使用,此处不做讨论。
由于只是一个娱乐自玩小程序,故没有太多的容错内容,也没考虑多少种情况,大概能用而已。

测试的dwg可见附件。
使用方法:
1. 打开dwg
2. 编译代码到DLL,另外编译下载的BOX2DX得到BOX2DX.DLL,Netload这两个ball.dll
   需要注意的是,在编译用于高版本ACAD的BOX2DX.DLL的时候,需要将其编译平台设为any cpu
3. 用mybox2d命令启动,选择不可移动物体,选择可移动物体,选择可发射物体(力在此图中建议为120000)
4. 要结束这个动态过程,请键入mys结束之,也一定在关闭cad前运行此命令
// ========================================================================
  • // The following codes are writen by QJCHEN                               ;
  • // Http://qjchen.mjtd.com                                                 ;
  • // Important: Box2d Library is necessary to support this code             ;
  • // http://code.google.com/p/box2dx/                                       ;
  • // You should download it to generate Box2DX.dll first                    ;
  • //     then you could use this code                                       ;
  • // Purpose: Test angry bird in Autocad                                    ;
  • // How to use:                                                            ;
  • // 1) open the dwg in the attachment                                      ;
  • // 2) netload Box2DX and this dll (compile this code to DLL)              ;
  • // 3) command mybox2d, then select the object for fix object(circle or    ;
  • //    lwpolyline), moving object, and ejecting object (these two is block ;
  • //    reference, I have make several one, such as 1*1 box, R=0.5 circle,  ;
  • //    then use different scalefactor to insert them). Then input the force;
  • //    because the unit of these world is (N, m), so it need a big force   ;
  • //    in this jpg, the force is 120000                                    ;
  • // 4) Use mys command to stop the game                                    ;
  • // The platform: Acad2008 and after                                       ;
  • // .Net platform is considered to be a better solution for this function  ;
  • // Version: 1.0                                                           ;
  • // 2013.01.28                                                             ;
  • // Thanks to Gile's function for judging the direction of lwpolyline      ;
  • // ========================================================================
  • //
  • // Permission to use, copy, modify, and distribute this software in
  • // object code form for any purpose and without fee is hereby granted,
  • // provided that the above copyright notice appears in all copies and
  • // that both that copyright notice and the limited warranty and
  • // restricted rights notice below appear in all supporting
  • // documentation.
  • using Autodesk.AutoCAD.ApplicationServices;
  • using Autodesk.AutoCAD.DatabaseServices;
  • using Autodesk.AutoCAD.Geometry;
  • using Autodesk.AutoCAD.Runtime;
  • using Autodesk.AutoCAD.EditorInput;
  • using System;
  • using System.Collections;
  • using Box2DX.Dynamics;
  • using Box2DX.Collision;
  • using Box2DX.Common;
  • //gile's function
  • using Body = Box2DX.Dynamics.Body;
  • using aapp = Autodesk.AutoCAD.ApplicationServices.Application;
  • using sm = System.Math;
  • namespace ball
  • {
  •     public class Class1
  •     {
  •         public static ObjectIdCollection mBodyId;//能移动的所有物体的id    Moving objects IDs
  •         public static ObjectIdCollection eBodyId;//能有初速度的所有物体的id  Ejecting objects IDs
  •         public static World world;
  •         public static float timeStep = 1.0f / 60.0f;
  •         public static int velocityIterations = 8;
  •         public static int positionIterations = 1;
  •         public static Body body;
  •         public static Body[] mbody;
  •         public static Body[] ebody;
  •         static System.Windows.Forms.Timer timer2 = new System.Windows.Forms.Timer();
  •         // 停止的命令
  •         [CommandMethod("mys")]
  •         public void drawpics()
  •         {
  •             timer2.Stop();
  •         }
  •         [CommandMethod("mybox2d")]
  •         public void test()
  •         {
  •             //世界的定义,只在其中是有用的,定义在-100到100的高度范围内
  •             //World of Box2d, -100 to 100
  •             AABB worldAABB = new AABB();
  •             worldAABB.LowerBound.Set(-100.0f);
  •             worldAABB.UpperBound.Set(100.0f);
  •             Vec2 gravity = new Vec2(0.0f, -10.0f);// Define the gravity vector.
  •             bool doSleep = true;// Do we want to let bodies sleep?
  •             world = new World(worldAABB, gravity, doSleep);// Construct a world object, which will hold and simulate the rigid bodies.
  •             //--选择物体分别作为刚体和可移动物体
  •             //--Select Object for Each group
  •             SelectForFixBody();
  •             SelectForMovingBody();
  •             SelectForEjectingBody();
  •             //--设置时间 Time setting
  •             timer2.Interval = 20;//设置时间为20秒-这个和动画间隔相关
  •             timer2.Tick += new EventHandler(timer2_Tick);
  •             timer2.Start();
  •         }
  •         private static void timer2_Tick(System.Object myObject, System.EventArgs myEventArgs)
  •         {
  •             DocumentLock docLock = aapp.DocumentManager.MdiActiveDocument.LockDocument(); // Code
  •             world.Step(timeStep, velocityIterations, positionIterations);
  •             //对每一个可移动的物体进行更新 Update for moving objects
  •             int i = 0;
  •             foreach (ObjectId id in mBodyId)
  •             {
  •                 Vec2 position = mbody.GetPosition();
  •                 float angle = mbody.GetAngle();
  •                 ChangeBlockRefInsPointAndAngle(id, new Point3d(position.X, position.Y, 0), angle);
  •                 i = i + 1;
  •             }
  •             //Update for ejecting objects
  •             i = 0;
  •             foreach (ObjectId id in eBodyId)
  •             {
  •                 Vec2 position = ebody.GetPosition();
  •                 float angle = ebody.GetAngle();
  •                 ChangeBlockRefInsPointAndAngle(id, new Point3d(position.X, position.Y, 0), angle);
  •                 i = i + 1;
  •             }
  •             docLock.Dispose();
  •         }
  •         //选择刚性不动物体,(必须是封闭的多义线-即用c进行闭合的多义线),否则会出错
  •         //Select Fixed Object(Circle or closed lwpolyline)
  •         public static ArrayList SelectForFixBody()
  •         {
  •             Document doc = Application.DocumentManager.MdiActiveDocument;
  •             Database db = doc.Database;
  •             Editor ed = doc.Editor;
  •             ArrayList res = new ArrayList();
  •             using (Transaction trans = db.TransactionManager.StartTransaction())
  •             {
  •                 PromptSelectionOptions acOptSel = new PromptSelectionOptions();
  •                 acOptSel.MessageForAdding = "\n请选择不可移动物体(Please select the fixed object):";
  •                 // Create a TypedValue array to define the filter criteria
  •                 TypedValue[] acTypValAr = new TypedValue[1];
  •                 acTypValAr.SetValue(new TypedValue((int)DxfCode.Start, "LWPOLYLINE,CIRCLE"), 0);
  •                 // Assign the filter criteria to a SelectionFilter object
  •                 SelectionFilter acSelFtr = new SelectionFilter(acTypValAr);
  •                 PromptSelectionResult acSSPrompt = ed.GetSelection(acOptSel, acSelFtr);
  •                 if (acSSPrompt.Status == PromptStatus.OK)
  •                 {
  •                     SelectionSet acSSet = acSSPrompt.Value;
  •                     foreach (SelectedObject acSSObj in acSSet)
  •                     {
  •                         if (acSSObj != null)
  •                         {
  •                             Entity acEnt = trans.GetObject(acSSObj.ObjectId, OpenMode.ForWrite) as Entity;
  •                             if (acEnt != null)
  •                             {
  •                                 ObjectId ObjID = acEnt.ObjectId;
  •                                 BodyDef groundBodyDef = new BodyDef();
  •                                 Entity ent0 = (Entity)trans.GetObject(ObjID, OpenMode.ForRead, false);
  •                                 if (ent0.GetType().Name == "Circle")
  •                                 {
  •                                     Circle ent = (Circle)trans.GetObject(ObjID, OpenMode.ForRead, false);
  •                                     Point3d cen = ent.Center;
  •                                     //----定义不可移动物体,默认属性
  •                                     groundBodyDef.Position.Set((float)cen.X, (float)cen.Y);
  •                                     Body groundBody = world.CreateBody(groundBodyDef);
  •                                     CircleDef groundShapeDef = new CircleDef();
  •                                     groundShapeDef.Radius = (float)ent.Radius;
  •                                     groundBody.CreateFixture(groundShapeDef);
  •                                     res.Add(groundBody);
  •                                 }
  •                                 else if (ent0.GetType().Name == "Polyline")
  •                                 {
  •                                     Polyline ent = (Polyline)trans.GetObject(ObjID, OpenMode.ForRead, false);
  •                                     Point2d v0 = ent.GetPoint2dAt(0);
  •                                     Vec2[] plvex = GetPolylineForBox2d(ent);
  •                                     //----定义不可移动物体,默认属性
  •                                     groundBodyDef.Position.Set((float)v0.X, (float)v0.Y);
  •                                     Body groundBody = world.CreateBody(groundBodyDef);
  •                                     PolygonDef groundShapeDef = new PolygonDef();
  •                                     groundShapeDef.VertexCount = plvex.Length;
  •                                     groundShapeDef.Vertices = plvex;
  •                                     groundBody.CreateFixture(groundShapeDef);
  •                                     res.Add(groundBody);
  •                                 }
  •                             }
  •                         }
  •                     }
  •                     trans.Commit();
  •                 }
  •                 return res;
  •             }
  •         }
  •         //选择可发射物体,必须是矩形或圆形的块,否则会出错
  •         //Select Ejecting Object, Should be rectangle of circle Block
  •         public static ArrayList SelectForEjectingBody()
  •         {
  •             Document doc = Application.DocumentManager.MdiActiveDocument;
  •             Database db = doc.Database;
  •             Editor ed = doc.Editor;
  •             ArrayList res = new ArrayList();
  •             eBodyId = new ObjectIdCollection();
  •             using (Transaction trans = db.TransactionManager.StartTransaction())
  •             {
  •                 // Create a TypedValue array to define the filter criteria
  •                 TypedValue[] acTypValAr = new TypedValue[1];
  •                 acTypValAr.SetValue(new TypedValue((int)DxfCode.Start, "INSERT"), 0);
  •                 SelectionFilter acSelFtr = new SelectionFilter(acTypValAr);
  •                 PromptSelectionOptions acOptSel = new PromptSelectionOptions();
  •                 acOptSel.MessageForAdding = "\n----\n请选择可发射物体(Please select ejecting object):";
  •                 PromptSelectionResult acSSPrompt = ed.GetSelection(acOptSel, acSelFtr);
  •                 PromptStringOptions pStrOpts = new PromptStringOptions("\n输入X水平力(Input the X force):(100000)N:");
  •                 pStrOpts.AllowSpaces = true;
  •                 PromptResult pStrRes = ed.GetString(pStrOpts);
  •                 float forcex = System.Convert.ToSingle(pStrRes.StringResult);
  •                 pStrOpts = new PromptStringOptions("\n输入Y水平力(Input the Y force):(100000)N:");
  •                 pStrOpts.AllowSpaces = true;
  •                 pStrRes = ed.GetString(pStrOpts);
  •                 float forcey = System.Convert.ToSingle(pStrRes.StringResult);
  •                 Vec2 force = new Vec2(forcex, forcey);
  •                 if (acSSPrompt.Status == PromptStatus.OK)
  •                 {
  •                     SelectionSet acSSet = acSSPrompt.Value;
  •                     ebody = new Body[acSSet.Count];
  •                     int i = 0;
  •                     foreach (SelectedObject acSSObj in acSSet)
  •                     {
  •                         if (acSSObj != null)
  •                         {
  •                             Entity acEnt = trans.GetObject(acSSObj.ObjectId, OpenMode.ForWrite) as Entity;
  •                             if (acEnt != null)
  •                             {
  •                                 var blkRef = trans.GetObject(acSSObj.ObjectId, OpenMode.ForWrite, false) as BlockReference;
  •                                 float dx = (float)blkRef.ScaleFactors.X;
  •                                 float dy = (float)blkRef.ScaleFactors.Y;
  •                                 float rotation = (float)blkRef.Rotation;
  •                                 Point3d cen = blkRef.Position;
  •                                 //只考虑方形和圆形两种物体
  •                                 //-----定义可移动物体,随便定义的属性
  •                                 BodyDef BodyDef = new BodyDef();
  •                                 BodyDef.Position.Set((float)cen.X, (float)cen.Y);
  •                                 Body eBodyi = world.CreateBody(BodyDef);
  •                                 Point3d respt = GetCircleInBlockReference(acSSObj.ObjectId);
  •                                 if (respt != Point3d.Origin)
  •                                 {
  •                                     CircleDef eShapeDef = new CircleDef();
  •                                     eShapeDef.Radius = dx / 2.0f;
  •                                     eShapeDef.Density = 1.0f;// Set the box density to be non-zero, so it will be dynamic.
  •                                     eShapeDef.Restitution = 0.35f;//这个是反弹的控制(0-1)
  •                                     eShapeDef.Friction = 0.25f;// Override the default friction.
  •                                     eBodyi.CreateFixture(eShapeDef);// Add the shape to the body.
  •                                     eBodyi.SetMassFromShapes();
  •                                     eBodyi.SetAngle(rotation);
  •                                     Vec2 forceP = new Vec2((float)cen.X, (float)cen.Y);
  •                                     eBodyi.ApplyForce(force, eBodyi.GetWorldCenter());
  •                                     ebody = eBodyi;
  •                                     eBodyId.Add(acSSObj.ObjectId);
  •                                 }
  •                                 else
  •                                 {
  •                                     PolygonDef eShapeDef = new PolygonDef();
  •                                     eShapeDef.SetAsBox(dx / 2.0f, dy / 2.0f);
  •                                     eShapeDef.VertexCount = 4;
  •                                     eShapeDef.Density = 1.0f;// Set the box density to be non-zero, so it will be dynamic.
  •                                     eShapeDef.Restitution = 0.35f;//这个是反弹的控制(0-1),不知道只设置一个有没有效果
  •                                     eShapeDef.Friction = 0.25f;// Override the default friction.
  •                                     eBodyi.CreateFixture(eShapeDef);// Add the shape to the body.
  •                                     eBodyi.SetMassFromShapes();
  •                                     eBodyi.SetAngle(rotation);
  •                                     eBodyi.ApplyForce(force, eBodyi.GetWorldCenter());
  •                                     ebody = eBodyi;
  •                                     eBodyId.Add(acSSObj.ObjectId);
  •                                 }
  •                             }
  •                         }
  •                         i++;
  •                     }
  •                 }
  •                 trans.Commit();
  •             }
  •             return res;
  •         }
  •         //选择可掉下物体,必须是矩形或圆形的块,否则会出错
  •         //Select Moving Object, Should be rectangle of circle Block
  •         public static ArrayList SelectForMovingBody()
  •         {
  •             Document doc = Application.DocumentManager.MdiActiveDocument;
  •             Database db = doc.Database;
  •             Editor ed = doc.Editor;
  •             ArrayList res = new ArrayList();
  •             mBodyId = new ObjectIdCollection();
  •             using (Transaction trans = db.TransactionManager.StartTransaction())
  •             {
  •                 // Create a TypedValue array to define the filter criteria
  •                 TypedValue[] acTypValAr = new TypedValue[1];
  •                 acTypValAr.SetValue(new TypedValue((int)DxfCode.Start, "INSERT"), 0);
  •                 SelectionFilter acSelFtr = new SelectionFilter(acTypValAr);
  •                 PromptSelectionOptions acOptSel = new PromptSelectionOptions();
  •                 acOptSel.MessageForAdding = "\n----\n请选择可移动物体(Please select Moving object):";
  •                 PromptSelectionResult acSSPrompt = ed.GetSelection(acOptSel, acSelFtr);
  •                 if (acSSPrompt.Status == PromptStatus.OK)
  •                 {
  •                     SelectionSet acSSet = acSSPrompt.Value;
  •                     mbody = new Body[acSSet.Count];
  •                     int i = 0;
  •                     foreach (SelectedObject acSSObj in acSSet)
  •                     {
  •                         if (acSSObj != null)
  •                         {
  •                             Entity acEnt = trans.GetObject(acSSObj.ObjectId, OpenMode.ForWrite) as Entity;
  •                             if (acEnt != null)
  •                             {
  •                                 var blkRef = trans.GetObject(acSSObj.ObjectId, OpenMode.ForWrite, false) as BlockReference;
  •                                 float dx = (float)blkRef.ScaleFactors.X;
  •                                 float dy = (float)blkRef.ScaleFactors.Y;
  •                                 float rotation = (float)blkRef.Rotation;
  •                                 Point3d cen = blkRef.Position;
  •                                 //只考虑方形和圆形两种物体
  •                                 //-----定义可移动物体,随便定义的属性
  •                                 BodyDef BodyDef = new BodyDef();
  •                                 BodyDef.Position.Set((float)cen.X, (float)cen.Y);
  •                                 Body mBodyi = world.CreateBody(BodyDef);
  •                                 Point3d respt = GetCircleInBlockReference(acSSObj.ObjectId);
  •                                 if (respt != Point3d.Origin)
  •                                 {
  •                                     CircleDef mShapeDef = new CircleDef();
  •                                     mShapeDef.Radius = dx / 2.0f;
  •                                     mShapeDef.Density = 1.0f;// Set the box density to be non-zero, so it will be dynamic.
  •                                     mShapeDef.Restitution = 0.35f;//这个是反弹的控制(0-1),不知道只设置一个有没有效果
  •                                     mShapeDef.Friction = 0.25f;// Override the default friction.
  •                                     mBodyi.CreateFixture(mShapeDef);// Add the shape to the body.
  •                                     mBodyi.SetMassFromShapes();
  •                                     mBodyi.SetAngle(rotation);
  •                                     mbody = mBodyi;
  •                                     mBodyId.Add(acSSObj.ObjectId);
  •                                 }
  •                                 else
  •                                 {
  •                                     PolygonDef mShapeDef = new PolygonDef();
  •                                     //Vec2[] plvex = ChangeBox2Poly(dx, dy, rotation);
  •                                     mShapeDef.SetAsBox(dx / 2.0f, dy / 2.0f);
  •                                     mShapeDef.VertexCount = 4;
  •                                     //mShapeDef.Vertices = plvex;
  •                                     mShapeDef.Density = 1.0f;// Set the box density to be non-zero, so it will be dynamic.
  •                                     mShapeDef.Restitution = 0.35f;//这个是反弹的控制(0-1),不知道只设置一个有没有效果
  •                                     mShapeDef.Friction = 0.25f;// Override the default friction.
  •                                     mBodyi.CreateFixture(mShapeDef);// Add the shape to the body.
  •                                     mBodyi.SetMassFromShapes();
  •                                     mBodyi.SetAngle(rotation);
  •                                     mbody = mBodyi;
  •                                     mBodyId.Add(acSSObj.ObjectId);
  •                                 }
  •                             }
  •                         }
  •                         i++;
  •                     }
  •                 }
  •                 trans.Commit();
  •             }
  •             return res;
  •         }
  •         //改变块的插入点和方向
  •         //Change the insertion point and direction of block reference
  •         public static void ChangeBlockRefInsPointAndAngle(ObjectId BlockRefId, Point3d newposition, float angle)
  •         {
  •             Database db = HostApplicationServices.WorkingDatabase;
  •             using (Transaction tr = db.TransactionManager.StartTransaction())
  •             {
  •                 Entity ent = (Entity)tr.GetObject(BlockRefId, OpenMode.ForWrite);
  •                 var blkRef = tr.GetObject(BlockRefId, OpenMode.ForWrite, false) as BlockReference;
  •                 blkRef.Position = newposition;
  •                 blkRef.Rotation = angle;
  •                 tr.Commit();
  •                 Autodesk.AutoCAD.ApplicationServices.Application.UpdateScreen();
  •             }
  •         }
  •         // Get some circle information in a block reference
  •         public static Point3d GetCircleInBlockReference(ObjectId oId)
  •         {
  •             Document doc = Application.DocumentManager.MdiActiveDocument;
  •             Database db = doc.Database;
  •             Point3d pt = new Point3d();
  •             using (Transaction tr = db.TransactionManager.StartTransaction())
  •             {
  •                 BlockReference bref = tr.GetObject(oId, OpenMode.ForRead) as BlockReference;
  •                 BlockTableRecord btr = tr.GetObject(bref.BlockTableRecord, OpenMode.ForRead) as BlockTableRecord;
  •                 foreach (ObjectId id in btr)
  •                 {
  •                     Circle cir = tr.GetObject(id, OpenMode.ForRead) as Circle;
  •                     if (cir != null)
  •                     {
  •                         pt = cir.Center.TransformBy(bref.BlockTransform);
  •                     }
  •                 }
  •             }
  •             return pt;
  •         }
  •         //Get lwPolyline information for drawing fixed object
  •         public static Vec2[] GetPolylineForBox2d(Polyline pl)
  •         {
  •             Point2d P0 = pl.GetPoint2dAt(0);
  •             Vec2[] res = new Vec2[pl.NumberOfVertices];
  •             Point3d P03d = new Point3d(pl.GetPoint2dAt(0).X, pl.GetPoint2dAt(0).Y, 0);
  •             Point3d P13d = new Point3d(pl.GetPoint2dAt(1).X, pl.GetPoint2dAt(1).Y, 0);
  •             Point3d P23d = new Point3d(pl.GetPoint2dAt(2).X, pl.GetPoint2dAt(2).Y, 0);
  •             Vector3d normal = new Vector3d(0, 0, 1);
  •             int judge = Clockwise(P03d, P13d, P23d, normal);
  •             Point2d Pti = new Point2d();
  •             for (int i = 0; i < pl.NumberOfVertices; i++)
  •             {
  •                 if (judge == -1)
  •                 { Pti = pl.GetPoint2dAt(i); }
  •                 else
  •                 { Pti = pl.GetPoint2dAt(pl.NumberOfVertices - 1 - i); }
  •                 Vec2 resi = new Vec2((float)(Pti.X - P0.X), (float)(Pti.Y - P0.Y));
  •                 res = resi;
  •             }
  •             return res;
  •         }
  •         //gile's function http://www.theswamp.org/index.php?topic=30428.msg360469#msg360469
  •         // Clockwise method, returns 1 if p1, p2, p3 are clockwise,
  •         // 0 if they're aligned, -1 if they're counterclockwise
  •         public static int Clockwise(Point3d p1, Point3d p2, Point3d p3, Vector3d normal)
  •         {
  •             const double pi = 3.141592653589793;
  •             Vector3d v1 = p1.GetVectorTo(p2);
  •             Vector3d v2 = p1.GetVectorTo(p3);
  •             double angle = v1.GetAngleTo(v2, normal);
  •             if (angle == 0.0 || angle == pi)
  •                 return 0;
  •             else
  •             {
  •                 if (v1.GetAngleTo(v2, normal) < pi)
  •                     return -1;
  •                 else
  •                     return 1;
  •             }
  •         }
  •     }
  • }

  • 本帖子中包含更多资源

    您需要 登录 才可以下载或查看,没有账号?注册

    x

    评分

    参与人数 1明经币 +2 收起 理由
    仲文玉 + 2 很给力!

    查看全部评分

    发表于 2013-1-28 20:45:04 | 显示全部楼层
    支持qjchen
    回复 支持 0 反对 1

    使用道具 举报

    发表于 2022-5-20 10:51:35 | 显示全部楼层
    相当棒的试验  受启发
    发表于 2022-9-3 21:22:23 | 显示全部楼层
    感谢分享,佩服,太有才了
    发表于 2013-1-28 22:59:29 | 显示全部楼层
    本帖最后由 chpmould 于 2013-1-28 23:00 编辑

    支持一下,写的很好
    发表于 2013-1-29 13:04:14 | 显示全部楼层
    陈老师~!赞啊~
    发表于 2013-1-29 13:46:40 | 显示全部楼层
    ~~佩服~~
    发表于 2013-1-29 15:04:11 | 显示全部楼层
    这个厉害,不过玩起来应该很费劲!
    发表于 2013-1-30 17:23:47 | 显示全部楼层
    ~老师相当厉害!~
    发表于 2013-2-1 08:45:32 | 显示全部楼层
    神技术
    发表于 2013-2-4 18:03:43 | 显示全部楼层
    太有才了。
    发表于 2013-2-8 23:34:05 | 显示全部楼层
    强人。。。。。
    您需要登录后才可以回帖 登录 | 注册

    本版积分规则

    小黑屋|手机版|CAD论坛|CAD教程|CAD下载|联系我们|关于明经|明经通道 ( 粤ICP备05003914号 )  
    ©2000-2023 明经通道 版权所有 本站代码,在未取得本站及作者授权的情况下,不得用于商业用途

    GMT+8, 2024-11-25 02:43 , Processed in 0.222683 second(s), 30 queries , Gzip On.

    Powered by Discuz! X3.4

    Copyright © 2001-2021, Tencent Cloud.

    快速回复 返回顶部 返回列表