diff --git a/pattern_frame_buffer/Makefile b/pattern_frame_buffer/Makefile index 3be4be6c6d07b77d8897994428ed716654cf8366..c144ed4391c5262d283c7797896cfd7becdb3aac 100755 --- a/pattern_frame_buffer/Makefile +++ b/pattern_frame_buffer/Makefile @@ -11,6 +11,8 @@ COMPILE_OPTS_M0 = -mfloat-abi=softfp -mcpu=cortex-m0 COMPILE_OPTS_M0plus = -mfloat-abi=softfp -mcpu=cortex-m0plus COMPILE_OPTS_M3 = -mfloat-abi=softfp -mcpu=cortex-m3 +MACROS = -DFB_MAX_BUFFER_LEN=16384 -DFBC_MAX_PATTERN_FUNC=16 -DFBC_MAX_DATA_PATTERN_LEN=32 -D FBC_MAX_COPY_FUNC=4 -DIMG_MAX_NUM_IMAGES=3 -DIMG_MAX_IMAGE_WIDTH=15 -DIMG_MAX_IMAGE_HEIGHT=15 -DMTN_X_LED_SPACING=10 -DMTN_Y_LED_SPACING=10 + INCLUDE_DIRS = -I./include/ -I../memory/include -I../scheduler/include DOC_DIR = ./doc @@ -49,13 +51,13 @@ PATTERN_FB_M3_OBJS = $(patsubst %,$(PATTERN_FB_M3_OBJ_DIR)%,$(PATTERN_FB_M3_OBJS all: $(PATTERN_FB_OUT_M4_FPU) $(PATTERN_FB_OUT_M0) $(PATTERN_FB_OUT_M0plus) $(PATTERN_FB_OUT_M3) $(PATTERN_FB_M4_FPU_OBJ_DIR)%.o: $(SRC_DIR)%.c - $(CC) -c $(CFLAGS) $(COMPILE_OPTS_M4_FPU) -o $@ $< + $(CC) -c $(CFLAGS) $(COMPILE_OPTS_M4_FPU) $(MACROS) -o $@ $< $(PATTERN_FB_M0_OBJ_DIR)%.o: $(SRC_DIR)%.c - $(CC) -c $(CFLAGS) $(COMPILE_OPTS_M0) -o $@ $< + $(CC) -c $(CFLAGS) $(COMPILE_OPTS_M0) $(MACROS) -o $@ $< $(PATTERN_FB_M0plus_OBJ_DIR)%.o: $(SRC_DIR)%.c - $(CC) -c $(CFLAGS) $(COMPILE_OPTS_M0plus) -o $@ $< + $(CC) -c $(CFLAGS) $(COMPILE_OPTS_M0plus) $(MACROS) -o $@ $< $(PATTERN_FB_M3_OBJ_DIR)%.o: $(SRC_DIR)%.c - $(CC) -c $(CFLAGS) $(COMPILE_OPTS_M3) -o $@ $< + $(CC) -c $(CFLAGS) $(COMPILE_OPTS_M3) $(MACROS) -o $@ $< mkdir_build: mkdir -p build/m4_fpu mkdir -p build/m0 diff --git a/pattern_frame_buffer/include/frame_buffer.h b/pattern_frame_buffer/include/frame_buffer.h index edf28ebf3b9ee5e993060749835fcb8d8b432177..6b48631151c97075bff569fdc8c376095b4c3f50 100644 --- a/pattern_frame_buffer/include/frame_buffer.h +++ b/pattern_frame_buffer/include/frame_buffer.h @@ -5,17 +5,25 @@ extern "C" { #endif -#include "memory.h" -#include "frame_buffer_registers.h" - #ifndef FB_MAX_BUFFER_LEN - #define FB_MAX_BUFFER_LEN 16*1024 + #error "Please, specify the maximum frame buffer length with the FB_MAX_BUFFER_LEN macro" #endif -#define BYTES_PER_PIXEL 3 -#define LEDS_BYTES_PER_PIXEL 12 - -unsigned char frame_buffer_init(TFrameBuffer *fb,TMemory *memory); +#define FB_BYTES_PER_PIXEL 3 + +typedef struct +{ + unsigned short int ram_base_address; + unsigned short int eeprom_base_address; + unsigned short int num_rows; + unsigned short int num_pixels_per_row; + unsigned short int num_buffers; + unsigned short int buffer_size; + unsigned short int free_mem; + unsigned char pixel_buffer[FB_MAX_BUFFER_LEN]; +}TFrameBuffer; + +void frame_buffer_init(TFrameBuffer *fb,unsigned short int ram_base_address,unsigned short int eeprom_base_address); void frame_buffer_set_num_rows(TFrameBuffer *fb,unsigned short int rows); unsigned short int frame_buffer_get_num_rows(TFrameBuffer *fb); void frame_buffer_set_pixels_per_row(TFrameBuffer *fb,unsigned short int pixels); @@ -23,10 +31,8 @@ unsigned short int frame_buffer_get_pixels_per_row(TFrameBuffer *fb); void frame_buffer_set_num_buffers(TFrameBuffer *fb,unsigned char num); unsigned char frame_buffer_get_num_buffers(TFrameBuffer *fb); unsigned short int frame_buffer_get_free_memory(TFrameBuffer *fb); -unsigned char frame_buffer_update_buffer(TFrameBuffer *fb); -unsigned char *frame_buffer_get_pixel_buffer(TFrameBuffer *fb); -void frame_buffer_set_pixel_buffer(TFrameBuffer *fb,unsigned char *buffer); -void frame_buffer_set_pixel(TFrameBuffer *fb,unsigned char R,unsigned char G,unsigned char B,unsigned short int row,unsigned short int col, unsigned char *buffer); +unsigned char *frame_buffer_get_buffer(TFrameBuffer *fb,unsigned char buffer_id); +void frame_buffer_set_pixel(TFrameBuffer *fb,unsigned char buffer_id,unsigned char R,unsigned char G,unsigned char B,unsigned short int row,unsigned short int col); #ifdef __cplusplus } diff --git a/pattern_frame_buffer/include/frame_buffer_control.h b/pattern_frame_buffer/include/frame_buffer_control.h new file mode 100644 index 0000000000000000000000000000000000000000..ed4deeed49e34676641ff1bf7423c07a28a3f337 --- /dev/null +++ b/pattern_frame_buffer/include/frame_buffer_control.h @@ -0,0 +1,74 @@ +#ifndef _FRAME_BUFFER_CONTROL_H +#define _FRAME_BUFFER_CONTROL_H + +#ifdef __cplusplus +extern "C" { +#endif + +#include "frame_buffer.h" +#include "patterns.h" +#include "memory.h" +#include "scheduler.h" + +#ifndef FBC_MAX_PATTERN_FUNC + #error "Please, specify the maximum number of pattern functions with the FBC_MAX_PATTERN_FUNC macro" +#endif + +#ifndef FBC_MAX_DATA_PATTERN_LEN + #error "Please, specify the maximum number of dtaa for each pattern with the FBC_MAX_DATA_PATTERN_LEN macro" +#endif + +#ifndef FBC_MAX_COPY_FUNC + #error "Please, specify the maximum number of copy functions with the FBC_MAX_COPY_FUNC macro" +#endif + +#include "frame_buffer_control_registers.h" + +typedef void (*copy_func_t)(void *data); + +typedef struct TFBControl +{ + TFrameBuffer frame_buffer; + TScheduler *scheduler; + sched_channel_t sch_channel; + unsigned short int period_ms; + TMemModule mem_module; + unsigned short int ram_base_address; + unsigned short int eeprom_base_address; + // pattern attributes + unsigned char num_patterns; + void (*pat_functions[FBC_MAX_PATTERN_FUNC])(TLEDArea *area,void *pattern_data,unsigned char buffer_id,unsigned short int period,struct TFBControl *control); + TLEDArea pat_area[FBC_MAX_PATTERN_FUNC]; + unsigned char pat_buffer_id[FBC_MAX_PATTERN_FUNC]; + unsigned char pat_parameters[FBC_MAX_PATTERN_FUNC][FBC_MAX_DATA_PATTERN_LEN]; + // copy attributes + unsigned char num_copy_functions; + copy_func_t copy_functions[FBC_MAX_COPY_FUNC]; + void *copy_data[FBC_MAX_COPY_FUNC]; +}TFBControl; + +typedef void (*pattern_func_t)(TLEDArea *area,void *pattern_data,unsigned char buffer_id,unsigned short int period,TFBControl *control); + +unsigned char frame_buffer_control_init(TFBControl *control,TMemory *memory,TScheduler *scheduler,sched_channel_t ch,unsigned short int ram_base_address,unsigned short int eeprom_base_address); +void frame_buffer_control_start(TFBControl *control); +void frame_buffer_control_stop(TFBControl *control); +void frame_buffer_control_set_period(TFBControl *control,unsigned short int period_ms); +unsigned short int frame_buffer_control_get_period(TFBControl *control); +// pattern functions +unsigned char frame_buffer_control_add_pattern(TFBControl *control,pattern_func_t function,TLEDArea *area,void *data,unsigned char data_length,unsigned char buffer_id); +void frame_buffer_control_remove_pattern(TFBControl *control,unsigned char index); +void frame_buffer_control_clear_patterns(TFBControl *control); +unsigned char frame_buffer_control_get_num_patterns(TFBControl *control); +unsigned char *frame_buffer_control_get_parameters(TFBControl *control, unsigned char index); +void frame_buffer_control_update(TFBControl *control); +// copy functions +unsigned char frame_buffer_control_add_copy_function(TFBControl *control,copy_func_t function,void *data); +void frame_buffer_control_remove_copy_function(TFBControl *control,unsigned char index); +void frame_buffer_control_clear_copy_functions(TFBControl *control); +unsigned char frame_buffer_control_get_num_copy_functions(TFBControl *control); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/pattern_frame_buffer/include/frame_buffer_control_registers.h b/pattern_frame_buffer/include/frame_buffer_control_registers.h new file mode 100644 index 0000000000000000000000000000000000000000..f44d32dd4e0a7187e457a68f0d1ac9294f072b83 --- /dev/null +++ b/pattern_frame_buffer/include/frame_buffer_control_registers.h @@ -0,0 +1,62 @@ +#ifndef _FRAME_BUFFER_CONTROL_REGISTERS_H +#define _FRAME_BUFFER_CONTROL_REGISTERS_H + +#define RAM_FRAME_BUFFER_CONTROL_LENGTH (18+FBC_MAX_DATA_PATTERN_LEN+IMG_MAX_NUM_IMAGES*IMG_MAX_IMAGE_WIDTH*IMG_MAX_IMAGE_HEIGHT*3) + +#define FRAME_BUFFER_CONTROL_NUM_PATTERN_OFFSET 0 +#define FRAME_BUFFER_CONTROL_PATTERN_INDEX_OFFSET 1 +#define FRAME_BUFFER_CONTROL_OFFSET 2 +#define FRAME_BUFFER_CONTROL_PATTERN_ID_OFFSET 3 +#define FRAME_BUFFER_CONTROL_MIN_ROW_OFFSET 4 +#define FRAME_BUFFER_CONTROL_MAX_ROW_OFFSET 6 +#define FRAME_BUFFER_CONTROL_MIN_COL_OFFSET 8 +#define FRAME_BUFFER_CONTROL_MAX_COL_OFFSET 10 +#define FRAME_BUFFER_CONTROL_BUFFER_ID_OFFSET 12 +#define FRAME_BUFFER_CONTROL_DATA_OFFSET 13 +#define FRAME_BUFFER_CONTROL_FREE_MEMORY_OFFSET (13+FBC_MAX_DATA_PATTERN_LEN) +#define FRAME_BUFFER_CONTROL_IMG_MAX_WIDTH_OFFSET (15+FBC_MAX_DATA_PATTERN_LEN) +#define FRAME_BUFFER_CONTROL_IMG_MAX_HEIGHT_OFFSET (16+FBC_MAX_DATA_PATTERN_LEN) +#define FRAME_BUFFER_CONTROL_IMG_NUM_IMGS_OFFSET (17+FBC_MAX_DATA_PATTERN_LEN) +#define FRAME_BUFFER_CONTROL_IMG_DATA_OFFSET (18+FBC_MAX_DATA_PATTERN_LEN) + + +#define FRAME_BUFFER_CONTROL_LOAD 0x01 +#define FRAME_BUFFER_CONTROL_REMOVE 0x02 +#define FRAME_BUFFER_CONTROL_CLEAR 0x04 +#define FRAME_BUFFER_CONTROL_START 0x08 +#define FRAME_BUFFER_CONTROL_STOP 0x10 +#define FRAME_BUFFER_CONTROL_RUNNING 0x80 + +#define EEPROM_FRAME_BUFFER_CONTROL_LENGTH 8 + +#define FRAME_BUFFER_CONTROL_PERIOD_OFFSET 0 +#define FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET 2 +#define FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET 4 +#define FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET 6 + + +#ifndef DEFAULT_FRAME_BUFFER_CONTROL_PERIOD + #define DEFAULT_FRAME_BUFFER_CONTROL_PERIOD 0x0004 +#endif +#ifndef DEFAULT_FRAME_BUFFER_CONTROL_NUM_ROWS + #define DEFAULT_FRAME_BUFFER_CONTROL_NUM_ROWS 0x0004 +#endif +#ifndef DEFAULT_FRAME_BUFFER_CONTROL_NUM_PIXELS + #define DEFAULT_FRAME_BUFFER_CONTROL_NUM_PIXELS 0x0030 +#endif +#ifndef DEFAULT_FRAME_BUFFER_CONTROL_NUM_BUFFERS + #define DEFAULT_FRAME_BUFFER_CONTROL_NUM_BUFFERS 0x0001 +#endif + +#define frame_buffer_control_eeprom_data(name,section_name,base_address) \ +unsigned short int name##_eeprom_data[] __attribute__ ((section (section_name)))={DEFAULT_FRAME_BUFFER_CONTROL_PERIOD&0x00FF,base_address+FRAME_BUFFER_CONTROL_PERIOD_OFFSET, \ + (DEFAULT_FRAME_BUFFER_CONTROL_PERIOD>>8)&0x00FF,base_address+FRAME_BUFFER_CONTROL_PERIOD_OFFSET+1, \ + DEFAULT_FRAME_BUFFER_CONTROL_NUM_ROWS&0x00FF,base_address+FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET, \ + (DEFAULT_FRAME_BUFFER_CONTROL_NUM_ROWS>>8)&0x00FF,base_address+FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET+1, \ + DEFAULT_FRAME_BUFFER_CONTROL_NUM_PIXELS&0x00FF,base_address+FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET, \ + (DEFAULT_FRAME_BUFFER_CONTROL_NUM_PIXELS>>8)&0x00FF,base_address+FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET+1, \ + DEFAULT_FRAME_BUFFER_CONTROL_NUM_BUFFERS&0x00FF,base_address+FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET, \ + (DEFAULT_FRAME_BUFFER_CONTROL_NUM_BUFFERS>>8)&0x00FF,base_address+FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET+1}; + +#endif + diff --git a/pattern_frame_buffer/include/frame_buffer_registers.h b/pattern_frame_buffer/include/frame_buffer_registers.h deleted file mode 100644 index 40c70306879ae7c0c13bbb6ebb448de5bd29c34d..0000000000000000000000000000000000000000 --- a/pattern_frame_buffer/include/frame_buffer_registers.h +++ /dev/null @@ -1,40 +0,0 @@ -#ifndef _FRAME_BUFFER_REGISTERS_H -#define _FRAME_BUFFER_REGISTERS_H - -#ifndef RAM_FB_BASE_ADDRESS - #define RAM_FB_BASE_ADDRESS ((unsigned short int)0x0000) -#endif - -#define RAM_FB_LENGTH 2 - -#define FB_FREE_MEMORY (RAM_FB_BASE_ADDRESS) - -#ifndef EEPROM_FB_BASE_ADDRESS - #define EEPROM_FB_BASE_ADDRESS ((unsigned short int)0x0000) -#endif - -#define EEPROM_FB_LENGTH 6 - -#define FB_NUM_ROWS (EEPROM_FB_BASE_ADDRESS) -#define FB_NUM_PIXELS (EEPROM_FB_BASE_ADDRESS+2) -#define FB_NUM_BUFFERS (EEPROM_FB_BASE_ADDRESS+4) - -#ifndef DEFAULT_FB_NUM_ROWS - #define DEFAULT_FB_NUM_ROWS 0x0004 -#endif -#ifndef DEFAULT_FB_NUM_PIXELS - #define DEFAULT_FB_NUM_PIXELS 0x0030 -#endif -#ifndef DEFAULT_FB_NUM_BUFFERS - #define DEFAULT_FB_NUM_BUFFERS 0x0001 -#endif - -#define frame_buffer_eeprom_data(name,section_name) \ -unsigned short int name##_eeprom_data[] __attribute__ ((section (".section_nane")))={DEFAULT_FB_NUM_ROWS&0x00FF,FB_NUM_ROWS, \ - (DEFAULT_FB_NUM_ROWS>>8)&0x00FF,FB_NUM_ROWS+1, \ - DEFAULT_FB_NUM_PIXELS&0x00FF,FB_NUM_PIXELS, \ - (DEFAULT_FB_NUM_PIXELS>>8)&0x00FF,FB_NUM_PIXELS+1, \ - DEFAULT_FB_NUM_BUFFERS&0x00FF,FB_NUM_BUFFERS, \ - (DEFAULT_FB_NUM_BUFFERS>>8)&0x00FF,FB_NUM_BUFFERS+1}; \ -#endif - diff --git a/pattern_frame_buffer/include/image_patterns.h b/pattern_frame_buffer/include/image_patterns.h index fe385c1e2c2f009b4e4afba0f1b5500ecfeb4fa8..69696474c272258aeb2b0e0c7b105b83a7b626bc 100644 --- a/pattern_frame_buffer/include/image_patterns.h +++ b/pattern_frame_buffer/include/image_patterns.h @@ -2,25 +2,25 @@ #define IMAGE_PATTERNS_H #include "patterns.h" -#include "memory.h" +#include "frame_buffer_control.h" -#ifndef MAX_NUM_IMAGES - #define MAX_NUM_IMAGES 1 +#ifndef IMG_MAX_NUM_IMAGES + #error "Please, specify the maximum number of images with the IMG_MAX_NUM_IMAGES macro" #endif -#ifndef MAX_IMAGE_WIDTH - #define MAX_IMAGE_WIDTH 15 +#ifndef IMG_MAX_IMAGE_WIDTH + #error "Please, specify the maximum image width with the IMG_MAX_IMAGE_WIDTH macro" #endif -#ifndef MAX_IMAGE_HEIGHT - #define MAX_IMAGE_HEIGHT 15 +#ifndef IMG_MAX_IMAGE_HEIGHT + #error "Please, specify the maximum image height with the IMG_MAX_IMAGE_HEIGHT macro" #endif -#include "image_patterns_registers.h" - #define IMAGE_GROUP 0x20 -unsigned char img_patterns_init(TMemory *memory); +extern unsigned char img_pattern_data[IMG_MAX_NUM_IMAGES][IMG_MAX_IMAGE_WIDTH][IMG_MAX_IMAGE_HEIGHT][3]; + +void img_patterns_init(unsigned short int ram_base_address); #pragma pack (push, 1) typedef struct @@ -40,6 +40,6 @@ typedef struct #define IMG_WF_INDEX_OFFSET 5 #define IMG_MTN_INDEX_OFFSET 6 -void img_general(TLEDArea *area,TIMGDisplayData *pattern_data,unsigned short int period,unsigned char *buffer); +void img_general(TLEDArea *area,TIMGDisplayData *pattern_data,unsigned char buffer_id,unsigned short int period,TFBControl *control); #endif diff --git a/pattern_frame_buffer/include/image_patterns_registers.h b/pattern_frame_buffer/include/image_patterns_registers.h deleted file mode 100644 index bf3e8b9146ab3bcc1695e7e7cc7810e445d4ee27..0000000000000000000000000000000000000000 --- a/pattern_frame_buffer/include/image_patterns_registers.h +++ /dev/null @@ -1,16 +0,0 @@ -#ifndef _IMAGE_PATTERNS_REGISTERS_H -#define _IMAGE_PATTERNS_REGISTERS_H - -#ifndef RAM_IMG_PATTERNS_BASE_ADDRESS - #define RAM_IMG_PATTERNS_BASE_ADDRESS ((unsigned short int)0x0000) -#endif - -#define RAM_IMG_PATTERNS_LENGTH MAX_NUM_IMAGES*MAX_IMAGE_WIDTH*MAX_IMAGE_HEIGHT*3+3 - -#define IMG_PATTERNS_MAX_WIDTH (RAM_IMG_PATTERNS_BASE_ADDRESS) -#define IMG_PATTERNS_MAX_HEIGHT (RAM_IMG_PATTERNS_BASE_ADDRESS+1) -#define IMG_PATTERNS_NUM_IMGS (RAM_IMG_PATTERNS_BASE_ADDRESS+2) -#define IMG_PATTERNS_DATA (RAM_IMG_PATTERNS_BASE_ADDRESS+3) - -#endif - diff --git a/pattern_frame_buffer/include/led_control.h b/pattern_frame_buffer/include/led_control.h deleted file mode 100644 index c5a30f0ef62dd2c05c01987aca8278842ca33fc3..0000000000000000000000000000000000000000 --- a/pattern_frame_buffer/include/led_control.h +++ /dev/null @@ -1,44 +0,0 @@ -#ifndef _LED_CONTROL_H -#define _LED_CONTROL_H - -#ifdef __cplusplus -extern "C" { -#endif - -#include "stm32f4xx.h" -#include "patterns.h" -#include "memory.h" - -#ifndef MAX_PATTERN_FUNC - #define MAX_PATTERN_FUNC 16 -#endif - -#ifndef MAX_DATA_PATTERN_LEN - #define MAX_DATA_PATTERN_LEN 32 -#endif - -#include "led_control_registers.h" - -typedef void (*pattern_func_t)(TLEDArea *area,void *pattern_data,uint16_t period,unsigned char *buffer); - -typedef struct -{ - unsigned char num_patterns; - pattern_func_t functions[MAX_PATTERN_FUNC]; - TLEDArea area[MAX_PATTERN_FUNC]; - unsigned char parameters[MAX_PATTERN_FUNC][MAX_DATA_PATTERN_LEN]; -}TPatterns; - -unsigned char led_control_init(TMemory *memory); -unsigned char led_control_add_pattern(pattern_func_t function,TLEDArea *area,void *data,unsigned char data_length); -void led_control_remove_pattern(unsigned char index); -void led_control_clear_patterns(void); -unsigned char led_control_get_num_patterns(void); -unsigned char *led_control_get_parameters(unsigned char index); -void led_control_loop(void); - -#ifdef __cplusplus -} -#endif - -#endif diff --git a/pattern_frame_buffer/include/led_control_registers.h b/pattern_frame_buffer/include/led_control_registers.h deleted file mode 100644 index 18f73d8986a839c18e47ee8413c6642e74b5a6b6..0000000000000000000000000000000000000000 --- a/pattern_frame_buffer/include/led_control_registers.h +++ /dev/null @@ -1,25 +0,0 @@ -#ifndef _LED_CONTROL_REGISTERS_H -#define _LED_CONTROL_REGISTERS_H - -#ifndef RAM_LED_CONTROL_BASE_ADDRESS - #define RAM_LED_CONTROL_BASE_ADDRESS ((unsigned short int)0x0000) -#endif - -#define RAM_LED_CONTROL_LENGTH 12+MAX_DATA_PATTERN_LEN - -#define LED_CONTROL_NUM_PATTERN (RAM_LED_CONTROL_BASE_ADDRESS) -#define LED_CONTROL_PATTERN_INDEX (RAM_LED_CONTROL_BASE_ADDRESS+1) -#define LED_CONTROL (RAM_LED_CONTROL_BASE_ADDRESS+2) -#define LED_CONTROL_PATTERN_ID (RAM_LED_CONTROL_BASE_ADDRESS+3) -#define LED_CONTROL_MIN_ROW (RAM_LED_CONTROL_BASE_ADDRESS+4) -#define LED_CONTROL_MAX_ROW (RAM_LED_CONTROL_BASE_ADDRESS+6) -#define LED_CONTROL_MIN_COL (RAM_LED_CONTROL_BASE_ADDRESS+8) -#define LED_CONTROL_MAX_COL (RAM_LED_CONTROL_BASE_ADDRESS+10) -#define LED_CONTROL_DATA (RAM_LED_CONTROL_BASE_ADDRESS+12) - -#define LED_CONTROL_LOAD 0x01 -#define LED_CONTROL_REMOVE 0x02 -#define LED_CONTROL_CLEAR 0x04 - -#endif - diff --git a/pattern_frame_buffer/include/motion_patterns.h b/pattern_frame_buffer/include/motion_patterns.h index 39a8a1d3162d37e12b765e2fcc439548401de129..146cffdf9e89d6efbce129212d6ce65fd0749b72 100644 --- a/pattern_frame_buffer/include/motion_patterns.h +++ b/pattern_frame_buffer/include/motion_patterns.h @@ -2,16 +2,17 @@ #define _MOTION_PATTERNS_H #include "patterns.h" +#include "frame_buffer_control.h" #ifndef MTN_X_LED_SPACING - #define MTN_X_LED_SPACING 10 + #error "Please, specify the LED spacing in mm in the X direction with the MTN_X_LED_SPACING macro" #endif #ifndef MTN_Y_LED_SPACING - #define MTN_Y_LED_SPACING 10 + #error "Please, specify the LED spacing in mm in the Y direction with the MTN_Y_LED_SPACING macro" #endif -#define MOTION_GROUP 0x30 +#define MOTION_GROUP 0x30 typedef enum {MTN_RAMP=0x01,MTN_TRIANGLE=0x02,MTN_CIRCLE=0x03,MTN_NONE=0x04} mtn_id_t; @@ -68,7 +69,7 @@ typedef struct #define MTN_CURRENT_COL_OFFSET 12 #define MTN_CURRENT_ROW_OFFSET 14 #define MTN_CURRENT_TIME_OFFSET 16 -void mtn_general(TLEDArea *area,TMotion *pattern_data,unsigned short int period,unsigned char *buffer); +void mtn_general(TLEDArea *area,TMotion *pattern_data,unsigned char buffer_id,unsigned short int period,TFBControl *control); void mtn_compute(TMotion *pattern_data); diff --git a/pattern_frame_buffer/include/patterns.h b/pattern_frame_buffer/include/patterns.h index bbf52cf8e0280b5d5804ea7c626ae37cd0be73bf..351756ccece8bb0e64da236b606ad5d4db5fff87 100644 --- a/pattern_frame_buffer/include/patterns.h +++ b/pattern_frame_buffer/include/patterns.h @@ -19,6 +19,4 @@ typedef struct unsigned char B; }TPixelRGB; - - #endif diff --git a/pattern_frame_buffer/include/waveform_patterns.h b/pattern_frame_buffer/include/waveform_patterns.h index ad5bab637fc93c94d1be19c2d9d8b2304686cac4..6e4cbea53e85ac6cf00d7ebda2635db61ba0ba41 100644 --- a/pattern_frame_buffer/include/waveform_patterns.h +++ b/pattern_frame_buffer/include/waveform_patterns.h @@ -2,6 +2,7 @@ #define WAVEFORM_PATTERNS_H #include "patterns.h" +#include "frame_buffer_control.h" #define WAVEFORM_GROUP 0x10 @@ -59,7 +60,7 @@ typedef struct #define WF_DATA_OFFSET 9 #define WF_ACTIVE 11 #define WF_CURRENT_PERIOD_OFFSET 12 -void wf_general(TLEDArea *area,TWaveform *pattern_data,unsigned short int period,unsigned char *buffer); +void wf_general(TLEDArea *area,TWaveform *pattern_data,unsigned char buffer_id,unsigned short int period,TFBControl *control); TPixelRGB wf_pixel(TWaveform *pattern_data); diff --git a/pattern_frame_buffer/src/frame_buffer.c b/pattern_frame_buffer/src/frame_buffer.c index 7cdf725562c0a5cbbd363d8072c30053c0aebc5e..4e35ec0c62296d8b1c294fde8d6e280acb18deac 100644 --- a/pattern_frame_buffer/src/frame_buffer.c +++ b/pattern_frame_buffer/src/frame_buffer.c @@ -1,296 +1,92 @@ #include "frame_buffer.h" - -typedef enum {FB_SRAM1,FB_SRAM2} fb_segment_t; - -typedef struct -{ - TMemModule *mem_module; - TScheduler *scheduler; - unsigned short int num_rows; - unsigned short int num_pixels_per_row; - unsigned short int num_buffers; - unsigned short int buffer_size; - unsigned short int free_mem; - fb_segment_t read_current_segment; - unsigned char read_current_buffer; - fb_segment_t write_current_segment; - unsigned char write_current_buffer; - unsigned char buffer1[FB_MAX_BUFFER_LEN]; - unsigned char buffer2[FB_MAX_BUFFER_LEN]; - unsigned char pixel_buffer[FB_MAX_BUFFER_LEN/(FB_BYTES_PER_PIXEL/FB_BYTES_PER_PIXEL)]; -}TFrameBuffer; +#include "frame_buffer_control_registers.h" +#include "ram.h" // private functions -void fb_write_cmd(void *module,unsigned short int address,unsigned short int length,unsigned char *data) -{ - TFrameBuffer *fb=(TFrameBuffer *)module; - unsigned short int new_value; - unsigned char *data_ptr; - - if(ram_in_window(FB_NUM_ROWS,2,address,length)) - { - new_value=fb->num_rows; - data_ptr=(unsigned char *)&new_value; - if(ram_in_range(FB_NUM_ROWS,address,length)) - data_ptr[0]=data[FB_NUM_ROWS-address]; - if(ram_in_range(FB_NUM_ROWS+1,address,length)) - data_ptr[1]=data[FB_NUM_ROWS+1-address]; - fb_set_num_rows(new_value); - } - if(ram_in_window(FB_NUM_PIXELS,2,address,length)) - { - new_value=fb->num_pixels_per_row; - data_ptr=(unsigned char *)&new_value; - if(ram_in_range(FB_NUM_PIXELS,address,length)) - data_ptr[0]=data[FB_NUM_PIXELS-address]; - if(ram_in_range(FB_NUM_PIXELS+1,address,length)) - data_ptr[1]=data[FB_NUM_PIXELS+1-address]; - fb_set_pixels_per_row(new_value); - } - if(ram_in_window(FB_NUM_BUFFERS,2,address,length)) - { - new_value=fb->num_buffers; - data_ptr=(unsigned char *)&new_value; - if(ram_in_range(FB_NUM_BUFFERS,address,length)) - data_ptr[0]=data[FB_NUM_BUFFERS-address]; - if(ram_in_range(FB_NUM_BUFFERS+1,address,length)) - data_ptr[1]=data[FB_NUM_BUFFERS+1-address]; - fb_set_num_buffers(new_value); - } -} - -void fb_read_cmd(void *module,unsigned short int address,unsigned short int length,unsigned char *data) +void frame_buffer_compute_free_memory(TFrameBuffer *fb) { - ram_read_table(address,length,data); -} - -void fb_compute_free_memory(TFrameBuffer *fb) -{ - leds_buffer_size=leds_num_rows*leds_num_pixels_per_row*FB_BYTES_PER_PIXEL+RESET_LENGTH; - leds_free_mem=MAX_BUFFER_LEN-leds_buffer_size*leds_num_buffers; - ram_data[FB_FREE_MEMORY]=leds_free_mem&0x00FF; - ram_data[FB_FREE_MEMORY+1]=(leds_free_mem&0xFF00)>>8; -} - -void leds_write_buffer(TFrameBuffer *fb,unsigned char *pixel_buffer,unsigned char *led_buffer) -{ - unsigned short int i,j,k,offset_pixel,offset_leds; - unsigned char pixel_g,pixel_r,pixel_b; - - for(i=0;i<leds_num_rows;i++) - { - for(j=0;j<leds_num_pixels_per_row;j++) - { - offset_pixel=(i*leds_num_pixels_per_row+j)*BYTES_PER_PIXEL; - pixel_r=pixel_buffer[offset_pixel]; - pixel_g=pixel_buffer[offset_pixel+1]; - pixel_b=pixel_buffer[offset_pixel+2]; - if(i%2)//odd - offset_leds=((i+1)*leds_num_pixels_per_row-1-j)*FB_BYTES_PER_PIXEL; - else//even - offset_leds=(i*leds_num_pixels_per_row+j)*FB_BYTES_PER_PIXEL; - for(k=0;k<4;k++) - { - if(pixel_g&(0x80>>(k*2))) - led_buffer[offset_leds+k]=0xC0; - else - led_buffer[offset_leds+k]=0x80; - if(pixel_g&(0x80>>((k*2)+1))) - led_buffer[offset_leds+k]|=0x0C; - else - led_buffer[offset_leds+k]|=0x08; - if(pixel_r&(0x80>>(k*2))) - led_buffer[offset_leds+(k+4)]=0xC0; - else - led_buffer[offset_leds+(k+4)]=0x80; - if(pixel_r&(0x80>>((k*2)+1))) - led_buffer[offset_leds+(k+4)]|=0x0C; - else - led_buffer[offset_leds+(k+4)]|=0x08; - if(pixel_b&(0x80>>(k*2))) - led_buffer[offset_leds+(k+8)]=0xC0; - else - led_buffer[offset_leds+(k+8)]=0x80; - if(pixel_b&(0x80>>((k*2)+1))) - led_buffer[offset_leds+(k+8)]|=0x0C; - else - led_buffer[offset_leds+(k+8)]|=0x08; - } - pixel_buffer[offset_pixel]=0x00; - pixel_buffer[offset_pixel+1]=0x00; - pixel_buffer[offset_pixel+2]=0x00; - } - } -} - -void leds_write_reset(TFrameBuffer *fb,unsigned char *led_buffer) -{ - unsigned short int i; - - for(i=0;i<RESET_LENGTH;i++) - led_buffer[leds_num_rows*leds_num_pixels_per_row*FB_BYTES_PER_PIXEL+i]=0x00; -} - -/* Interrupt handlers */ -void leds_scheduler(void) -{ - unsigned char *start_address; - - /* switch to the next buffer*/ - if(leds_spi_current_buffer>=leds_num_buffers) - { - leds_spi_current_buffer=0; - if(leds_spi_current_segment==FB_SRAM1) - { - leds_spi_current_segment=FB_SRAM2; - start_address=&leds_buffer2[0]; - } - else - { - leds_spi_current_segment=FB_SRAM1; - start_address=&leds_buffer1[0]; - } - } - else - { - if(leds_spi_current_segment==FB_SRAM1) - start_address=&leds_buffer1[leds_spi_current_buffer*leds_buffer_size]; - else - start_address=&leds_buffer2[leds_spi_current_buffer*leds_buffer_size]; - } - leds_spi_current_buffer++; - HAL_SPI_Transmit_DMA(&led_spi,start_address,leds_buffer_size); - leds_update=0x01; + fb->buffer_size=fb->num_rows*fb->num_pixels_per_row*FB_BYTES_PER_PIXEL; + fb->free_mem=FB_MAX_BUFFER_LEN-fb->buffer_size*fb->num_buffers; + ram_data[fb->ram_base_address+FRAME_BUFFER_CONTROL_FREE_MEMORY_OFFSET]=fb->free_mem&0x00FF; + ram_data[fb->ram_base_address+FRAME_BUFFER_CONTROL_FREE_MEMORY_OFFSET+1]=(fb->free_mem&0xFF00)>>8; } // public functions -unsigned char fb_init(TFrameBuffer *fb,TMemory *memory) +void frame_buffer_init(TFrameBuffer *fb,unsigned short int ram_base_address,unsigned short int eeprom_base_address) { unsigned int i; /* initialize internal data */ - fb_set_period(fb,DEFAULT_FB_PERIOD); - fb_set_num_rows(fb,DEFAULT_FB_NUM_ROWS); - fb_set_pixels_per_row(fb,DEFAULT_FB_NUM_PIXELS); - fb_set_num_buffers(fb,DEFAULT_FB_NUM_BUFFERS); - fb->read_current_buffer=0; - fb->read_current_segment=FB_SRAM2; - fb->write_current_buffer=0; - fb->write_current_segment=FB_SRAM2; + frame_buffer_set_num_rows(fb,DEFAULT_FRAME_BUFFER_CONTROL_NUM_ROWS); + frame_buffer_set_pixels_per_row(fb,DEFAULT_FRAME_BUFFER_CONTROL_NUM_PIXELS); + frame_buffer_set_num_buffers(fb,DEFAULT_FRAME_BUFFER_CONTROL_NUM_BUFFERS); + fb->ram_base_address=ram_base_address; + fb->eeprom_base_address=eeprom_base_address; - for(i=0;i<FB_MAX_BUFFER_LEN/(FB_BYTES_PER_PIXEL/FB_BYTES_PER_PIXEL);i++) + for(i=0;i<FB_MAX_BUFFER_LEN;i++) fb->pixel_buffer[i]=0x00; - for(i=0;i<fb->num_buffers;i++) - { - fb_write_buffer(fb,fb->pixel_buffer,&fb->buffer1[fb->buffer_size*i]); - fb_write_reset(fb,&fb->buffer1[fb->buffer_size*i]); - fb_write_buffer(fb,fb->pixel_buffer,&fb->buffer2[fb->buffer_size*i]); - fb_write_reset(fb,&fb->buffer2[fb->buffer_size*i]); - } - - mem_module_init(&fb->mem_module); - fb->mem_module.write_cmd=fb_write_cmd; - fb->mem_module.read_cmd=fb_read_cmd; - fb->data=fb; - if(!mem_module_add_ram_segment(&fb->mem_module,RAM_FB_BASE_ADDRESS,RAM_FB_LENGTH)) - return 0x00; - if(!mem_module_add_eeprom_segment(&fb->mem_module,EEPROM_FB_BASE_ADDRESS,EEPROM_FB_LENGTH)) - return 0x00; - if(!mem_add_module(memory,&fb->mem_module)) - return 0x00; - - return 0x01; -} - -void fb_set_num_rows(TFrameBuffer *fb,unsigned short int rows) -{ - leds_num_rows=rows; - ram_data[FB_NUM_ROWS]=rows&0x00FF; - ram_data[FB_NUM_ROWS+1]=(rows&0xFF00)>>8; - leds_compute_free_memory(); } -unsigned short int fb_get_num_rows(TFrameBuffer *fb) +void frame_buffer_set_num_rows(TFrameBuffer *fb,unsigned short int rows) { - return leds_num_rows; + fb->num_rows=rows; + ram_data[fb->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET]=rows&0x00FF; + ram_data[fb->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET+1]=(rows&0xFF00)>>8; + frame_buffer_compute_free_memory(fb); } -void fb_set_pixels_per_row(TFrameBuffer *fb,unsigned short int pixels) +unsigned short int frame_buffer_get_num_rows(TFrameBuffer *fb) { - leds_num_pixels_per_row=pixels; - ram_data[FB_NUM_PIXELS]=pixels&0x00FF; - ram_data[FB_NUM_PIXELS+1]=(pixels&0xFF00)>>8; - leds_compute_free_memory(); + return fb->num_rows; } -unsigned short int fb_get_pixels_per_row(TFrameBuffer *fb) +void frame_buffer_set_pixels_per_row(TFrameBuffer *fb,unsigned short int pixels) { - return leds_num_pixels_per_row; + fb->num_pixels_per_row=pixels; + ram_data[fb->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET]=pixels&0x00FF; + ram_data[fb->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET+1]=(pixels&0xFF00)>>8; + frame_buffer_compute_free_memory(fb); } -void fb_set_num_buffers(TFrameBuffer *fb,unsigned char num) +unsigned short int frame_buffer_get_pixels_per_row(TFrameBuffer *fb) { - leds_num_buffers=num; - ram_data[FB_NUM_BUFFERS]=num&0x00FF; - ram_data[FB_NUM_BUFFERS+1]=(num&0xFF00)>>8; - leds_compute_free_memory(); + return fb->num_pixels_per_row; } -unsigned char fb_get_num_buffers(TFrameBuffer *fb) +void frame_buffer_set_num_buffers(TFrameBuffer *fb,unsigned char num) { - return leds_num_buffers; + fb->num_buffers=num; + ram_data[fb->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET]=num&0x00FF; + ram_data[fb->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET+1]=(num&0xFF00)>>8; + frame_buffer_compute_free_memory(fb); } -unsigned short int fb_get_free_memory(TFrameBuffer *fb) +unsigned char frame_buffer_get_num_buffers(TFrameBuffer *fb) { - return leds_free_mem; + return fb->num_buffers; } -unsigned char fb_update_buffer(TFrameBuffer *fb) +unsigned short int frame_buffer_get_free_memory(TFrameBuffer *fb) { - if(leds_update) - { - leds_update=0x00; - return 0x01; - } - else - return 0x00; + return fb->free_mem; } -unsigned char *fb_get_pixel_buffer(TFrameBuffer *fb) +void frame_buffer_set_pixel(TFrameBuffer *fb,unsigned char buffer_id,unsigned char R,unsigned char G,unsigned char B,unsigned short int row,unsigned short int col) { - return leds_pixel_buffer; -} + unsigned short int offset; -void fb_set_pixel_buffer(TFrameBuffer *fb,unsigned char *buffer) -{ - if(leds_user_current_segment==FB_SRAM1) - { - leds_write_buffer(buffer,&leds_buffer1[leds_buffer_size*leds_user_current_buffer]); - leds_write_reset(&leds_buffer1[leds_buffer_size*leds_user_current_buffer]); - leds_user_current_buffer++; - if(leds_user_current_buffer>=leds_num_buffers) - { - leds_user_current_buffer=0; - leds_user_current_segment=FB_SRAM2; - } - } + if(buffer_id>=fb->num_buffers) + return; else { - leds_write_buffer(buffer,&leds_buffer2[leds_buffer_size*leds_user_current_buffer]); - leds_write_reset(&leds_buffer2[leds_buffer_size*leds_user_current_buffer]); - leds_user_current_buffer++; - if(leds_user_current_buffer>=leds_num_buffers) - { - leds_user_current_buffer=0; - leds_user_current_segment=FB_SRAM1; - } + offset=fb->num_rows*fb->num_pixels_per_row*FB_BYTES_PER_PIXEL*buffer_id; + fb->pixel_buffer[offset+((row*fb->num_pixels_per_row+col)*FB_BYTES_PER_PIXEL)]=R; + fb->pixel_buffer[offset+((row*fb->num_pixels_per_row+col)*FB_BYTES_PER_PIXEL)+1]=G; + fb->pixel_buffer[offset+((row*fb->num_pixels_per_row+col)*FB_BYTES_PER_PIXEL)+2]=B; } } -void fb_set_pixel(TFrameBuffer *fb,unsigned char R,unsigned char G,unsigned char B,unsigned short int row,unsigned short int col, unsigned char *buffer) +unsigned char *frame_buffer_get_buffer(TFrameBuffer *fb,unsigned char buffer_id) { - buffer[((row*leds_num_pixels_per_row+col)*BYTES_PER_PIXEL)]=R; - buffer[((row*leds_num_pixels_per_row+col)*BYTES_PER_PIXEL)+1]=G; - buffer[((row*leds_num_pixels_per_row+col)*BYTES_PER_PIXEL)+2]=B; + return &fb->pixel_buffer[fb->num_rows*fb->num_pixels_per_row*FB_BYTES_PER_PIXEL*buffer_id]; } diff --git a/pattern_frame_buffer/src/frame_buffer_control.c b/pattern_frame_buffer/src/frame_buffer_control.c new file mode 100644 index 0000000000000000000000000000000000000000..12efbd809630cd1fe262fc46e5c4f34b7271bd68 --- /dev/null +++ b/pattern_frame_buffer/src/frame_buffer_control.c @@ -0,0 +1,392 @@ +#include "frame_buffer_control.h" +#include "patterns.h" +#include "waveform_patterns.h" +#include "image_patterns.h" +#include "motion_patterns.h" +#include "ram.h" + +/* private functions */ +void frame_buffer_control_write_cmd(void *module,unsigned short int address,unsigned short int length,unsigned char *data) +{ + TFBControl *control=(TFBControl *)module; + static TLEDArea ptrn_area={0}; + static unsigned char ptrn_data[FBC_MAX_DATA_PATTERN_LEN]={0},data_len=0,pattern_id=0,pattern_index=0,buffer_id=0; + unsigned char *data_ptr; + unsigned short int new_value,ram_offset,eeprom_offset,i; + pattern_func_t function=0x00000000; + + ram_offset=address-control->ram_base_address; + eeprom_offset=address-control->eeprom_base_address; + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_OFFSET,1,address,length)) + { + if(data[FRAME_BUFFER_CONTROL_OFFSET-ram_offset]&FRAME_BUFFER_CONTROL_LOAD)// add the new pattern + { + switch(pattern_id&PATTERN_GROUP) + { + case WAVEFORM_GROUP: + function=(pattern_func_t)wf_general; + // initialize static data + ptrn_data[WF_CURRENT_PERIOD_OFFSET]=0x00; + ptrn_data[WF_CURRENT_PERIOD_OFFSET+1]=0x00; + data_len+=2; + break; + case MOTION_GROUP: + function=(pattern_func_t)mtn_general; + ptrn_data[MTN_CURRENT_COL_OFFSET]=0x00; + ptrn_data[MTN_CURRENT_COL_OFFSET+1]=0x00; + ptrn_data[MTN_CURRENT_ROW_OFFSET]=0x00; + ptrn_data[MTN_CURRENT_ROW_OFFSET+1]=0x00; + ptrn_data[MTN_CURRENT_TIME_OFFSET]=0x00; + ptrn_data[MTN_CURRENT_TIME_OFFSET+1]=0x00; + data_len+=6; + break; + case IMAGE_GROUP: + function=(pattern_func_t)img_general; + break; + default: break; + } + frame_buffer_control_add_pattern(control,function,&ptrn_area,ptrn_data,data_len,buffer_id); + /* clear the internal data for the next pattern */ + data_len=0; + ptrn_area.min_row=0; + ptrn_area.max_row=0; + ptrn_area.min_col=0; + ptrn_area.max_col=0; + pattern_id=0; + buffer_id=0; + for(i=0;i<FBC_MAX_DATA_PATTERN_LEN;i++) + ptrn_data[i]=0; + } + else if(data[FRAME_BUFFER_CONTROL_OFFSET-ram_offset]&FRAME_BUFFER_CONTROL_REMOVE) + frame_buffer_control_remove_pattern(control,pattern_index); + else if(data[FRAME_BUFFER_CONTROL_OFFSET-ram_offset]&FRAME_BUFFER_CONTROL_CLEAR) + frame_buffer_control_clear_patterns(control); + else if(data[FRAME_BUFFER_CONTROL_OFFSET-ram_offset]&FRAME_BUFFER_CONTROL_START) + frame_buffer_control_start(control); + else if(data[FRAME_BUFFER_CONTROL_OFFSET-ram_offset]&FRAME_BUFFER_CONTROL_STOP) + frame_buffer_control_stop(control); + } + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_PATTERN_INDEX_OFFSET,1,address,length)) + pattern_index=data[FRAME_BUFFER_CONTROL_PATTERN_INDEX_OFFSET-ram_offset]; + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_PATTERN_ID_OFFSET,1,address,length)) + pattern_id=data[FRAME_BUFFER_CONTROL_PATTERN_ID_OFFSET-ram_offset]; + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_MIN_ROW_OFFSET,2,address,length)) + { + data_ptr=(unsigned char *)&ptrn_area.min_row; + if(ram_in_range(control->ram_base_address+FRAME_BUFFER_CONTROL_MIN_ROW_OFFSET,address,length)) + data_ptr[0]=data[FRAME_BUFFER_CONTROL_MIN_ROW_OFFSET-ram_offset]; + if(ram_in_range(control->ram_base_address+FRAME_BUFFER_CONTROL_MIN_ROW_OFFSET+1,address,length)) + data_ptr[1]=data[FRAME_BUFFER_CONTROL_MIN_ROW_OFFSET+1-ram_offset]; + } + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_MAX_ROW_OFFSET,2,address,length)) + { + data_ptr=(unsigned char *)&ptrn_area.max_row; + if(ram_in_range(control->ram_base_address+FRAME_BUFFER_CONTROL_MAX_ROW_OFFSET,address,length)) + data_ptr[0]=data[FRAME_BUFFER_CONTROL_MAX_ROW_OFFSET-ram_offset]; + if(ram_in_range(control->ram_base_address+FRAME_BUFFER_CONTROL_MAX_ROW_OFFSET+1,address,length)) + data_ptr[1]=data[FRAME_BUFFER_CONTROL_MAX_ROW_OFFSET+1-ram_offset]; + } + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_MIN_COL_OFFSET,2,address,length)) + { + data_ptr=(unsigned char *)&ptrn_area.min_col; + if(ram_in_range(control->ram_base_address+FRAME_BUFFER_CONTROL_MIN_COL_OFFSET,address,length)) + data_ptr[0]=data[FRAME_BUFFER_CONTROL_MIN_COL_OFFSET-ram_offset]; + if(ram_in_range(control->ram_base_address+FRAME_BUFFER_CONTROL_MIN_COL_OFFSET+1,address,length)) + data_ptr[1]=data[FRAME_BUFFER_CONTROL_MIN_COL_OFFSET+1-ram_offset]; + } + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_MAX_COL_OFFSET,2,address,length)) + { + data_ptr=(unsigned char *)&ptrn_area.max_col; + if(ram_in_range(control->ram_base_address+FRAME_BUFFER_CONTROL_MAX_COL_OFFSET,address,length)) + data_ptr[0]=data[FRAME_BUFFER_CONTROL_MAX_COL_OFFSET-ram_offset]; + if(ram_in_range(control->ram_base_address+FRAME_BUFFER_CONTROL_MAX_COL_OFFSET+1,address,length)) + data_ptr[1]=data[FRAME_BUFFER_CONTROL_MAX_COL_OFFSET+1-ram_offset]; + } + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_BUFFER_ID_OFFSET,1,address,length)) + buffer_id=data[FRAME_BUFFER_CONTROL_BUFFER_ID_OFFSET-ram_offset]; + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_DATA_OFFSET,FBC_MAX_DATA_PATTERN_LEN,address,length)) + { + for(i=0;i<length-(FRAME_BUFFER_CONTROL_DATA_OFFSET-ram_offset) && i<FBC_MAX_DATA_PATTERN_LEN;i++) + { + ptrn_data[i]=data[FRAME_BUFFER_CONTROL_DATA_OFFSET-ram_offset+i]; + data_len++; + } + } + if(ram_in_window(control->eeprom_base_address+FRAME_BUFFER_CONTROL_PERIOD_OFFSET,2,address,length)) + { + new_value=control->period_ms; + data_ptr=(unsigned char *)&new_value; + if(ram_in_range(control->eeprom_base_address+FRAME_BUFFER_CONTROL_PERIOD_OFFSET,address,length)) + data_ptr[0]=data[FRAME_BUFFER_CONTROL_PERIOD_OFFSET-eeprom_offset]; + if(ram_in_range(control->eeprom_base_address+FRAME_BUFFER_CONTROL_PERIOD_OFFSET+1,address,length)) + data_ptr[1]=data[FRAME_BUFFER_CONTROL_PERIOD_OFFSET+1-eeprom_offset]; + frame_buffer_control_set_period(control,new_value); + } + if(ram_in_window(control->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET,2,address,length)) + { + new_value=control->frame_buffer.num_rows; + data_ptr=(unsigned char *)&new_value; + if(ram_in_range(control->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET,address,length)) + data_ptr[0]=data[FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET-eeprom_offset]; + if(ram_in_range(control->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET+1,address,length)) + data_ptr[1]=data[FRAME_BUFFER_CONTROL_NUM_ROWS_OFFSET+1-eeprom_offset]; + frame_buffer_set_num_rows(&control->frame_buffer,new_value); + } + if(ram_in_window(control->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET,2,address,length)) + { + new_value=control->frame_buffer.num_pixels_per_row; + data_ptr=(unsigned char *)&new_value; + if(ram_in_range(control->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET,address,length)) + data_ptr[0]=data[FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET-eeprom_offset]; + if(ram_in_range(control->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET+1,address,length)) + data_ptr[1]=data[FRAME_BUFFER_CONTROL_NUM_PIXELS_OFFSET+1-eeprom_offset]; + frame_buffer_set_pixels_per_row(&control->frame_buffer,new_value); + } + if(ram_in_window(control->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET,2,address,length)) + { + new_value=control->frame_buffer.num_buffers; + data_ptr=(unsigned char *)&new_value; + if(ram_in_range(control->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET,address,length)) + data_ptr[0]=data[FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET-eeprom_offset]; + if(ram_in_range(control->eeprom_base_address+FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET+1,address,length)) + data_ptr[1]=data[FRAME_BUFFER_CONTROL_NUM_BUFFERS_OFFSET+1-eeprom_offset]; + frame_buffer_set_num_buffers(&control->frame_buffer,new_value); + } + if(ram_in_window(control->ram_base_address+FRAME_BUFFER_CONTROL_IMG_DATA_OFFSET,IMG_MAX_NUM_IMAGES*IMG_MAX_IMAGE_WIDTH*IMG_MAX_IMAGE_HEIGHT*3,address,length)) + { + for(i=0;i<length;i++) + ((unsigned char *)img_pattern_data)[address-control->ram_base_address-FRAME_BUFFER_CONTROL_IMG_DATA_OFFSET+i]=data[i]; + } +} + +void frame_buffer_control_read_cmd(void *module,unsigned short int address,unsigned short int length,unsigned char *data) +{ + ram_read_table(address,length,data); +} + +void frame_buffer_control_scheduler(void *data) +{ + TFBControl *control=(TFBControl *)data; + unsigned char i; + + frame_buffer_control_update(control); + for(i=0;i<control->num_copy_functions;i++) + control->copy_functions[i](control->copy_data[i]); +} + +/* public functions */ +unsigned char frame_buffer_control_init(TFBControl *control,TMemory *memory,TScheduler *scheduler,sched_channel_t ch,unsigned short int ram_base_address,unsigned short int eeprom_base_address) +{ + // initialize internal variables + frame_buffer_control_clear_patterns(control); + frame_buffer_control_clear_copy_functions(control); + frame_buffer_init(&control->frame_buffer,ram_base_address,eeprom_base_address); + control->ram_base_address=ram_base_address; + control->eeprom_base_address=eeprom_base_address; + + /* assigna a scheduler channel */ + scheduler_set_channel(scheduler,ch,frame_buffer_control_scheduler,DEFAULT_FRAME_BUFFER_CONTROL_PERIOD,control); + control->scheduler=scheduler; + control->sch_channel=ch; + + img_patterns_init(ram_base_address); + + /* initialize memory module */ + mem_module_init(&control->mem_module); + control->mem_module.write_cmd=frame_buffer_control_write_cmd; + control->mem_module.read_cmd=frame_buffer_control_read_cmd; + control->mem_module.data=control; + if(!mem_module_add_ram_segment(&control->mem_module,ram_base_address,RAM_FRAME_BUFFER_CONTROL_LENGTH)) + return 0x00; + if(!mem_module_add_eeprom_segment(&control->mem_module,eeprom_base_address,EEPROM_FRAME_BUFFER_CONTROL_LENGTH)) + return 0x00; + if(!mem_add_module(memory,&control->mem_module)) + return 0x00; + + return 0x01; +} + +void frame_buffer_control_start(TFBControl *control) +{ + scheduler_enable_channel(control->scheduler,control->sch_channel); + ram_data[control->ram_base_address+FRAME_BUFFER_CONTROL_OFFSET]|=FRAME_BUFFER_CONTROL_RUNNING; +} + +void frame_buffer_control_stop(TFBControl *control) +{ + scheduler_disable_channel(control->scheduler,control->sch_channel); + ram_data[control->ram_base_address+FRAME_BUFFER_CONTROL_OFFSET]&=(~FRAME_BUFFER_CONTROL_RUNNING); +} + +void frame_buffer_control_set_period(TFBControl *control,unsigned short int period_ms) +{ + scheduler_change_period(control->scheduler,control->sch_channel,period_ms); + ram_data[control->eeprom_base_address+FRAME_BUFFER_CONTROL_PERIOD_OFFSET]=period_ms&0x00FF; + ram_data[control->eeprom_base_address+FRAME_BUFFER_CONTROL_PERIOD_OFFSET+1]=(period_ms&0xFF00)>>8; + control->period_ms=period_ms; +} + +unsigned short int frame_buffer_control_get_period(TFBControl *control) +{ + return control->period_ms; +} + +// pattern functions +unsigned char frame_buffer_control_add_pattern(TFBControl *control,pattern_func_t function,TLEDArea *area,void *data,unsigned char data_length,unsigned char buffer_id) +{ + unsigned short int num_rows,num_cols; + unsigned char i,j; + + num_rows=frame_buffer_get_num_rows(&control->frame_buffer); + num_cols=frame_buffer_get_pixels_per_row(&control->frame_buffer); + if(area->min_row>num_rows || area->max_row>num_rows || area->min_row>area->max_row) + { + ram_data[control->ram_base_address+FRAME_BUFFER_CONTROL_PATTERN_INDEX_OFFSET]=0xFF; + return 0xFF; + } + if(area->min_col>num_cols || area->max_col>num_cols || area->min_col>area->max_col) + { + ram_data[control->ram_base_address+FRAME_BUFFER_CONTROL_PATTERN_INDEX_OFFSET]=0xFF; + return 0xFF; + } + if(data_length>FBC_MAX_DATA_PATTERN_LEN) + { + ram_data[control->ram_base_address+FRAME_BUFFER_CONTROL_PATTERN_INDEX_OFFSET]=0xFF; + return 0xFF; + } + if(buffer_id>=frame_buffer_get_num_buffers(&control->frame_buffer)) + { + ram_data[control->ram_base_address+FRAME_BUFFER_CONTROL_PATTERN_INDEX_OFFSET]=0xFF; + return 0xFF; + } + + for(j=0;j<FBC_MAX_PATTERN_FUNC;j++) + { + // find the first empty pattern + if(control->pat_functions[j]==0x00000000) + { + control->pat_area[j].min_row=area->min_row; + control->pat_area[j].max_row=area->max_row; + control->pat_area[j].min_col=area->min_col; + control->pat_area[j].max_col=area->max_col; + control->pat_buffer_id[j]=buffer_id; + for(i=0;i<data_length;i++) + control->pat_parameters[j][i]=((unsigned char *)data)[i]; + control->pat_functions[j]=function; + control->num_patterns++; + ram_data[control->ram_base_address+FRAME_BUFFER_CONTROL_NUM_PATTERN_OFFSET]=control->num_patterns; + ram_data[control->ram_base_address+FRAME_BUFFER_CONTROL_PATTERN_INDEX_OFFSET]=j; + return j; + } + } + // the pattern could not be added + ram_data[control->ram_base_address+FRAME_BUFFER_CONTROL_PATTERN_INDEX_OFFSET]=0xFF; + return 0xFF; +} + +void frame_buffer_control_remove_pattern(TFBControl *control,unsigned char index) +{ + unsigned char i; + + if(control->num_patterns>0 && index<FBC_MAX_PATTERN_FUNC) + { + control->pat_functions[index]=0x00000000; + control->pat_area[index].min_row=0; + control->pat_area[index].max_row=0; + control->pat_area[index].min_col=0; + control->pat_area[index].max_col=0; + control->pat_buffer_id[index]=-1; + for(i=0;i<FBC_MAX_DATA_PATTERN_LEN;i++) + control->pat_parameters[index][i]=0; + control->num_patterns--; + } +} + +void frame_buffer_control_clear_patterns(TFBControl *control) +{ + unsigned char i,j; + + control->num_patterns=0; + for(i=0;i<FBC_MAX_PATTERN_FUNC;i++) + { + control->pat_functions[i]=0x00000000; + control->pat_area[i].min_row=0; + control->pat_area[i].max_row=0; + control->pat_area[i].min_col=0; + control->pat_area[i].max_col=0; + control->pat_buffer_id[i]=-1; + for(j=0;j<FBC_MAX_DATA_PATTERN_LEN;j++) + control->pat_parameters[i][j]=0; + } +} + +unsigned char frame_buffer_control_get_num_patterns(TFBControl *control) +{ + return control->num_patterns; +} + +unsigned char *frame_buffer_control_get_parameters(TFBControl *control,unsigned char index) +{ + if(index>=0 && index<FBC_MAX_PATTERN_FUNC) + return (unsigned char *)&control->pat_parameters[index]; + else + return (unsigned char *)0x00000000; +} + +void frame_buffer_control_update(TFBControl *control) +{ + unsigned char i; + + for(i=0;i<FBC_MAX_PATTERN_FUNC;i++) + { + if(control->pat_functions[i]!=0x00000000) + control->pat_functions[i](&control->pat_area[i],&control->pat_parameters[i],control->pat_buffer_id[i],control->period_ms,control); + } +} + +// copy functions +unsigned char frame_buffer_control_add_copy_function(TFBControl *control,copy_func_t function,void *data) +{ + unsigned char i; + + for(i=0;i<FBC_MAX_COPY_FUNC;i++) + { + // find the first empty pattern + if(control->copy_functions[i]==0x00000000) + { + control->copy_functions[i]=function; + control->copy_data[i]=data; + control->num_copy_functions++; + return i; + } + } + + return 0xFF; +} + +void frame_buffer_control_remove_copy_function(TFBControl *control,unsigned char index) +{ + if(control->num_copy_functions>0 && index<FBC_MAX_COPY_FUNC) + { + control->copy_functions[index]=0x00000000; + control->copy_data[index]=0x0000000; + control->num_copy_functions--; + } +} + +void frame_buffer_control_clear_copy_functions(TFBControl *control) +{ + unsigned char i; + + control->num_copy_functions=0; + for(i=0;i<FBC_MAX_COPY_FUNC;i++) + { + control->copy_functions[i]=0x00000000; + control->copy_data[i]=0x00000000; + } +} + +unsigned char frame_buffer_control_get_num_copy_functions(TFBControl *control) +{ + return control->num_copy_functions; +} diff --git a/pattern_frame_buffer/src/image_patterns.c b/pattern_frame_buffer/src/image_patterns.c new file mode 100644 index 0000000000000000000000000000000000000000..f49a883511e192516bc59d9508efcc551d841141 --- /dev/null +++ b/pattern_frame_buffer/src/image_patterns.c @@ -0,0 +1,100 @@ +#include "image_patterns.h" +#include "frame_buffer_control.h" +#include "waveform_patterns.h" +#include "motion_patterns.h" +#include "ram.h" + +// private variables +unsigned char img_pattern_data[IMG_MAX_NUM_IMAGES][IMG_MAX_IMAGE_WIDTH][IMG_MAX_IMAGE_HEIGHT][3]={{{{0}}}}; + +// private functions +void img_patterns_compute_range(unsigned short int area_min,unsigned short int area_max,short int pattern_start,unsigned short int max_size,unsigned short int *buff_start, unsigned short int *buff_end,unsigned char *img_start) +{ + unsigned short int cp_size; + + if(pattern_start<0) + { + *buff_start=area_min; + *img_start=-pattern_start; + if((-pattern_start)<max_size) + cp_size=max_size+pattern_start; + else + cp_size=0; + } + else if(pattern_start>(area_max-area_min)) + { + *buff_start=0; + *img_start=0; + cp_size=0; + } + else + { + *buff_start=area_min+pattern_start; + *img_start=0; + cp_size=max_size-1; + } + if(*buff_start+cp_size>area_max) + { + *buff_end=area_max; + cp_size-=area_max; + } + else + *buff_end=*buff_start+cp_size; +} + +// public functions +void img_patterns_init(unsigned short int ram_base_address) +{ + //initialize internal variables (read only variables) + ram_data[ram_base_address+FRAME_BUFFER_CONTROL_IMG_MAX_WIDTH_OFFSET]=IMG_MAX_IMAGE_WIDTH; + ram_data[ram_base_address+FRAME_BUFFER_CONTROL_IMG_MAX_HEIGHT_OFFSET]=IMG_MAX_IMAGE_HEIGHT; + ram_data[ram_base_address+FRAME_BUFFER_CONTROL_IMG_NUM_IMGS_OFFSET]=IMG_MAX_NUM_IMAGES; +} + +void img_general(TLEDArea *area,TIMGDisplayData *pattern_data,unsigned char buffer_id,unsigned short int period,TFBControl *control) +{ + unsigned short int buff_row=0,buff_col=0,img_row=0,img_col=0; + unsigned short int buff_start_row=0,buff_end_row=0,buff_start_col=0,buff_end_col=0; + unsigned char img_start_row=0,img_start_col=0; + short int row_offset,col_offset; + TWaveform *waveform; + TMotion *motion; + TPixelRGB pixel; + + // execute motion + if(pattern_data->motion_index!=0xFF) + { + motion=(TMotion *)frame_buffer_control_get_parameters(control,pattern_data->motion_index); + mtn_compute(motion); + col_offset=motion->current_col; + row_offset=motion->current_row; + } + else + { + col_offset=0; + row_offset=0; + } + // compute displayed area + img_patterns_compute_range(area->min_row,area->max_row,row_offset,IMG_MAX_IMAGE_HEIGHT,&buff_start_row,&buff_end_row,&img_start_row); + img_patterns_compute_range(area->min_col,area->max_col,col_offset,IMG_MAX_IMAGE_WIDTH,&buff_start_col,&buff_end_col,&img_start_col); + // execute waveform + for(buff_row=buff_start_row,img_row=img_start_row;buff_row<=buff_end_row;buff_row++,img_row++) + for(buff_col=buff_start_col,img_col=img_start_col;buff_col<=buff_end_col;buff_col++,img_col++) + { + if(pattern_data->waveform_index!=0xFF) + { + waveform=(TWaveform *)frame_buffer_control_get_parameters(control,pattern_data->waveform_index); + waveform->max.R=img_pattern_data[pattern_data->buffer_id][img_row][img_col][0]; + waveform->max.G=img_pattern_data[pattern_data->buffer_id][img_row][img_col][1]; + waveform->max.B=img_pattern_data[pattern_data->buffer_id][img_row][img_col][2]; + pixel=wf_pixel(waveform); + } + else + { + pixel.R=img_pattern_data[pattern_data->buffer_id][img_row][img_col][0]; + pixel.G=img_pattern_data[pattern_data->buffer_id][img_row][img_col][1]; + pixel.B=img_pattern_data[pattern_data->buffer_id][img_row][img_col][2]; + } + frame_buffer_set_pixel(&control->frame_buffer,buffer_id,pixel.R,pixel.G,pixel.B,buff_row,buff_col); + } +} diff --git a/pattern_frame_buffer/src/motion_patterns.c b/pattern_frame_buffer/src/motion_patterns.c new file mode 100644 index 0000000000000000000000000000000000000000..041243bbb103de18f7f8b6e49f188f4bb8e0ef23 --- /dev/null +++ b/pattern_frame_buffer/src/motion_patterns.c @@ -0,0 +1,108 @@ +#include "motion_patterns.h" +#include <math.h> + +// private functions +void mtn_ramp(TMotion *pattern_data) +{ + unsigned short int ms_pixel_x,delta_x_mm; + unsigned short int ms_pixel_y,delta_y_mm; + unsigned short int dist_mm; + + delta_x_mm=(pattern_data->motion_data.ramp_data.max_coord_x-pattern_data->motion_data.ramp_data.min_coord_x)*MTN_X_LED_SPACING; + delta_y_mm=(pattern_data->motion_data.ramp_data.max_coord_y-pattern_data->motion_data.ramp_data.min_coord_y)*MTN_Y_LED_SPACING; + + dist_mm=sqrt(pow(delta_x_mm,2)+pow(delta_y_mm,2)); + + ms_pixel_x=(dist_mm*1000)/(delta_x_mm*pattern_data->speed_mm_s); + ms_pixel_y=(dist_mm*1000)/(delta_y_mm*pattern_data->speed_mm_s); + + if(pattern_data->motion_data.ramp_data.direction==0x01) + { + pattern_data->current_col=pattern_data->motion_data.ramp_data.min_coord_x+(pattern_data->current_time/ms_pixel_x); + pattern_data->current_row=pattern_data->motion_data.ramp_data.min_coord_y+(pattern_data->current_time/ms_pixel_y); + + if((pattern_data->current_col>=pattern_data->motion_data.ramp_data.max_coord_x) && + (pattern_data->current_row>=pattern_data->motion_data.ramp_data.max_coord_y)) + { + pattern_data->current_col=pattern_data->motion_data.ramp_data.min_coord_x; + pattern_data->current_row=pattern_data->motion_data.ramp_data.min_coord_y; + pattern_data->current_time=0; + } + } + else + { + pattern_data->current_col=pattern_data->motion_data.ramp_data.max_coord_x-(pattern_data->current_time/ms_pixel_x); + pattern_data->current_row=pattern_data->motion_data.ramp_data.max_coord_y-(pattern_data->current_time/ms_pixel_y); + + if((pattern_data->current_col<=pattern_data->motion_data.ramp_data.min_coord_x) && + (pattern_data->current_row<=pattern_data->motion_data.ramp_data.min_coord_y)) + { + pattern_data->current_col=pattern_data->motion_data.ramp_data.max_coord_x; + pattern_data->current_row=pattern_data->motion_data.ramp_data.max_coord_y; + pattern_data->current_time=0; + } + } +} + +void mtn_triangle(TMotion *pattern_data) +{ + unsigned short int ms_pixel_x,delta_x_mm; + unsigned short int ms_pixel_y,delta_y_mm; + unsigned short int dist_mm; + + delta_x_mm=(pattern_data->motion_data.ramp_data.max_coord_x-pattern_data->motion_data.ramp_data.min_coord_x)*MTN_X_LED_SPACING; + delta_y_mm=(pattern_data->motion_data.ramp_data.max_coord_y-pattern_data->motion_data.ramp_data.min_coord_y)*MTN_Y_LED_SPACING; + + dist_mm=sqrt(pow(delta_x_mm,2)+pow(delta_y_mm,2)); + + ms_pixel_x=(dist_mm*1000)/(delta_x_mm*pattern_data->speed_mm_s); + ms_pixel_y=(dist_mm*1000)/(delta_y_mm*pattern_data->speed_mm_s); + + if(pattern_data->motion_data.ramp_data.direction==0x01) + { + pattern_data->current_col=pattern_data->motion_data.ramp_data.min_coord_x+(pattern_data->current_time/ms_pixel_x); + pattern_data->current_row=pattern_data->motion_data.ramp_data.min_coord_y+(pattern_data->current_time/ms_pixel_y); + + if((pattern_data->current_col>=pattern_data->motion_data.ramp_data.max_coord_x) && + (pattern_data->current_row>=pattern_data->motion_data.ramp_data.max_coord_y)) + { + pattern_data->current_time=0; + pattern_data->motion_data.ramp_data.direction=0x00; + } + } + else + { + pattern_data->current_col=pattern_data->motion_data.ramp_data.max_coord_x-(pattern_data->current_time/ms_pixel_x); + pattern_data->current_row=pattern_data->motion_data.ramp_data.max_coord_y-(pattern_data->current_time/ms_pixel_y); + + if((pattern_data->current_col<=pattern_data->motion_data.ramp_data.min_coord_x) && + (pattern_data->current_row<=pattern_data->motion_data.ramp_data.min_coord_y)) + { + pattern_data->current_time=0; + pattern_data->motion_data.ramp_data.direction=0x01; + } + } +} + +// public functions +void mtn_general(TLEDArea *area,TMotion *pattern_data,unsigned char buffer_id,unsigned short int period,TFBControl *control) +{ + pattern_data->current_time+=period; +} + +void mtn_compute(TMotion *pattern_data) +{ + // image pattern motion + switch(pattern_data->motion_id) + { + case MTN_RAMP: mtn_ramp(pattern_data); + break; + case MTN_TRIANGLE: mtn_triangle(pattern_data); + break; + case MTN_CIRCLE: + break; + case MTN_NONE: pattern_data->current_col=0; + pattern_data->current_row=0; + break; + } +} diff --git a/pattern_frame_buffer/src/waveform_patterns.c b/pattern_frame_buffer/src/waveform_patterns.c new file mode 100644 index 0000000000000000000000000000000000000000..af76f80d641eaccb997efeb6d3aa8bba20cc9507 --- /dev/null +++ b/pattern_frame_buffer/src/waveform_patterns.c @@ -0,0 +1,146 @@ +#include "waveform_patterns.h" +#include "frame_buffer.h" +#include <math.h> + +float sin_lut[256]={0,0.0245,0.0491,0.0736,0.0980,0.1224,0.1467,0.1710,0.1951,0.2191,0.2430,0.2667,0.2903,0.3137,0.3369,0.3599, + 0.3827,0.4052,0.4276,0.4496,0.4714,0.4929,0.5141,0.5350,0.5556,0.5758,0.5957,0.6152,0.6344,0.6532,0.6716,0.6895, + 0.7071,0.7242,0.7410,0.7572,0.7730,0.7883,0.8032,0.8176,0.8315,0.8449,0.8577,0.8701,0.8819,0.8932,0.9040,0.9142, + 0.9239,0.9330,0.9415,0.9495,0.9569,0.9638,0.9700,0.9757,0.9808,0.9853,0.9892,0.9925,0.9952,0.9973,0.9988,0.9997, + 1.0000,0.9997,0.9988,0.9973,0.9952,0.9925,0.9892,0.9853,0.9808,0.9757,0.9700,0.9638,0.9569,0.9495,0.9415,0.9330, + 0.9239,0.9142,0.9040,0.8932,0.8819,0.8701,0.8577,0.8449,0.8315,0.8176,0.8032,0.7883,0.7730,0.7572,0.7410,0.7242, + 0.7071,0.6895,0.6716,0.6532,0.6344,0.6152,0.5957,0.5758,0.5556,0.5350,0.5141,0.4929,0.4714,0.4496,0.4276,0.4052, + 0.3827,0.3599,0.3369,0.3137,0.2903,0.2667,0.2430,0.2191,0.1951,0.1710,0.1467,0.1224,0.0980,0.0736,0.0491,0.0245, + 0.0000,-0.0245,-0.0491,-0.0736,-0.0980,-0.1224,-0.1467,-0.1710,-0.1951,-0.2191,-0.2430,-0.2667,-0.2903,-0.3137,-0.3369, + -0.3599,-0.3827,-0.4052,-0.4276,-0.4496,-0.4714,-0.4929,-0.5141,-0.5350,-0.5556,-0.5758,-0.5957,-0.6152,-0.6344,-0.6532, + -0.6716,-0.6895,-0.7071,-0.7242,-0.7410,-0.7572,-0.7730,-0.7883,-0.8032,-0.8176,-0.8315,-0.8449,-0.8577,-0.8701,-0.8819, + -0.8932,-0.9040,-0.9142,-0.9239,-0.9330,-0.9415,-0.9495,-0.9569,-0.9638,-0.9700,-0.9757,-0.9808,-0.9853,-0.9892,-0.9925, + -0.9952,-0.9973,-0.9988,-0.9997,-1.0000,-0.9997,-0.9988,-0.9973,-0.9952,-0.9925,-0.9892,-0.9853,-0.9808,-0.9757,-0.9700, + -0.9638,-0.9569,-0.9495,-0.9415,-0.9330,-0.9239,-0.9142,-0.9040,-0.8932,-0.8819,-0.8701,-0.8577,-0.8449,-0.8315,-0.8176, + -0.8032,-0.7883,-0.7730,-0.7572,-0.7410,-0.7242,-0.7071,-0.6895,-0.6716,-0.6532,-0.6344,-0.6152,-0.5957,-0.5758,-0.5556, + -0.5350,-0.5141,-0.4929,-0.4714,-0.4496,-0.4276,-0.4052,-0.3827,-0.3599,-0.3369,-0.3137,-0.2903,-0.2667,-0.2430,-0.2191, + -0.1951,-0.1710,-0.1467,-0.1224,-0.0980,-0.0736,-0.0491,-0.0245}; + +TPixelRGB wf_sine(TWaveform *pattern_data) +{ + unsigned char amplitude,mean,value; + TPixelRGB pixel; + + amplitude=(pattern_data->max.R-pattern_data->min.R)/2; + mean=(pattern_data->max.R+pattern_data->min.R)/2; + value=(255*pattern_data->current_period/pattern_data->period)+pattern_data->data.sine_data.phase; + pixel.R=(unsigned char)(amplitude*sin_lut[value]+mean); + amplitude=(pattern_data->max.G-pattern_data->min.G)/2; + mean=(pattern_data->max.G+pattern_data->min.G)/2; + value=(255*pattern_data->current_period/pattern_data->period)+pattern_data->data.sine_data.phase; + pixel.G=(unsigned char)(amplitude*sin_lut[value]+mean); + amplitude=(pattern_data->max.B-pattern_data->min.B)/2; + mean=(pattern_data->max.B+pattern_data->min.B)/2; + value=(255*pattern_data->current_period/pattern_data->period)+pattern_data->data.sine_data.phase; + pixel.B=(unsigned char)(amplitude*sin_lut[value]+mean); + + return pixel; +} + +TPixelRGB wf_square(TWaveform *pattern_data) +{ + TPixelRGB pixel; + + if(pattern_data->current_period<pattern_data->data.square_data.t_on) + { + pixel.R=pattern_data->max.R; + pixel.G=pattern_data->max.G; + pixel.B=pattern_data->max.B; + } + else + { + pixel.R=pattern_data->min.R; + pixel.G=pattern_data->min.G; + pixel.B=pattern_data->min.B; + } + + return pixel; +} + +TPixelRGB wf_ramp(TWaveform *pattern_data) +{ + TPixelRGB pixel; + + pixel.R=pattern_data->min.R+((pattern_data->max.R-pattern_data->min.R)*pattern_data->current_period)/pattern_data->period; + pixel.G=pattern_data->min.G+((pattern_data->max.G-pattern_data->min.G)*pattern_data->current_period)/pattern_data->period; + pixel.B=pattern_data->min.B+((pattern_data->max.B-pattern_data->min.B)*pattern_data->current_period)/pattern_data->period; + + return pixel; +} + +TPixelRGB wf_triangle(TWaveform *pattern_data) +{ + unsigned short int time; + TPixelRGB pixel; + + if(pattern_data->current_period<(pattern_data->period/2)) + { + pixel.R=pattern_data->min.R+((pattern_data->max.R-pattern_data->min.R)*pattern_data->current_period)/(pattern_data->period/2); + pixel.G=pattern_data->min.G+((pattern_data->max.G-pattern_data->min.G)*pattern_data->current_period)/(pattern_data->period/2); + pixel.B=pattern_data->min.B+((pattern_data->max.B-pattern_data->min.B)*pattern_data->current_period)/(pattern_data->period/2); + } + else + { + time=pattern_data->current_period-(pattern_data->period/2); + pixel.R=pattern_data->max.R-((pattern_data->max.R-pattern_data->min.R)*time)/(pattern_data->period/2); + pixel.G=pattern_data->max.G-((pattern_data->max.G-pattern_data->min.G)*time)/(pattern_data->period/2); + pixel.B=pattern_data->max.B-((pattern_data->max.B-pattern_data->min.B)*time)/(pattern_data->period/2); + } + + return pixel; +} + +TPixelRGB wf_none(TWaveform *pattern_data) +{ + TPixelRGB pixel; + + pixel.R=pattern_data->max.R; + pixel.G=pattern_data->max.G; + pixel.B=pattern_data->max.B; + + return pixel; +} + +TPixelRGB wf_pixel(TWaveform *pattern_data) +{ + TPixelRGB pixel; + + switch(pattern_data->waveform_id) + { + case WF_SINE: pixel=wf_sine(pattern_data); + break; + case WF_SQUARE: pixel=wf_square(pattern_data); + break; + case WF_RAMP: pixel=wf_ramp(pattern_data); + break; + case WF_TRIANGLE: pixel=wf_triangle(pattern_data); + break; + case WF_NONE: pixel=wf_none(pattern_data); + break; + } + + return pixel; +} + +// public functions +void wf_general(TLEDArea *area,TWaveform *pattern_data,unsigned char buffer_id,unsigned short int period,TFBControl *control) +{ + unsigned short int i,j; + TPixelRGB pixel; + + // always compute time + pattern_data->current_period+=period; + if(pattern_data->current_period>=pattern_data->period) + pattern_data->current_period-=pattern_data->period; + if(pattern_data->active)// motion only when active + { + pixel=wf_pixel(pattern_data); + for(i=area->min_row;i<=area->max_row;i++) + for(j=area->min_col;j<=area->max_col;j++) + frame_buffer_set_pixel(&control->frame_buffer,buffer_id,pixel.R,pixel.G,pixel.B,i,j); + } +}