Author Topic: object to matrix  (Read 7204 times)

0 Members and 1 Guest are viewing this topic.

Coder

  • Swamp Rat
  • Posts: 827
object to matrix
« on: June 09, 2014, 09:33:00 AM »
Hello guys .

Is there a way to get any object the matrix list ? for example when we use the nentselp function on some objects ?

Code: [Select]
(setq obj (nentselp))
will get something like this .

Quote
(<Entity name: 7efc75a0> (2447.52 783.137 0.0) ((1.0 0.0 0.0 2447.24) (0.0 1.0 0.0 783.079) (0.0 0.0 1.0 0.0) (0.0 0.0 0.0 1.0)) (<Entity name: 7efc7638>))

for example , how to get the matrix values with ssget or entsel function ?

Code: [Select]
(setq obj (car (entsel "\n Select object :")))

many thanks in advance .  :-)
« Last Edit: June 09, 2014, 09:44:29 AM by Coder »

reltro

  • Guest
Re: object to matrix
« Reply #1 on: June 09, 2014, 02:50:20 PM »
Hello guys .

Is there a way to get any object the matrix list ? for example when we use the nentselp function on some objects ?

Code: [Select]
(setq obj (nentselp))
will get something like this .

Quote
(<Entity name: 7efc75a0> (2447.52 783.137 0.0) ((1.0 0.0 0.0 2447.24) (0.0 1.0 0.0 783.079) (0.0 0.0 1.0 0.0) (0.0 0.0 0.0 1.0)) (<Entity name: 7efc7638>))

for example , how to get the matrix values with ssget or entsel function ?

Code: [Select]
(setq obj (car (entsel "\n Select object :")))

many thanks in advance .  :-)

Hey Coder...

I'm not sure how (nentselp) works or calculates the matrix...
When I read ur question the "Abritrary Axis Algorithm" come up in mind...
Its the way acad calculates the groupCode 210...

