Enable just enough of the message based format used in Icon-O-Matic to allow

BIconUtils to understand and render it. This makes it possible to use the
HVIFTranslator to also read Icon-O-Matic files out of the box. Will cleanup
now duplicated files next.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@30794 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Michael Lotz 2009-05-18 20:15:04 +00:00
parent dca631302d
commit 8b8d44bfcc
26 changed files with 374 additions and 41 deletions

View File

@ -23,6 +23,7 @@
#include "Icon.h"
#include "IconRenderer.h"
#include "FlatIconImporter.h"
#include "MessageImporter.h"
#ifndef HAIKU_TARGET_PLATFORM_HAIKU
# define B_MINI_ICON_TYPE 'MICN'
@ -244,8 +245,14 @@ BIconUtils::GetVectorIcon(const uint8* buffer, size_t size, BBitmap* result)
FlatIconImporter importer;
ret = importer.Import(&icon, const_cast<uint8*>(buffer), size);
if (ret < B_OK)
return ret;
if (ret < B_OK) {
// try the message based format used by Icon-O-Matic
MessageImporter messageImporter;
BMemoryIO memoryIO(const_cast<uint8*>(buffer), size);
ret = messageImporter.Import(&icon, &memoryIO);
if (ret < B_OK)
return ret;
}
IconRenderer renderer(temp);
renderer.SetIcon(&icon);

View File

@ -6,6 +6,7 @@ AddSubDirSupportedPlatforms libbe_test ;
# source directories
local sourceDirs =
flat_icon
message
shape
style
transformable
@ -29,6 +30,10 @@ StaticLibrary libicon.a :
LittleEndianBuffer.cpp
PathCommandQueue.cpp
# message
Defines.cpp
MessageImporter.cpp
# shape
PathContainer.cpp
Shape.cpp

View File

@ -0,0 +1,11 @@
/*
* Copyright 2007, Haiku. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Authors:
* Stephan Aßmus <superstippi@gmx.de>
*/
#include "Defines.h"
const uint32 kNativeIconMagicNumber = 'IMSG';
const char* kNativeIconMimeType = "application/x-vnd.Haiku-icon";

View File

@ -0,0 +1,17 @@
/*
* Copyright 2007, Haiku. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Authors:
* Stephan Aßmus <superstippi@gmx.de>
*/
#ifndef DEFINES_H
#define DEFINES_H
#include <SupportDefs.h>
extern const uint32 kNativeIconMagicNumber;
extern const char* kNativeIconMimeType;
#endif // DEFINES_H

View File

