суббота, 5 февраля 2011 г.

Графический интерфейс, часть первая. Общие проблемы создания интерфейсов

Продолжение - во второй части.

Хотел порассуждать о разработке интерфейсов пользователя.

Сначала - исключительно применительно к Питону.

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

Хорошо, поговорим о создании Graphic User Interface (GUI) "вообще", постаравшись проиллюстрировать это примерами из популярных кроссплатформенных библиотек.

И тут не всё гладко: задачи, стоящие перед разработчиком standalone application на Qt довольно похожи на создание полноценного интерактивного интерфейса с помощью ajax, long polling, web sockets и прочих умных слов.

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

В web разработке более или менее успешно решаются другие серьезные проблемы: масштабирование, высоконагруженные системы. Но в плане сложного интерфейса - увы и ах - запросы, как правило, невелики.

При этом принципы дизайна и стоящие вызовы, повторюсь, очень похожи.

Итак, будем говорить о графическом интерфейсе, не делая принципиального различия между web и standalone приложениями.

Model-View-Controller

Первое, что приходит в голову при мысли о хорошей архитектуре GUI - MVC. За детальным описанием обратитесь, например, к википедии.

Модель содержит данные и бизнес-логику работы с ними - всё чётко и ясно.

А вот с видом и контроллером ситуация гораздо хуже.

Возможно, в Smalltalk (от которого всё пошло) и было четкое разделение.

В нынешних системах оно утеряно. Примеры:

  1. Django. Есть вид, но контроллер отсутствует. За него иногда на полном серьезе выдают правила роутинга (urls.py) - что просто смешно.

  2. Pylons. Появился контроллер (при том что роутинг тоже никуда не делся), вид отсутствует. Иногда в качестве вида пытаются указывать шаблон страницы.

  3. Pyramid, новая поделка. В попытках уйти от неоднозначности ввели новый термин ресурс, оставив вид. К чести создателей Пирамиды, ребята постарались явно описать причины отказа от MVC и предложили иную схему: Model-Resource-View-Renderer.

Может, MVC не применима к веб разработке? А на её "родном" поле всё хорошо?

Как бы не так: Qt, wxWidgets, WinForms, Swing - все эти библиотеки используют понятие widget, объединяя в нём вид и контроллер. Для сложных виджетов модель выделяется в отдельный класс, в то время как тривиальные моделью не обладают, предпочитая держать всё вместе.

Более того. Если вы попробуете внимательно почитать те статьи, которые явно разделяют модель-вид-контроллер -- заметите занятную вещь.

Взаимодействие между этой тройкой описывается каждый раз иначе. Может ли вид изменять модель? А модель шлет свои сообщения виду или контроллеру? Ответ на вопрос зависит от автора статьи.

MVC ни разу не является шаблоном проектирования (design pattern), где все четко расписано: какие классы входят в шаблон, за что отвечают и каким образом взаимодействуют.

Наверное, поэтому схема Model-View-Controller не вошла в знаменитую книгу "Design Patterns" (GoF) - это просто набор благих пожеланий и никак не строгая структура.

Похоже, концепция MVC чем то напоминает смысл жизни: каждый подсознательно чувствует, что он есть. И вместе с тем все попытки описать этот смысл вербально ни к чему хорошему не приводят.

View

В мире библиотек для GUI наблюдается интересная стандартизация.

Веб давно и прочно сидит на HTML+CSS.

Это позволило выделить отдельную категорию разработчиков - верстальщики.

В последние годы тенденция распространяется и на средства разработки standalone aplication.

Проблема в следующем: программисты, как правило - плохие дизайнеры. Слишком разный склад ума.

Посредственный программист, являющийся при этом не самым лучшим художником - находка для работодателя. Я не шучу.

Что получается, если типичному программисту заказывают дизайн "в розовых тонах с симпатичными рюшечками?".

Правильно! Изделие напоминает выпуск военно-промышленного комплекса, покрашенное в розовый цвет и снабженное криво сидящим унылым бантиком.

