ОО-дизайн интерфейса программы рисования - PullRequest
1 голос
/ 16 июля 2010

Я пишу программу рисования.Мои основные классы:

  class Workspace { Bitmap b; List<Command> undoList; }

  class Command { void execute(); }

  class ClearScreen extends Command

  class BlurEffect extends Command

  class View { Bitmap screen; }

  class Interface

Объект рабочей области содержит растровое изображение, которое представляет состояние программы.Класс Command представляет шаблон Command для выполнения команд в рабочей области, где отмена работает путем сброса состояния рабочей области и воспроизведения старых команд.Объект интерфейса связывает кнопки пользователя с командами, и представление отображает состояние рабочего пространства на растровое изображение экрана.

Моя проблема заключается в представлении команд.Команда ClearScreen проста;он просто говорит рабочей области заполнить растровое изображение белым, и это происходит мгновенно.Команда BlurEffect является более сложной;Blurring принимает параметр, определяющий степень размытия экрана, выполнение может занять некоторое время, и пользователь обычно хочет попробовать несколько параметров размытия перед тем, как выбрать один (т. е. ему необходимо предварительно просмотреть, как будет выглядеть эффект размытия, перед тем как совершить коммит).Как я могу изменить вышеупомянутое, чтобы поддержать этот вид предварительного просмотра?

Лучшее, что я могу придумать, это расширить Command с помощью чего-то вроде:

  class BlurCommand extends Command
  {
    void setBlurAmount(float x) ...

    // View can use this to render a preview to the
    // screen bitmap, where the workspace bitmap isn't modified in the process
    void preview(Workspace w, Bitmap b)

    void execute() // apply blur effect to workspace 
  }

Таким образом, идея в том, что в интерфейсе нажатие кнопки «размытия» создает новый объект BlurCommandзатем метод «рендеринга экрана» в View начнет вызывать метод «предварительного просмотра» для рендеринга экрана, а «execute» вызывается только тогда, когда пользователь хочет применить эффект.

Это самый чистый способ, которым я могу это сделать?Я пытаюсь придерживаться модели Model-View-Controller и не хочу, чтобы мое поведение предварительного просмотра усложняло ситуацию.

Ответы [ 3 ]

0 голосов
/ 16 июля 2010

Есть ли у вас какие-либо юнит-тесты, которые проверяют текущие функции вашей программы рисования?Одна вещь, которая, я думаю, действительно поможет вам прийти к твердому дизайну, - это использование TDD (Test Driven Development / Design)Напишите тест, который будет имитировать действие типа «предварительный просмотр», а затем выполните этот тест.Как только ваши существующие тесты и новый предварительный тест пройдены, посмотрите, как выглядит код вашего приложения.

0 голосов
/ 17 июня 2011

Ваш дизайн пока выглядит великолепно. Вот мое мнение: проблема, с которой вы сталкиваетесь с помощью команды размытия, является индикатором появления большего количества таких вещей, и поэтому добавление большего количества таких команд должно быть встроено в ваш дизайн. Таким образом, вы можете создать два подкласса для Command - FastCommand и SlowCommand. FastCommand имеет только методы doIt и undoIt и будет просто выполняться и добавлять его в стек команд. SlowCommand должна быть асинхронной командой с двухступенчатым процессом для выполнения действий - предварительного просмотра и фиксации. При первом выполнении SlowCommand он должен быть выполнен, но не добавлен в стек команд. Вместо этого просто сохраните его в рабочей области в качестве ссылки. Когда пользователь на самом деле подтверждает действие, выполните его снова (на этот раз он делает реальную вещь), а затем переместите его в стек команд.

Класс View, вероятно, не требуется.

Принимая во внимание фактический механизм отмены-повтора для SlowCommand, вы можете выбрать лучший подход на основе производительности и доступной памяти - создать копию буфера и затем отбросить ее, или, возможно, запустить обратный алгоритм в том же буфере. Если вы обнаружите, что вы используете обе стратегии в своем приложении, * * * * * * * * * * * * * * * * * может быть использовано внутри команды.

0 голосов
/ 16 июля 2010

Да, в качестве альтернативы вы можете применить размытие и отменить его, если операция отменяется, или отменить и повторить его, если параметр был изменен. Если воспроизведение всего стека команд занимает слишком много времени, можно сделать снимок до применения размытия.

...