Subversion Repositories Projects

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
801 - 1
/*
2
*
3
* This file is part of QMapControl,
4
* an open-source cross-platform map widget
5
*
6
* Copyright (C) 2007 - 2008 Kai Winter
7
*
8
* This program is free software: you can redistribute it and/or modify
9
* it under the terms of the GNU Lesser General Public License as published by
10
* the Free Software Foundation, either version 3 of the License, or
11
* (at your option) any later version.
12
*
13
* This program is distributed in the hope that it will be useful,
14
* but WITHOUT ANY WARRANTY; without even the implied warranty of
15
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16
* GNU Lesser General Public License for more details.
17
*
18
* You should have received a copy of the GNU Lesser General Public License
19
* along with QMapControl. If not, see <http://www.gnu.org/licenses/>.
20
*
21
* Contact e-mail: kaiwinter@gmx.de
22
* Program URL   : http://qmapcontrol.sourceforge.net/
23
*
24
*/
25
 
26
#include "imagemanager.h"
27
namespace qmapcontrol
28
{
29
    ImageManager* ImageManager::m_Instance = 0;
30
    ImageManager::ImageManager(QObject* parent)
31
        :QObject(parent), emptyPixmap(QPixmap(1,1)), net(new MapNetwork(this)), doPersistentCaching(false)
32
    {
33
        emptyPixmap.fill(Qt::transparent);
34
 
35
        if (QPixmapCache::cacheLimit() <= 20000)
36
        {
37
            QPixmapCache::setCacheLimit(20000); // in kb
38
        }
39
    }
40
 
41
 
42
    ImageManager::~ImageManager()
43
    {
44
        if (ImageManager::m_Instance != 0)
45
        {
46
            delete ImageManager::m_Instance;
47
        }
48
        delete net;
49
    }
50
 
51
    QPixmap ImageManager::getImage(const QString& host, const QString& url)
52
    {
53
        //qDebug() << "ImageManager::getImage";
54
        QPixmap pm;
55
        //pm.fill(Qt::black);
56
 
57
        //is image cached (memory) or currently loading?
58
        if (!QPixmapCache::find(url, pm) && !net->imageIsLoading(url))
59
            //  if (!images.contains(url) && !net->imageIsLoading(url))
60
        {
61
            //image cached (persistent)?
62
            if (doPersistentCaching && tileExist(url))
63
            {
64
                loadTile(url,pm);
65
                QPixmapCache::insert(url.toAscii().toBase64(), pm);
66
            }
67
            else
68
            {
69
                //load from net, add empty image
70
                net->loadImage(host, url);
71
                //QPixmapCache::insert(url, emptyPixmap);
72
                return emptyPixmap;
73
            }
74
        }
75
        return pm;
76
    }
77
 
78
    QPixmap ImageManager::prefetchImage(const QString& host, const QString& url)
79
    {
80
#ifdef Q_WS_QWS
81
        // on mobile devices we don´t want the display resfreshing when tiles are received which are
82
        // prefetched... This is a performance issue, because mobile devices are very slow in
83
        // repainting the screen
84
        prefetch.append(url);
85
#endif
86
        return getImage(host, url);
87
    }
88
 
89
    void ImageManager::receivedImage(const QPixmap pixmap, const QString& url)
90
    {
91
        //qDebug() << "ImageManager::receivedImage";
92
        QPixmapCache::insert(url, pixmap);
93
        //images[url] = pixmap;
94
 
95
        // needed?
96
        if (doPersistentCaching && !tileExist(url) )
97
            saveTile(url,pixmap);
98
 
99
        //((Layer*)this->parent())->imageReceived();
100
 
101
        if (!prefetch.contains(url))
102
        {
103
            emit(imageReceived());
104
        }
105
        else
106
        {
107
 
108
#ifdef Q_WS_QWS
109
            prefetch.remove(prefetch.indexOf(url));
110
#endif
111
        }
112
    }
113
 
114
    void ImageManager::loadingQueueEmpty()
115
    {
116
        emit(loadingFinished());
117
        //((Layer*)this->parent())->removeZoomImage();
118
        //qDebug() << "size of image-map: " << images.size();
119
        //qDebug() << "size: " << QPixmapCache::cacheLimit();
120
    }
121
 
122
    void ImageManager::abortLoading()
123
    {
124
        net->abortLoading();
125
    }
126
    void ImageManager::setProxy(QString host, int port)
127
    {
128
        net->setProxy(host, port);
129
    }
130
 
131
    void ImageManager::setCacheDir(const QDir& path)
132
    {
133
        doPersistentCaching = true;
134
        cacheDir = path;
135
        if (!cacheDir.exists())
136
        {
137
            cacheDir.mkpath(cacheDir.absolutePath());
138
        }
139
    }
140
 
141
    bool ImageManager::saveTile(QString tileName,QPixmap tileData)
142
    {
143
        tileName.replace("/","-");
144
 
145
        QFile file(cacheDir.absolutePath() + "/" + tileName.toAscii().toBase64());
146
 
147
        //qDebug() << "writing: " << file.fileName();
148
        if (!file.open(QIODevice::ReadWrite )){
149
            qDebug()<<"error reading file";
150
            return false;
151
        }
152
        QByteArray bytes;
153
        QBuffer buffer(&bytes);
154
        buffer.open(QIODevice::WriteOnly);
155
        tileData.save(&buffer, "PNG");
156
 
157
        file.write(bytes);
158
        file.close();
159
        return true;
160
    }
161
    bool ImageManager::loadTile(QString tileName,QPixmap &tileData)
162
    {
163
        tileName.replace("/","-");
164
        QFile file(cacheDir.absolutePath() + "/" + tileName.toAscii().toBase64());
165
        if (!file.open(QIODevice::ReadOnly )) {
166
            return false;
167
        }
168
        tileData.loadFromData( file.readAll() );
169
 
170
        file.close();
171
        return true;
172
    }
173
    bool ImageManager::tileExist(QString tileName)
174
    {
175
        tileName.replace("/","-");
176
        QFile file(cacheDir.absolutePath() + "/" + tileName.toAscii().toBase64());
177
        if (file.exists())
178
            return true;
179
        else
180
            return false;
181
    }
182
}