Отмена и Восстановление (Undo и Redo)

Имеются два основных пути регистрации состояния для операции отмены. Автоматический механизм отмены, значение по умолчанию, позволяет системе копировать законченное состояние объекта, вызывая dwgOutFields объекта () функция с регистратором отмены. Альтернативный механизм, упомянутый как частичный механизм отмены, требует большего количества усилия программирования, но дает возможность Вам выписывать и читать в только определенную информацию относительно специфических модификаций, которые были сделаны к объекту. Каждая функция модификации для вашего нового класса (например, любой набор () функция) требуется, чтобы назвать assertWriteEnabled () функцией, которая проверяет{*отмечает*}, чтобы объект был допускаемый записью. Если значение параметра автоотмены для этой функции - kTrue, объект зарегистрирован для отмены. Когда объектная модификация закончена, и объект закрыт, содержание регистратора сохранено в файл отмены. Для данного класса, некоторые функции модификации могут использовать авто механизм отмены, и другие могут осуществлять частичный механизм отмены. Частичный механизм отмены полезен, если модификация возводит в степень маленькое количество данных.

Когда команда UNDO вызвана, и авто операция отмены была выполнена, AutoCAD вызывает dwgInFields () на объекте, таким образом считывая содержание файла отмены.

Автоматическая Отмена

AssertWriteEnabled () функция имеет следующую сигнатуру:

Пусто assertWriteEnabled (

Adesk:: Булева автоотмена = Adesk:: kTrue,

НЕ нашли? Не то? Что вы ищете?

Adesk:: Булев recordModified = Adesk:: kTrue);

Когда функция модификации вызывает{*называет*} assertWriteEnabled (), это сначала проверяет{*отмечает*} значение recordModified параметра. Если recordModified - kFalse, никакая регистрация отмены не выполнена. Если recordModified - kTrue, это затем проверяет{*отмечает*} параметр автоотмены, который определяет, должна ли авто операция отмены быть выполнена.

Если автоотмена - kTrue (значение по умолчанию), полное объектное государство{*состояние*} автоматически написано к регистратору отмены объекта. Если Вы определяете kFalse для автоотмены, никакая информация не зарегистрирована. AutoCAD предполагает, что ваша функция модификации будет заботиться о регистрации измененного{*замененного*} объектного государства{*состояния*} к регистратору отмены объекта.

Даже если Вы планируете осуществлять частичный механизм отмены для вашего класса, Вы можете полагаться на автоматическую отмену в первых стадиях развития.

Частичная Отмена

Это - доработка нового класса, чтобы решить, осуществить ли частичный механизм отмены для некоторых функций модификации класса. Если только маленькая часть состояния объекта типично изменяется в специфической функции элемента, используя частичную отмену может давать существенные выгоды выполнения{ работы*}.

Однако, если ваше объектное состояние маленькое (512 байтов или меньше), это не вероятно стоит усилие, чтобы осуществить вашу собственную частичную регистрацию отмены и восстановление схемы.

Если ваша функция модификации делает запись частичного объектного состояния, Вы должны осуществить applyPartialUndo () функция для вашего класса так, чтобы данные могли также быть восстановлены выборочно. См. “ Восстанавливающий Государство{*состояние*} ” на странице 326.

Регистрация состояния

Чтобы делать запись только части государства{*состояния*} объекта, определите kFalse для параметра автоотмены, и затем используйте undoFiler:: writeItem () функция (или другой writexxx () функция) чтобы сохранить{*экономить*} уместную информацию в файле отмены.

SetNumSides () функция AsdkPoly - типичный пример функции модификации. Поскольку assertWriteEnabled () определяет kFalse для автоотмены, класс принимает ответственность регистрации уместных частей государства{*состояния*} объекта. Сначала, функция модификации должна делать запись объекта описателя класса так, чтобы полученные классы могли проверять{*отмечать*} и позволять этому классу обрабатывать его частичные данные отмены в случае необходимости.

undoFiler()->writeItem((long)AsdkPoly::desc());

Тогда функция модификации должна указать тип действия, сопровождаемого данными. В этом примере, тип операции - kSetNumSides, и данные - mNumSides.

Acad::ErrorStatus

AsdkPoly::setNumSides(int numSides)

{

assertWriteEnabled(Adesk::kFalse, Adesk::kTrue);

if (numSides<3)

return Acad::eInvalidInput;

if (mNumSides == numSides)

return Acad::eOk;

// There are situations under which AutoCAD doesn’t

// want to do undo recording, so it won’t create an

// undo filer. Check for the existence of the filer

// before starting to write into it.

//

AcDbDwgFiler *pFiler = NULL;

if ((pFiler = undoFiler()) != NULL) {

undoFiler()->writeItem((long)AsdkPoly::desc());

undoFiler()->writeItem((Adesk::Int16)kSetNumSides);

undoFiler()->writeItem((Adesk::Int32)mNumSides);

}

mNumSides = numSides;

return Acad::eOk;

}

Как только объект выполнил авто операцию отмены, которая делает запись ее полных состояний, дополнительных просьб о авто отмене, игнорируются.

Восстановление состояния

