├── .gitignore ├── heart-2014-02-14.png ├── aux ├── print-2019-02-14.pdf ├── README.md ├── Makefile └── print-2019-02-14.tex ├── Makefile ├── heart-2019-02-14.txt ├── LICENSE.md ├── heart.c ├── README.md └── heart.py /.gitignore: -------------------------------------------------------------------------------- 1 | *.sw? 2 | *.out 3 | *.aux 4 | *.log 5 | venv 6 | -------------------------------------------------------------------------------- /heart-2014-02-14.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/susam/heart/HEAD/heart-2014-02-14.png -------------------------------------------------------------------------------- /aux/print-2019-02-14.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/susam/heart/HEAD/aux/print-2019-02-14.pdf -------------------------------------------------------------------------------- /aux/README.md: -------------------------------------------------------------------------------- 1 | Auxiliary Files 2 | =============== 3 | 4 | This directory contains additional auxiliary files used to generate 5 | additional printable artifacts that could later be packaged into a 6 | Valentine's Day gift. 7 | 8 | See [Makefile](Makefile) for available `make` targets to generate the 9 | artifacts. 10 | -------------------------------------------------------------------------------- /aux/Makefile: -------------------------------------------------------------------------------- 1 | help: 2 | @echo 'Usage: make [target]' 3 | @echo 4 | @echo 'Targets:' 5 | @echo ' 2019 Create printable PDF for 2019 C program and output.' 6 | @echo ' help Show this help message.' 7 | 8 | 2019: clean 9 | pdflatex print-2019-02-14.tex 10 | make view FILE=print-2019-02-14.pdf 11 | make clean 12 | 13 | view: 14 | if command -v xdg-open > /dev/null; then \ 15 | xdg-open "$(FILE)"; \ 16 | elif command -v open > /dev/null; then \ 17 | open "$(FILE)"; \ 18 | else \ 19 | echo Cannot find xdg-open or open.; \ 20 | fi 21 | 22 | clean: 23 | rm -rf *.log *.aux 24 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | help: 2 | @echo 'Usage: make [target]' 3 | @echo 4 | @echo 'Targets:' 5 | @echo ' py-venv Set up virtual Python environment.' 6 | @echo ' py-heart Run Python program to plot heart.' 7 | @echo ' c-heart Compile and run C program to print heart.' 8 | @echo ' help Show this help message.' 9 | 10 | py-venv: 11 | python3 -m venv ~/.venv/heart 12 | echo . ~/.venv/heart/bin/activate > venv 13 | . ./venv && pip install matplotlib 14 | 15 | py-heart: 16 | . ./venv && python3 heart.py 17 | 18 | c-heart: 19 | cc -std=c89 -Wall -Wextra -pedantic heart.c 20 | ./a.out > heart-2019-02-14.txt 21 | @echo 22 | @cat heart-2019-02-14.txt 23 | @echo 24 | 25 | clean: 26 | rm -f a.out 27 | -------------------------------------------------------------------------------- /aux/print-2019-02-14.tex: -------------------------------------------------------------------------------- 1 | \documentclass{article} 2 | \usepackage[a4paper,top=0.9in,bottom=0.9in,left=1.85in]{geometry} 3 | \usepackage{xcolor} 4 | \usepackage{textcomp} 5 | \usepackage{listings} 6 | \pagestyle{empty} 7 | \lstset{ 8 | basicstyle=\ttfamily, 9 | columns=fullflexible, 10 | keepspaces=true, 11 | upquote=true 12 | } 13 | \lstdefinestyle{c}{ 14 | language=c, 15 | showstringspaces=false, 16 | commentstyle=\color{darkgray}, 17 | directivestyle=\color{teal}, 18 | keywordstyle=\color{blue}, 19 | identifierstyle=\color{violet}, 20 | stringstyle=\color{magenta} 21 | } 22 | \lstdefinestyle{out}{ 23 | basicstyle=\ttfamily\color{magenta}, 24 | } 25 | \begin{document} 26 | \lstinputlisting[style=c,firstline=29]{../heart.c} 27 | \lstinputlisting[style=out]{../heart-2019-02-14.txt} 28 | \end{document} 29 | -------------------------------------------------------------------------------- /heart-2019-02-14.txt: -------------------------------------------------------------------------------- 1 | ............................................................... 2 | ............................................................... 3 | .................. @@@@@@@ ......... @@@@@@@ .................. 4 | ............... @@@@ @@@@ ... @@@@ @@@@ ............... 5 | ............. @@@ @@@ @@@ @@@ ............. 6 | ............ @@@ @ @@@ ............ 7 | ............ @@@ Cutie Pai, @@@ ............ 8 | ............ @@@ @@@ ............ 9 | ............. @@@ I love you! @@@ ............. 10 | ............... @@@@ @@@@ ............... 11 | .................. @@@@ -- Susam @@@@ .................. 12 | ..................... @@@@ @@@@ ..................... 13 | ........................ @@@@ @@@@ ........................ 14 | ........................... @@@ @@@ ........................... 15 | .............................. @ .............................. 16 | ............................................................... 17 | ............................................................... 18 | -------------------------------------------------------------------------------- /LICENSE.md: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | ===================== 3 | Copyright (c) 2014-2019 Susam Pal 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining 6 | a copy of this software and associated documentation files (the 7 | "Software"), to deal in the Software without restriction, including 8 | without limitation the rights to use, copy, modify, merge, publish, 9 | distribute, sublicense, and/or sell copies of the Software, and to 10 | permit persons to whom the Software is furnished to do so, subject to 11 | the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be 14 | included in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 17 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 20 | CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 21 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 22 | SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | -------------------------------------------------------------------------------- /heart.c: -------------------------------------------------------------------------------- 1 | /* 2 | The MIT License (MIT) 3 | --------------------- 4 | Copyright (c) 2019 Susam Pal 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining 7 | a copy of this software and associated documentation files (the 8 | "Software"), to deal in the Software without restriction, including 9 | without limitation the rights to use, copy, modify, merge, publish, 10 | distribute, sublicense, and/or sell copies of the Software, and to 11 | permit persons to whom the Software is furnished to do so, subject to 12 | the following conditions: 13 | 14 | The above copyright notice and this permission notice shall be 15 | included in all copies or substantial portions of the Software. 16 | 17 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 18 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 19 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 20 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 21 | CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 22 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 23 | SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 24 | 25 | If you redistribute this code with modification, you must remove the 26 | strings "Cutie Pai" and "Susam" from line 55 of this code. 27 | */ 28 | 29 | #include 30 | 31 | void print_heart(void) 32 | { 33 | const int show[] = {'.', '@', ' ', '\n'}; 34 | const int love[] = { 35 | 252, 7, 252, 7, 72, 6, 29, 6, 36, 6, 29, 36 | 6, 72, 7, 60, 6, 17, 22, 17, 6, 12, 6, 37 | 38 | 17, 22, 17, 6, 39 | 60, 7, 52, 6, 13, 46, 13, 40 | 6, 13, 46, 13, 6, 52, 7, 48, 6, 13, 41 | 62, 5, 62, 13, 6, 48, 7, 48, 6, 13, 42 | 18, 1, 70, 13, 6, 48, 7, 48, 6, 13, 43 | 126, 13, 6, 48, 7, 52, 6, 13, 38, 2, 44 | 38, 13, 6, 52, 7, 60, 6, 17, 94, 45 | 17, 6, 60, 7, 72, 6, 17, 22, 46 | 3, 18, 17, 6, 72, 7, 84, 47 | 6, 17, 46, 17, 6, 48 | 84, 7, 96, 6, 49 | 17, 22, 50 | 17, 51 | 52 | 6, 96, 7, 108, 6, 13, 6, 13, 6, 108, 7, 53 | 120, 6, 5, 6, 120, 7, 252, 7, 252, 7, 54 | }; 55 | const char *say[] = {"", "Cutie Pai,", "I love you!", "-- Susam"}; 56 | size_t i; 57 | int j; 58 | for (i = 0; i < sizeof love / sizeof *love; i++) 59 | if (love[i] < 4) 60 | printf("%s", say[love[i]]); 61 | else 62 | for (j = 0; j < love[i] / 4; j++) 63 | putchar(show[love[i] % 4]); 64 | } 65 | 66 | int main() 67 | { 68 | print_heart(); 69 | return 0; 70 | } 71 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | Heart 2 | ===== 3 | 4 | This project contains a few programs written in Python and C that plot 5 | my heart for my [Cutie Pai][SUNAINA]. 6 | 7 | [SUNAINA]: https://github.com/sunainapai/ 8 | 9 | 10 | Contents 11 | -------- 12 | * [Python (2014)](#python-2014) 13 | * [C (2019)](#c-2019) 14 | 15 | 16 | Python (2014) 17 | ------------ 18 | 19 | The source code in [heart.py](heart.py) may be executed with Python 3.4 20 | or any later version of Python interpreter. It depends on the the 21 | [Matplotlib](https://pypi.org/project/matplotlib/) package. 22 | 23 | 24 | ### Setup and Run 25 | 26 | Enter these commands to set up a virtual Python environment with this 27 | package and run the Python program. 28 | 29 | make py-venv 30 | make py-heart 31 | 32 | The output is written to a PNG file named 33 | [heart-2014-02-14.png](heart-2014-02-14.png). 34 | 35 | 36 | ### Output 37 | 38 | ![heart-2014-02-14.png](heart-2014-02-14.png) 39 | 40 | 41 | ### Quadratic and Quartic Curves 42 | 43 | To read about the two mathematical functions used in the source code, 44 | see [this thread on Reddit][REDDIT] where I have explained how these 45 | functions plot the curves that form the heart. 46 | 47 | [REDDIT]: https://www.reddit.com/r/math/comments/1xwuv3/a_mathematical_valentine/cffeykn/ 48 | 49 | 50 | C (2019) 51 | -------- 52 | 53 | The source code in [heart.c](heart.c) may be compiled with any standard 54 | C compiler that supports C89 (ANSI C). 55 | 56 | 57 | ### Compile and Run 58 | 59 | Enter these commands to compile and run the C program. 60 | 61 | make c-heart 62 | 63 | The output is written to a text file named 64 | [heart-2019-02-14.txt](heart-2019-02-14.txt). 65 | 66 | 67 | ### Output 68 | 69 | ............................................................... 70 | ............................................................... 71 | .................. @@@@@@@ ......... @@@@@@@ .................. 72 | ............... @@@@ @@@@ ... @@@@ @@@@ ............... 73 | ............. @@@ @@@ @@@ @@@ ............. 74 | ............ @@@ @ @@@ ............ 75 | ............ @@@ Cutie Pai, @@@ ............ 76 | ............ @@@ @@@ ............ 77 | ............. @@@ I love you! @@@ ............. 78 | ............... @@@@ @@@@ ............... 79 | .................. @@@@ -- Susam @@@@ .................. 80 | ..................... @@@@ @@@@ ..................... 81 | ........................ @@@@ @@@@ ........................ 82 | ........................... @@@ @@@ ........................... 83 | .............................. @ .............................. 84 | ............................................................... 85 | ............................................................... 86 | 87 | 88 | License 89 | ------- 90 | 91 | This is free and open source software. You can use, copy, modify, 92 | merge, publish, distribute, sublicense, and/or sell copies of it, 93 | under the terms of the MIT License. See [LICENSE.md][L] for details. 94 | 95 | This software is provided "AS IS", WITHOUT WARRANTY OF ANY KIND, 96 | express or implied. See [LICENSE.md][L] for details. 97 | 98 | [L]: LICENSE.md 99 | -------------------------------------------------------------------------------- /heart.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python3 2 | 3 | # The MIT License (MIT) 4 | # 5 | # Copyright (c) 2014-2019 Susam Pal 6 | # 7 | # Permission is hereby granted, free of charge, to any person obtaining 8 | # a copy of this software and associated documentation files (the 9 | # "Software"), to deal in the Software without restriction, including 10 | # without limitation the rights to use, copy, modify, merge, publish, 11 | # distribute, sublicense, and/or sell copies of the Software, and to 12 | # permit persons to whom the Software is furnished to do so, subject to 13 | # the following conditions: 14 | # 15 | # The above copyright notice and this permission notice shall be 16 | # included in all copies or substantial portions of the Software. 17 | # 18 | # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 19 | # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 20 | # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 21 | # IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 22 | # CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 23 | # TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 24 | # SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 25 | # 26 | # If you redistribute this code with modification, you must remove the 27 | # strings 'Cutie Pai' and 'Susam' from the last statement in this code. 28 | 29 | 30 | """My heart for Cutie Pai.""" 31 | 32 | __version__ = '0.1' 33 | __date__ = '14 February 2014' 34 | __author__ = 'Susam Pal ' 35 | __credits__ = 'Sunaina Pai, the inspiration behind my creativity.' 36 | 37 | 38 | import numpy 39 | from matplotlib import pyplot 40 | from matplotlib import ticker 41 | 42 | 43 | def plot_heart(message, signature, filename): 44 | """Plot heart shaped curves. 45 | 46 | The following two functions are used to plot the curves: 47 | 48 | 1. y = sqrt(1 - |x|) * sqrt(|x|) 49 | 2. y = -(3/2) * sqrt(1 - sqrt(|x|)) 50 | 51 | Arguments: 52 | 53 | message -- Message to be displayed within the heart 54 | signature -- Name of the person writing the message 55 | filename -- Name of the file where the graph is to be saved 56 | """ 57 | # Legend label 58 | function1 = r'$y = \sqrt{1 - |x|} \sqrt{|x|}$' 59 | function2 = r'$y = -\frac{3}{2} \sqrt{1 - \sqrt{|x|}}$' 60 | 61 | # Plot points 62 | x = numpy.linspace(-1, 1, 10001) 63 | y1 = numpy.sqrt(1 - numpy.abs(x)) * numpy.sqrt(numpy.abs(x)) 64 | y2 = (-3/2) * numpy.sqrt(1 - numpy.sqrt((numpy.abs(x)))) 65 | pyplot.plot(x, y1, color='red', label=function1 + ', ' + function2) 66 | pyplot.plot(x, y2, color='red') 67 | 68 | # Write messages 69 | text_args = { 70 | 'size': 'x-large', 71 | 'color': '#ff1493', 72 | 'family': 'fantasy', 73 | } 74 | pyplot.text(0, -0.4, message, 75 | horizontalalignment='center', **text_args) 76 | pyplot.text(0.98, -1.3, signature, 77 | horizontalalignment='right', **text_args) 78 | 79 | # Set graph properties 80 | pyplot.legend(fancybox=True, shadow=True) 81 | pyplot.xlim([-1.5, 1.5]) 82 | pyplot.ylim([-1.6, 1.0]) 83 | pyplot.tick_params(which='major', colors='green', width='0.2') 84 | pyplot.tick_params(which='minor', colors='green', width='0.1') 85 | pyplot.grid(True, which='major', color='green', 86 | linestyle='-', linewidth='0.2') 87 | pyplot.grid(True, which='minor', color='green', 88 | linestyle='-', linewidth='0.1') 89 | axes = pyplot.axes() 90 | axes.set_aspect('equal') 91 | axes.spines['bottom'].set_color('green') 92 | axes.spines['top'].set_color('green') 93 | axes.spines['right'].set_color('green') 94 | axes.spines['left'].set_color('green') 95 | axes.xaxis.set_major_locator(ticker.MultipleLocator(0.5)) 96 | axes.xaxis.set_minor_locator(ticker.MultipleLocator(0.1)) 97 | axes.yaxis.set_major_locator(ticker.MultipleLocator(0.5)) 98 | axes.yaxis.set_minor_locator(ticker.MultipleLocator(0.1)) 99 | 100 | # Save the graph to a file 101 | figure = pyplot.gcf() 102 | figure.set_size_inches(9.6, 7.2) 103 | pyplot.savefig(filename) 104 | 105 | if __name__ == '__main__': 106 | plot_heart('I love you, my Cutie Pai!', '\u2014 Susam', 107 | 'heart-2014-02-14.png') 108 | --------------------------------------------------------------------------------