@ -0,0 +1,236 @@
/*
* Copyright 2006-2007, Haiku. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Authors:
* Stephan Aßmus <superstippi@gmx.de>
*/
#include "MessageImporter.h"
#include <new>
#include <stdio.h>
#include <Archivable.h>
#include <ByteOrder.h>
#include <DataIO.h>
#include <Message.h>
#include "Defines.h"
#include "Icon.h"
#include "PathContainer.h"
#include "Shape.h"
#include "Style.h"
#include "StyleContainer.h"
#include "VectorPath.h"
using std::nothrow;
// constructor
MessageImporter::MessageImporter()
#ifdef ICON_O_MATIC
: Importer()
#endif
{
}
// destructor
MessageImporter::~MessageImporter()
{
}
// Import
status_t
MessageImporter::Import(Icon* icon, BPositionIO* stream)
{
#ifdef ICON_O_MATIC
status_t ret = Init(icon);
if (ret < B_OK) {
printf("MessageImporter::Import() - "
"Init() error: %s\n", strerror(ret));
return ret;
}
#else
status_t ret;
#endif
uint32 magic = 0;
ssize_t size = sizeof(magic);
off_t position = stream->Position();
ssize_t read = stream->Read(&magic, size);
if (read != size) {
if (read < 0)
ret = (status_t)read;
else
ret = B_IO_ERROR;
return ret;
}
if (B_BENDIAN_TO_HOST_INT32(magic) != kNativeIconMagicNumber) {
// this might be an old native icon file, where
// we didn't prepend the magic number yet, seek back
if (stream->Seek(position, SEEK_SET) != position) {
printf("MessageImporter::Import() - "
"failed to seek back to beginning of stream\n");
return B_IO_ERROR;
}
}
BMessage archive;
ret = archive.Unflatten(stream);
if (ret < B_OK) {
printf("MessageImporter::Import() - "
"error unflattening icon archive: %s\n", strerror(ret));
return ret;
}
// paths
PathContainer* paths = icon->Paths();
ret = _ImportPaths(&archive, paths);
if (ret < B_OK) {
printf("MessageImporter::Import() - "
"error importing paths: %s\n", strerror(ret));
return ret;
}
// styles
StyleContainer* styles = icon->Styles();
ret = _ImportStyles(&archive, styles);
if (ret < B_OK) {
printf("MessageImporter::Import() - "
"error importing styles: %s\n", strerror(ret));
return ret;
}
// shapes
ret = _ImportShapes(&archive, paths, styles, icon->Shapes());
if (ret < B_OK) {
printf("MessageImporter::Import() - "
"error importing shapes: %s\n", strerror(ret));
return ret;
}
return B_OK;
}
// #pragma mark -
// _ImportPaths
status_t
MessageImporter::_ImportPaths(const BMessage* archive,
PathContainer* paths) const
{
BMessage allPaths;
status_t ret = archive->FindMessage("paths", &allPaths);
if (ret < B_OK)
return ret;
BMessage pathArchive;
for (int32 i = 0;
allPaths.FindMessage("path", i, &pathArchive) == B_OK; i++) {
VectorPath* path = new (nothrow) VectorPath(&pathArchive);
if (!path || !paths->AddPath(path)) {
delete path;
ret = B_NO_MEMORY;
}
if (ret < B_OK)
break;
}
return ret;
}
// _ImportStyles
status_t
MessageImporter::_ImportStyles(const BMessage* archive,
StyleContainer* styles) const
{
BMessage allStyles;
status_t ret = archive->FindMessage("styles", &allStyles);
if (ret < B_OK)
return ret;
BMessage styleArchive;
for (int32 i = 0;
allStyles.FindMessage("style", i, &styleArchive) == B_OK; i++) {
Style* style = new (nothrow) Style(&styleArchive);
if (!style || !styles->AddStyle(style)) {
delete style;
ret = B_NO_MEMORY;
}
if (ret < B_OK)
break;
}
return ret;
}
// _ImportShapes
status_t
MessageImporter::_ImportShapes(const BMessage* archive,
PathContainer* paths,
StyleContainer* styles,
ShapeContainer* shapes) const
{
BMessage allShapes;
status_t ret = archive->FindMessage("shapes", &allShapes);
if (ret < B_OK)
return ret;
BMessage shapeArchive;
for (int32 i = 0;
allShapes.FindMessage("shape", i, &shapeArchive) == B_OK; i++) {
// find the right style
int32 styleIndex;
if (shapeArchive.FindInt32("style ref", &styleIndex) < B_OK) {
printf("MessageImporter::_ImportShapes() - "
"Shape %ld doesn't reference a Style!", i);
continue;
}
#ifdef ICON_O_MATIC
Style* style = styles->StyleAt(StyleIndexFor(styleIndex));
#else
Style* style = styles->StyleAt(styleIndex);
#endif
if (!style) {
printf("MessageImporter::_ImportShapes() - "
"Shape %ld wants Style %ld, which does not exist\n",
i, styleIndex);
continue;
}
// create shape
Shape* shape = new (nothrow) Shape(style);
if (!shape || shape->InitCheck() < B_OK || !shapes->AddShape(shape)) {
delete shape;
ret = B_NO_MEMORY;
}
if (ret < B_OK)
break;
// find the referenced paths
int32 pathIndex;
for (int32 j = 0;
shapeArchive.FindInt32("path ref", j, &pathIndex) == B_OK;
j++) {
#ifdef ICON_O_MATIC
VectorPath* path = paths->PathAt(PathIndexFor(pathIndex));
#else
VectorPath* path = paths->PathAt(pathIndex);
#endif
if (!path) {
printf("MessageImporter::_ImportShapes() - "
"Shape %ld referenced path %ld, "
"which does not exist\n", i, pathIndex);
continue;
}
shape->Paths()->AddPath(path);
}
// Shape properties
if (ret == B_OK)
shape->Unarchive(&shapeArchive);
}
return ret;
}

