diff options
| author | Felipe Corr??a da Silva Sanches <juca@members.fsf.org> | 2009-12-06 08:00:44 +0000 |
|---|---|---|
| committer | Felipe C. da S. Sanches <juca@members.fsf.org> | 2009-12-06 08:00:44 +0000 |
| commit | 2e19b78376f047bbde8eda750522d7250b05cdc6 (patch) | |
| tree | c93ca0dd6a9d1a72eaddeb4098bedde6d20af494 /src | |
| parent | added an icon to the color picker dialog to alert when there is too much ink ... (diff) | |
| download | inkscape-2e19b78376f047bbde8eda750522d7250b05cdc6.tar.gz inkscape-2e19b78376f047bbde8eda750522d7250b05cdc6.zip | |
* infrastructure to store device colors as described in http://www.w3.org/TR/2009/WD-SVGColor12-20091001/#device
* related to https://bugs.launchpad.net/inkscape/+bug/444021
(bzr r8871)
Diffstat (limited to 'src')
| -rw-r--r-- | src/color.cpp | 58 | ||||
| -rw-r--r-- | src/color.h | 2 | ||||
| -rw-r--r-- | src/style.cpp | 12 | ||||
| -rw-r--r-- | src/svg/svg-color.cpp | 107 | ||||
| -rw-r--r-- | src/svg/svg-color.h | 3 | ||||
| -rw-r--r-- | src/svg/svg-device-color.h | 26 |
6 files changed, 202 insertions, 6 deletions
diff --git a/src/color.cpp b/src/color.cpp index b16d9950f..abaab6310 100644 --- a/src/color.cpp +++ b/src/color.cpp @@ -17,6 +17,7 @@ #include <math.h> #include "color.h" #include "svg/svg-icc-color.h" +#include "svg/svg-device-color.h" #include "svg/svg-color.h" #include "svg/css-ostringstream.h" @@ -29,7 +30,8 @@ static bool profileMatches( SVGICCColor const* first, SVGICCColor const* second #define PROFILE_EPSILON 0.00000001 SPColor::SPColor() : - icc(0) + icc(0), + device(0) { v.c[0] = 0; v.c[1] = 0; @@ -37,19 +39,22 @@ SPColor::SPColor() : } SPColor::SPColor( SPColor const& other ) : - icc(0) + icc(0), + device(0) { *this = other; } SPColor::SPColor( float r, float g, float b ) : - icc(0) + icc(0), + device(0) { set( r, g, b ); } SPColor::SPColor( guint32 value ) : - icc(0) + icc(0), + device(0) { set( value ); } @@ -57,20 +62,29 @@ SPColor::SPColor( guint32 value ) : SPColor::~SPColor() { delete icc; + delete device; icc = 0; + device = 0; } SPColor& SPColor::operator= (SPColor const& other) { - SVGICCColor* tmp = other.icc ? new SVGICCColor(*other.icc) : 0; + SVGICCColor* tmp_icc = other.icc ? new SVGICCColor(*other.icc) : 0; + SVGDeviceColor* tmp_device = other.device ? new SVGDeviceColor(*other.device) : 0; + v.c[0] = other.v.c[0]; v.c[1] = other.v.c[1]; v.c[2] = other.v.c[2]; if ( icc ) { delete icc; } - icc = tmp; + icc = tmp_icc; + + if ( device ) { + delete device; + } + device = tmp_device; return *this; } @@ -86,6 +100,7 @@ bool SPColor::operator == (SPColor const& other) const && (v.c[2] != other.v.c[2]); match &= profileMatches( icc, other.icc ); +//TODO?: match &= devicecolorMatches( device, other.device ); return match; } @@ -204,6 +219,37 @@ std::string SPColor::toString() const css << ')'; } + if ( device && device->type != DEVICE_COLOR_INVALID) { + if ( !css.str().empty() ) { + css << " "; + } + + switch(device->type){ + case DEVICE_GRAY: + css << "device-gray("; + break; + case DEVICE_RGB: + css << "device-rgb("; + break; + case DEVICE_CMYK: + css << "device-cmyk("; + break; + case DEVICE_NCHANNEL: + css << "device-nchannel("; + break; + case DEVICE_COLOR_INVALID: + //should not be reached + break; + } + + for (vector<double>::const_iterator i(device->colors.begin()), + iEnd(device->colors.end()); + i != iEnd; ++i) { + css << ", " << *i; + } + css << ')'; + } + return css.str(); } diff --git a/src/color.h b/src/color.h index bebeaec60..7fd351360 100644 --- a/src/color.h +++ b/src/color.h @@ -34,6 +34,7 @@ #define SP_RGBA32_F_COMPOSE(r,g,b,a) SP_RGBA32_U_COMPOSE (SP_COLOR_F_TO_U (r), SP_COLOR_F_TO_U (g), SP_COLOR_F_TO_U (b), SP_COLOR_F_TO_U (a)) struct SVGICCColor; +struct SVGDeviceColor; /** * An RGB color with optional icc-color part @@ -59,6 +60,7 @@ struct SPColor { std::string toString() const; SVGICCColor* icc; + SVGDeviceColor* device; union { float c[3]; } v; diff --git a/src/style.cpp b/src/style.cpp index 0b946f348..111018c2a 100644 --- a/src/style.cpp +++ b/src/style.cpp @@ -28,6 +28,7 @@ #include "svg/svg.h" #include "svg/svg-color.h" #include "svg/svg-icc-color.h" +#include "svg/svg-device-color.h" #include "display/canvas-bpath.h" #include "attributes.h" @@ -3184,6 +3185,17 @@ sp_style_read_ipaint(SPIPaint *paint, gchar const *str, SPStyle *style, SPDocume } paint->value.color.icc = tmp; } + if (strneq(str, "device-gray(", 12) || + strneq(str, "device-rgb(", 11) || + strneq(str, "device-cmyk(", 12) || + strneq(str, "device-nchannel(", 16)) { + SVGDeviceColor* tmp = new SVGDeviceColor(); + if ( ! sp_svg_read_device_color( str, &str, tmp ) ) { + delete tmp; + tmp = 0; + } + paint->value.color.device = tmp; + } } } } diff --git a/src/svg/svg-color.cpp b/src/svg/svg-color.cpp index d6b33402f..0eaa4431a 100644 --- a/src/svg/svg-color.cpp +++ b/src/svg/svg-color.cpp @@ -35,6 +35,7 @@ #include "preferences.h" #include "svg-color.h" #include "svg-icc-color.h" +#include "svg-device-color.h" #if ENABLE_LCMS #include <lcms.h> @@ -604,6 +605,112 @@ bool sp_svg_read_icc_color( gchar const *str, SVGICCColor* dest ) return sp_svg_read_icc_color(str, NULL, dest); } +bool sp_svg_read_device_color( gchar const *str, gchar const **end_ptr, SVGDeviceColor* dest) +{ + bool good = true; + unsigned int max_colors; + + if ( end_ptr ) { + *end_ptr = str; + } + if ( dest ) { + dest->colors.clear(); + } + + if ( !str ) { + // invalid input + good = false; + } else { + while ( g_ascii_isspace(*str) ) { + str++; + } + + dest->type = DEVICE_COLOR_INVALID; + if (strneq( str, "device-gray(", 12 )){ + dest->type = DEVICE_GRAY; + max_colors=1; + str += 12; + } + + if (strneq( str, "device-rgb(", 11 )){ + dest->type = DEVICE_RGB; + max_colors=3; + str += 11; + } + + if (strneq( str, "device-cmyk(", 12 )){ + dest->type = DEVICE_CMYK; + max_colors=4; + str += 12; + } + + if (strneq( str, "device-nchannel(", 16 )){ + dest->type = DEVICE_NCHANNEL; + max_colors=0; + str += 16; + } + + if ( dest->type != DEVICE_COLOR_INVALID ) { + while ( g_ascii_isspace(*str) ) { + str++; + } + + while ( *str && *str != ')' ) { + if ( g_ascii_isdigit(*str) || *str == '.' || *str == '-' || *str == '+') { + gchar* endPtr = 0; + gdouble dbl = g_ascii_strtod( str, &endPtr ); + if ( !errno ) { + if ( dest ) { + dest->colors.push_back( dbl ); +g_message("color: %f", dbl); + } + str = endPtr; + } else { + good = false; + break; + } + + while ( g_ascii_isspace(*str) || *str == ',' ) { + str++; + } + } else { + break; + } + } + } + + // We need to have ended on a closing parenthesis + if ( good ) { + while ( g_ascii_isspace(*str) ) { + str++; + } + good &= (*str == ')'); + } + } + + if ( dest->colors.size() == 0) good=false; + if ( dest->type != DEVICE_NCHANNEL && (dest->colors.size() != max_colors)) good=false; + + if ( good ) { + if ( end_ptr ) { + *end_ptr = str; + } + } else { + if ( dest ) { + dest->type = DEVICE_COLOR_INVALID; + dest->colors.clear(); + } + } + + return good; +} + + +bool sp_svg_read_device_color( gchar const *str, SVGDeviceColor* dest) +{ + return sp_svg_read_device_color(str, NULL, dest); +} + /* Local Variables: mode:c++ diff --git a/src/svg/svg-color.h b/src/svg/svg-color.h index a3868c149..f4e534652 100644 --- a/src/svg/svg-color.h +++ b/src/svg/svg-color.h @@ -4,6 +4,7 @@ #include <glib/gtypes.h> class SVGICCColor; +class SVGDeviceColor; guint32 sp_svg_read_color(gchar const *str, unsigned int dfl); guint32 sp_svg_read_color(gchar const *str, gchar const **end_ptr, guint32 def); @@ -11,6 +12,8 @@ void sp_svg_write_color(char *buf, unsigned int buflen, unsigned int rgba32); bool sp_svg_read_icc_color( gchar const *str, gchar const **end_ptr, SVGICCColor* dest ); bool sp_svg_read_icc_color( gchar const *str, SVGICCColor* dest ); +bool sp_svg_read_device_color( gchar const *str, gchar const **end_ptr, SVGDeviceColor* dest ); +bool sp_svg_read_device_color( gchar const *str, SVGDeviceColor* dest ); void icc_color_to_sRGB(SVGICCColor* dest, guchar* r, guchar* g, guchar* b); #endif /* !SVG_SVG_COLOR_H_SEEN */ diff --git a/src/svg/svg-device-color.h b/src/svg/svg-device-color.h new file mode 100644 index 000000000..305133ed3 --- /dev/null +++ b/src/svg/svg-device-color.h @@ -0,0 +1,26 @@ +#ifndef SVG_DEVICE_COLOR_H_SEEN +#define SVG_DEVICE_COLOR_H_SEEN + +#include <string> +#include <vector> + +typedef enum {DEVICE_COLOR_INVALID, DEVICE_GRAY, DEVICE_RGB, DEVICE_CMYK, DEVICE_NCHANNEL} SVGDeviceColorType; + +struct SVGDeviceColor { + SVGDeviceColorType type; + std::vector<double> colors; +}; + + +#endif /* !SVG_DEVICE_COLOR_H_SEEN */ + +/* + Local Variables: + mode:c++ + c-file-style:"stroustrup" + c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +)) + indent-tabs-mode:nil + fill-column:99 + End: +*/ +// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=99 : |
