summaryrefslogtreecommitdiff
path: root/apps/plugins/fractals/fractal.c
diff options
context:
space:
mode:
authorTomer Shalev <shalev.tomer@gmail.com>2010-01-15 05:53:15 +0000
committerTomer Shalev <shalev.tomer@gmail.com>2010-01-15 05:53:15 +0000
commit7719d297f2a1da0e45fd39cad21e99e23fd695c8 (patch)
treeae2b97d1b372340627ca3537554cd45310bace92 /apps/plugins/fractals/fractal.c
parent51630cbac1dcb04345fb1384812f1576f0ea29db (diff)
FS#10911 - Plugins: Fractals (formerly Mandelbrot)
- Rename the mandelbrot plugin to fractals - Update manual accordingly - Separate plugin's functionality into separate files - Lay the ground for having fractals sets other than the Mandelbrot set. For that the following will need to be implemented: - Create a new file for the new fracral set - Provide key mapping to switch between sets git-svn-id: svn://svn.rockbox.org/rockbox/trunk@24230 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'apps/plugins/fractals/fractal.c')
-rw-r--r--apps/plugins/fractals/fractal.c260
1 files changed, 260 insertions, 0 deletions
diff --git a/apps/plugins/fractals/fractal.c b/apps/plugins/fractals/fractal.c
new file mode 100644
index 0000000000..3a0c785bdd
--- /dev/null
+++ b/apps/plugins/fractals/fractal.c
@@ -0,0 +1,260 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Copyright (C) 2004 Matthias Wientapper
+ * Heavily extended 2005 Jens Arnold
+ * Extended 2009 Tomer Shalev
+ *
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+#include "plugin.h"
+
+#ifdef HAVE_LCD_BITMAP
+
+#include "fractal.h"
+#include "fractal_rect.h"
+#include "fractal_sets.h"
+#include "mandelbrot_set.h"
+
+#if (LCD_DEPTH < 8)
+#define USEGSLIB
+#define MYLCD(fn) grey_ub_ ## fn
+#define MYLCD_UPDATE()
+#define MYXLCD(fn) grey_ub_ ## fn
+#else
+#define MYLCD(fn) rb->lcd_ ## fn
+#define MYLCD_UPDATE() rb->lcd_update();
+#define MYXLCD(fn) xlcd_ ## fn
+#endif
+
+#ifdef USEGSLIB
+GREY_INFO_STRUCT
+static unsigned char *gbuf;
+static size_t gbuf_size = 0;
+unsigned char imgbuffer[LCD_HEIGHT];
+#else
+fb_data imgbuffer[LCD_HEIGHT];
+#endif
+
+#define REDRAW_NONE 0
+#define REDRAW_PARTIAL 1
+#define REDRAW_FULL 2
+
+PLUGIN_HEADER
+
+/* returns 1 if a button has been pressed, 0 otherwise */
+static int button_yield(void *ctx)
+{
+ long *button = (long *)ctx;
+
+ *button = rb->button_get(false);
+ switch (*button)
+ {
+ case FRACTAL_QUIT:
+ case FRACTAL_UP:
+ case FRACTAL_DOWN:
+ case FRACTAL_LEFT:
+ case FRACTAL_RIGHT:
+ case FRACTAL_ZOOM_IN:
+ case FRACTAL_ZOOM_OUT:
+ case FRACTAL_PRECISION_INC:
+ case FRACTAL_PRECISION_DEC:
+ case FRACTAL_RESET:
+#ifdef FRACTAL_ZOOM_IN2
+ case FRACTAL_ZOOM_IN2:
+#endif
+#ifdef FRACTAL_ZOOM_IN_PRE
+ case FRACTAL_ZOOM_IN_PRE:
+#endif
+ return 1;
+ default:
+ *button = BUTTON_NONE;
+ return 0;
+ }
+}
+
+static void cleanup(void *parameter)
+{
+ (void)parameter;
+#ifdef USEGSLIB
+ grey_release();
+#endif
+}
+
+enum plugin_status plugin_start(const void* parameter)
+{
+ long lastbutton = BUTTON_NONE;
+ int redraw = REDRAW_FULL;
+ struct fractal_ops *ops = &mandelbrot_ops;
+
+ (void)parameter;
+
+#ifdef USEGSLIB
+ /* get the remainder of the plugin buffer */
+ gbuf = (unsigned char *)rb->plugin_get_buffer(&gbuf_size);
+
+ /* initialize the greyscale buffer.*/
+ if (!grey_init(gbuf, gbuf_size, GREY_ON_COP, LCD_WIDTH, LCD_HEIGHT, NULL))
+ {
+ rb->splash(HZ, "Couldn't init greyscale display");
+ return 0;
+ }
+ grey_show(true); /* switch on greyscale overlay */
+#endif
+
+#if LCD_DEPTH > 1
+ rb->lcd_set_backdrop(NULL);
+#endif
+
+ ops->init();
+
+ /* main loop */
+ while (true)
+ {
+ long button = BUTTON_NONE;
+
+ if (redraw != REDRAW_NONE)
+ {
+#ifdef HAVE_ADJUSTABLE_CPU_FREQ
+ rb->cpu_boost(true);
+#endif
+ if (redraw == REDRAW_FULL)
+ {
+ MYLCD(clear_display)();
+ MYLCD_UPDATE();
+ rects_queue_init();
+ }
+
+ /* paint all rects */
+ rects_calc_all(ops->calc, button_yield, (void *)&button);
+#ifdef HAVE_ADJUSTABLE_CPU_FREQ
+ rb->cpu_boost(false);
+#endif
+ /* not interrupted by button press - screen is fully drawn */
+ redraw = (button == BUTTON_NONE) ? REDRAW_NONE : REDRAW_PARTIAL;
+ }
+
+ if (button == BUTTON_NONE)
+ button = rb->button_get(true);
+
+ switch (button)
+ {
+#ifdef FRACTAL_RC_QUIT
+ case FRACTAL_RC_QUIT:
+#endif
+ case FRACTAL_QUIT:
+#ifdef USEGSLIB
+ grey_release();
+#endif
+ return PLUGIN_OK;
+
+ case FRACTAL_ZOOM_OUT:
+#ifdef FRACTAL_ZOOM_OUT_PRE
+ if (lastbutton != FRACTAL_ZOOM_OUT_PRE)
+ break;
+#endif
+ ops->zoom(-1);
+ redraw = REDRAW_FULL;
+ break;
+
+
+ case FRACTAL_ZOOM_IN:
+#ifdef FRACTAL_ZOOM_IN_PRE
+ if (lastbutton != FRACTAL_ZOOM_IN_PRE)
+ break;
+#endif
+#ifdef FRACTAL_ZOOM_IN2
+ case FRACTAL_ZOOM_IN2:
+#endif
+ ops->zoom(1);
+ redraw = REDRAW_FULL;
+ break;
+
+ case FRACTAL_UP:
+ ops->move(0, +1);
+ MYXLCD(scroll_down)(LCD_SHIFT_Y);
+ MYLCD_UPDATE();
+ if (redraw != REDRAW_FULL)
+ redraw = rects_move_down() ? REDRAW_FULL : REDRAW_PARTIAL;
+ break;
+
+ case FRACTAL_DOWN:
+ ops->move(0, -1);
+ MYXLCD(scroll_up)(LCD_SHIFT_Y);
+ MYLCD_UPDATE();
+ if (redraw != REDRAW_FULL)
+ redraw = rects_move_up() ? REDRAW_FULL : REDRAW_PARTIAL;
+ break;
+
+ case FRACTAL_LEFT:
+ ops->move(-1, 0);
+ MYXLCD(scroll_right)(LCD_SHIFT_X);
+ MYLCD_UPDATE();
+ if (redraw != REDRAW_FULL)
+ redraw = rects_move_right() ? REDRAW_FULL : REDRAW_PARTIAL;
+ break;
+
+ case FRACTAL_RIGHT:
+ ops->move(+1, 0);
+ MYXLCD(scroll_left)(LCD_SHIFT_X);
+ MYLCD_UPDATE();
+ if (redraw != REDRAW_FULL)
+ redraw = rects_move_left() ? REDRAW_FULL : REDRAW_PARTIAL;
+ break;
+
+ case FRACTAL_PRECISION_DEC:
+#ifdef FRACTAL_PRECISION_DEC_PRE
+ if (lastbutton != FRACTAL_PRECISION_DEC_PRE)
+ break;
+#endif
+ if (ops->precision(-1))
+ redraw = REDRAW_FULL;
+
+ break;
+
+ case FRACTAL_PRECISION_INC:
+#ifdef FRACTAL_PRECISION_INC_PRE
+ if (lastbutton != FRACTAL_PRECISION_INC_PRE)
+ break;
+#endif
+ if (ops->precision(+1))
+ redraw = REDRAW_FULL;
+
+ break;
+
+ case FRACTAL_RESET:
+ ops->init();
+ redraw = REDRAW_FULL;
+ break;
+
+ default:
+ if (rb->default_event_handler_ex(button, cleanup, NULL)
+ == SYS_USB_CONNECTED)
+ return PLUGIN_USB_CONNECTED;
+ break;
+ }
+
+ if (button != BUTTON_NONE)
+ lastbutton = button;
+ }
+#ifdef USEGSLIB
+ grey_release();
+#endif
+ return PLUGIN_OK;
+}
+
+#endif