Если Вы определили kFalse для автоотмены, applyPartialUndo объекта () функция называется, когда команда UNDO вызвана. ApplyPartialUndo () функция - виртуальная функция на AcDbObject.

Полученные классы могут осуществлять эту функцию, чтобы интерпретировать класс - определенную информацию, сохраненную регистратором отмены и читать это в. ApplyPartialUndo () функция должна гарантировать, что ваш класс выполнил модификацию. Если не, это супер-сообщение, как показано в следующем примере.

Если Вы осуществляете частичный механизм отмены, убедитесь, что вызвали{*назвали*} следующую функцию так, чтобы никакая регистрация не случилась по умолчанию.

AssertWriteEnabled (kFalse, kFalse);

Как пример, имеется AsdkPoly-функция applyPartialUndo()

Acad::ErrorStatus

AsdkPoly::applyPartialUndo(AcDbDwgFiler* filer,

AcRxClass* classObj)

{

// The first thing to check is whether the class matches

// ours. If it doesn’t, we call the base class’s

// applyPartialUndo(); hopefully, one of them will

// take care of it.

//

if (classObj!= AsdkPoly::desc())

return AcDbCurve::applyPartialUndo(filer, classObj);

// Read the op-code and call the appropriate "set"

// method to undo what was done. The "set" does the

// filing again for redo.

//

Adesk::Int16 shortCode;

filer->readItem(&shortCode);

PolyOpCodeForPartialUndo code;

code = (PolyOpCodeForPartialUndo)shortCode;

Adesk::UInt32 value32;

switch (code) {

case kSetNumSides:

filer->readItem(&value32);

AOK(setNumSides(value32));

break;

default:

assert(Adesk::kFalse);

break;

}

return Acad::eOk;

}

Redo ( Восстановить )

Когда операция отмены отменяет вашу работу, это также делает запись текущего состояния в подготовке к восстановленной операции. Эта регистрация для восстанавливает, не требует никакой дальнейшей работы с Вашей стороны, потому что это использует тот же самый файловый механизм как операция отмены, вызывая dwgOutFields(), чтобы делать запись состояния объекта.

Если Вы осуществляете частичную отмену для вашей функции модификации, Вы ответствены за регистрацию для, восстанавливают в вашей операции отмены. Это обычно выполняется, вызывая соответствующий set() функции. Когда ваш set() функция называется, assertWriteEnabled () вызван, который делает запись данных для отмены.

subErase, subOpen, subClose, and subCancel

Ф-ции erase(), open(), close(), и cancel() все имеют соответствующие виртуальные функции, начинающиеся с префиксной замены. Вы можете отменять эти вспомогательные функции, чтобы обеспечить дополнительные функциональные возможности для полученных классов. Вспомогательная функция вызвана невиртуальной “главной” функцией. Например, erase() - subErase(). Сигнатура для subErase() следующие:

virtual Acad::ErrorStatus

subErase(Adesk::Boolean pErasing);

Перегрузите вспомогательную функцию

1 Проверяют правильность вашей окрестности. Например, если ваш объект имеет жесткую ссылку указателя к другому объекту, и ваш объект не стирается, Вы можете проверять, чтобы объект, к которому Вы относите все еще, существовал. Если имеются проблемы, немедленно возвращают соответствующее состояние ошибки и не упускают сообщение, потому что ваше плохое состояние ошибки эффективно уничтожит операцию.

2, если все - OK, затем вызывает Ваше Родительское подстирание:: () функция. Исследуйте его результат. Если это не возвращает eOK, то возвращается.

3, если все - OK, затем исполняет ваши действия.

Лучше не изменить{*заменить*} любое государство{*состояние*} во вспомогательной функции. Если Вы изменили{*заменили*} государство{*состояние*}, затем пробовать изменить{*заменить*} это после вызова родительского выполнения класса той же самой функции (в случае, если код ошибки возвращен). Если Вы изменили{*заменить*} государство{*состояние*} перед вызовом родительской функции класса, то подготовлены, чтобы полностью изменить это, если родительский класс возвращает плохое состояние.

Следующий пример показывает выполнению subErase() функция, которая называется, когда объект стерт. subErase() проверяет жесткие ссылки указателя к другим объектам и стирает их также.

class AsdkEllipse : public AcDbEllipse

// Этот класс расширяет AcDbEllipse, добавляясь в функциональных возможностях

// Сохранять динамический массив жесткого объекта IDs указателя.

//

// subErase () функция элемента отменяет и

// Осуществленный, так, когда объект этого класса

// Стертый, объекты, указанные жестким указателем IDs

// Сохраненный в пределах объекта будет также стерт.

//

{

public:

ACRX_DECLARE_MEMBERS(AsdkEllipse);

AsdkEllipse() {};

AsdkEllipse(const AsdkEllipse&);

AsdkEllipse(const AcDbObjectIdArray& ellipses)

: mEllipseIds(ellipses) {};

AsdkEllipse(const AcGePoint3d& center,

const AcGeVector3d& unitNormal,

const AcGeVector3d& majorAxis,

double radiusRatio,

double startAngle = 0.0,

double endAngle = 6.28318530717958647692);

Из за большого объема этот материал размещен на нескольких страницах:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132