This program was my attempt to plot a given equation on a VGA screen using Prof. Hunter Adam's VGA Library for the RaspberryPi Pico. The resources for the project include the C SDK User Guide, the RP2040 Datasheet and Prof. Hunter's website.
/*
* Parth Sarthi Sharma (pss242@cornell.edu)
* Code based on examples from Raspberry Pi Foundation.
* This code is an implementation of a custom sin cos tan function
* on the Raspberry Pi Pico to draw a pattern.
*/
#include <stdio.h> //The standard C library
#include <math.h> //The standard math library
#include "pico/stdlib.h" //Standard library for Pico
#include "hardware/pio.h" //The hardware PIO library
#include "hardware/dma.h" //The hardware DMA library
#include "pico/time.h" //The pico time library
#include "hardware/gpio.h" //The hardware GPIO library
#include "pico/multicore.h" //The pico multicore library
#include "vga_graphics.h" //The graphics library
#define HEIGHT 480 //Height of the VGA screen
#define WIDTH 640 //Width of the VGA screen
void core1_entry() { //The program running on core 1
double error = 0.01, step = 0.01, x, y, ans; //The error, step, x coordiante, y coordinate and the answer variables
for(x = 0; x < 5; x += step){ //For x in range [0, 5) with 0.01 step size
for(y = 4; y > -4; y -= step){ //For y in range (-4, 4] with 0.01 step size
ans = sin(cos(tan(x * y))) - sin(cos(tan(x))) - sin(cos(tan(y))); //Solve for the equation
if((ans < error) && (ans > -error)){ //If the solution is within the given error limits
fillCircle((50 * x) + (WIDTH / 2), (HEIGHT / 2) - (50 * y), 1, RED); //Draw a red circle to create an enlarged image
}
}
}
}
int main(){ //The program running on core 0
double error = 0.01, step = 0.01, x, y, ans; //The error, step, x coordiante, y coordinate and the answer variables
stdio_init_all(); //Initialize all of the present standard stdio types that are linked into the binary
initVGA(); //Initialize the VGA screen and functions
multicore_launch_core1(core1_entry); //Reset core1 and enter the core1_entry function on core 1 using the default core 1 stack
for(x = -5; x < 0; x += step){ //For x in range [-5, 0) with 0.01 step size
for(y = 4; y > -4; y -= step){ //For y in range (-4, 4] with 0.01 step size
ans = sin(cos(tan(x * y))) - sin(cos(tan(x))) - sin(cos(tan(y))); //Solve for the equation
if((ans < error) && (ans > -error)){ //If the solution is within the given error limits
fillCircle((50 * x) + (WIDTH / 2), (HEIGHT / 2) - (50 * y), 1, RED); //Draw a red circle to create an enlarged image
}
}
}
}
The code has a VGA library which has been explained really nicely by Prof. Adams and the main file.
The main crux of the program lies in the fact that I needed to compute the equation within a given error as trying to find the exact solution can be really computationally expensive. Therefore, I divided the x-coordinates and the y-coordinates into a series of small steps and computed the equation on using those coordinates. If the answer is within the given error limit, draw a red circle at the given location.
cmake_minimum_required(VERSION 3.13)
include(pico_sdk_import.cmake)
project(SinCosTan-project)
pico_sdk_init()
add_executable(SinCosTan)
pico_enable_stdio_usb(SinCosTan 1)
pico_enable_stdio_uart(SinCosTan 1)
pico_generate_pio_header(SinCosTan ${CMAKE_CURRENT_LIST_DIR}/hsync.pio)
pico_generate_pio_header(SinCosTan ${CMAKE_CURRENT_LIST_DIR}/vsync.pio)
pico_generate_pio_header(SinCosTan ${CMAKE_CURRENT_LIST_DIR}/rgb.pio)
target_sources(SinCosTan PRIVATE SinCosTan.c vga_graphics.c)
target_link_libraries(SinCosTan PRIVATE pico_stdlib hardware_pio hardware_dma hardware_adc hardware_irq pico_time pico_multicore)
pico_add_extra_outputs(SinCosTan)