Я работаю над html canvas. Я реализовал следующие функции:

1) Simple Draw
2) Erasor
3) Shapes Draw
4) Shapes Resize
5) Shapes Move
6) Color Select

Теперь я хочу добавить функциональность undo/redo.

Учитывая реализованные выше функции, я думаю о сохранении экземпляра всего canvas при каждом выполнении события. Например, при выполнении shape resize я помещаю весь экземпляр холста в массив.

Когда пользователь нажимает на undo, я просто pop последний элемент массива и перерисовываю canvas.

Но я думаю, что сохранение всего экземпляра canvas каждый раз будет занимать много памяти, а также не очень оптимально с точки зрения производительности. Кроме того, при таком подходе мне придется ограничить максимальное разрешенное количество undo/redo. Какое было бы идеальное количество undo/redo, которое я должен оставить, если буду придерживаться этого подхода. Кроме того, есть ли лучший подход для этого, учитывая вышеуказанные особенности.

0
helloworld 14 Сен 2018 в 16:16

2 ответа

Лучший ответ

Используйте шаблон проектирования command и перерисуйте холст из истории команд. Вы сможете сэкономить большое количество шагов (сотни, если не тысячи).

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

В вашем случае у вас также будут команды для выбора инструмента, поэтому выбор также будет «записан» в вашу историю.

Как только вы начнете использовать этот шаблон, вы можете обнаружить, что все ваше приложение будет лучше структурировано с использованием объекта state, заключенного в store, который использует операции commit для любого доступа. Тогда вы получите отмену и повтор действий бесплатно. См. redux, vuex и flux для получения информации о стандартах де-факто этой конструкции store. Какими бы мощными ни были эти библиотеки, они действительно компактны и довольно просты.

https://en.wikipedia.org/wiki/Command_pattern

3
Steven Spungin 14 Сен 2018 в 13:27

Альтернативой шаблону команд является шаблон Memento, в котором вы просто сохраняете текущее состояние холста. каждый раз, когда выполняется действие. Это требует больше памяти и, как правило, нужно ограничивать небольшим количеством правок. Однако восстановление более раннего состояния должно быть довольно быстрым.

1
Simmetric 14 Сен 2018 в 13:26