View File

@ -0,0 +1,56 @@
/*
* Copyright 2006-2007, Haiku. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Authors:
* Stephan Aßmus <superstippi@gmx.de>
*/
#ifndef MESSAGE_IMPORTER_H
#define MESSAGE_IMPORTER_H
#ifdef ICON_O_MATIC
# include "Importer.h"
#else
# include <SupportDefs.h>
#endif
class BMessage;
class BPositionIO;
namespace BPrivate {
namespace Icon {
class Icon;
class PathContainer;
class ShapeContainer;
class StyleContainer;
#ifdef ICON_O_MATIC
class MessageImporter : public Importer {
#else
class MessageImporter {
#endif
public:
MessageImporter();
virtual ~MessageImporter();
status_t Import(Icon* icon,
BPositionIO* stream);
private:
status_t _ImportPaths(const BMessage* archive,
PathContainer* paths) const;
status_t _ImportStyles(const BMessage* archive,
StyleContainer* styles) const;
status_t _ImportShapes(const BMessage* archive,
PathContainer* paths,
StyleContainer* styles,
ShapeContainer* shapes) const;
};
} // namespace Icon
} // namespace BPrivate
#endif // MESSAGE_IMPORTER_H

View File

@ -157,16 +157,18 @@ Shape::~Shape()
// #pragma mark -
#ifdef ICON_O_MATIC
// Unarchive
status_t
Shape::Unarchive(const BMessage* archive)
{
#ifdef ICON_O_MATIC
// IconObject properties
status_t ret = IconObject::Unarchive(archive);
if (ret < B_OK)
return ret;
#else
status_t ret;
#endif
// recreate transformers
BMessage transformerArchive;
@ -217,6 +219,8 @@ Shape::Unarchive(const BMessage* archive)
return B_OK;
}
#ifdef ICON_O_MATIC
// Archive
status_t
Shape::Archive(BMessage* into, bool deep) const
@ -407,10 +411,10 @@ Shape::InitCheck() const
void
Shape::SetStyle(::Style* style)
{
#ifdef ICON_O_MATIC
if (fStyle == style)
return;
#ifdef ICON_O_MATIC
if (fStyle) {
fStyle->RemoveObserver(this);
fStyle->Release();

View File

@ -59,9 +59,9 @@ class Shape : public BPrivate::Icon::Transformable {
Shape(const Shape& other);
virtual ~Shape();
#ifdef ICON_O_MATIC
// IconObject interface
virtual status_t Unarchive(const BMessage* archive);
#ifdef ICON_O_MATIC
virtual status_t Archive(BMessage* into,
bool deep = true) const;

View File

@ -21,10 +21,12 @@
#ifdef ICON_O_MATIC
#include <debugger.h>
#include <typeinfo>
#endif // ICON_O_MATIC
#include <Message.h>
#include <TypeConstants.h>
#ifdef ICON_O_MATIC
# include "support.h"
# include "CommonPropertyIDs.h"
@ -119,12 +121,15 @@ VectorPath::VectorPath(const VectorPath& from)
*this = from;
}
#ifdef ICON_O_MATIC
// constructor
VectorPath::VectorPath(BMessage* archive)
#ifdef ICON_O_MATIC
: BArchivable(),
IconObject(archive),
fListeners(20),
#else
:
#endif
fPath(NULL),
fClosed(false),
fPointCount(0),
@ -161,7 +166,6 @@ VectorPath::VectorPath(BMessage* archive)
fClosed = false;
}
#endif // ICON_O_MATIC
// destructor
VectorPath::~VectorPath()

View File

@ -70,9 +70,8 @@ class VectorPath {
VectorPath();
VectorPath(const VectorPath& from);
#ifdef ICON_O_MATIC
VectorPath(BMessage* archive);
#endif
virtual ~VectorPath();
#ifdef ICON_O_MATIC

View File

@ -38,12 +38,15 @@ Gradient::Gradient(bool empty)
}
}
#ifdef ICON_O_MATIC
// constructor
Gradient::Gradient(BMessage* archive)
#ifdef ICON_O_MATIC
: BArchivable(archive),
Observable(),
Transformable(),
#else
: Transformable(),
#endif
fColors(4),
fType(GRADIENT_LINEAR),
@ -80,7 +83,6 @@ Gradient::Gradient(BMessage* archive)
&fInheritTransformation) < B_OK)
fInheritTransformation = true;
}
#endif // ICON_O_MATIC
// constructor
Gradient::Gradient(const Gradient& other)

