На главную... Продукты | Технологии | Классификаторы | Проекты | Скачать | Цены| Форум | Статьи | Обучение | Контакты

Правильно работать с mapPaintMapObjectToXImage

Поиск  Пользователи  Правила  Войти
Форум » Настольные приложения » GIS ToolKit, GIS ToolKit Active, ГИС Конструктор для Windows
Страницы: 1
RSS
Правильно работать с mapPaintMapObjectToXImage
 
Отображаю карту с помощью MAPAPI (слизано с примера MapView)
Карта отображается правильно, теперь хочу мигать выделенными объектами, предварительно найденными через mapSeekSiteObject и внесенные в список selectedObjects.
Вывожу объект через mapPaintMapObjectToXImage, но на карте не вижу отрисовку объекта другим цветом (объект на карте находится, его рамка определяется правильно)
Что-то не так со значениями параметров функции mapPaintMapObjectToXImage?
Цитата
long int x, long int y, LRECT * rect

Цитата
void GISMapView::paintEvent(QPaintEvent *event)
{
   if (!hMap) return;
   int x = event->rect().left();
   int y = event->rect().top();
   int width= event->rect().right() - event->rect().left() + 1;
   int height = event->rect().bottom() - event->rect().top() + 1;

   if (CheckMemoryNeeded(width, height))
   {
     WidthBM = width;
     HeightBM = height;
   }

   QPainter p;
   p.begin(this);

   // Область отрисовки карты в пикселях
   RECT rectDraw;
   rectDraw.left = x+mapLeft;
   rectDraw.top = y+mapTop;
   rectDraw.right = x + width+mapLeft;
   rectDraw.bottom = y + height+mapTop;

   if (BitMap)
   {
       memset(BitMap, 0x0, BitMapSize);

       XIMAGEDESC xImageDesc;
       xImageDesc.Point = BitMap;                     // Адрес начала области пикселов
       xImageDesc.Width = width;                         // Ширина строки в пикселах
       xImageDesc.Height = height;                        // Число строк
       xImageDesc.Depth = MAPDEPTH;                   // Размер элемента в битах (8,15,16,24,32)
       xImageDesc.CellSize = BMCELLSIZE;              // Размер элемента(пиксела) в байтах
       xImageDesc.RowSize = width * xImageDesc.CellSize; // Ширина строки в байтах

       // Отобразим фрагмент карты на экран
       if (mapPaintToXImage(hMap, &xImageDesc, 0, 0, &rectDraw))
       {
           //есть выделенные объекты, надо их наложить сверху
           if (selectedObjects.count()>0){
               IMGLINE objectImage;
               memset(&objectImage, 0, sizeof(objectImage));
               objectImage.Thick = PIX2MKM(5);

               PAINTPARM objectView;
               memset(&objectView, 0, sizeof(objectView));
               objectView.Parm = (char*) &objectImage;
               objectView.Mode = R2_COPYPEN;
               //мигание объекта по таймеру (голубой/малиновый)
               if (colorState) objectImage.Color = selColor1;
               else objectImage.Color = selColor2;

               LRECT rectObj;
               double oX, oY;
               DFRAME frame;

               for (int i=0; i<selectedObjects.count(); i++){
                   HOBJ hObj=selectedObjects.at(i);

                   //координаты области объекта на карте в метрах
                   mapObjectFrame(hObj,&frame);

                   //координаты области объекта на карте в пикселях
                   oX=frame.X1; oY=frame.Y1;
                   mapPlaneToPicture(hMap,&oX,&oY);
                   rectObj.left=oX; rectObj.top=oY;
                   oX=frame.X2; oY=frame.Y2;
                   mapPlaneToPicture(hMap,&oX,&oY);
                   rectObj.right=oX; rectObj.bottom=oY;

                   //отобразим объект на XImage поверх существующего изображения (-2)
                   if (mapObjectLocal(hObj)!=LOCAL_LINE) objectView.Image = IMG_OBJECT;
                   else objectView.Image = IMG_LINE;
                   mapPaintMapObjectToXImage(hMap,&xImageDesc,-2,rectObj.left-rectDraw.left,rectObj.top-rectDraw.top,&rectObj,&objectView,hObj);
               }
           }

           //вывод на экран
           QImage image((uchar *)BitMap, width, height, QImage::Format_RGB32);
           p.drawImage(x, y, image, 0, 0, width, height);
       }
   }

   p.end();
}
 
Добрый день!

