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

Freeze a layer in all Viewports

7 REPLIES 7
Reply
Message 1 of 8
Anonymous
644 Views, 7 Replies

Freeze a layer in all Viewports

I want to freeze the current layer in all viewports of Paperspace.
I wrote a program, but it doesn't work.
It seems that layouts aren't update.
Please, help me.

Acad::ErrorStatus es;
AcDbObjectIdArray ListPV;
AcDbObjectIdArray ListLayers;
AcDbViewport *PView0;
AcDbObjectId Id0;
int i;
AcDbLayerTableRecord *Clayer0;
AcDbDictionary *pDic;
AcDbDictionaryIterator *pDicIter;
AcDbLayout *pLayout;

Id0 = acdbHostApplicationServices()->workingDatabase()->clayer();
ListLayers.append(Id0);

es = acdbOpenObject(Clayer0,Id0,AcDb::kForWrite);
if (es != Acad::eOk) goto fin1;

Clayer0->setVPDFLT(true);
Clayer0->close();

es = acdbHostApplicationServices()->workingDatabase()->getLayoutDictionary( pDic, AcDb::kForRead );
if (es!= Acad::eOk) goto fin1;

pDicIter = pDic->newIterator(AcRx::kDictCollated);
pDic->close();

for( ; !pDicIter->done() ; pDicIter->next() )
{
es = pDicIter->getObject((AcDbObject*&)pLayout,AcDb::kForWrite);
if (es!= Acad::eOk) goto fin2;
if (pLayout->modelType() == Adesk::kFalse)
{
ListPV = pLayout->getViewportArray();
for ( i = 1 ; i < ListPV.length() ; i++ )
{
Id0 = ListPV.at(i);
es = acdbOpenObject(PView0,Id0,AcDb::kForWrite);
if (es != Acad::eOk) goto fin3;
es = PView0->freezeLayersInViewport(ListLayers);
PView0->close();
if (es != Acad::eOk) goto fin3;
}
}
pLayout->close();
}
goto fin2;
fin3:
pLayout->close();
fin2:
delete pDicIter;
fin1:
;
7 REPLIES 7
Message 2 of 8
20130610
in reply to: Anonymous

I have the same problem,who can help me?
Message 3 of 8
tbrammer
in reply to: 20130610

Try different values of LAYOUTREGENCTL..

Try to redraw all entities on the affected layers.

 

AcDbObjectIdArray arrObjectsToRedraw; //Your entities on the affected layers
for (int i=0; i<arrObjectsToRedraw.length(); i++)
{
	es = acdbOpenObject(pEntity, arrObjectsToRedraw[i], AcDb::kForWrite);
	if (es==Acad::eOk)
	{
		pEntity->recordGraphicsModified();
		pEntity->close();
	}
}

Hope that helps.

 --Thomas


Thomas Brammer ● Software Developer ● imos AGLinkedIn
If an answer solves your problem please [ACCEPT SOLUTION]. Otherwise explain why not.

Message 4 of 8
nolanjian
in reply to: tbrammer

I meet with the same problem today, and try recordGraphicsModified(), but make no effect...

Message 5 of 8

@nolanjian

 

Try to call ads_regen() after freezing all layers.

http://jprdintprev.autodesk.com/adn/servlet/devnote?siteID=4814862&id=11845587&preview=1&linkID=4900...

Відповідь корисна? Клікніть на "ВПОДОБАЙКУ" цім повідомленням! | Do you find the posts helpful? "LIKE" these posts!
Находите сообщения полезными? Поставьте "НРАВИТСЯ" этим сообщениям!
На ваше запитання відповіли? Натисніть кнопку "ПРИЙНЯТИ РІШЕННЯ" | Have your question been answered successfully? Click "ACCEPT SOLUTION" button.
На ваш вопрос успешно ответили? Нажмите кнопку "УТВЕРДИТЬ РЕШЕНИЕ"


Alexander Rivilis / Александр Ривилис / Олександр Рівіліс
Programmer & Teacher & Helper / Программист - Учитель - Помощник / Програміст - вчитель - помічник
Facebook | Twitter | LinkedIn
Expert Elite Member

Message 6 of 8

hi, Alexander

I use Autocad 2014 and 2010, maybe I can't use this method, in VS2010, it fails to find this symble.

 

