luiscarneirorm Posted September 15, 2011 Share Posted September 15, 2011 Hi. I am trying to develop an application to simplify my work, and I need to do the following: I need to divide the elements found in a particular layer (base), for various layers (base1, base2 ...), each layer can have only objects within a given area. two drawings below show, the first is the original, the second is what I intend to get. ex1.dxf ex2.dxf in this example I have divided the drawing with a reference area of 200 * 200, but this value is supposed to be variable ... if there is any object that does not fit in the area of reference it should be changed to the layer base_too_large I have in my head about the idea of how I do it, but transpose it to the lisp is that it is more complicated ... Excuse the English (google translate:oops:) Quote Link to comment Share on other sites More sharing options...
BIGAL Posted September 16, 2011 Share Posted September 16, 2011 Look up help for SSGET "C" ie pick all objects that are crossing box and then do something with them like change layer. Quote Link to comment Share on other sites More sharing options...
pBe Posted September 16, 2011 Share Posted September 16, 2011 (edited) Sample (defun c:test () (vl-load-com) (if (not BArea)(setq BArea 100.00)) (setq BArea (cond ((getreal (strcat "\nEnter Base Area: <" (rtos BArea 2 2) ">: "))) (BArea))) (setq LayerBase (getstring "\nEnter Layer Name: ")) (setq objs (ssget '((0 . "LWPOLYLINE,CIRCLE,HATCH")))) (repeat (sslength objs) (if (> (vla-get-area (vlax-ename->vla-object (setq ent (ssname objs 0)))) BArea) (entmod (subst (cons 8 LayerBase) (assoc 8 (setq ent (entget ent))) ent)) ) (ssdel (ssname objs 0) objs) ) ) Problems i see with this approach is if you want to split them based on their areas in one go, you need to pass two values as arguments each time you run the code. a MAX and a MIN (fuzz) probably using a list and also mind the sequence. Otherwise run the routine starting with small areas first then big ones. Edited September 16, 2011 by pBe Quote Link to comment Share on other sites More sharing options...
luiscarneirorm Posted September 16, 2011 Author Share Posted September 16, 2011 I think not myself clear, What I mean is: I have all the entities in a layer (base), then beginning to scan the layer from the bottom left corner. when you find the first entity, create a window of 200 * 200 for example, and all entities that are completely within this window are sent to a new layer (base_1), then keep doing this scan and find another entity then again the previous step. is what I intend to keep the layers separate entities in the area with maximum of 200 * 200, and leave only the original layer entities that do not fit this area. sorry if I am doing to understand:oops: Quote Link to comment Share on other sites More sharing options...
pBe Posted September 16, 2011 Share Posted September 16, 2011 Oh.. i see now.. My bad Quote Link to comment Share on other sites More sharing options...
luiscarneirorm Posted September 20, 2011 Author Share Posted September 20, 2011 Can someone help me??? Quote Link to comment Share on other sites More sharing options...
pBe Posted September 21, 2011 Share Posted September 21, 2011 I think not myself clear,What I mean is: I have all the entities in a layer (base), then beginning to scan the layer from the bottom left corner. when you find the first entity, create a window of 200 * 200 for example, and all entities that are completely within this window are sent to a new layer (base_1), then keep doing this scan and find another entity then again the previous step. is what I intend to keep the layers separate entities in the area with maximum of 200 * 200, and leave only the original layer entities that do not fit this area. Now I think i understand what you want to do. So youre saying entities inside a 200x2000 window will be one layer? then do the same for the next window of the same size to another layer. and other entites outside of those boundaries will be named base_too_large Starting from an user input point as the lower left corner. bottom row first left to right, then the next row on top of that left to right? and. YES, someone here can and will help you EDIT: the windows size, is it always a square? Quote Link to comment Share on other sites More sharing options...
pBe Posted September 21, 2011 Share Posted September 21, 2011 (edited) Here's a draft: (defun c:test (/ sp osp cmt Boxobj lyn lnm lylst) [color=olive] (setq sp '(0.0 0.0))[/color] (setq osp sp [color=olive] wp sp[/color] cnt 1 ) [color=blue] (if (not WdwSize)[/color] [color=blue] (setq WdwSize 200.00))[/color] [color=blue] (setq WdwSize (cond[/color] [color=blue] ((getreal[/color] [color=blue] (strcat "\nEnter Distance <"[/color] [color=blue] (rtos WdwSize 2 2)[/color] [color=blue] ">: ")))[/color] [color=blue] (WdwSize)))[/color] (while (if (null (setq BoxObj (ssget [color=blue]"_C"[/color] sp (setq ep (polar sp 0.785398163 (* WdwSize 1.412) ) ) '((0 . "LWPOLYLINE,CIRCLE")) ) ) ) (progn (if (setq BoxObj (ssget [color=blue]"_C"[/color] (setq sp (polar osp 1.57079633 WdwSize)) (polar sp 0.785398163 (* WdwSize 1.412)) '((0 . "LWPOLYLINE,CIRCLE")) ) osp sp ) BoxObj (setq BoxObj nil) ) ) BoxObj ) (repeat (sslength BoxObj) (setq ent (entget (ssname BoxObj 0))) (entmod (subst (cons 8 (setq lnm (strcat "Base_" (itoa cnt)))) (assoc 8 ent) ent ) ) (if (not (member lnm lylst)) (progn (setq lylst (cons lnm lylst) lyn (entget (tblobjname "LAYER" lnm))) (entmod (subst (cons 62 cnt)(assoc 62 lyn) lyn)))) (setq BoxObj (ssdel (ssname BoxObj 0) BoxObj)) ) (setq sp (polar sp 0 WdwSize) cnt (1+ cnt) ) ) (princ) ) Entities highlighted at the end of the routine are considered "outsiders" and havent yet decided what to do with it CODE UPDATED Edited September 22, 2011 by pBe Update for No startpoint / proceed prompt Quote Link to comment Share on other sites More sharing options...
luiscarneirorm Posted September 21, 2011 Author Share Posted September 21, 2011 Thank you, so it's something like what I need. Yes, the window is always a square. res1 the file is the result using its function. res2 the file is the result I was expecting, there is an entity that was not placed in the new layers and should have been. and I also hoped it was not necessary to select the first point, but it was detected automatically, but if not possible will not be the biggest problem. Thank you in advance for your help res1.dxf res2.dxf Quote Link to comment Share on other sites More sharing options...
pBe Posted September 21, 2011 Share Posted September 21, 2011 (edited) What value did you input for window size? Draw a square from 0,0 with the window size you just entered. it had to be inisde that window . i drew a square on your sample file and the object on the left upper box is an "outsider" on the third quadrant (see attached) BTW do you want to be prompted for the "Proceed Next Row" input? we can lose that if you want. we can always start at 0,0,0 if thats what you need EDIT: POSTED CODE updated Edited September 21, 2011 by pBe Quote Link to comment Share on other sites More sharing options...
luiscarneirorm Posted September 21, 2011 Author Share Posted September 21, 2011 I am trying to make a gif like I've seen around here to try to show what I intend to do. Quote Link to comment Share on other sites More sharing options...
luiscarneirorm Posted September 21, 2011 Author Share Posted September 21, 2011 Here is my gif (too big??) I put here also the initial and final file for the example that appears in gif. This file is not the best to explain my problem, because it is very "linear", but I think you can try to explain what I do. Quote Link to comment Share on other sites More sharing options...
pBe Posted September 21, 2011 Share Posted September 21, 2011 Seriously, I will tell you right now the way you had those numbers grouped a square box wont work. What you need to consider is the window size. Originally the sample code prompts you for a start point, that way you can somehow dictate where the "scan" will start. you can get away with that for such an example., but then again NOT, an equal LxW selection will more likely give you problems , with a prompt for 2 points for the window size can eliminate that problem. Quote Link to comment Share on other sites More sharing options...
luiscarneirorm Posted September 21, 2011 Author Share Posted September 21, 2011 sorry, I do not quite understand your post. in my previous post I tried to put a gif but it seems not work very well. sorry but my English is very bad, and I'm using the translator, which means that sometimes I can not explain very well, I can not understand what I'm trying to say, as was the case in previous post :oops: in my previous post I said I'd put 2 files, but failed and ended up not placing. Now yes, I got the files to see if I understand myself that way, because in words is difficult:cry: The first file is the original and the second is what I intend to get. placa1.dxf placa2.dxf Quote Link to comment Share on other sites More sharing options...
luiscarneirorm Posted September 21, 2011 Author Share Posted September 21, 2011 Maybe if I explain what my goal is easier to understand you guys. So is this, I'm working with a laser engraving machine, and the recording area is 200x200, or other values depending on the lens I am using. so when I have a drawing area larger than that, I have to go in this area with several layers and then proceed with the recording. I think that this is noticeable which is my goal. This is one of the functions that I need to have this automated process, which would save me many hours of work. Quote Link to comment Share on other sites More sharing options...
Jeff H Posted September 22, 2011 Share Posted September 22, 2011 I think I understand what he is after. I am not a lisp guy but a way to do it .NET that might resemble a lisp approach would be to do a SelectWindow from 0,0 to 200,200 then change all the entites layers that fall in select window Now do a CrossingWindow from 0,0 to 200,200 and see if any objects are in crossing window compared to previous select window.(To see if any objects only partialy in select window) If there are no new objects the next window will be from 200, 0 to 400, 200. If there were new objects then get the bounding box for each one for each bounding box that the upper right corner is more than 200 then use the lowest Y value to be the start of the next level.(So if the lowest Y value was 180 then when you move up to next row you start at 0,180) for the rest get the lowest X value to be the start of the next set of windows. In the picture for the first 2 set windows the d is made of 2 different objects so the green part did fully fall in the window and its lowest X value will be the X value of the next window in green. Problems could happen and one for example you need to check if a object has already has layer changed when you move up because a object could fall in more than one window. Maybe that will work if the all objects are no larger than a certain size compared to the window. When you get the bounding box if it is area is more than a percentage of the windows area then you show a error message and stop the routine Quote Link to comment Share on other sites More sharing options...
pBe Posted September 22, 2011 Share Posted September 22, 2011 (edited) In the picture for the first 2 set windows the d is made of 2 different objects so the green part did fully fall in the window and its lowest X value will be the X value of the next window in green. I noticed that too. I was working under the "Too_Large" rule. we could modify selection via "_C" rather than "_W", only thing is it will supersede the "too_large" condition. A quick solution would be create a copy of the entity where it falls in more than one window. that way that entity will be shown on both window (layer) Also from the dxf sample the OP posted, it appears that the 200*200 box did not start at 0,0. so i tested the code with "_C" selection, and its slightly off. If there were new objects then get the bounding box for each one for each bounding box that the upper right corner is more than 200 then use the lowest Y value to be the start of the next level.(So if the lowest Y value was 180 then when you move up to next row you start at 0,180) for the rest get the lowest X value to be the start of the next set of windows. too much work Posted code updated The attached lisp includes the CopytoPreviousLayer option SplitToLayers2.LSP Edited September 23, 2011 by pBe Quote Link to comment Share on other sites More sharing options...
luiscarneirorm Posted September 22, 2011 Author Share Posted September 22, 2011 Thank you for your interest in my problem. I've been testing the code pBe provided by and is already close to my goal, one problem is that function only k are selected lwpolilines and circles, but fix it myself with ease. a problem that has detected is the question of the entities that are larger than the area defined. Quote Link to comment Share on other sites More sharing options...
pBe Posted September 22, 2011 Share Posted September 22, 2011 (edited) Thank you for your interest in my problem. I've been testing the code pBe provided by and is already close to my goal, one problem is that function only k are selected lwpolilines and circles, but fix it myself with ease. a problem that has detected is the question of the entities that are larger than the area defined. I think we can handle that problem. did you use the one with CopyToPrevousLayer ? Need to know which one works for you so i can make the necessary adjustments. and what modifications you did on the code. Edited September 22, 2011 by pBe Quote Link to comment Share on other sites More sharing options...
luiscarneirorm Posted September 22, 2011 Author Share Posted September 22, 2011 Used the function that you put the two posts ago, is necessary to do something to activate this function? a modification that I also needed to do is perform this function also for the layer "Cheio" but this problem is not too serious because I can duplicate the function and changing its name from the layer it will scan:) Quote Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.