lyx_mirror/src/graphics/GraphicsCache.C
Angus Leeming aa70718501 * Cure the crash that became a memory leak properly.
* Enable the loading of XPM files with crappy color strings. Print
  out a nice friendly message on what's gone wrong and how to resolve
  it properly.


git-svn-id: svn://svn.lyx.org/lyx/lyx-devel/trunk@3599 a592a061-630c-0410-9148-cb99ea01b6c8
2002-02-27 17:27:59 +00:00

191 lines
3.9 KiB
C

/*
* \file GraphicsCache.C
* Copyright 2002 the LyX Team
* Read the file COPYING
*
* \author Baruch Even <baruch.even@writeme.com>
* \author Angus Leeming <a.leeming@ic.ac.uk>
*/
#include <config.h>
#ifdef __GNUG__
#pragma implementation
#endif
#include "GraphicsCache.h"
#include "GraphicsCacheItem.h"
#include "GraphicsImage.h"
#include "GraphicsParams.h"
#include "insets/insetgraphics.h"
// I think that graphicsInit should become a new Dialogs::graphicsInit
// static method.
// These #includes would then be moved to Dialogs.C.
// Angus 25 Feb 2002
#include "GraphicsImageXPM.h"
//#include "xformsGraphicsImage.h"
namespace {
void graphicsInit()
{
using namespace grfx;
using SigC::slot;
// connect the image loader based on the XPM library
GImage::newImage.connect(slot(&GImageXPM::newImage));
GImage::loadableFormats.connect(slot(&GImageXPM::loadableFormats));
// connect the image loader based on the xforms library
// GImage::newImage.connect(slot(&xformsGImage::newImage));
// GImage::loadableFormats.connect(slot(&xformsGImage::loadableFormats));
}
} // namespace anon
namespace grfx {
GCache & GCache::get()
{
static bool start = true;
if (start) {
start = false;
graphicsInit();
}
// Now return the cache
static GCache singleton;
return singleton;
}
GCache::GCache()
{
cache = new CacheType;
}
// all elements are destroyed by the shared_ptr's in the map.
GCache::~GCache()
{
delete cache;
}
void GCache::update(InsetGraphics const & inset)
{
// A subset only of InsetGraphicsParams is needed for display purposes.
// The GraphicsParams c-tor also interrogates lyxrc to ascertain whether
// to display or not.
GParams params(inset.params());
// Each inset can reference only one file, so check the cache for any
// graphics files referenced by inset. If the name of this file is
// different from that in params, then remove the reference.
CacheType::iterator it = find(inset);
if (it != cache->end()) {
CacheItemType item = it->second;
if (item->filename() != params.filename) {
item->remove(inset);
if (item->empty())
cache->erase(it);
}
}
// Are we adding a new file or modifying the display of an existing one?
it = cache->find(params.filename);
if (it != cache->end()) {
it->second->modify(inset, params);
return;
}
CacheItemType item(new GCacheItem(inset, params));
if (item.get() != 0)
(*cache)[params.filename] = item;
}
void GCache::remove(InsetGraphics const & inset)
{
CacheType::iterator it = find(inset);
if (it == cache->end())
return;
CacheItemType item = it->second;
item->remove(inset);
if (item->empty()) {
cache->erase(it);
}
}
void GCache::startLoading(InsetGraphics const & inset)
{
CacheType::iterator it = find(inset);
if (it == cache->end())
return;
it->second->startLoading(inset);
}
ImagePtr const GCache::image(InsetGraphics const & inset) const
{
CacheType::const_iterator it = find(inset);
if (it == cache->end())
return ImagePtr();
return it->second->image(inset);
}
ImageStatus GCache::status(InsetGraphics const & inset) const
{
CacheType::const_iterator it = find(inset);
if (it == cache->end())
return ErrorUnknown;
return it->second->status(inset);
}
void GCache::changeDisplay(bool changed_background)
{
CacheType::iterator it = cache->begin();
CacheType::iterator end = cache->end();
for(; it != end; ++it)
it->second->changeDisplay(changed_background);
}
GCache::CacheType::iterator
GCache::find(InsetGraphics const & inset)
{
CacheType::iterator it = cache->begin();
for (; it != cache->end(); ++it) {
if (it->second->referencedBy(inset))
return it;
}
return cache->end();
}
GCache::CacheType::const_iterator
GCache::find(InsetGraphics const & inset) const
{
CacheType::const_iterator it = cache->begin();
for (; it != cache->end(); ++it) {
if (it->second->referencedBy(inset))
return it;
}
return cache->end();
}
} // namespace grfx