Im not sure if its the right way... Just have a look...
Code - Auto/Visual Lisp: [Select]
  1. ;;;-------------------------------------------------------------------------------------------
  2. ;;;                    ___...:::{Abritrary Axis Algorithm}:::...___
  3. ;;;
  4. ;;; http://www.autodesk.com/techpubs/autocad/acadr14/dxf/arbitrary_axis_algorithm_al_u05_c.htm
  5. (setq AAA
  6.         (lambda (P1 P2 P3 / cross Ax Ay Az)
  7.                 (setq cross
  8.                         (lambda (V1 V2 / )
  9.                                 (    (lambda (nV / o len)
  10.                                                 (setq len (sqrt (apply '+ (foreach k nV (setq o (cons (expt k 2) o))))))
  11.                                                 (mapcar '(lambda (a / ) (/ a len)) nV)
  12.                                         )
  13.                                         (mapcar
  14.                                                 '(lambda (n / ) (- (* (nth (car n) V1) (nth (cadr n) V2)) (* (nth (cadr n) V1) (nth (car n) V2))))
  15.                                                 '((1 2) (2 0) (0 1))
  16.                                         )
  17.                                 )
  18.                         )
  19.                 )
  20.                 (setq    Az    (cross (mapcar '- P1 P2) (mapcar '- P1 P3))
  21.                                 Ax    (if (and (< (abs (car Az)) (/ 1 64.0)) (< (abs (cadr Az)) (/ 1 64.0)))
  22.                                                 (cross '(0 1 0) Az)
  23.                                                 (cross '(0 0 1) Az)
  24.                                         )
  25.                                 Ay    (cross Az Ax)
  26.                 )
  27.                 (list Ax Ay Az)
  28.         )
  29. )
  30. ;;;-------------------------------------------------------------------------------------------
  31.  
  32.  

greets reltro

Coder

  • Swamp Rat
  • Posts: 827
Re: object to matrix
« Reply #2 on: June 09, 2014, 03:14:37 PM »
Thank you so much reltro for your help .

Can you please tell me how to call this function ?

Thank you  :-)

reltro

  • Guest
Re: object to matrix
« Reply #3 on: June 09, 2014, 04:10:29 PM »
Thank you so much reltro for your help .

Can you please tell me how to call this function ?

Thank you  :-)

I don't tought it would be usefull...
Code: [Select]
(AAA (getpoint) (getpoint) (getpoint)

roy_043

  • Water Moccasin
  • Posts: 1895
  • BricsCAD 18
Re: object to matrix
« Reply #4 on: June 09, 2014, 06:56:58 PM »
Let's not forget the (trans) function...

Coder

  • Swamp Rat
  • Posts: 827
Re: object to matrix
« Reply #5 on: June 10, 2014, 01:04:02 AM »
Thank you so much reltro for your help .

Can you please tell me how to call this function ?

Thank you  :-)

I don't tought it would be usefull...
Code: [Select]
(AAA (getpoint) (getpoint) (getpoint)

Thank you reltro for your help .

But i need to run the function on entity name and not through getting points .  :oops:

Can you please modify the code ?
Many many thanks .

Coder

  • Swamp Rat
  • Posts: 827
Re: object to matrix
« Reply #6 on: June 10, 2014, 01:06:44 AM »
Let's not forget the (trans) function...

Hi roy .
Can you give me example if you have time to ?

Many thanks  :-)

gile

  • Gator
  • Posts: 2520
  • Marseille, France
Re: object to matrix
« Reply #7 on: June 10, 2014, 01:53:24 AM »
Hi,

I think you'd rather explain what you want to achieve, because it looks like you're going a wrong route.

Only block reference have such transformation matrices.
When you run nentsel(p) on an entity, you'll get this kind of matrix only in case the entity is a block component. The matrix reflects the block reference transformations.
Speaking English as a French Frog

Coder

  • Swamp Rat
  • Posts: 827
Re: object to matrix
« Reply #8 on: June 10, 2014, 02:20:33 AM »
Hi,

I think you'd rather explain what you want to achieve, because it looks like you're going a wrong route.

Only block reference have such transformation matrices.
When you run nentsel(p) on an entity, you'll get this kind of matrix only in case the entity is a block component. The matrix reflects the block reference transformations.

Thank you gile for your kind reply .

yes I want to get the matrix for Circle or LWpolyline in block to be able to create a copy of it and transfer it to current space ( model ) .

Code: [Select]
  (if (setq sel (ssget "_:L" '((0 . "INSERT"))))
    (repeat (setq num (sslength sel))
      (setq ent (ssname sel (setq num (1- num))))
      (setq tbl-obj (tblobjname "BLOCK" (cdr (assoc 2 (entget ent)))))
     
      (while (setq tbl-obj (entnext tbl-obj))
        (if (or (equal (cdr (assoc 0 (entget tbl-obj))) "CIRCLE")
                (equal (cdr (assoc 0 (entget tbl-obj))) "LWPOLYLINE")
                )
          (progn
            (setq mat (.....)) ;; <<<<<<<<<<<<<<<<<<<<
            (setq obj (entmakex (entget (car ent))))
            (vla-transformby (vlax-ename->vla-object obj) (vlax-tmatrix (caddr mat)))
            )
          )
        )
      )
    )
                   
                   

reltro

  • Guest
Re: object to matrix
« Reply #9 on: June 10, 2014, 03:46:27 AM »
Hey Coder...
Try this, calculates the Matrix for a BlockRef... I did not tested it carefully but in this tests I did it calculates the same transformation-matrix as nentselp...

Code - Auto/Visual Lisp: [Select]
  1. (defun TMatrix (BlockRef / TransformationMatrix BlockRef)
  2.     ;;;    ****
  3.     ;;;    Author:    Reltro
  4.     ;;;    ****
  5.     (setq TransformationMatrix
  6.         (lambda (P1 P2 P3 / AAA tMatrix Rotation mxm)
  7.             ;;;-------------------------------------------------------------------------------------------
  8.             ;;;                    ___...:::{Abritrary Axis Algorithm}:::...___
  9.             ;;;
  10.             ;;; http://www.autodesk.com/techpubs/autocad/acadr14/dxf/arbitrary_axis_algorithm_al_u05_c.htm
  11.             (setq AAA
  12.                 (lambda (P1 P2 P3 / cross Ax Ay Az)
  13.                     (setq cross
  14.                         (lambda (V1 V2 / )
  15.                             (    (lambda (nV / o len)
  16.                                     (setq len (sqrt (apply '+ (foreach k nV (setq o (cons (expt k 2) o))))))
  17.                                     (mapcar '(lambda (a / ) (/ a len)) nV)
  18.                                 )
  19.                                 (mapcar
  20.                                     '(lambda (n / ) (- (* (nth (car n) V1) (nth (cadr n) V2)) (* (nth (cadr n) V1) (nth (car n) V2))))
  21.                                     '((1 2) (2 0) (0 1))
  22.                                 )
  23.                             )
  24.                         )
  25.                     )
  26.                     (setq    Az    (cross (mapcar '- P1 P2) (mapcar '- P1 P3))
  27.                             Ax    (if (and (< (abs (car Az)) (/ 1 64.0)) (< (abs (cadr Az)) (/ 1 64.0)))
  28.                                     (cross '(0 1 0) Az)
  29.                                     (cross '(0 0 1) Az)
  30.                                 )
  31.                             Ay    (cross Az Ax)
  32.                     )
  33.                     (list Ax Ay Az)
  34.                 )
  35.             )
  36.             ;;;-------------------------------------------------------------------------------------------
  37.  
  38.  
  39.             ;;;-------------------------------------------------------------------------------------------
  40.             (setq   mxm         (lambda (m v) (mapcar '(lambda (r) (apply '+ (mapcar '* r v))) m))
  41.                     Rotation    (lambda (V ang / m+m mxs vxs)
  42.                                     ;;; >>>>>>>>>
  43.                                     ;;; Lee Mac
  44.                                     ;;; http://www.lee-mac.com/matrixtransformationfunctions.html
  45.                                     (setq m+m   (lambda (m n) (mapcar '(lambda (r s) (mapcar '+ r s)) m n))
  46.                                              mxs    (lambda (m s) (mapcar '(lambda (r) (mapcar '(lambda (n) (* n s)) r)) m))
  47.                                              vxs     (lambda (v s) (mapcar '(lambda (n) (* n s)) v))
  48.                                     )
  49.  
  50.                                     (m+m
  51.                                         (list
  52.                                             (list (cos ang) 0. 0.)
  53.                                             (list 0. (cos ang) 0.)
  54.                                             (list 0. 0. (cos ang))
  55.                                         )
  56.                                         (m+m
  57.                                             (mxs
  58.                                                 (list
  59.                                                     (list 0. (- (nth 2 V)) (nth 1 V))
  60.                                                     (list (nth 2 V) 0. (- (nth 0 V)))
  61.                                                     (list (- (nth 1 V)) (nth 0 V) 0.)
  62.                                                 )
  63.                                                 (sin ang)
  64.                                             )
  65.                                             (mxs (mapcar '(lambda (e) (vxs V e)) V) (- 1. (cos ang)))
  66.                                         )
  67.                                     )
  68.                                     ;;; <<<<<<<<<
  69.                                 )
  70.             )
  71.             ;;;-------------------------------------------------------------------------------------------
  72.             (setq tMatrix (AAA P1 P2 P3))
  73.  
  74.             (append
  75.                 (mapcar
  76.                     '(lambda (v o / ) (append (mxm tMatrix v) (list o)))
  77.                     (Rotation
  78.                         (nth 2 tMatrix)
  79.                         (angle (mxm tMatrix P1) (mxm tMatrix P2))
  80.                     )
  81.                     P1
  82.                 )
  83.                 (list '(0 0 0 1))
  84.             )
  85.         )
  86.     )
  87.    
  88.     (defun BCS2WCS (BlockRef pointlist / ent inspkt ang)
  89.         (setq ent (entget BlockRef))
  90.         (setq inspkt (cdr (assoc 10 ent)))
  91.         (setq ang (cdr (assoc 50 ent)))
  92.         (mapcar
  93.             '(lambda (Pt /)
  94.                 (trans
  95.                     (mapcar
  96.                         '+
  97.                         (polar
  98.                             '(0 0 0)
  99.                             (+ ang (angle '(0 0 0) Pt))
  100.                             (distance '(0 0 0) Pt)
  101.                         )
  102.                         inspkt
  103.                     )
  104.                     BlockRef
  105.                     0
  106.                 )
  107.             )
  108.             pointlist
  109.         )
  110.     )
  111.    
  112.     (apply
  113.         '(lambda (P1 P2 P3 / )
  114.             (TransformationMatrix P1 P2 P3)
  115.         )
  116.         (BCS2WCS BlockRef '((0 0 0) (1 0 0) (1 1 0)))
  117.     )
  118. )

Code - Auto/Visual Lisp: [Select]
  1. (TMatrix (car (entsel))) ;Select a BlockReferene


reltro

gile

  • Gator
  • Posts: 2520
  • Marseille, France
Re: object to matrix
« Reply #10 on: June 10, 2014, 04:20:59 AM »
here's a way:
Code - Auto/Visual Lisp: [Select]
  1. ;; gc:EnameMatrix (gile)
  2. ;; Returns the transformation matrix of a block reference,
  3. ;; the same as the one returnd by (caddr (nentselp)).
  4. ;;
  5. ;; Argument
  6. ;; ename : entity name of the block reference
  7. (defun gc:EnameMatrix (ename / trp mxv mxm elst ang norm mat)
  8.  
  9.   ;; TRP
  10. ;; Transpose a matrix -Doug Wilson-
  11. (defun trp (m) (apply 'mapcar (cons 'list m)))
  12.  
  13. ;; MXV
  14. ;; Apply a transformation matrix to a vector -Vladimir Nesterovsky-
  15. (defun mxv (m v)
  16.   (mapcar (function (lambda (r) (apply '+ (mapcar '* r v)))) m)
  17. )
  18.  
  19. ;; MXM
  20. ;; Multiply two matrices -Vladimir Nesterovsky-
  21. (defun mxm (m q)
  22.   (mapcar (function (lambda (r) (mxv (trp q) r))) m)
  23. )
  24.  
  25.   ;; Main
  26.   (setq elst (entget ename)
  27.         ang  (cdr (assoc 50 elst))
  28.         norm (cdr (assoc 210 elst))
  29.   )
  30.   (append
  31.     (mapcar
  32.       (function
  33.         (lambda (v1 v2)
  34.           (append v1 (list v2))
  35.         )
  36.       )
  37.       (setq mat
  38.              (mxm
  39.                (mapcar (function (lambda (v) (trans v 0 norm T)))
  40.                        '((1. 0. 0.) (0. 1. 0.) (0. 0. 1.))
  41.                )
  42.                (mxm
  43.                  (list (list (cos ang) (- (sin ang)) 0.)
  44.                        (list (sin ang) (cos ang) 0.)
  45.                        '(0. 0. 1.)
  46.                  )
  47.                  (list (list (cdr (assoc 41 elst)) 0. 0.)
  48.                        (list 0. (cdr (assoc 42 elst)) 0.)
  49.                        (list 0. 0. (cdr (assoc 43 elst)))
  50.                  )
  51.                )
  52.              )
  53.       )
  54.       (mapcar
  55.         '-
  56.         (trans (cdr (assoc 10 elst)) norm 0)
  57.         (mxv mat
  58.              (cdr (assoc 10 (tblsearch "BLOCK" (cdr (assoc 2 elst)))))
  59.         )
  60.       )
  61.     )
  62.     '((0. 0. 0. 1.))
  63.   )
  64. )

<EDIT: see reply #12>
About your code, using entmake to copy the entity, adds the copy to the same owner (here, the block definition). To copy objects form an owner to another (here, the model space), you have to use vla-CopyObjects.
You'd have to take care the block reference is uniformly scaled, if not, vla-TransformBy will raise an error.

Test command:
Code - Auto/Visual Lisp: [Select]
  1. (defun c:test (/ butlast uniformp ms sel num ent mat ent lst)
  2.   (or *acad* (setq *acad* (vlax-get-acad-object)))
  3.   (or *acdoc* (setq *acdoc* (vla-get-ActiveDocument *acad*)))
  4.   (or *blocks* (setq *blocks* (vla-get-Blocks *acdoc*)))
  5.  
  6.   ;; butlast
  7.   ;; Return the list but last item
  8.   (defun butlast (l) (reverse (cdr (reverse l))))
  9.  
  10.   ;; uniformp
  11.   ;; Evaluate if a 4x4 transformation matrix is uniformly scaled
  12.   (defun uniformp (m)
  13.     (setq m (butlast (mapcar 'butlast m)))
  14.     (vl-every
  15.       (function
  16.         (lambda (v)
  17.           (equal (distance '(0. 0. 0.) (car m))
  18.                  (distance '(0. 0. 0.) v)
  19.                  1e-12
  20.           )
  21.         )
  22.       )
  23.       m
  24.     )
  25.   )
  26.  
  27.   ;; Main
  28.   (setq ms (vla-get-ModelSpace *acdoc*))
  29.   (if (setq sel (ssget "_:L" '((0 . "INSERT"))))
  30.     (repeat (setq num (sslength sel))
  31.       (setq mat (gc:EnameMatrix (setq ent (ssname sel (setq num (1- num))))))
  32.       (if (uniformp mat)
  33.         (progn
  34.           (setq lst nil)
  35.           (vlax-for o (vla-Item *blocks* (cdr (assoc 2 (entget ent))))
  36.             (if (wcmatch (vla-get-ObjectName o) "AcDbCircle,AcDbPolyline")
  37.               (setq lst (cons o lst))
  38.             )
  39.           )
  40.           (foreach o (vlax-invoke *acdoc* 'CopyObjects lst ms)
  41.             (vla-transformby o (vlax-tmatrix mat))
  42.           )
  43.         )
  44.       )
  45.     )
  46.   )
  47.   (princ)
  48. )
« Last Edit: June 10, 2014, 05:16:27 AM by gile »
Speaking English as a French Frog

roy_043

  • Water Moccasin
  • Posts: 1895
  • BricsCAD 18
Re: object to matrix
« Reply #11 on: June 10, 2014, 04:55:41 AM »
My attempt (not as sophisticated as gile's code):
Code: [Select]
; Get a 4X4 nentselp or 'tmatrix' from an insert.
(defun c:test1 ( / ang elist ename scaleX scaleY scaleZ)
  (setq ename (car (entsel))) ; Ename of insert.
  (setq elist (entget ename))
  (setq ang (cdr (assoc 50 elist)))
  (setq scaleX (cdr (assoc 41 elist)))
  (setq scaleY (cdr (assoc 42 elist)))
  (setq scaleZ (cdr (assoc 43 elist)))
  (KGA_Geom_MatrixMake
    (mapcar '* (trans (list (cos ang) (sin ang) 0.0) ename 0 T)     (list scaleX scaleX scaleX)) ; XVector.
    (mapcar '* (trans (list (- (sin ang)) (cos ang) 0.0) ename 0 T) (list scaleY scaleY scaleY)) ; YVector.
    (mapcar '* (trans '(0.0 0.0 1.0) ename 0 T)                     (list scaleZ scaleZ scaleZ)) ; ZVector.
    (vlax-get (vlax-ename->vla-object ename) 'insertionpoint)
  )
)

; Get a nentsel matrix from an insert.
(defun c:test2 ( / ang elist ename scaleX scaleY scaleZ)
  (setq ename (car (entsel))) ; Ename of insert.
  (setq elist (entget ename))
  (setq ang (cdr (assoc 50 elist)))
  (setq scaleX (cdr (assoc 41 elist)))
  (setq scaleY (cdr (assoc 42 elist)))
  (setq scaleZ (cdr (assoc 43 elist)))
  (list
    (mapcar '* (trans (list (cos ang) (sin ang) 0.0) ename 0 T)     (list scaleX scaleX scaleX)) ; XVector.
    (mapcar '* (trans (list (- (sin ang)) (cos ang) 0.0) ename 0 T) (list scaleY scaleY scaleY)) ; YVector.
    (mapcar '* (trans '(0.0 0.0 1.0) ename 0 T)                     (list scaleZ scaleZ scaleZ)) ; ZVector.
    (vlax-get (vlax-ename->vla-object ename) 'insertionpoint)
  )
)

;;; ======================================================================
;;; Lib function: KGA_Geom_MatrixMake (20120201)
;;; Purpose:      Get a matrix from three vectors and an origin.
;;; Arguments:    xVector - x vector
;;;               yVector - y vector
;;;               zVector - z vector
;;;               origin  - origin
;;; Return value: A matrix. See Matrix Theory.
;;; Examples:     None
;;; ======================================================================
(defun KGA_Geom_MatrixMake (xVector yVector zVector origin / lst)
  (setq lst (list xVector yVector zVector origin))
  (append
    (mapcar
      '(lambda (a) (mapcar a lst))
      '(car cadr caddr)
    )
    '((0.0 0.0 0.0 1.0))
  )
)
Code: [Select]
;;; ======================================================================
;;; Matrix theory:
;;;
;;; A 4X4 matrix represents a coordinate system:
;;; (
;;;   (Xx  Yx  Zx  Ox )
;;;   (Xy  Yy  Zy  Oy )
;;;   (Xz  Yz  Zz  Oz )
;;;   (0.0 0.0 0.0 1.0) ; this row is not used!
;;; )
;;; X = X-axis vector
;;;       Xx = x-component of X-axis vector
;;;       Xy = y-component of X-axis vector
;;;       Xz = z-component of X-axis vector
;;; Y = Y-axis vector
;;;       idem
;;; Z = Z-axis vector
;;;       idem
;;; O = origin
;;;       idem
;;; The vectors don't have to be unit vectors. For instance in a matrix
;;; produced by using nentselp on an entity in an insert, they will
;;; reflect the block's scaling.
;;;
;;; Note:
;;; Whereas nentselp uses this standard matrix type, nentsel uses this
;;; matrix type instead:
;;; (
;;;   (Xx  Xy  Xz)
;;;   (Yx  Yy  Yz)
;;;   (Zx  Zy  Zz)
;;;   (Ox  Oy  Oz)
;;; )
;;; ======================================================================

roy_043

  • Water Moccasin
  • Posts: 1895
  • BricsCAD 18
Re: object to matrix
« Reply #12 on: June 10, 2014, 05:00:55 AM »
using entmake to copy the entity, adds the copy to the same owner (here, the block definition).
This is not correct. The entity is added to the active space.

gile

  • Gator
  • Posts: 2520
  • Marseille, France
Re: object to matrix
« Reply #13 on: June 10, 2014, 05:18:21 AM »
Thanks roy_043.
I misinterpreted an error during my tests.
Speaking English as a French Frog

Coder

  • Swamp Rat
  • Posts: 827
Re: object to matrix
« Reply #14 on: June 10, 2014, 07:12:37 AM »
reltro

Thank you so much reltro for your help  :-)

Your codes after selecting a block give a list of matrix values , does that mean we can use these values with any entity name in the same block  to transfer to model space for example ?

gile

Your codes is fantastic and the same I wanted , many many thanks to you .  :-)

roy_043

I tried your codes but nothing happened , maybe I missed something or did not use it should be . sorry  :oops:

Many thanks to you for your help .