View File

@ -50,9 +50,7 @@ class Gradient : public Transformable {
public:
Gradient(bool empty = false);
#ifdef ICON_O_MATIC
Gradient(BMessage* archive);
#endif
Gradient(const Gradient& other);
virtual ~Gradient();

View File

@ -10,9 +10,9 @@
#include <new>
#ifdef ICON_O_MATIC
# include <Message.h>
#ifdef ICON_O_MATIC
# include "ui_defines.h"
#else
# define kWhite (rgb_color){ 255, 255, 255, 255 }
@ -77,11 +77,14 @@ Style::Style(const Style& other)
SetGradient(other.fGradient);
}
#ifdef ICON_O_MATIC
// constructor
Style::Style(BMessage* archive)
#ifdef ICON_O_MATIC
: IconObject(archive),
Observer(),
#else
:
#endif
fColor(kWhite),
fGradient(NULL),
@ -102,7 +105,6 @@ Style::Style(BMessage* archive)
SetGradient(&gradient);
}
}
#endif // ICON_O_MATIC
// destructor
Style::~Style()

View File

@ -22,6 +22,8 @@
#include <agg_color_rgba.h>
class BMessage;
namespace BPrivate {
namespace Icon {
@ -37,9 +39,8 @@ class Style {
Style();
Style(const Style& other);
Style(const rgb_color& color);
#ifdef ICON_O_MATIC
Style(BMessage* archive);
#endif
virtual ~Style();
#ifdef ICON_O_MATIC

View File

@ -31,7 +31,6 @@ AffineTransformer::AffineTransformer(VertexSource& source)
{
}
#ifdef ICON_O_MATIC
// constructor
AffineTransformer::AffineTransformer(VertexSource& source,
BMessage* archive)
@ -50,7 +49,6 @@ AffineTransformer::AffineTransformer(VertexSource& source,
load_from((const double*)matrix);
}
}
#endif // ICON_O_MATIC
// destructor
AffineTransformer::~AffineTransformer()

View File

@ -31,11 +31,10 @@ class AffineTransformer : public Transformer,
AffineTransformer(
VertexSource& source);
#ifdef ICON_O_MATIC
AffineTransformer(
VertexSource& source,
BMessage* archive);
#endif
virtual ~AffineTransformer();
virtual Transformer* Clone(VertexSource& source) const;

View File

@ -33,7 +33,6 @@ ContourTransformer::ContourTransformer(VertexSource& source)
auto_detect_orientation(true);
}
#ifdef ICON_O_MATIC
// constructor
ContourTransformer::ContourTransformer(VertexSource& source,
BMessage* archive)
@ -62,7 +61,6 @@ ContourTransformer::ContourTransformer(VertexSource& source,
if (archive->FindDouble("inner miter limit", &value) == B_OK)
inner_miter_limit(value);
}
#endif // ICON_O_MATIC
// destructor
ContourTransformer::~ContourTransformer()

View File

@ -28,11 +28,10 @@ class ContourTransformer : public Transformer,
ContourTransformer(
VertexSource& source);
#ifdef ICON_O_MATIC
ContourTransformer(
VertexSource& source,
BMessage* archive);
#endif
virtual ~ContourTransformer();
virtual Transformer* Clone(VertexSource& source) const;

View File

@ -26,7 +26,6 @@ PerspectiveTransformer::PerspectiveTransformer(VertexSource& source)
{
}
#ifdef ICON_O_MATIC
// constructor
PerspectiveTransformer::PerspectiveTransformer(VertexSource& source,
BMessage* archive)
@ -35,7 +34,6 @@ PerspectiveTransformer::PerspectiveTransformer(VertexSource& source,
{
// TODO: upgrade AGG to be able to use load_from() etc
}
#endif
// destructor
PerspectiveTransformer::~PerspectiveTransformer()

View File

@ -31,11 +31,10 @@ class PerspectiveTransformer : public Transformer,
PerspectiveTransformer(
VertexSource& source);
#ifdef ICON_O_MATIC
PerspectiveTransformer(
VertexSource& source,
BMessage* archive);
#endif
virtual ~PerspectiveTransformer();
// Transformer interface

View File

@ -31,7 +31,6 @@ StrokeTransformer::StrokeTransformer(VertexSource& source)
{
}
#ifdef ICON_O_MATIC
// constructor
StrokeTransformer::StrokeTransformer(VertexSource& source,
BMessage* archive)
@ -64,7 +63,6 @@ StrokeTransformer::StrokeTransformer(VertexSource& source,
if (archive->FindDouble("shorten", &value) == B_OK)
shorten(value);
}
#endif // ICON_O_MATIC
// destructor
StrokeTransformer::~StrokeTransformer()

View File

@ -28,11 +28,10 @@ class StrokeTransformer : public Transformer,
StrokeTransformer(
VertexSource& source);
#ifdef ICON_O_MATIC
StrokeTransformer(
VertexSource& source,
BMessage* archive);
#endif
virtual ~StrokeTransformer();
// Transformer interface

View File

@ -36,15 +36,17 @@ Transformer::Transformer(VertexSource& source, const char* name)
{
}
#ifdef ICON_O_MATIC
// constructor
Transformer::Transformer(VertexSource& source,
BMessage* archive)
#ifdef ICON_O_MATIC
: IconObject(archive),
#else
:
#endif
fSource(source)
{
}
#endif // ICON_O_MATIC
// destructor
Transformer::~Transformer()

View File

@ -12,6 +12,7 @@
#ifdef ICON_O_MATIC
# include "IconObject.h"
#else
# include <Message.h>
# include <SupportDefs.h>
#endif
@ -41,10 +42,9 @@ class Transformer : public VertexSource {
public:
Transformer(VertexSource& source,
const char* name);
#ifdef ICON_O_MATIC
Transformer(VertexSource& source,
BMessage* archive);
#endif
virtual ~Transformer();
// Transformer

View File

@ -38,7 +38,6 @@ TransformerFactory::TransformerFor(uint32 type, VertexSource& source)
return NULL;
}
#ifdef ICON_O_MATIC
// TransformerFor
Transformer*
TransformerFactory::TransformerFor(BMessage* message,
@ -58,6 +57,8 @@ TransformerFactory::TransformerFor(BMessage* message,
return NULL;
}
#ifdef ICON_O_MATIC
// NextType
bool
TransformerFactory::NextType(int32* cookie, uint32* type, BString* name)

View File

@ -26,10 +26,10 @@ class TransformerFactory {
static Transformer* TransformerFor(uint32 type,
VertexSource& source);
#ifdef ICON_O_MATIC
static Transformer* TransformerFor(BMessage* archive,
VertexSource& source);
#ifdef ICON_O_MATIC
static bool NextType(int32* cookie,
uint32* type,
BString* name);