.NET
cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Checking if a layer is empty

16 REPLIES 16
Reply
Message 1 of 17
Anonymous
5529 Views, 16 Replies

Checking if a layer is empty

What is the best way to check if a layer is empty?
Can it be done using a side database?
Using C# prefered but I can work with VB.

Thanks for any and all input,

Tim
16 REPLIES 16
Message 2 of 17
Anonymous
in reply to: Anonymous

Try to delete the layer and if an exception is thrown, it means the layer is
referenced by something in the drawing.


--
http://www.caddzone.com

AcadXTabs: MDI Document Tabs for AutoCAD
Supporting AutoCAD 2000 through 2010

http://www.acadxtabs.com

Email: string.Format("{0}@{1}.com", "tonyt", "caddzone");

wrote in message news:6313752@discussion.autodesk.com...
What is the best way to check if a layer is empty?
Can it be done using a side database?
Using C# prefered but I can work with VB.

Thanks for any and all input,

Tim
Message 3 of 17
Anonymous
in reply to: Anonymous

Well that one is easy enough! Don't know why I didn't think of that one.
Guess I was just thinking that the layer has to stay in the drawing (not sure why) but I can just recreate it if it deletes.
Layer "0" has to be in the drawing but nothing can be on it... go figure.

Thanks Tony

Tim
Message 4 of 17
chiefbraincloud
in reply to: Anonymous

Things can be on layer '0'.

The point is it has a special purpose for block creation. Nothing else should be on layer 0, because that's just bad drawing organization.

Any entity placed on layer 0 in a block definition will assume the layer properties of whatever layer the block reference is placed on. That is, any properties that were not explicitly set to the entity.