Не потому, что программист сделал работу "на отвяжись" - просто он иначе мыслит. Я тоже немного понимаю в живописи - но не сумею нарисовать ваш акварельный портрет.

Или таки нарисую (если сильно прижмут) - но мне будет стыдно, а вам неловко.

Итак, естественным образом возникла идея: раз уж дизайнеры (технические художники) присутствуют в массовых количествах и они волей-неволей освоили вёрстку веба - нужно дать им похожий инструмент для создания пользовательского интерфейса традиционных программ.

Некоторые поделки я видел уже давно - они были неуклюжие, малораспространенные а зачастую еще и стоили очень недешево.

Появилась идея HTML Applications. Весь интерфейс в html, вместо удаленного сайта используется локально запущенный сервер, и всё оформляется в едином флаконе - запусти приложение и увидишь красивую картинку.

Всеми уважаемая фирма Microsoft некоторое время усиленно продвигала этот подход.

Получилось не то чтобы успешно. Причина очевидна: html в первую очередь ориентирован на создание сайтов. Его выразительная мощь проигрывает традиционным библиотекам GUI. HTML Applications были красивыми внешне, но отличались крайне низкой usability.

При том подход не умер: есть множество задач, в которых он более чем оправдан.

И тем не менее это - не mainstream.

Сейчас присутствуют и более многообещающие альтернативы.

  1. В Qt 4.7 появились Declarative Views и язык разметки QML.
  2. Microsoft выпустила Windows Presentation Framework (WPF) с разметкой в XAML.
  3. Меня попросили добавить XUL - язык разметки пользовательского интерфейса для Mozilla project. Я с ним никогда не имел дела - но пусть будет.

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

Как мне кажется, основная цель этих поделок:

  1. Дать возможность программистам сосредоточиться на функциональной стороне продукта.
  2. Предоставить дизайнерам язык разметки, очень похожий на привычный им html/css. При минимальном времени на привыкание дизайнеры могут создавать внешний вид программы используя родные для библиотеки виджеты, обладающие требуемой программистам функциональностью.

Этот подход в корне отличается от использования средств графического проектирования.

Если помните, для веба тоже были (и есть до сих пор) похожие инструменты.

Например, Adobe Dreamweaver. О "замусоренности" выдаваемой вёрстки говорить не буду: кто сталкивался - понимает.

При всех достоинствах практика показала: хороший верстальщик с твердым знанием html и css гораздо лучше изумительного художника, выдающего результат исключительно в Dreamweaver.

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

У нашего бедняги и без того задач хватает. Будет заниматься версткой - не успеет сделать функционал.

Такой же подход должен прийти на рынок "не веба".

Для "традиционных" GUI библиотек ситуация с версткой еще драматичней.

Есть средства графического проектирования интерфейса. Они - глюкавые. Это - факт.

Гораздо легче создать Domain Specific Language (DSL) для описания узкой области размещения красиво оформленных элементов на форме, чем сделать удобный редактор, работающий без ошибок.

Для набора этого текста я использую rst формат, затем markdown перегонит его в html. Набор в emacs. Это гораздо удобней Microsoft Office Word или Open Office Writer, даёт лучший контроль.

Но у автоматических средств GUI есть и более существенный недостаток.

Сейчас ими могут пользоваться только программисты. Просто потому, эта автоматика оперирует свойствами объектов, доступными только в "программерской" документации.

В то время как для веба уже давно есть отдельные доки по html и css, написанные для верстальщиков и не затрагивающие даже java script.

Не говорю уже про HTTP, незнакомый даже большинству веб-программистов нового поколения.

Заключение

Погружение в предметную область вышло неожиданно длинным.

Рассуждения об изменеиях в подходе визуалиации форм для "традиционных" приложений заняли очень много времени.

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

Есть опасение, что второй статьи такого же размера всё равно не хватит.

Продолжение - во второй части.