C++ (Qt)class Tile : public QGraphicsItem{...};
#include <QtGui>#include <iostream.h>#include "MyView.h"int main(int argc, char** argv){ QApplication app(argc, argv); QGraphicsScene scene(QRectF(0, 0, 30000, 30000)); MyView * pView = new MyView(&scene); QWidget w; QPushButton *btn = new QPushButton("Button", pView); QHBoxLayout *lay = new QHBoxLayout; QObject::connect(btn, SIGNAL(clicked()), pView, SLOT(pressBotton())); std::cout<<"run\n"; pView->init(); //pView->show(); lay->addWidget(btn); lay->addWidget(pView); w.setLayout(lay); w.show(); return app.exec();}
#ifndef TILE_H#define TILE_H#include <QtGui>class Tile{private: int x; int y; QGraphicsRectItem * rect;public: Tile(int pos_x, int pos_y, QGraphicsRectItem * qGraphicsRectItem) { x = pos_x; y = pos_y; rect = qGraphicsRectItem; } int pos_x() { return x; } int pos_y() { return y; } QGraphicsRectItem* item() { return rect; }};#endif // TILE_H
#ifndef _MyView_h_#define _MyView_h_#include <QGraphicsView>#include <windows.h>#include "tile.h"class MyView: public QGraphicsView { Q_OBJECTpublic: MyView(QGraphicsScene* pScene, QWidget* pwgt = 0) : QGraphicsView(pScene, pwgt) { resize(1000, 800); setDragMode(QGraphicsView::ScrollHandDrag); }private: static const int divide = 500; RGBTRIPLE mas[divide][divide]; tagBITMAPFILEHEADER stHead; tagBITMAPINFOHEADER stInfoHead; FILE *pInFile2; QList<Tile *> tileList;public slots: void pressBotton();private slots: void scrollBars();public: void moved(int verticalScrollBar, int horizontalScrollBar); void init(); Tile * showRect(int x, int y);};#endif //_MyView_h_
#include "MyView.h"#include "tile.h"#include <QtGui>#include <iostream>using namespace std;void MyView::scrollBars(){ moved(this->verticalScrollBar()->value(), this->horizontalScrollBar()->value());}void MyView::moved(int verticalScrollBar, int horizontalScrollBar){ static int qw = 1; if (qw == 1) { qw--; return; } // Сохраняем static int xx = 0, yy = 0; //Теперь нам нужно понять какие тайлы сейчас видны на экране. int viewTile_x = horizontalScrollBar / divide; int viewTile_y = verticalScrollBar / divide; int colTile_x = ((this->rect().height() + (verticalScrollBar % divide)) / divide) + 1; int colTile_y = ((this->rect().width() + (horizontalScrollBar % divide)) / divide) + 1; cout<<"\nhor: "<< viewTile_x <<" "<<colTile_x; cout<<"\nver: "<< viewTile_y <<" "<<colTile_y; std::cout<< "\nvert x hor: " << verticalScrollBar << " x " << horizontalScrollBar; if ((abs(xx - viewTile_x) + abs(yy - viewTile_y)) < 1) return; // Отображение for (int y = viewTile_y; y < viewTile_y + colTile_y; y++) for (int x = viewTile_x; x < viewTile_x + colTile_x + 1; x++) { tileList.append(showRect(x, y)); } xx = viewTile_x; yy = viewTile_y;}void MyView::init(){ connect(this->horizontalScrollBar(), SIGNAL(valueChanged(int)), this, SLOT(scrollBars())); connect(this->verticalScrollBar(), SIGNAL(valueChanged(int)), this, SLOT(scrollBars())); // Чтение изображения из файла FILE *pInFile; if ((pInFile = fopen("1.bmp", "rb")) != NULL) { // Чтение заголовков fread(&stHead, sizeof(tagBITMAPFILEHEADER), 1, pInFile); fread(&stInfoHead, sizeof(tagBITMAPINFOHEADER), 1, pInFile); fclose(pInFile); cout<<"file readed\n"; } cout<<"\nWidth: "<<stInfoHead.biWidth; cout<<"\nHeight: "<<stInfoHead.biHeight; // Преобразование файла в свою структуру данных if ((pInFile2 = fopen("1.slko", "rb")) == NULL) { RGBTRIPLE ** BitMap = new RGBTRIPLE *[divide]; FILE *pInFile1 = fopen("1.slko", "wb"); for(int i = 0; i < divide; i++) { BitMap[i] = new RGBTRIPLE[stInfoHead.biWidth]; } cout<<"\nkontrol point 1\n"; for(int col_h = stInfoHead.biHeight / divide; col_h > 0 ; col_h--) { for (int i = 0; i < divide; i++) { fseek(pInFile, (stHead.bfOffBits + ((stInfoHead.biWidth * 3) * ((divide * col_h) - i))), SEEK_SET); fread(BitMap[i], sizeof(RGBTRIPLE), stInfoHead.biWidth, pInFile); } cout<<"kontrol point 2\n"; // Осталось разбить матрицу (500 х stInfoHead.biWidth) на квадраты for (int y = 0; y < stInfoHead.biWidth / divide; y++) { for (int j = 0; j < divide; j++) { for (int k = 0; k < divide; k++) { mas[j][k] = BitMap[j][y * divide + k]; } } fwrite(mas, sizeof(RGBTRIPLE), divide*divide, pInFile1); } } cout<<"kontrol point"; fclose(pInFile1); pInFile2 = fopen("1.slko", "rb"); }}Tile * MyView::showRect(int x, int y){ // Просто отображаем один квадрат int kolW = stInfoHead.biWidth / divide; fseek(pInFile2, (divide * divide * 3 * (y * kolW + x)), SEEK_SET); fread(mas, sizeof(RGBTRIPLE), divide*divide, pInFile2); QImage *img = new QImage(divide, divide, QImage::Format_RGB32); for(int i = 0; i < divide; i++) for(int j = 0; j < divide; j++) { QRgb rgb = qRgb(mas[i][j].rgbtRed, mas[i][j].rgbtGreen, mas[i][j].rgbtBlue); img->setPixel(j, i, rgb); } QGraphicsRectItem * item = new QGraphicsRectItem(x * divide, y * divide, divide, divide, 0, this->scene()); //item->setPen(Qt::NoPen); item->setBrush(QPixmap::fromImage(*img)); Tile *tile = new Tile(x, y, item); return tile; //this->scene()->itemAt(x * divide, y * divide)->~QGraphicsItem(); //return this->scene()->addRect(x * divide, y * divide, divide, divide, Qt::NoPen, QBrush(QPixmap::fromImage(*img)));}void MyView::pressBotton(){ cout<<"\nPress"; cout<<"\ntile count: "<<tileList.count(); QList<QGraphicsItem *> oldList; oldList = this->scene()->items(); cout<<"\noldList: "<<oldList.count(); for (int i = 0; i < tileList.count(); ++i) { cout<<'\n'<<tileList[i]->pos_x(); tileList[i]->item()->~QGraphicsRectItem(); tileList.removeAt(i); }}
QGraphicsItem(QGraphicsItem *parent = 0#ifndef Q_QDOC // obsolete argument , QGraphicsScene *scene = 0#endif );
void MyView::pressBotton(){ cout<<"\nPress"; cout<<"\ntile count: "<<tileList.count(); cout<<"\noldList: "<<this->scene()->items().count(); tileList.clear(); this->scene()->clear();}