So, I can create some widget. Place it on layer 0, color bylayer, linetype bylayer...
draw a centerline on it. on Layer 0, color red, linetype centerline...
attach some gadget to it (I don't know... a J-Box for wiring maybe) layer 0, color ByBlock, linetype ByBlock.

Now make all that into a block and place several instances on different layers with different color and linetype settings.
Then take a couple of the blocks and change the color or linetype of the block itself.

The result is:
the centerline will always be color red, linetype centerline in all instances.
the widget will always follow the layer settings in all instances
the gadget will follow the settings given to the block reference (which can be bylayer making it the same as the widget, or specific color/Ltype, making the widget and the gadget appear differently.
Dave O.                                                                  Sig-Logos32.png
Message 5 of 17
Anonymous
in reply to: Anonymous

No, it will not work for Layer 0.

You don't have to recreate the layer if it gets deleted, you just unerase it.

--
http://www.caddzone.com

AcadXTabs: MDI Document Tabs for AutoCAD
Supporting AutoCAD 2000 through 2010

http://www.acadxtabs.com

Email: string.Format("{0}@{1}.com", "tonyt", "caddzone");

wrote in message news:6313984@discussion.autodesk.com...
Well that one is easy enough! Don't know why I didn't think of that one.
Guess I was just thinking that the layer has to stay in the drawing (not sure
why) but I can just recreate it if it deletes.
Layer "0" has to be in the drawing but nothing can be on it... go figure.

Thanks Tony

Tim
Message 6 of 17
Anonymous
in reply to: Anonymous

Thanks for the insight chiefbraincloud, and point well taken.
You can't delete layer 0 so I guess I am back to square one again. What I need/want to do is check a bunch of drawings (>5000) to see if there is anything on layer 0 that should not be there. I was spot checking them and I have found 2 that had objects on them, lines and blocks. 2 out of the 30 or so I checked warrants me to check them all. I also need to delete layers that don't belong. There is a layer standard we follow and all layers have to be there and the ones that don't belong should be deleted.
I have taken it upon myself to learn how to do this and have most of it written but its an uphill battle with limited documentation on .NET. Maybe if I get good enough or prove the value they will let me sign up for ADN.
So could somebody show me how to do this tidbit of code? I would be forever grateful.

Tim
Message 7 of 17
Anonymous
in reply to: Anonymous

neeeevermind, didn't see "won't" in that sentence. Edited by: ViktorCad on Jan 8, 2010 1:11 AM
Message 8 of 17
Anonymous
in reply to: Anonymous

Your problem may actually a bit more complicated than you assume.

The first question you need to answer is in your case, whether you want
to know if any entity is on a given layer, regardless of where the entity is.

IOW, is it acceptable for entities in block definitions to be on layer 0?

If the answer is no, you can use the following method to test if a layer
is referenced by *any* entity, including entities in any block definition:

1. Call the LayerTable's GenerateUsageData() method.

2. Check the IsUsed property of one or more LayerTableRecords.

IsUsed is only valid after GenerateUsageData() was called, up to the
point where the database is modified.

OTOH, if you're only interested in knowing if entities in model and/or
paper space reside on a given layer, it becomes more complicated
because the IsUsed property cannot tell you that.

In that case, have a look at the code here:

http://www.caddzone.com/LayerUtils.cs

--
http://www.caddzone.com

AcadXTabs: MDI Document Tabs for AutoCAD
Supporting AutoCAD 2000 through 2010

http://www.acadxtabs.com

Email: string.Format("{0}@{1}.com", "tonyt", "caddzone");

wrote in message news:6313984@discussion.autodesk.com...
Well that one is easy enough! Don't know why I didn't think of that one.
Guess I was just thinking that the layer has to stay in the drawing (not sure
why) but I can just recreate it if it deletes.
Layer "0" has to be in the drawing but nothing can be on it... go figure.

Thanks Tony

Tim
Message 9 of 17
Anonymous
in reply to: Anonymous

Thanks Tony that helped alot. The entities of the blocks can be on layer 0 but nothing else.
Message 10 of 17
chiefbraincloud
in reply to: Anonymous

Based on your question in the beginning about the ability to do this as a side database, combined with the fact that you indicated a very large number of drawings needing searched, I worked up an example of how to do it, as a side database.

It would be much simpler if you opened the drawings into the editor, because you could use a selection filter to get all entities on layer 0, however, if you tried to do it that way on 5000 drawings it might take about a week. (depending somewhat on the drawing content)

Since you can't use the editor methods on a side database, you have to loop through both the ModelSpace and the PaperSpace opening every entity you find to check it's layer property.

I had a routine for copying block definitions from a side database to the current database, so I hacked up a copy of it (attached) to make a simple text report (In your MyDocuments Folder) of all entities found to be on layer 0 (with one exception, next paragraph). You pass it a string collection of filenames to process.

Tony, If you have any interest, you may note that my code here does not use the IsUsed property of the layer to short circuit the process. I did try to do that, thinking that at least that way if a drawing is clean, you don't have to loop the whole MS and PS to find out, but I found that it always returned true. (At first, I was not aware of the need for calling GenerateUsageData first, but even after it still always returned true) I believe through my limited efforts to test this routine, I determined that the root PaperSpace Viewport (the one that exists even of there are no mview created viewports) is reporting itself on layer 0, therefore IsUsed may work fine for other layers but could never be false for layer 0.

Of course this simple text report does you little good, but you would just insert whatever code you desire at the points where I am writing to the report, and there is one more detail which may need some work. I think if the drawing has multiple layouts there is more work to be done to catch all the paperspaces.

Anyone got any input on that? I used the SymbolUtilityServices.GetBlockPaperSpaceID(db) method to get the paperspace entities. Is that a 'Parent' PaperSpace to the multiple 'child' layout PaperSpaces, or will it represent the most recently activated Layout?
Dave O.                                                                  Sig-Logos32.png
Message 11 of 17
Anonymous
in reply to: Anonymous

I've been meaning to publish some sample code that
shows how to use Linq in AutoCAD development, and
found that your task was an good problem case for
demonstrating how Linq can be used.

So I've revised that code to be more 'Linq-oriented', and
in the process made it less complicated and more generic.
Most of the code is implemented as extension methods
that are reusable in a range of similar problems as well.

See the updated version just posted if you're interested
in seeing how Linq can be leveraged to solve this and a
variety of similar problems.

Oh and BTW, that code can be used on any database,
whether it's open in the editor, or not. With an outboard
Database or a Database open in the editor, just call the
BlockTableRecord.IsLayerUsed() extension method on the
specific BlockTableRecord(s) you're interested in.

If you want to be more helpful to users, then not only
would you detect whether entities are not on the correct
layer. You could also help them to locate those entities
too. What you might do is store their ObjectIds in an
extension dictionary within the drawing, and also provide
another tool that can use that data to select the objects
for the user when they later open the file to correct the
issues you find.

One last point, is that if you're interested in specific
information about layer usage within a given block or
several blocks, then you shouldn't bother with calling
GenerateUsageData() or looking at the IsUsed property,
because GenerateUsageData() has to look for references
to every layer in the drawing, and may have to look at
every single object in the drawing as well, not just the
entities in the block you're interested in, and because
of that, it could take much longer in very large files, or
files with many blocks.

--
http://www.caddzone.com

AcadXTabs: MDI Document Tabs for AutoCAD
Supporting AutoCAD 2000 through 2010

http://www.acadxtabs.com

Email: string.Format("{0}@{1}.com", "tonyt", "caddzone");

wrote in message news:6314708@discussion.autodesk.com...
Thanks Tony that helped alot. The entities of the blocks can be on layer 0 but
nothing else.
Message 12 of 17
Anonymous
in reply to: Anonymous

I'm not going to get into what's wrong with the chief's endeavor
other than to just advise you that it doesn't do what he seems to
think it does. It will not find all layer references that can exist,
and will leave the outboard database open should an error cause
the code to terminate prematurely, which is mainly because the
code is badly written (e.g, doesn't use 'Using' where appropriate,
nor uses exception/termination handling correctly to ensure the
database is disposed if an error stops the code).

--
http://www.caddzone.com

AcadXTabs: MDI Document Tabs for AutoCAD
Supporting AutoCAD 2000 through 2010

http://www.acadxtabs.com

Email: string.Format("{0}@{1}.com", "tonyt", "caddzone");

wrote in message news:6314708@discussion.autodesk.com...
Thanks Tony that helped alot. The entities of the blocks can be on layer 0 but
nothing else.
Message 13 of 17
Anonymous
in reply to: Anonymous

Wow, thanks! It's going to take me a little to digest all this, but great example.
One more question, where or what do you use for reference? I mean do you get all this information from the SDK documentation? Is there some other source of documentation available outside of joining ADN (company won't go for that yet)? I read Kean Walmsley's blogs and I have learned quite a bit there but there has to be some sort of reference that lists what all of the classes and methods of the API do.

Thanks again,

Tim
Message 14 of 17
chiefbraincloud
in reply to: Anonymous

That's crap. It does exactly what I said it does.

It will find all Graphical references to Layer 0 (the specific problem presented) other than my question about multiple layouts.

It does use Using as much as is neccessary, and has plenty of exception handling.

I missed putting the DB.closeinput and dispose into a finally... sue me. If it had actually failed once I would have caught that.

And for Tim's benefit I'll mention that in the process of trying to figure out what was up with the viewports I accidentally made it only report the viewports from paperspace, so needs an Else in the If.
Dave O.                                                                  Sig-Logos32.png
Message 15 of 17
Anonymous
in reply to: Anonymous

No it doesn't do what you think, and you're not
worthy of a debate about it.


over and out

--
http://www.caddzone.com

AcadXTabs: MDI Document Tabs for AutoCAD
Supporting AutoCAD 2000 through 2010

http://www.acadxtabs.com

Email: string.Format("{0}@{1}.com", "tonyt", "caddzone");

wrote in message news:6315127@discussion.autodesk.com...
That's crap. It does exactly what I said it does.

It will find all Graphical references to Layer 0 (the specific problem
presented) other than my question about multiple layouts.

It does use Using as much as is neccessary, and has plenty of exception
handling.

I missed putting the DB.closeinput and dispose into a finally... sue me. If it
had actually failed once I would have caught that.

And for Tim's benefit I'll mention that in the process of trying to figure out
what was up with the viewports I accidentally made it only report the viewports
from paperspace, so needs an Else in the If.
Message 16 of 17
Anonymous
in reply to: Anonymous

Aside from the docs that come with the SDK, there are some online docs that
include basic code samples for common tasks. The links to them can be found on
the same page where you download the SDK.

My own experience is rooted in native ObjectARX, and has been very helpful in
unraveling the managed API.

--
http://www.caddzone.com

AcadXTabs: MDI Document Tabs for AutoCAD
Supporting AutoCAD 2000 through 2010

http://www.acadxtabs.com

Email: string.Format("{0}@{1}.com", "tonyt", "caddzone");

wrote in message news:6314899@discussion.autodesk.com...
Wow, thanks! It's going to take me a little to digest all this, but great
example.
One more question, where or what do you use for reference? I mean do you get all
this information from the SDK documentation? Is there some other source of
documentation available outside of joining ADN (company won't go for that yet)?
I read Kean Walmsley's blogs and I have learned quite a bit there but there has
to be some sort of reference that lists what all of the classes and methods of
the API do.

Thanks again,

Tim
Message 17 of 17
Anonymous
in reply to: Anonymous

Maybe this?

Public Shared Function LayerIsEmpty(ByVal layerName As String) As Boolean
Dim db As acaDb.Database =
Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument.Database
Using tr As acaDb.Transaction = db.TransactionManager.StartTransaction
Dim tbl As acaDb.LayerTable = tr.GetObject(db.LayerTableId,
acaDb.OpenMode.ForRead)
If tbl.Has(layerName) Then
Dim ltr As acaDb.LayerTableRecord =
tr.GetObject(tbl.Item(layerName), acaDb.OpenMode.ForRead)
Dim ids As New acaDb.ObjectIdCollection
ids.Add(ltr.ObjectId)
db.Purge(ids)
If ids.Count > 0 Then
Return True
End If
End If
End Using
Return False
End Function

tp

"TimBlanch" escreveu na mensagem news:6313752@discussion.autodesk.com...
> What is the best way to check if a layer is empty?
> Can it be done using a side database?
> Using C# prefered but I can work with VB.
>
> Thanks for any and all input,
>
> Tim

Can't find what you're looking for? Ask the community or share your knowledge.

Post to forums  

Forma Design Contest


Autodesk Design & Make Report