summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--!NetSurf/Resources/intro,faf1
-rw-r--r--!NetSurf/Resources/png,b60bin0 -> 8574 bytes
-rw-r--r--content/content.c34
-rw-r--r--content/content.h16
-rw-r--r--desktop/browser.c5
-rw-r--r--desktop/netsurf.c3
-rw-r--r--makefile10
-rw-r--r--render/html.c11
-rw-r--r--riscos/filetype.c3
-rw-r--r--riscos/gui.c27
-rw-r--r--riscos/jpeg.c13
-rw-r--r--riscos/jpeg.h4
-rw-r--r--riscos/png.c307
-rw-r--r--riscos/png.h19
14 files changed, 414 insertions, 39 deletions
diff --git a/!NetSurf/Resources/intro,faf b/!NetSurf/Resources/intro,faf
index deb57bfb2..8f27ea8c8 100644
--- a/!NetSurf/Resources/intro,faf
+++ b/!NetSurf/Resources/intro,faf
@@ -35,6 +35,7 @@ fetching</li>
<h2>In Progress</h2>
<ul>
+<li><strong>PNGs <img src="png" alt=""> now partially supported</strong></li>
<li>Improved memory handling (currently exits when memory is exhausted)</li>
<li>Forms (display but don't submit)</li>
<li><img style="float: left" src="jpeg" alt="">Images (JPEGs so far)</li>
diff --git a/!NetSurf/Resources/png,b60 b/!NetSurf/Resources/png,b60
new file mode 100644
index 000000000..f3a6df448
--- /dev/null
+++ b/!NetSurf/Resources/png,b60
Binary files differ
diff --git a/content/content.c b/content/content.c
index 70933a97b..2a2cf700e 100644
--- a/content/content.c
+++ b/content/content.c
@@ -1,5 +1,5 @@
/**
- * $Id: content.c,v 1.8 2003/04/17 21:35:02 bursa Exp $
+ * $Id: content.c,v 1.9 2003/05/10 11:13:34 bursa Exp $
*/
#include <assert.h>
@@ -10,6 +10,7 @@
#include "netsurf/render/html.h"
#include "netsurf/render/textplain.h"
#include "netsurf/riscos/jpeg.h"
+#include "netsurf/riscos/png.h"
#include "netsurf/utils/utils.h"
@@ -20,7 +21,7 @@ struct mime_entry {
};
static const struct mime_entry mime_map[] = {
{"image/jpeg", CONTENT_JPEG},
-/* {"image/png", CONTENT_PNG},*/
+ {"image/png", CONTENT_PNG},
{"text/css", CONTENT_CSS},
{"text/html", CONTENT_HTML},
{"text/plain", CONTENT_TEXTPLAIN},
@@ -35,14 +36,19 @@ struct handler_entry {
void (*revive)(struct content *c, unsigned int width, unsigned int height);
void (*reformat)(struct content *c, unsigned int width, unsigned int height);
void (*destroy)(struct content *c);
+ void (*redraw)(struct content *c, long x, long y,
+ unsigned long width, unsigned long height);
};
static const struct handler_entry handler_map[] = {
- {html_create, html_process_data, html_convert, html_revive, html_reformat, html_destroy},
+ {html_create, html_process_data, html_convert, html_revive,
+ html_reformat, html_destroy, 0},
{textplain_create, textplain_process_data, textplain_convert,
- textplain_revive, textplain_reformat, textplain_destroy},
- {jpeg_create, jpeg_process_data, jpeg_convert, jpeg_revive, jpeg_reformat, jpeg_destroy},
- {css_create, css_process_data, css_convert, css_revive, css_reformat, css_destroy},
-/* {png_create, png_process_data, png_convert, png_revive, png_destroy},*/
+ textplain_revive, textplain_reformat, textplain_destroy, 0},
+ {jpeg_create, jpeg_process_data, jpeg_convert, jpeg_revive,
+ jpeg_reformat, jpeg_destroy, jpeg_redraw},
+ {css_create, css_process_data, css_convert, css_revive, css_reformat, css_destroy, 0},
+ {nspng_create, nspng_process_data, nspng_convert, nspng_revive,
+ nspng_reformat, nspng_destroy, nspng_redraw},
};
@@ -154,3 +160,17 @@ void content_destroy(struct content *c)
xfree(c);
}
+
+/**
+ * content_redraw -- display content on screen
+ */
+
+void content_redraw(struct content *c, long x, long y,
+ unsigned long width, unsigned long height)
+{
+ assert(c != 0);
+ assert(c->type < CONTENT_OTHER);
+ if (handler_map[c->type].redraw != 0)
+ handler_map[c->type].redraw(c, x, y, width, height);
+}
+
diff --git a/content/content.h b/content/content.h
index 462d58b69..8a4fcbd17 100644
--- a/content/content.h
+++ b/content/content.h
@@ -1,11 +1,13 @@
/**
- * $Id: content.h,v 1.9 2003/04/15 17:53:00 bursa Exp $
+ * $Id: content.h,v 1.10 2003/05/10 11:13:34 bursa Exp $
*/
#ifndef _NETSURF_DESKTOP_CONTENT_H_
#define _NETSURF_DESKTOP_CONTENT_H_
#include "libxml/HTMLparser.h"
+#include "libpng/png.h"
+#include "oslib/osspriteop.h"
#include "netsurf/content/cache.h"
#include "netsurf/css/css.h"
#include "netsurf/render/box.h"
@@ -98,6 +100,16 @@ struct content
unsigned long length;
} jpeg;
+ struct
+ {
+ png_structp png;
+ png_infop info;
+ unsigned long rowbytes;
+ osspriteop_area *sprite_area;
+ char *sprite_image;
+ enum { PNG_PALETTE, PNG_DITHER, PNG_DEEP } type;
+ } png;
+
} data;
struct cache_entry *cache;
@@ -118,5 +130,7 @@ int content_convert(struct content *c, unsigned long width, unsigned long height
void content_revive(struct content *c, unsigned long width, unsigned long height);
void content_reformat(struct content *c, unsigned long width, unsigned long height);
void content_destroy(struct content *c);
+void content_redraw(struct content *c, long x, long y,
+ unsigned long width, unsigned long height);
#endif
diff --git a/desktop/browser.c b/desktop/browser.c
index 0a9c674ac..fb2980486 100644
--- a/desktop/browser.c
+++ b/desktop/browser.c
@@ -1,5 +1,5 @@
/**
- * $Id: browser.c,v 1.35 2003/04/25 08:03:15 bursa Exp $
+ * $Id: browser.c,v 1.36 2003/05/10 11:13:34 bursa Exp $
*/
#include "netsurf/content/cache.h"
@@ -218,7 +218,8 @@ void browser_window_open_location_historical(struct browser_window* bw, const ch
bw->time0 = clock();
fetchcache(url, 0, browser_window_callback, bw,
gui_window_get_width(bw->window), 0,
- (1 << CONTENT_HTML) | (1 << CONTENT_TEXTPLAIN) | (1 << CONTENT_JPEG));
+ (1 << CONTENT_HTML) | (1 << CONTENT_TEXTPLAIN) |
+ (1 << CONTENT_JPEG) | (1 << CONTENT_PNG));
LOG(("end"));
}
diff --git a/desktop/netsurf.c b/desktop/netsurf.c
index 446f8c05a..c28d96ad3 100644
--- a/desktop/netsurf.c
+++ b/desktop/netsurf.c
@@ -1,5 +1,5 @@
/**
- * $Id: netsurf.c,v 1.7 2003/03/04 11:59:35 bursa Exp $
+ * $Id: netsurf.c,v 1.8 2003/05/10 11:13:34 bursa Exp $
*/
#include "netsurf/desktop/netsurf.h"
@@ -30,6 +30,7 @@ void netsurf_init(int argc, char** argv)
gui_init(argc, argv);
fetch_init();
cache_init();
+ nspng_init();
}
diff --git a/makefile b/makefile
index 515e485b4..845804499 100644
--- a/makefile
+++ b/makefile
@@ -1,4 +1,4 @@
-# $Id: makefile,v 1.18 2003/04/11 21:06:51 bursa Exp $
+# $Id: makefile,v 1.19 2003/05/10 11:13:34 bursa Exp $
all: !NetSurf/!RunImage,ff8
clean:
@@ -25,6 +25,7 @@ OBJECTS = \
riscos/arm-riscos-aof/font.o riscos/arm-riscos-aof/gui.o \
riscos/arm-riscos-aof/theme.o riscos/arm-riscos-aof/jpeg.o \
riscos/arm-riscos-aof/filetype.o utils/arm-riscos-aof/utils.o \
+ riscos/arm-riscos-aof/png.o \
css/arm-riscos-aof/css.o css/arm-riscos-aof/css_enum.o \
css/arm-riscos-aof/parser.o css/arm-riscos-aof/scanner.o \
css/arm-riscos-aof/ruleset.o
@@ -34,11 +35,14 @@ HEADERS = \
render/html.h render/layout.h \
riscos/font.h riscos/gui.h riscos/theme.h utils/log.h \
utils/utils.h render/textplain.h \
- css/css.h css/css_enum.h css/parser.h css/scanner.h
+ css/css.h css/css_enum.h css/parser.h css/scanner.h \
+ riscos/png.h
LIBS = \
/usr/local/riscoslibs/libxml2/libxml2.ro \
/usr/local/riscoslibs/OSLib/OSLib.ro \
- /usr/local/riscoslibs/curl/libcurl.ro
+ /usr/local/riscoslibs/curl/libcurl.ro \
+ /usr/local/riscoslibs/libpng/libpng.ro \
+ /usr/local/riscoslibs/zlib/libz.ro
!NetSurf/!RunImage,ff8: $(OBJECTS)
$(CC) $(FLAGS) -o !NetSurf/!RunImage,ff8 $(OBJECTS) $(LIBS)
diff --git a/render/html.c b/render/html.c
index 8b2cd7338..8b572fd24 100644
--- a/render/html.c
+++ b/render/html.c
@@ -1,5 +1,5 @@
/**
- * $Id: html.c,v 1.16 2003/04/25 08:03:15 bursa Exp $
+ * $Id: html.c,v 1.17 2003/05/10 11:13:34 bursa Exp $
*/
#include <assert.h>
@@ -324,7 +324,8 @@ void html_fetch_image(struct content *c, char *url, struct box *box)
c->active++;
fetchcache(url, c->url,
html_image_callback,
- fetch_data, 0, 0, 1 << CONTENT_JPEG);
+ fetch_data, 0, 0,
+ (1 << CONTENT_JPEG) | (1 << CONTENT_PNG));
}
@@ -345,7 +346,7 @@ void html_image_callback(fetchcache_msg msg, struct content *image,
box->style->width.width = CSS_WIDTH_LENGTH;
box->style->width.value.length.unit = CSS_UNIT_PX;
box->style->width.value.length.value = image->width;
- box->min_width = box->max_width = image->width;
+ box->min_width = box->max_width = box->width = image->width;
/* invalidate parent min, max widths */
if (box->parent->max_width != UNKNOWN_MAX_WIDTH) {
struct box *b = box->parent;
@@ -381,6 +382,7 @@ void html_image_callback(fetchcache_msg msg, struct content *image,
if (c->active == 1 && c->status == CONTENT_PENDING) {
/* all images have arrived */
content_reformat(c, c->available_width, 0);
+ /*box_dump(c->data.html.layout->children, 0);*/
}
c->active--;
if (c->active == 0)
@@ -413,7 +415,8 @@ void html_revive(struct content *c, unsigned int width, unsigned int height)
c->active++;
fetchcache(c->data.html.object[i].url, c->url,
html_image_callback,
- fetch_data, 0, 0, 1 << CONTENT_JPEG);
+ fetch_data, 0, 0,
+ (1 << CONTENT_JPEG) | (1 << CONTENT_PNG));
}
}
diff --git a/riscos/filetype.c b/riscos/filetype.c
index 81b0920e5..520e2617a 100644
--- a/riscos/filetype.c
+++ b/riscos/filetype.c
@@ -1,5 +1,5 @@
/**
- * $Id: filetype.c,v 1.3 2003/04/09 21:57:09 bursa Exp $
+ * $Id: filetype.c,v 1.4 2003/05/10 11:13:34 bursa Exp $
*/
#include <stdlib.h>
@@ -15,6 +15,7 @@ struct type_entry {
char mime_type[16];
};
static const struct type_entry type_map[] = {
+ {0xb60, "image/png"},
{0xc85, "image/jpeg"},
{0xf79, "text/css"},
{0xfaf, "text/html"},
diff --git a/riscos/gui.c b/riscos/gui.c
index 1173132c0..31b6d215c 100644
--- a/riscos/gui.c
+++ b/riscos/gui.c
@@ -1,5 +1,5 @@
/**
- * $Id: gui.c,v 1.27 2003/04/15 18:07:25 bursa Exp $
+ * $Id: gui.c,v 1.28 2003/05/10 11:13:34 bursa Exp $
*/
#include "netsurf/riscos/font.h"
@@ -10,7 +10,6 @@
#include "oslib/os.h"
#include "oslib/wimp.h"
#include "oslib/colourtrans.h"
-#include "oslib/jpeg.h"
#include "oslib/wimpspriteop.h"
#include "netsurf/riscos/theme.h"
#include "netsurf/utils/log.h"
@@ -581,11 +580,10 @@ void ro_gui_window_redraw_box(gui_window* g, struct box * box, signed long x,
if (box->object != 0)
{
- if (box->object->type == CONTENT_JPEG) {
- xjpeg_plot_scaled((jpeg_image *) box->object->data.jpeg.data,
- (int) x + (int) box->x * 2, (int) y - (int) box->y * 2 - (int) box->height * 2,
- 0, (int) box->object->data.jpeg.length, jpeg_SCALE_DITHERED);
- }
+ content_redraw(box->object,
+ (int) x + (int) box->x * 2,
+ (int) y - (int) box->y * 2 - (int) box->height * 2,
+ box->width * 2, box->height * 2);
}
/* if (box->img != 0)
{
@@ -848,9 +846,7 @@ void ro_gui_window_redraw(gui_window* g, wimp_draw* redraw)
while (more)
{
- switch (c->type)
- {
- case CONTENT_HTML:
+ if (c->type == CONTENT_HTML) {
gadget_subtract_x = redraw->box.x0 - redraw->xscroll;
gadget_subtract_y = redraw->box.y1 - redraw->yscroll;
assert(c->data.html.layout != NULL);
@@ -858,17 +854,12 @@ void ro_gui_window_redraw(gui_window* g, wimp_draw* redraw)
c->data.html.layout->children,
redraw->box.x0 - redraw->xscroll, redraw->box.y1 - redraw->yscroll,
&redraw->clip, 0xffffff);
- break;
- case CONTENT_JPEG:
- xjpeg_plot_scaled((jpeg_image *) c->data.jpeg.data,
+ } else {
+ content_redraw(c,
(int) redraw->box.x0 - (int) redraw->xscroll,
(int) redraw->box.y1 - (int) redraw->yscroll - (int) c->height * 2,
- 0, (int) c->data.jpeg.length, jpeg_SCALE_DITHERED);
- break;
-
- default:
- break;
+ c->width, c->height);
}
more = wimp_get_rectangle(redraw);
}
diff --git a/riscos/jpeg.c b/riscos/jpeg.c
index b329d3393..090f36cf4 100644
--- a/riscos/jpeg.c
+++ b/riscos/jpeg.c
@@ -1,5 +1,5 @@
/**
- * $Id: jpeg.c,v 1.3 2003/03/03 22:40:39 bursa Exp $
+ * $Id: jpeg.c,v 1.4 2003/05/10 11:13:34 bursa Exp $
*
* This is just a temporary implementation using the JPEG renderer
* available in some versions of RISC OS.
@@ -61,3 +61,14 @@ void jpeg_destroy(struct content *c)
xfree(c->data.jpeg.data);
xfree(c->title);
}
+
+
+void jpeg_redraw(struct content *c, long x, long y,
+ unsigned long width, unsigned long height)
+{
+ /* TODO: scale to width, height */
+ xjpeg_plot_scaled((jpeg_image *) c->data.jpeg.data,
+ x, y, 0, (int) c->data.jpeg.length,
+ jpeg_SCALE_DITHERED);
+}
+
diff --git a/riscos/jpeg.h b/riscos/jpeg.h
index 99601f729..db6371959 100644
--- a/riscos/jpeg.h
+++ b/riscos/jpeg.h
@@ -1,5 +1,5 @@
/**
- * $Id: jpeg.h,v 1.1 2003/02/25 21:00:27 bursa Exp $
+ * $Id: jpeg.h,v 1.2 2003/05/10 11:13:34 bursa Exp $
*/
#ifndef _NETSURF_RISCOS_JPEG_H_
@@ -13,5 +13,7 @@ int jpeg_convert(struct content *c, unsigned int width, unsigned int height);
void jpeg_revive(struct content *c, unsigned int width, unsigned int height);
void jpeg_reformat(struct content *c, unsigned int width, unsigned int height);
void jpeg_destroy(struct content *c);
+void jpeg_redraw(struct content *c, long x, long y,
+ unsigned long width, unsigned long height);
#endif
diff --git a/riscos/png.c b/riscos/png.c
new file mode 100644
index 000000000..842c18ff4
--- /dev/null
+++ b/riscos/png.c
@@ -0,0 +1,307 @@
+/**
+ * $Id: png.c,v 1.1 2003/05/10 11:15:49 bursa Exp $
+ */
+
+#include <assert.h>
+#include <string.h>
+#include <stdlib.h>
+#include "libpng/png.h"
+#include "oslib/colourtrans.h"
+#include "oslib/os.h"
+#include "oslib/osspriteop.h"
+#include "netsurf/content/content.h"
+#include "netsurf/riscos/png.h"
+#include "netsurf/utils/log.h"
+#include "netsurf/utils/utils.h"
+
+/* libpng uses names starting png_, so use nspng_ here to avoid clashes */
+
+/* maps colours to 256 mode colour numbers */
+static os_colour_number colour_table[4096];
+
+static void info_callback(png_structp png, png_infop info);
+static void row_callback(png_structp png, png_bytep new_row,
+ png_uint_32 row_num, int pass);
+static void end_callback(png_structp png, png_infop info);
+
+
+void nspng_init(void)
+{
+ /* generate colour lookup table for reducing to 8bpp */
+ unsigned int red, green, blue;
+ for (red = 0; red != 0xf; red++)
+ for (green = 0; green != 0xf; green++)
+ for (blue = 0; blue != 0xf; blue++)
+ colour_table[red << 8 | green << 4 | blue] =
+ colourtrans_return_colour_number_for_mode(
+ blue << 28 | blue << 24 |
+ green << 20 | green << 16 |
+ red << 12 | red << 8, 21, 0);
+}
+
+
+void nspng_create(struct content *c)
+{
+ c->data.png.sprite_area = 0;
+ c->data.png.png = png_create_read_struct(PNG_LIBPNG_VER_STRING,
+ 0, 0, 0);
+ assert(c->data.png.png != 0);
+ c->data.png.info = png_create_info_struct(c->data.png.png);
+ assert(c->data.png.info != 0);
+
+ if (setjmp(png_jmpbuf(c->data.png.png))) {
+ png_destroy_read_struct(&c->data.png.png,
+ &c->data.png.info, 0);
+ assert(0);
+ }
+
+ png_set_progressive_read_fn(c->data.png.png, c,
+ info_callback, row_callback, end_callback);
+}
+
+
+void nspng_process_data(struct content *c, char *data, unsigned long size)
+{
+ if (setjmp(png_jmpbuf(c->data.png.png))) {
+ png_destroy_read_struct(&c->data.png.png,
+ &c->data.png.info, 0);
+ assert(0);
+ }
+
+ LOG(("data %p, size %li", data, size));
+ png_process_data(c->data.png.png, c->data.png.info,
+ data, size);
+
+ c->size += size;
+}
+
+
+/**
+ * info_callback -- PNG header has been completely received, prepare to process
+ * image data
+ */
+
+void info_callback(png_structp png, png_infop info)
+{
+ char *row, **row_pointers;
+ int i, bit_depth, color_type, palette_size, log2bpp, interlace;
+ unsigned int rowbytes, sprite_size;
+ unsigned long width, height;
+ struct content *c = png_get_progressive_ptr(png);
+ os_palette *palette;
+ os_sprite_palette *sprite_palette;
+ osspriteop_area *sprite_area;
+ osspriteop_header *sprite;
+ png_color *png_palette;
+ png_color_16 *png_background;
+ png_color_16 default_background = {0, 0xffff, 0xffff, 0xffff, 0xffff};
+
+ /* screen mode image result
+ * any 8bpp or less (palette) 8bpp sprite
+ * 8bpp or less 16 or 24bpp dither to 8bpp
+ * 16 or 24bpp 16 or 24bpp sprite of same depth
+ */
+
+ png_get_IHDR(png, info, &width, &height, &bit_depth,
+ &color_type, &interlace, 0, 0);
+ png_get_PLTE(png, info, &png_palette, &palette_size);
+
+ if (interlace == PNG_INTERLACE_ADAM7)
+ png_set_interlace_handling(png);
+
+ if (png_get_bKGD(png, info, &png_background))
+ png_set_background(png, png_background,
+ PNG_BACKGROUND_GAMMA_FILE, 1, 1.0);
+ else
+ png_set_background(png, &default_background,
+ PNG_BACKGROUND_GAMMA_SCREEN, 0, 1.0);
+
+ xos_read_mode_variable(os_CURRENT_MODE, os_MODEVAR_LOG2_BPP,
+ &log2bpp, 0);
+
+ /* make sprite */
+ sprite_size = sizeof(*sprite_area) + sizeof(*sprite);
+ if (color_type == PNG_COLOR_TYPE_PALETTE)
+ sprite_size += 8 * 256 + height * ((width + 3) & ~3u);
+ else if (log2bpp < 4)
+ sprite_size += height * ((width + 3) & ~3u);
+ else
+ sprite_size += height * ((width + 3) & ~3u) * 4;
+
+ sprite_area = xcalloc(sprite_size + 1000, 1);
+ sprite_area->size = sprite_size;
+ sprite_area->sprite_count = 1;
+ sprite_area->first = sizeof(*sprite_area);
+ sprite_area->used = sprite_size;
+ sprite = (osspriteop_header *) (sprite_area + 1);
+ sprite->size = sprite_size - sizeof(*sprite_area);
+ strcpy(sprite->name, "png");
+ sprite->height = height - 1;
+
+ c->data.png.sprite_area = sprite_area;
+
+ if (color_type == PNG_COLOR_TYPE_PALETTE) {
+ /* making 256 colour sprite with PNG's palette */
+ LOG(("palette with %i entries", palette_size));
+ c->data.png.type = PNG_PALETTE;
+
+ sprite->width = ((width + 3) & ~3u) / 4 - 1;
+ sprite->left_bit = 0;
+ sprite->right_bit = (8 * (((width - 1) % 4) + 1)) - 1;
+ sprite->mask = sprite->image = sizeof(*sprite) + 8 * 256;
+ sprite->mode = (os_mode) 21;
+ sprite_palette = (os_sprite_palette *) (sprite + 1);
+ for (i = 0; i != palette_size; i++)
+ sprite_palette->entries[i].on =
+ sprite_palette->entries[i].off =
+ png_palette[i].blue << 24 |
+ png_palette[i].green << 16 |
+ png_palette[i].red << 8 | 16;
+
+ /* make 8bpp */
+ if (bit_depth < 8)
+ png_set_packing(png);
+
+ } else /*if (log2bpp < 4)*/ {
+ /* making 256 colour sprite with no palette */
+ LOG(("dithering down"));
+ c->data.png.type = PNG_DITHER;
+
+ sprite->width = ((width + 3) & ~3u) / 4 - 1;
+ sprite->left_bit = 0;
+ sprite->right_bit = (8 * (((width - 1) % 4) + 1)) - 1;
+ sprite->mask = sprite->image = sizeof(*sprite);
+ sprite->mode = (os_mode) 21;
+
+ if (color_type == PNG_COLOR_TYPE_GRAY && bit_depth < 8)
+ png_set_gray_1_2_4_to_8(png);
+ if (color_type == PNG_COLOR_TYPE_GRAY ||
+ color_type == PNG_COLOR_TYPE_GRAY_ALPHA)
+ png_set_gray_to_rgb(png);
+ if (bit_depth == 16)
+ png_set_strip_16(png);
+
+ } /*else {*/
+ /* convert everything to 24-bit RGB (actually 32-bit) */
+ /* LOG(("24-bit"));
+ c->data.png.type = PNG_DEEP;
+
+ if (color_type == PNG_COLOR_TYPE_PALETTE)
+ png_set_palette_to_rgb(png);
+ if (color_type == PNG_COLOR_TYPE_GRAY && bit_depth < 8)
+ png_set_gray_1_2_4_to_8(png);
+ if (color_type == PNG_COLOR_TYPE_GRAY ||
+ color_type == PNG_COLOR_TYPE_GRAY_ALPHA)
+ png_set_gray_to_rgb(png);
+ if (bit_depth == 16)
+ png_set_strip_16(png);
+ if (color_type == PNG_COLOR_TYPE_RGB)
+ png_set_filler(png, 0xff, PNG_FILLER_AFTER);
+ }*/
+
+ png_read_update_info(png, info);
+
+ c->data.png.rowbytes = rowbytes = png_get_rowbytes(png, info);
+ c->data.png.sprite_image = ((char *) sprite) + sprite->image;
+ c->width = width;
+ c->height = height;
+
+ LOG(("size %li * %li, bpp %i, rowbytes %lu", width,
+ height, bit_depth, rowbytes));
+}
+
+
+void row_callback(png_structp png, png_bytep new_row,
+ png_uint_32 row_num, int pass)
+{
+ struct content *c = png_get_progressive_ptr(png);
+ unsigned long i, rowbytes = c->data.png.rowbytes;
+ int red, green, blue, alpha;
+ char *row = c->data.png.sprite_image + row_num * ((c->width + 3) & ~3u);
+ os_colour_number col;
+
+ /*LOG(("PNG row %li, pass %i, row %p, new_row %p",
+ row_num, pass, row, new_row));*/
+
+ if (new_row == 0)
+ return;
+
+ if (c->data.png.type == PNG_PALETTE)
+ png_progressive_combine_row(png, row, new_row);
+
+ else if (c->data.png.type == PNG_DITHER) {
+ for (i = 0; i * 3 != rowbytes; i++) {
+ red = new_row[i * 3];
+ green = new_row[i * 3 + 1];
+ blue = new_row[i * 3 + 2];
+ row[i] = colour_table[(red >> 4) << 8 |
+ (green >> 4) << 4 |
+ (blue >> 4)];
+ }
+ }
+}
+
+
+void end_callback(png_structp png, png_infop info)
+{
+ struct content *c = png_get_progressive_ptr(png);
+
+ LOG(("PNG end"));
+
+ /*xosspriteop_save_sprite_file(osspriteop_USER_AREA, c->data.png.sprite_area,
+ "png");*/
+}
+
+
+
+int nspng_convert(struct content *c, unsigned int width, unsigned int height)
+{
+ png_destroy_read_struct(&c->data.png.png, &c->data.png.info, 0);
+ c->title = xcalloc(100, 1);
+ sprintf(c->title, "png image (%ux%u)", c->width, c->height);
+ return 0;
+}
+
+
+void nspng_revive(struct content *c, unsigned int width, unsigned int height)
+{
+}
+
+
+void nspng_reformat(struct content *c, unsigned int width, unsigned int height)
+{
+}
+
+
+void nspng_destroy(struct content *c)
+{
+ xfree(c->title);
+ xfree(c->data.png.sprite_area);
+}
+
+
+void nspng_redraw(struct content *c, long x, long y,
+ unsigned long width, unsigned long height)
+{
+ /* TODO: scale to width, height */
+ int size;
+ osspriteop_trans_tab *table;
+
+ xcolourtrans_generate_table_for_sprite(c->data.png.sprite_area,
+ (osspriteop_id) (c->data.png.sprite_area + 1),
+ colourtrans_CURRENT_MODE, colourtrans_CURRENT_PALETTE,
+ 0, colourtrans_GIVEN_SPRITE, 0, 0, &size);
+ table = xcalloc(size, 1);
+ xcolourtrans_generate_table_for_sprite(c->data.png.sprite_area,
+ (osspriteop_id) (c->data.png.sprite_area + 1),
+ colourtrans_CURRENT_MODE, colourtrans_CURRENT_PALETTE,
+ table, colourtrans_GIVEN_SPRITE, 0, 0, 0);
+
+ xosspriteop_put_sprite_scaled(osspriteop_PTR,
+ c->data.png.sprite_area,
+ (osspriteop_id) (c->data.png.sprite_area + 1),
+ x, y, 0, 0, table);
+
+ xfree(table);
+}
+
diff --git a/riscos/png.h b/riscos/png.h
new file mode 100644
index 000000000..7f79a9a68
--- /dev/null
+++ b/riscos/png.h
@@ -0,0 +1,19 @@
+/**
+ * $Id: png.h,v 1.1 2003/05/10 11:15:49 bursa Exp $
+ */
+
+#ifndef _NETSURF_RISCOS_PNG_H_
+#define _NETSURF_RISCOS_PNG_H_
+
+#include "netsurf/content/content.h"
+
+void nspng_init(void);
+void nspng_create(struct content *c);
+void nspng_process_data(struct content *c, char *data, unsigned long size);
+int nspng_convert(struct content *c, unsigned int width, unsigned int height);
+void nspng_revive(struct content *c, unsigned int width, unsigned int height);
+void nspng_reformat(struct content *c, unsigned int width, unsigned int height);
+void nspng_destroy(struct content *c);
+void nspng_redraw(struct content *c, long x, long y,
+ unsigned long width, unsigned long height);
+#endif