Решил написать пост о популярном нынче Canvas из HTML5 и о своем проекте dbcartajs, его использующем. Почему Canvas? Немного истории. Прежде для создания изображений, иллюстрирующих различные расчетные модели (например, вывод окружности по радиусу и центру в координатах, вывод многоугольника с количеством вершин N и площадью S, вывод окружности на сферу и т.д.), я и мои коллеги по работе в институте использовали различные элементы управления из разных сред разработки: PictureBox их VB6, QPainter и QCanvas из Qt, Canvas из Tk и, наконец, создание изображений по mapfile из MapServer. Позже после знакомства с возможностями HTML5 я решил перейти на использование Canvas и Web-разработку с JavaScript. Удобно — для отладки и разработки нужен лишь браузер.


Собравшись с силами и вооружившись документацией от W3C, я переписал часть функционала компонентов, которые мы используем в работе, на JavaScript, оформив это в проект dbcartajs на GitHub. Код реализован в виде объекта dbCarta, чтобы использовать его как виджет на страницах без копирования частей исходного кода.
Собственно идейно dbcartajs портирован из проекта dbCarta, реализованном на Python и Tkinter, доступном в репозитории GitHub.

Как это работает


dbcartajs использует Canvas для вывода объектов по координатам (долгота, широта в градусах) или пойнтам (points). В проект включена библиотека Proj4js, реализующая пересчеты картографических проекций. Из нее на использование настроены несколько проекций — это сферические nsper, ortho, laea и меркатор (как у популярного Google Maps — Google Mercator). По умолчанию используется холст с соотношением сторон ширина-высота 2:1, что соответствует плоской проекции longlat из Proj4js. Если proj4js-combined.js подгружен, то доступны другие проекции через интерфейсы changeProject или initProj объекта dbCarta.


Проекция Меркатор

Конечно, не все возможности Canvas реализованы в dbcartajs, но некоторым я постарался уделить внимание. Первое, это шрифты. При масштабировании они не меняются. Второе, это использование метода isPointInPath, позволяющего реализовать аналог использования элементов MAP, AREA и IMG. И третье, это возможность совмещения объектов из разных проекций. В демо StarrySky для вывода границ Земли, контуров материков используется сферическая проекция nsper, для вывода звезд, орбит космических аппаратов — плоская проекция longlat. Для смены проекций используются методы initProj (с указанием параметров проекции для Proj4js) или changeProject (без параметров).


Совмещение проекций в StarrySky.

Про управление


Перемещение по карте доступно по клику (по клику центрируется точка в пределах карты). Масштабирование карты осуществляется через интерфейс scaleCarta или по кнопкам "+" и "-", расположенным справа. В сферических проекциях вращение глобуса осуществляется через интерфейс initProj.

Где посмотреть


Примеры проекта можно посмотреть на сaйте egaxegax.github.io/dbcartajs. Исходники доступны в репозитории GitHub .