diff options
| -rw-r--r-- | io-psd.c | 55 |
1 files changed, 16 insertions, 39 deletions
| @@ -1,5 +1,5 @@ | |||
| 1 | /* -*- mode: C; c-file-style: "linux" -*- */ | 1 | /* |
| 2 | /* GdkPixbuf library - PSD image loader | 2 | * GdkPixbuf library - PSD image loader |
| 3 | * | 3 | * |
| 4 | * Copyright (C) 2008 Jan Dudek | 4 | * Copyright (C) 2008 Jan Dudek |
| 5 | * | 5 | * |
| @@ -108,7 +108,6 @@ typedef struct | |||
| 108 | guint pos; | 108 | guint pos; |
| 109 | guint16* lines_lengths; | 109 | guint16* lines_lengths; |
| 110 | gboolean finalized; | 110 | gboolean finalized; |
| 111 | gboolean use_alpha; | ||
| 112 | } PsdContext; | 111 | } PsdContext; |
| 113 | 112 | ||
| 114 | 113 | ||
| @@ -221,7 +220,7 @@ decompress_line(const guchar* src, guint line_length, guchar* dest) | |||
| 221 | } else if (byte > -1) { | 220 | } else if (byte > -1) { |
| 222 | gint count = byte + 1; | 221 | gint count = byte + 1; |
| 223 | 222 | ||
| 224 | // copy next count bytes | 223 | /* copy next count bytes */ |
| 225 | for (int k = 0; k < count; ++k) { | 224 | for (int k = 0; k < count; ++k) { |
| 226 | *dest = src[bytes_read]; | 225 | *dest = src[bytes_read]; |
| 227 | ++dest; | 226 | ++dest; |
| @@ -230,7 +229,7 @@ decompress_line(const guchar* src, guint line_length, guchar* dest) | |||
| 230 | } else { | 229 | } else { |
| 231 | gint count = -byte + 1; | 230 | gint count = -byte + 1; |
| 232 | 231 | ||
| 233 | // copy next byte count times | 232 | /* copy next byte count times */ |
| 234 | guchar next_byte = src[bytes_read]; | 233 | guchar next_byte = src[bytes_read]; |
| 235 | ++bytes_read; | 234 | ++bytes_read; |
| 236 | for (int k = 0; k < count; ++k) { | 235 | for (int k = 0; k < count; ++k) { |
| @@ -272,7 +271,7 @@ gdk_pixbuf__psd_image_begin_load (GdkPixbufModuleSizeFunc size_func, | |||
| 272 | 271 | ||
| 273 | context->state = PSD_STATE_HEADER; | 272 | context->state = PSD_STATE_HEADER; |
| 274 | 273 | ||
| 275 | // we'll allocate larger buffer once we know image size | 274 | /* we'll allocate larger buffer once we know image size */ |
| 276 | context->buffer = g_malloc(PSD_HEADER_SIZE); | 275 | context->buffer = g_malloc(PSD_HEADER_SIZE); |
| 277 | reset_context_buffer(context); | 276 | reset_context_buffer(context); |
| 278 | 277 | ||
| @@ -282,7 +281,6 @@ gdk_pixbuf__psd_image_begin_load (GdkPixbufModuleSizeFunc size_func, | |||
| 282 | context->pos = 0; | 281 | context->pos = 0; |
| 283 | context->lines_lengths = NULL; | 282 | context->lines_lengths = NULL; |
| 284 | context->finalized = FALSE; | 283 | context->finalized = FALSE; |
| 285 | context->use_alpha = FALSE; | ||
| 286 | 284 | ||
| 287 | return (gpointer) context; | 285 | return (gpointer) context; |
| 288 | } | 286 | } |
| @@ -339,14 +337,6 @@ gdk_pixbuf__psd_image_load_increment (gpointer context_ptr, | |||
| 339 | ctx->depth_bytes = (ctx->depth/8 > 0 ? ctx->depth/8 : 1); | 337 | ctx->depth_bytes = (ctx->depth/8 > 0 ? ctx->depth/8 : 1); |
| 340 | ctx->color_mode = hd.color_mode; | 338 | ctx->color_mode = hd.color_mode; |
| 341 | 339 | ||
| 342 | /* | ||
| 343 | if (ctx->color_mode == PSD_MODE_RGB && ctx->channels == 4) { | ||
| 344 | ctx->use_alpha = TRUE; | ||
| 345 | }*/ | ||
| 346 | |||
| 347 | //g_message("color_mode=%d, channels=%d, depth=%d", | ||
| 348 | // ctx->color_mode, ctx->channels, ctx->depth); | ||
| 349 | |||
| 350 | if (ctx->color_mode != PSD_MODE_RGB | 340 | if (ctx->color_mode != PSD_MODE_RGB |
| 351 | && ctx->color_mode != PSD_MODE_GRAYSCALE | 341 | && ctx->color_mode != PSD_MODE_GRAYSCALE |
| 352 | && ctx->color_mode != PSD_MODE_CMYK | 342 | && ctx->color_mode != PSD_MODE_CMYK |
| @@ -374,17 +364,17 @@ gdk_pixbuf__psd_image_load_increment (gpointer context_ptr, | |||
| 374 | } | 364 | } |
| 375 | } | 365 | } |
| 376 | 366 | ||
| 377 | // we need buffer that can contain one channel data for one | 367 | /* we need buffer that can contain one channel data for one |
| 378 | // row in RLE compressed format. 2*width should be enough | 368 | row in RLE compressed format. 2*width should be enough */ |
| 379 | g_free(ctx->buffer); | 369 | g_free(ctx->buffer); |
| 380 | ctx->buffer = g_malloc(ctx->width * 2 * ctx->depth_bytes); | 370 | ctx->buffer = g_malloc(ctx->width * 2 * ctx->depth_bytes); |
| 381 | 371 | ||
| 382 | // this will be needed for RLE decompression | 372 | /* this will be needed for RLE decompression */ |
| 383 | ctx->lines_lengths = | 373 | ctx->lines_lengths = |
| 384 | g_malloc(2 * ctx->channels * ctx->height); | 374 | g_malloc(2 * ctx->channels * ctx->height); |
| 385 | 375 | ||
| 386 | ctx->pixbuf = gdk_pixbuf_new(GDK_COLORSPACE_RGB, | 376 | ctx->pixbuf = gdk_pixbuf_new(GDK_COLORSPACE_RGB, |
| 387 | ctx->use_alpha, 8, ctx->width, ctx->height); | 377 | FALSE, 8, ctx->width, ctx->height); |
| 388 | 378 | ||
| 389 | if (ctx->lines_lengths == NULL || ctx->buffer == NULL || | 379 | if (ctx->lines_lengths == NULL || ctx->buffer == NULL || |
| 390 | ctx->pixbuf == NULL) | 380 | ctx->pixbuf == NULL) |
| @@ -395,7 +385,7 @@ gdk_pixbuf__psd_image_load_increment (gpointer context_ptr, | |||
| 395 | return FALSE; | 385 | return FALSE; |
| 396 | } | 386 | } |
| 397 | 387 | ||
| 398 | // create separate buffers for each channel | 388 | /* create separate buffers for each channel */ |
| 399 | ctx->ch_bufs = g_malloc(sizeof(guchar*) * ctx->channels); | 389 | ctx->ch_bufs = g_malloc(sizeof(guchar*) * ctx->channels); |
| 400 | for (int i = 0; i < ctx->channels; i++) { | 390 | for (int i = 0; i < ctx->channels; i++) { |
| 401 | ctx->ch_bufs[i] = | 391 | ctx->ch_bufs[i] = |
| @@ -457,7 +447,7 @@ gdk_pixbuf__psd_image_load_increment (gpointer context_ptr, | |||
| 457 | (guchar*) ctx->lines_lengths, &ctx->bytes_read, &data, | 447 | (guchar*) ctx->lines_lengths, &ctx->bytes_read, &data, |
| 458 | &size, 2 * ctx->height * ctx->channels)) | 448 | &size, 2 * ctx->height * ctx->channels)) |
| 459 | { | 449 | { |
| 460 | // convert from different endianness | 450 | /* convert from different endianness */ |
| 461 | for (int i = 0; i < ctx->height * ctx->channels; i++) { | 451 | for (int i = 0; i < ctx->height * ctx->channels; i++) { |
| 462 | ctx->lines_lengths[i] = read_uint16( | 452 | ctx->lines_lengths[i] = read_uint16( |
| 463 | (guchar*) &ctx->lines_lengths[i]); | 453 | (guchar*) &ctx->lines_lengths[i]); |
| @@ -510,11 +500,11 @@ gdk_pixbuf__psd_image_load_increment (gpointer context_ptr, | |||
| 510 | } | 500 | } |
| 511 | 501 | ||
| 512 | if (ctx->state == PSD_STATE_DONE && !ctx->finalized) { | 502 | if (ctx->state == PSD_STATE_DONE && !ctx->finalized) { |
| 513 | // convert or copy channel buffers to our GdkPixbuf | 503 | /* convert or copy channel buffers to our GdkPixbuf */ |
| 514 | guchar* pixels = gdk_pixbuf_get_pixels(ctx->pixbuf); | 504 | guchar* pixels = gdk_pixbuf_get_pixels(ctx->pixbuf); |
| 515 | guint b = ctx->depth_bytes; | 505 | guint b = ctx->depth_bytes; |
| 516 | 506 | ||
| 517 | if (ctx->color_mode == PSD_MODE_RGB && !ctx->use_alpha) { | 507 | if (ctx->color_mode == PSD_MODE_RGB) { |
| 518 | for (int i = 0; i < ctx->height; i++) { | 508 | for (int i = 0; i < ctx->height; i++) { |
| 519 | for (int j = 0; j < ctx->width; j++) { | 509 | for (int j = 0; j < ctx->width; j++) { |
| 520 | pixels[3*j+0] = ctx->ch_bufs[0][ctx->width*i*b + j*b]; | 510 | pixels[3*j+0] = ctx->ch_bufs[0][ctx->width*i*b + j*b]; |
| @@ -533,22 +523,9 @@ gdk_pixbuf__psd_image_load_increment (gpointer context_ptr, | |||
| 533 | } | 523 | } |
| 534 | pixels += gdk_pixbuf_get_rowstride(ctx->pixbuf); | 524 | pixels += gdk_pixbuf_get_rowstride(ctx->pixbuf); |
| 535 | } | 525 | } |
| 536 | } | 526 | } else if (ctx->color_mode == PSD_MODE_CMYK) { |
| 537 | #if 0 | 527 | /* unfortunately, this doesn't work 100% correctly... |
| 538 | else if (ctx->color_mode == PSD_MODE_RGB && ctx->use_alpha) { | 528 | CMYK-RGB conversion distorts colors significantly */ |
| 539 | guchar* pixels = gdk_pixbuf_get_pixels(ctx->pixbuf); | ||
| 540 | for (int i = 0; i < ctx->height; i++) { | ||
| 541 | for (int j = 0; j < ctx->width; j++) { | ||
| 542 | pixels[4*j+0] = ctx->ch_bufs[0][ctx->width*i + j]; | ||
| 543 | pixels[4*j+1] = ctx->ch_bufs[1][ctx->width*i + j]; | ||
| 544 | pixels[4*j+2] = ctx->ch_bufs[2][ctx->width*i + j]; | ||
| 545 | pixels[4*j+3] = ctx->ch_bufs[3][ctx->width*i + j]; | ||
| 546 | } | ||
| 547 | pixels += gdk_pixbuf_get_rowstride(ctx->pixbuf); | ||
| 548 | } | ||
| 549 | #endif | ||
| 550 | else if (ctx->color_mode == PSD_MODE_CMYK) { | ||
| 551 | // unfortunately, this doesn't seem to work correctly... | ||
| 552 | 529 | ||
| 553 | guchar* pixels = gdk_pixbuf_get_pixels(ctx->pixbuf); | 530 | guchar* pixels = gdk_pixbuf_get_pixels(ctx->pixbuf); |
| 554 | for (int i = 0; i < ctx->height; i++) { | 531 | for (int i = 0; i < ctx->height; i++) { |