thx,

nolan

Message 7 of 8


@nolanjian wrote:

hi, Alexander

I use Autocad 2014 and 2010, maybe I can't use this method, in VS2010, it fails to find this symble.

 

thx,

nolan


You can use ads_regen in all AutoCAD versions since 2000.

With AutoCAD 2014 you have to add next definition (as far as this function is not documented and is not defined in any of .h-files):

 

void ads_regen(void);

Also you have to link with accore.lib

Відповідь корисна? Клікніть на "ВПОДОБАЙКУ" цім повідомленням! | Do you find the posts helpful? "LIKE" these posts!
Находите сообщения полезными? Поставьте "НРАВИТСЯ" этим сообщениям!
На ваше запитання відповіли? Натисніть кнопку "ПРИЙНЯТИ РІШЕННЯ" | Have your question been answered successfully? Click "ACCEPT SOLUTION" button.
На ваш вопрос успешно ответили? Нажмите кнопку "УТВЕРДИТЬ РЕШЕНИЕ"


Alexander Rivilis / Александр Ривилис / Олександр Рівіліс
Programmer & Teacher & Helper / Программист - Учитель - Помощник / Програміст - вчитель - помічник
Facebook | Twitter | LinkedIn
Expert Elite Member

Message 8 of 8
tbrammer
in reply to: Anonymous

I have made some changed to your code and tested it successfully with AutoCAD 2018. No additional ads_regen() was required.

I'm not sure what made the difference at the end. This is my general advice:

 

  • Avoid to open objects kForWrite unless you really want to modify them.
  • Close open objects as soon as possible.
  • Avoid goto! It's the natural enemy of structured programming Smiley Wink
  • Avoid to modify or erase objects within an iterator. Better collect their IDs and modify them in a separate loop.

 

 

void cmdFreezeCurLayerInAllVPs()
{
	Acad::ErrorStatus es;
	AcDbObjectIdArray ListPV;
	AcDbObjectIdArray ListLayers;
	AcDbViewport *PView0;
	AcDbObjectId Id0;
	int i;
	AcDbLayerTableRecord *Clayer0;
	AcDbDictionary *pDic=0;
	AcDbDictionaryIterator *pDicIter=0;
	AcDbLayout *pLayout=0;

	Id0 = acdbHostApplicationServices()->workingDatabase()->clayer();
	ListLayers.append(Id0);

	es = acdbOpenObject(Clayer0, Id0, AcDb::kForWrite);
	if (es != Acad::eOk)
		return;
	else
	{
		Clayer0->setVPDFLT(true);
		Clayer0->close();
	}

	es = acdbHostApplicationServices()->workingDatabase()->getLayoutDictionary(pDic, AcDb::kForRead);
	if (es != Acad::eOk)
		return;
	else
	{
		AcDbObjectIdArray allViewportIDs;
		if (pDicIter = pDic->newIterator())
		{
			for (; !pDicIter->done(); pDicIter->next())
			{
				es = pDicIter->getObject((AcDbObject*&)pLayout, AcDb::kForRead); // don't need kForWrite
				if (es == Acad::eOk)
				{
					if (pLayout->modelType() == Adesk::kFalse)
					{
						AcDbObjectIdArray vpsInLayout(pLayout->getViewportArray());
						if (!vpsInLayout.isEmpty())
						{
							vpsInLayout.removeFirst();  // remove the paperspace VP
							ListPV.append(vpsInLayout); // Just collect them all
						}
					}
					pLayout->close();
				}
			}
			delete pDicIter;
		}

		pDic->close();
	}

	// Now freeze the Layer all VPs
	for (i = 0; i < ListPV.length(); i++) // Start with i=0 because paperspace VPs are already removed
	{
		Id0 = ListPV.at(i);
		es = acdbOpenObject(PView0, Id0, AcDb::kForWrite);
		if (es == Acad::eOk)
		{
			es = PView0->freezeLayersInViewport(ListLayers);
			PView0->close();
		}
	}
}

 


Thomas Brammer ● Software Developer ● imos AGLinkedIn
If an answer solves your problem please [ACCEPT SOLUTION]. Otherwise explain why not.

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

Post to forums  

Autodesk Design & Make Report

”Boost