📄 mandelbrot.c
字号:
#ifndef lintstatic char sccsid[] = "@(#)mandelbrot.c 1.1 92/07/30 Copyr 1989, 1990 Sun Micro";#endif#include <stdio.h>#include <signal.h>#include <xgl/xgl.h>#include "WS_macros.h"#include "XGL.icon"/* * For sunview */#define W_HEIGHT 800 #define W_WIDTH 1000#define C_HEIGHT 550 #define C_WIDTH 550#define Init_Pt_F2D(pt, X, Y) (pt.x = X, pt.y = Y)/* * global extern defines */extern void reset_proc();extern void reset_vdc();extern void redraw_proc();extern void granular_proc();extern void iterate_proc();extern void go_home();extern void create_panel();extern void zoom_pan_proc();static void update_panel();static void choose_cmap_proc();static void canvas_repaint_proc();static void canvas_resize_proc();static Notify_value quit_proc();/* * Global vars */static Frame frame; static Canvas canvas; /* graphics canvas */ static Panel panel;static Panel_item draw, quit;static struct rect *crect; /*canvas size & location */static Panel_item eye_slider_itemx, eye_slider_itemy, eye_slider_itemz, fly_mode_item;static Panel_item center_x_item, center_y_item;static Panel_item delta_x_item, delta_y_item;static Panel_item sample_size_item, iterations_item;static float zoom_coord_x, zoom_coord_y;static int can_wid, can_hgt;static Xgl_sys_state sys_state;/* * For the FRACTAL stuff only */ #define COL_WHITE 127#define BUFFER_SIZE 1#define MY_CMAP_SIZE 128typedef struct { float real, imag; } COMPLEX;#define C_SQ(z_out, z_in) \ { \ z_out.imag = 2*z_in.real*z_in.imag; \ z_out.real = temp.real - temp.imag; \ }#define C_ADD(z_out, z_op1, z_op2) \ { \ z_out.real = z_op1.real+z_op2.real; \ z_out.imag = z_op1.imag+z_op2.imag; \ } #define C_ABS(out, z) \ { \ temp.real = z.real*z.real; \ temp.imag = z.imag*z.imag; \ out = temp.real+temp.imag; \ } static Xgl_color col, white;static Xgl_color_facet *rects_facet;static Xgl_rect_list rect_list;static Xgl_rect_f2d rect;static Xgl_2d_ctx ctx;static Xgl_trans transform;static Xgl_ras ras;static Xgl_cmap cmap=NULL;static Xgl_pt_list zoom_pl;static Xgl_pt_f2d zoom_pts[5];static Xgl_color c[128];static Xgl_color_list clist;static COMPLEX center, range, granularity, scale;static int iterations;static int shift_factor;static int pix_count=0;staticvoid put_rectangle(color, x, y)Xgl_color *color;float x, y;{ int pt_index; int i; float temp_x = x+granularity.real; float temp_y = y+granularity.imag; rect.corner_min.x = x; rect.corner_min.y = y; rect.corner_min.flag = 0; rect.corner_max.x = temp_x; rect.corner_max.y = temp_y; xgl_object_set(ctx, XGL_CTX_SURF_FRONT_COLOR, color, 0); xgl_multirectangle(ctx, &rect_list);}staticvoid recalc_granularity(){ Xgl_pt_i2d ras_width; xgl_object_get(ras, XGL_RAS_WIDTH, &ras_width.x); xgl_object_get(ras, XGL_RAS_HEIGHT, &ras_width.y); granularity.real = scale.real*2*range.real / (float)ras_width.x; granularity.imag = scale.imag*2*range.imag / (float)ras_width.y; }/* * This is the heart of the program */staticvoid page_proc(){COMPLEX z, c;COMPLEX temp; Xgl_color color;int color_count;float val;update_panel();recalc_granularity();if ((granularity.real > 1.e-4) && (granularity.imag > 1.e-4)) { for (c.real=center.real - range.real; c.real<=center.real + range.real; c.real+=granularity.real ) { for (c.imag=center.imag - range.imag; c.imag<=center.imag + range.imag; c.imag+=granularity.imag ) { z.real = 0.0; z.imag=0.0; temp.real=0.0; temp.imag=0.0; for (color_count=0; color_count < (iterations-1); color_count++) { C_SQ(z,z); C_ADD(z, z, c); C_ABS(val, z); if (val >= 4) break; } color.index = color_count >> shift_factor; put_rectangle(&color, c.real, c.imag); } } }}main(argc, argv)int argc;char **argv;{xgl_icon = icon_create(ICON_IMAGE, &icon_pixrect, 0);sys_state = xgl_open(0);(void) signal(SIGINT, go_home);create_panel();reset_proc();xv_main_loop(frame);}staticvoid update_panel(){char output_str[50];sprintf(output_str, "%1.8f", center.real);panel_set_value(center_x_item, output_str );sprintf(output_str, "%1.8f", center.imag);panel_set_value(center_y_item, output_str );sprintf(output_str, "%1.8f", range.real);panel_set_value(delta_x_item, output_str );sprintf(output_str, "%1.8f", range.imag);panel_set_value(delta_y_item, output_str );panel_set_value(sample_size_item, (int) scale.real);panel_set_value(iterations_item, iterations);}static void create_panel (){ /* Processing begins here */ if ((frame = xv_create (NULL, FRAME, WIN_DYNAMIC_VISUAL, TRUE, FRAME_ICON, xgl_icon, FRAME_LABEL, "Fractal Demo", WIN_HEIGHT, W_HEIGHT, WIN_WIDTH, W_WIDTH, 0)) == NULL) { printf ("Cannot make frame\n"); exit (0); } (void) notify_interpose_destroy_func(frame, quit_proc); /* Create the control panel */ panel = xv_create (frame, PANEL, WIN_COLUMNS, 30, PANEL_LAYOUT, PANEL_VERTICAL, 0); center_x_item = panel_create_item(panel, PANEL_TEXT, PANEL_LABEL_STRING, "Ctr x;", XV_X, xv_col(panel, 1), XV_Y, xv_row(panel, 1), PANEL_VALUE_DISPLAY_LENGTH, 12, 0); center_y_item = panel_create_item(panel, PANEL_TEXT, PANEL_LABEL_STRING, "Ctr y:", XV_X, xv_col(panel, 1), XV_Y, xv_row(panel, 2), PANEL_VALUE_DISPLAY_LENGTH, 12, 0); delta_x_item = panel_create_item(panel, PANEL_TEXT, PANEL_LABEL_STRING, "Rad x:", XV_X, xv_col(panel, 1), XV_Y, xv_row(panel, 3), PANEL_VALUE_DISPLAY_LENGTH, 12, 0); delta_y_item = panel_create_item(panel, PANEL_TEXT, PANEL_LABEL_STRING, "Rad y:", XV_X, xv_col(panel, 1), XV_Y, xv_row(panel, 4), PANEL_VALUE_DISPLAY_LENGTH, 11, 0); panel_create_item (panel, PANEL_BUTTON, PANEL_LABEL_STRING, "Reset", PANEL_NOTIFY_PROC, reset_proc, XV_X, xv_col(panel, 2), XV_Y, xv_row(panel, 6), 0); panel_create_item (panel, PANEL_BUTTON, PANEL_LABEL_STRING, "Redraw", PANEL_NOTIFY_PROC, redraw_proc, XV_X, xv_col(panel, 2), XV_Y, xv_row(panel, 8), 0); panel_create_item (panel, PANEL_BUTTON, PANEL_LABEL_STRING, "Quit", PANEL_NOTIFY_PROC, go_home, XV_X, xv_col(panel, 2), XV_Y, xv_row(panel, 10), 0); sample_size_item = panel_create_item (panel, PANEL_SLIDER, PANEL_MIN_VALUE, 1, PANEL_MAX_VALUE, 32, PANEL_LABEL_STRING, "Sample Size", XV_X, xv_col(panel, 1), XV_Y, xv_row(panel, 13), PANEL_SLIDER_WIDTH, xv_col(panel, 10), PANEL_SHOW_RANGE, FALSE, PANEL_SHOW_VALUE, TRUE, PANEL_PAINT, PANEL_CLEAR, PANEL_VALUE, 32, PANEL_NOTIFY_PROC, granular_proc, 0); iterations_item = panel_create_item (panel, PANEL_SLIDER, PANEL_VALUE, MY_CMAP_SIZE, PANEL_MIN_VALUE, 8, PANEL_MAX_VALUE, 256, PANEL_LABEL_STRING, "Iterations", XV_X, xv_col(panel, 1), XV_Y, xv_row(panel, 17), PANEL_SLIDER_WIDTH, xv_col(panel, 10), PANEL_SHOW_RANGE, FALSE, PANEL_SHOW_VALUE, TRUE, PANEL_PAINT, PANEL_CLEAR, PANEL_NOTIFY_PROC, iterate_proc, 0); panel_create_item(panel, PANEL_CYCLE, XV_Y, xv_row(panel, 20), XV_X, xv_col(panel, 1), PANEL_NOTIFY_PROC, choose_cmap_proc, PANEL_LABEL_STRING, "Cmap:", PANEL_CHOICE_STRINGS, "Crayola", "Green Grade", 0, PANEL_VALUE, 0, 0); if ((canvas = xv_create (frame, CANVAS, WIN_SHOW, TRUE, WIN_DYNAMIC_VISUAL, TRUE, CANVAS_RETAINED, FALSE, CANVAS_AUTO_CLEAR, FALSE, CANVAS_FIXED_IMAGE, FALSE, WIN_EVENT_PROC, zoom_pan_proc, WIN_RIGHT_OF, panel, 0)) == NULL) { printf ("Cannot make canvas\n"); exit (0); } xv_set (canvas, WIN_CONSUME_PICK_EVENTS, WIN_MOUSE_BUTTONS, LOC_DRAG, 0, 0); /* Get the size of the canvas in pixels */ can_wid = (int) xv_get (canvas, CANVAS_WIDTH); can_hgt = (int) xv_get (canvas, CANVAS_HEIGHT); { Atom catom; Window canvas_window, frame_window; display = (Display *)xv_get(frame, XV_DISPLAY); pw = (Xv_Window)canvas_paint_window(canvas); canvas_window = (Window)xv_get(pw, XV_XID); frame_window = (Window)xv_get(frame, XV_XID); xv_set(pw, WIN_EVENT_PROC, zoom_pan_proc, WIN_CONSUME_EVENTS, LOC_DRAG, 0, 0); catom = XInternAtom(display, "WM_COLORMAP_WINDOWS", False); XChangeProperty(display, frame_window, catom, XA_WINDOW, 32, PropModeAppend, &canvas_window, 1); xgl_x_win.X_display = (void *)XV_DISPLAY_FROM_WINDOW(pw); xgl_x_win.X_window = (Xgl_usgn32)canvas_window; xgl_x_win.X_screen = (int)DefaultScreen(display); xv_set(canvas, CANVAS_RESIZE_PROC, canvas_resize_proc, CANVAS_REPAINT_PROC, canvas_repaint_proc, 0); ras = xgl_window_raster_device_create(XGL_WIN_X, &xgl_x_win, 0); } white.index = COL_WHITE; ctx = xgl_2d_context_create(XGL_CTX_DEVICE, ras, XGL_CTX_VDC_MAP, XGL_VDC_MAP_ALL, XGL_CTX_LINE_COLOR, &white, 0); choose_cmap_proc(NULL, 0, NULL); xgl_object_get(ctx, XGL_CTX_VIEW_TRANS, &transform); rect_list.num_rects = 1; rect_list.rect_type = XGL_MULTIRECT_F2D; rect_list.bbox = NULL; rect_list.rects.f2d = ▭ /* * init point list--used for drawing the zoom area. */ zoom_pl.pt_type = XGL_PT_F2D; zoom_pl.bbox = NULL; zoom_pl.num_pts = 5; zoom_pl.pts.f2d = zoom_pts;}/* Quitting routines */staticvoid go_home(){ xgl_close(sys_state); exit(0);}staticNotify_value quit_proc(frame, status)Frame frame;Destroy_status status;{ if (status == DESTROY_CHECKING) xgl_close(sys_state); return(notify_next_destroy_func(frame, status));}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -