CreateAsset_test now passes the compiler, after quite some tinkering....
This commit is contained in:
parent
26374ce409
commit
814f6fc734
7 changed files with 136 additions and 53 deletions
|
|
@ -26,9 +26,28 @@
|
|||
** and the asset::ID primary key wrapper. Normally, Assets should be handled
|
||||
** using asset::PAsset, a ref counting smart pointer.
|
||||
**
|
||||
** These classes are placed into namespace asset and proc_interface.
|
||||
** These classes are placed into namespace asset and proc_interface.
|
||||
**
|
||||
** Assets are handled by a hierarchy of interfaces. Below the top level Asset interface
|
||||
** there are interfaces for various different <i>Kinds</i> of Assets, like asset::Media,
|
||||
** asset::Proc, etc. Code utilizing the specific properties of e.g. Media assets, will
|
||||
** be implemented directly against the asset::Media interface. To make this feasible
|
||||
** while at the same time being able to handle all asset Kinds in a uniform manner,
|
||||
** we use a hierarchy of ID classes. These IDs are actually just thin wrappers around
|
||||
** a hash value, but they carry a template parameter specifying the Asset Kind and the
|
||||
** Asset Kind subinterfaces provide a overloaded getID method with a covariant return
|
||||
** value. For example the asset::Media#getID returns an ID<Media>. By using the
|
||||
** templated query function AssetManager#getAsset, we can get at references to the more
|
||||
** specific subinterface asset::media just by using the ID value in a typesafe manner.
|
||||
** This helps avoiding dynamic typing and switch-on-type, leading to much more robust,
|
||||
** extensible and clear code.
|
||||
**
|
||||
** (Implementation detail: as g++ is not able to handle member function template
|
||||
** instantiations completely automatic, we need to trigger some template instantiations
|
||||
** at the end of assetmanager.cpp )
|
||||
**
|
||||
** @see assetmanager.hpp
|
||||
** @see media.hpp
|
||||
*/
|
||||
|
||||
|
||||
|
|
@ -70,6 +89,7 @@ namespace asset
|
|||
* @see Asset
|
||||
* @see AssetManager#getID generating ID values
|
||||
* @see asset::Media
|
||||
* @see ID<asset::Media>
|
||||
*/
|
||||
template<class KIND>
|
||||
class ID
|
||||
|
|
@ -85,16 +105,9 @@ namespace asset
|
|||
class AssetManager;
|
||||
typedef const ID<Asset>& IDA;
|
||||
|
||||
class Media;
|
||||
|
||||
|
||||
template<>
|
||||
class ID<Media> : public ID<Asset>
|
||||
{
|
||||
public:
|
||||
ID (size_t id);
|
||||
ID (const Media&);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Superinterface describing especially bookeeping properties.
|
||||
|
|
@ -105,7 +118,7 @@ namespace asset
|
|||
* <li>asset::Struct representing structural components used in the sesion (e.g. Tracks)</li>
|
||||
* <li>asset::Meta representing meta objects created while editing (e.g. Automation)</li>
|
||||
* </ul>
|
||||
* And of course, there are various concret Asset subclasses, like asset::Clip,
|
||||
* And of course there are various concret Asset subclasses, like asset::Clip,
|
||||
* asset::Effect, asset::Codec, asset::Track, asset::Dataset.
|
||||
* @note Assets objects have a strict unique identity and because of this are non-copyable.
|
||||
* You can not create an Asset derived object without registering it with the AssetManager
|
||||
|
|
@ -168,7 +181,7 @@ namespace asset
|
|||
|
||||
const Ident ident; ///< Asset identification tuple
|
||||
virtual const ID<Asset>& getID() const { return id; }
|
||||
private:
|
||||
protected:
|
||||
const ID<Asset> id; ///< Asset primary key.
|
||||
|
||||
|
||||
|
|
@ -256,8 +269,8 @@ namespace proc_interface
|
|||
{
|
||||
using asset::Asset;
|
||||
using asset::Category;
|
||||
// using asset::ID;
|
||||
// using asset::IDA;
|
||||
using asset::ID;
|
||||
using asset::IDA;
|
||||
using asset::PAsset;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -81,11 +81,10 @@ namespace asset
|
|||
{
|
||||
IdHashtable table;
|
||||
|
||||
friend class AssetManager;
|
||||
|
||||
DB () : table() {}
|
||||
~DB () {}
|
||||
|
||||
friend class cinelerra::singleton::Static<DB>;
|
||||
};
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -57,20 +57,28 @@ namespace asset
|
|||
return "";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
MediaFactory Media::create; ///< storage for the static MediaFactory instance
|
||||
|
||||
MediaFactory Media::create;
|
||||
|
||||
|
||||
/** Factory method for Media Asset instances. Depending on the filename given,
|
||||
* either a asset::Media object or an "Unknown" placeholder will be provided. If
|
||||
* the given Category already contains an "Unkown", we just get the
|
||||
* corresponding smart-ptr. Otherwise a new asset::Unknown is created. */
|
||||
* corresponding smart-ptr. Otherwise a new asset::Unknown is created.
|
||||
* @return an Media smart ptr linked to the internally registered smart ptr
|
||||
* created as a side effect of calling the concrete Media subclass ctor.
|
||||
*/
|
||||
MediaFactory::PType
|
||||
MediaFactory::operator() (Asset::Ident& key, const string& file)
|
||||
{
|
||||
asset::Media* pM (0);
|
||||
AssetManager& aMang = AssetManager::instance();
|
||||
|
||||
TODO ("check and fix Category if necessary");
|
||||
|
||||
if (isnil (file))
|
||||
{
|
||||
if (isnil (key.name)) key.name="nil";
|
||||
|
|
@ -86,11 +94,13 @@ namespace asset
|
|||
TODO ("file exists?");
|
||||
pM = new Media (key,file);
|
||||
}
|
||||
ASSERT (pM);
|
||||
ENSURE (key.category.hasKind (VIDEO) || key.category.hasKind(AUDIO));
|
||||
ENSURE (isnil (key.name));
|
||||
ENSURE (dynamic_cast<Media*>(pM) || (isnil (file) && dynamic_cast<Unknown*>(pM)));
|
||||
|
||||
return PType (pM, &destroy);
|
||||
return aMang.getAsset (pM->getID()); // note: because we query with an ID<Media>,
|
||||
// we get a Media smart ptr.
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -101,7 +111,14 @@ namespace asset
|
|||
MediaFactory::operator() (const string& file, Category& cat)
|
||||
{
|
||||
Asset::Ident key(extractName(file), cat, "cin3", 1);
|
||||
return MediaFactory::operator() (key, file);
|
||||
return operator() (key, file);
|
||||
}
|
||||
|
||||
MediaFactory::PType
|
||||
MediaFactory::operator() (const string& file, asset::Kind kind)
|
||||
{
|
||||
Category cat(kind);
|
||||
return operator() (file, cat);
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -109,16 +126,22 @@ namespace asset
|
|||
MediaFactory::operator() (const char* file, Category& cat)
|
||||
{
|
||||
if (!file) file = "";
|
||||
return operator() (file,cat);
|
||||
return operator() (string(file),cat);
|
||||
}
|
||||
|
||||
MediaFactory::PType
|
||||
MediaFactory::operator() (const char* file, asset::Kind kind)
|
||||
{
|
||||
if (!file) file = "";
|
||||
return operator() (string(file),kind);
|
||||
}
|
||||
|
||||
MediaFactory::PType
|
||||
MediaFactory::operator() (Asset::Ident& key, const char* file)
|
||||
{
|
||||
if (!file) file = "";
|
||||
return operator() (key,file);
|
||||
return operator() (key, string(file));
|
||||
}
|
||||
|
||||
|
||||
|
||||
} // namespace asset
|
||||
|
|
|
|||
|
|
@ -21,6 +21,17 @@
|
|||
*/
|
||||
|
||||
|
||||
/** @file media.hpp
|
||||
** Media data is a specific Kind of Asset.
|
||||
** For the different <i>Kinds</i> of Assets, we use sub-intefaces inheriting
|
||||
** from the general Asset interface. To be able to get asset::Media instances
|
||||
** directly from the AssetManager, we define a specialization of the Asset ID.
|
||||
**
|
||||
** @see asset.hpp for explanation
|
||||
** @see MediaFactory creating concrete asset::Media instances
|
||||
**
|
||||
*/
|
||||
|
||||
#ifndef ASSET_MEDIA_H
|
||||
#define ASSET_MEDIA_H
|
||||
|
||||
|
|
@ -36,8 +47,16 @@ namespace asset
|
|||
class MediaFactory;
|
||||
|
||||
|
||||
template<>
|
||||
class ID<Media> : public ID<Asset>
|
||||
{
|
||||
public:
|
||||
ID (size_t id);
|
||||
ID (const Media&);
|
||||
};
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* key abstraction: media-like assets
|
||||
*/
|
||||
|
|
@ -46,27 +65,29 @@ namespace asset
|
|||
string filename_;
|
||||
|
||||
public:
|
||||
virtual const ID<Media>& getID() const { return getID(); }
|
||||
static MediaFactory create;
|
||||
const string& getFilename () { return filename_; }
|
||||
const string& getFilename () const { return filename_; }
|
||||
|
||||
virtual const ID<Media>& getID() const ///< @return ID of kind Media
|
||||
{
|
||||
return static_cast<const ID<Media>& > (Asset::getID());
|
||||
}
|
||||
|
||||
protected:
|
||||
Media (const Asset::Ident& idi, const string& file) : Asset(idi), filename_(file) {}
|
||||
friend class MediaFactory;
|
||||
};
|
||||
|
||||
|
||||
|
||||
// definition of ID<Media> ctors is possible now,
|
||||
// after providing full definition of class Media
|
||||
/*
|
||||
ID<Media>::ID(size_t id)
|
||||
: ID<Asset> (id) {};
|
||||
|
||||
ID<Media>::ID(const Media& media)
|
||||
: ID<Asset> (media.getID()) {};
|
||||
|
||||
*/
|
||||
|
||||
inline ID<Media>::ID(size_t id) : ID<Asset> (id) {};
|
||||
inline ID<Media>::ID(const Media& media) : ID<Asset> (media.getID()) {};
|
||||
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Factory specialized for createing Media Asset objects.
|
||||
*/
|
||||
|
|
@ -77,9 +98,11 @@ namespace asset
|
|||
|
||||
PType operator() (Asset::Ident& key, const string& file="");
|
||||
PType operator() (const string& file, Category& cat);
|
||||
PType operator() (const string& file, asset::Kind);
|
||||
|
||||
PType operator() (Asset::Ident& key, const char* file); ///< convienience overload using cString
|
||||
PType operator() (Asset::Ident& key, const char* file); ///< convienience overload using C-String
|
||||
PType operator() (const char* file, Category& cat);
|
||||
PType operator() (const char* file, asset::Kind);
|
||||
|
||||
protected:
|
||||
static void destroy (Media* m) { delete m; }
|
||||
|
|
|
|||
|
|
@ -23,7 +23,6 @@
|
|||
|
||||
#include "proc/assetmanager.hpp"
|
||||
#include "proc/asset/db.hpp"
|
||||
#include "common/singleton.hpp"
|
||||
|
||||
//#include <boost/functional/hash.hpp>
|
||||
|
||||
|
|
@ -35,14 +34,10 @@ namespace asset
|
|||
/** get at the system-wide asset manager instance.
|
||||
* Implemented as singleton.
|
||||
*/
|
||||
AssetManager&
|
||||
AssetManager::instance ()
|
||||
{
|
||||
return *(new AssetManager); //////////////////////////////TODO Singleton<AssetManager>::instance();
|
||||
}
|
||||
Singleton<AssetManager> AssetManager::instance;
|
||||
|
||||
AssetManager::AssetManager ()
|
||||
: registry (*(new DB)) //(Singleton<asset::DB>::instance())
|
||||
: registry (Singleton<asset::DB>() ())
|
||||
{ }
|
||||
|
||||
|
||||
|
|
@ -61,7 +56,7 @@ namespace asset
|
|||
*/
|
||||
template<class KIND>
|
||||
ID<KIND>
|
||||
AssetManager::reg (KIND& obj, const Asset::Ident& idi)
|
||||
AssetManager::reg (KIND* obj, const Asset::Ident& idi)
|
||||
throw(cinelerra::error::Invalid)
|
||||
{
|
||||
UNIMPLEMENTED ("AssetManager::reg");
|
||||
|
|
@ -110,6 +105,32 @@ namespace asset
|
|||
{
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
} // namespace asset
|
||||
|
||||
|
||||
|
||||
|
||||
/************************************************************/
|
||||
/* explicit template instantiations for various Asset Kinds */
|
||||
/************************************************************/
|
||||
|
||||
#include "proc/asset/media.hpp"
|
||||
#include "proc/asset/proc.hpp"
|
||||
#include "proc/asset/struct.hpp"
|
||||
#include "proc/asset/meta.hpp"
|
||||
|
||||
|
||||
namespace asset
|
||||
{
|
||||
|
||||
template ID<Asset> AssetManager::reg (Asset* obj, const Asset::Ident& idi);
|
||||
|
||||
|
||||
template shared_ptr<Asset> AssetManager::getAsset (const ID<Asset>& id) throw(cinelerra::error::Invalid);
|
||||
template shared_ptr<Media> AssetManager::getAsset (const ID<Media>& id) throw(cinelerra::error::Invalid);
|
||||
template shared_ptr<Proc> AssetManager::getAsset (const ID<Proc>& id) throw(cinelerra::error::Invalid);
|
||||
template shared_ptr<Struct> AssetManager::getAsset (const ID<Struct>& id) throw(cinelerra::error::Invalid);
|
||||
template shared_ptr<Meta> AssetManager::getAsset (const ID<Meta>& id) throw(cinelerra::error::Invalid);
|
||||
|
||||
} // namespace asset
|
||||
|
|
|
|||
|
|
@ -38,6 +38,7 @@
|
|||
|
||||
#include "proc/asset.hpp"
|
||||
#include "common/error.hpp"
|
||||
#include "common/singleton.hpp"
|
||||
|
||||
#include <cstddef>
|
||||
#include <string>
|
||||
|
|
@ -62,7 +63,7 @@ namespace asset
|
|||
|
||||
|
||||
public:
|
||||
static AssetManager& instance();
|
||||
static cinelerra::Singleton<AssetManager> instance;
|
||||
|
||||
/** provide the unique ID for given Asset::Ident tuple */
|
||||
static ID<Asset> getID (const Asset::Ident&);
|
||||
|
|
@ -90,12 +91,14 @@ namespace asset
|
|||
* @internal used by the Asset base class ctor to create Asset::id.
|
||||
*/
|
||||
template<class KIND>
|
||||
static ID<KIND> reg (KIND& obj, const Asset::Ident& idi)
|
||||
static ID<KIND> reg (KIND* obj, const Asset::Ident& idi)
|
||||
throw(cinelerra::error::Invalid);
|
||||
|
||||
friend Asset::Asset (const Asset::Ident& idi);
|
||||
|
||||
AssetManager ();
|
||||
|
||||
friend class cinelerra::singleton::Static<AssetManager>;
|
||||
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -60,13 +60,12 @@ namespace asset
|
|||
|
||||
void createMedia()
|
||||
{
|
||||
/* typedef shared_ptr<asset::Media> PM;
|
||||
typedef shared_ptr<asset::Media> PM;
|
||||
Category cat(VIDEO,"bin1");
|
||||
Asset::Ident key("Name-1", cat, "ichthyo", 5);
|
||||
PM mm1 = asset::Media::create(key,"testfile.mov");
|
||||
PM mm2 = asset::Media::create(key);
|
||||
Category vid(VIDEO);////////////////////////////////////////////////FIXME
|
||||
PM mm3 = asset::Media::create("testfile2.mov", vid);
|
||||
PM mm3 = asset::Media::create("testfile2.mov", VIDEO);
|
||||
|
||||
// Assets have been registered and can be retrieved by ID
|
||||
AssetManager& aMang = AssetManager::instance();
|
||||
|
|
@ -76,11 +75,11 @@ namespace asset
|
|||
|
||||
ASSERT (aMang.getAsset (mm1->getID()) != mm2);
|
||||
|
||||
// PAsset aa1 = aMang.getAsset (ID<Asset>(mm1->getID())); // note we get an Asset ref
|
||||
// ASSERT (aa1 == mm1);
|
||||
PAsset aa1 = aMang.getAsset (ID<Asset>(mm1->getID())); // note we get an Asset ref
|
||||
ASSERT (aa1 == mm1);
|
||||
PM mX1 = aMang.getAsset (mm1->getID()); // ..and now we get a Media ref
|
||||
ASSERT (mX1 == mm1);
|
||||
// ASSERT (mX1 == aa1);
|
||||
ASSERT (mX1 == aa1);
|
||||
|
||||
ASSERT (aMang.known (mm1->getID()));
|
||||
ASSERT (aMang.known (mm2->getID()));
|
||||
|
|
@ -89,7 +88,7 @@ namespace asset
|
|||
ASSERT ( !aMang.known (mm3->getID(), Category(AUDIO))); // not found within AUDIO-Category
|
||||
try
|
||||
{ // can't be found if specifying wrong Asset kind....
|
||||
// aMang.getAsset (ID<asset::Proc>(mm1->getID()));
|
||||
aMang.getAsset (ID<asset::Proc>(mm1->getID()));
|
||||
NOTREACHED;
|
||||
}
|
||||
catch (cinelerra::error::Invalid) { }
|
||||
|
|
@ -116,6 +115,8 @@ namespace asset
|
|||
ASSERT (mm1->getFilename() == "testfile.mov");
|
||||
ASSERT (isnil (mm2->getFilename()));
|
||||
ASSERT (mm3->getFilename() == "testfile2.mov");
|
||||
/*
|
||||
////////////////////////////////////////////////////////////////////////////////TODO fuck the compiler!!!
|
||||
*/
|
||||
}
|
||||
};
|
||||
|
|
|
|||
Loading…
Reference in a new issue