Пример реализации мигания контура выбранных объектов на карте можно посмотреть в исходных текстах библиотеки компонентов (/usr/share/gisdesigner/examples/Sdk/qmapcomponents) в файле qdmanimator.cpp.
Если требуется отрисовать карту вместе c выделенными объектами, то можно воспользоваться функцией mapPaintAndSelectToXImage (mapapi.h).
Код
  // Вывести изображение карты в XImage (массив) и выделить
  // на карте отобранные объекты
  // Описание структуры XIMAGEDESC в maptype.h
  // x,y - координаты левого верхнего угла внутри
  // битовой области XImage для размещения изображения
  // rect - выводимый фрагмент карты
  // select - условия отбора объектов, если равны 0, то применяются
  //          условия обобщенного поиска\выделения (см. mapTotalPaintSelect95).
  // color  - цвет, которым будут выделяться объекты на карте
  // При ошибке в параметрах возвращает ноль

_MAPIMP long int _MAPAPI mapPaintAndSelectToXImage(HMAP hMap, const XIMAGEDESC *imagedesc,
                                                    long int x, long int y, const RECT *rect,
                                                    HSELECT select, COLORREF color);
 
Как мигать объектами я знаю, делал на MAPAPI через mapDrawImageMapObject в общий буфер экрана HIMAGE, потом в XImage и на экран
В примере же MapView сразу изображение выводится в XImage и потом на экран.
Делаю я все на чистом MAPAPI без применения QD-классов, поэтому код из qdmanimator.cpp не то.
Хотелось бы вывести объект через mapPaintMapObjectToXImage,

Функцию mapPaintAndSelectToXImage попробовал, работает. Но все же это полная перерисовка окна по таймеру, если хочется мигать цветом.
Целесообразнее будет отдельные объекты перерисовывать через mapPaintMapObjectToXImage.
Изменено: Валерий Парусов - 06.10.2025 20:44:33
 
В приведенном примере кода для вызова mapPaintMapObjectToXImage() при пересчете рамки объекта в пиксели меняются местами верх и низ объекта, что может являться причиной наблюдаемого поведения.
 
В результате экспериментов выяснилось, что не надо никаких рамок объекта вычислять, надо так:  
Код
LRECT rectObj;
rectObj.left=rectDraw.left;
rectObj.top = rectDraw.top;
rectObj.right = rectDraw.right;
rectObj.bottom = rectDraw.bottom;

for (int i=0; i<selectedObjects.count(); i++){
 HOBJ hObj=selectedObjects.at(i);              
 if (mapObjectLocal(hObj)!=LOCAL_LINE) objectView.Image = IMG_OBJECT;
 else objectView.Image = IMG_LINE;
                    
 //отобразим объект на XImage поверх существующего изображения (-2)
 mapPaintMapObjectToXImage(hMap,&xImageDesc,-2,0,0,&rectObj,&objectView,hObj);
}
вот только по флагу erase вопрос: что 0, что 1, что -2  - вообще визуально ничем не отличается вывод
Изменено: Валерий Парусов - 08.10.2025 18:49:21
 
Добрый день!

Спасибо за обратную связь! Провели дополнительное тестирование - на текущий момент параметр erase функцией mapPaintMapObjectToXImage() обрабатывается в соответствии с описанием, за исключением значения 1 (очистка фрагмента цветом фона). Обработку данного значения доработаем и включим в состав следующей версии ГИС Конструктор. О выходе обновленной версии сообщим в данной ветке форума.
Код
 // Вывести изображение объекта в XImage
 //  hmap      - идентификатор открытых данных
 //  imagedesc - описание буфера вывода (см. maptype.h)
 //  erase     - признак предварительной очистки фона изображения
 //              (0 - фон не стирать, 1 - очистить фрагмент цветом фона, -2 - выполнить отображение поверх существующего изображения)
 //  x, y      - смещения отображеня в XImage
 //  rect      - координаты фрагмента карты
 //              в изображении (Picture).
 //  image     - описание вида объекта (см. MAPGDI.H), если объект
 //              должен рисоваться своим условным знаком - значение параметра
 //              можно установить в ноль,
 //  object    - идентификатор объекта карты в памяти
 // При ошибке в параметрах возвращает ноль

_MAPIMP long int _MAPAPI mapPaintMapObjectToXImage(HMAP hMap, XIMAGEDESC * imagedesc, long int erase,
                                                   long int x, long int y, LRECT * rect, PAINTPARM* image, HOBJ object);
 
Добрый день!

Обновленная версия ГИС Конструктор с исправленной обработкой параметра erase в функции mapPaintMapObjectToXImage() доступна для скачивания на нашем сайте.
Спасибо за ожидание!
 
А в ToolKit тоже  поправлено?
 
Обновление ГИС Конструктор для Windows и GIS ToolKit планируется в ближайшее время.
О выходе версий оповестим в данной теме.
 
Добрый день!

Обновленные версии ГИС Конструктор для Windows и GIS ToolKit доступны для скачивания на нашем сайте.
Спасибо за ожидание!
Страницы: 1
Читают тему (гостей: 1)



© КБ Панорама, 1991-2026

Регистрируясь или авторизуясь на форуме, Вы соглашаетесь с Политикой конфиденциальности