Skip to content

Instantly share code, notes, and snippets.

@fgaz
Created December 22, 2015 22:04
Show Gist options
  • Save fgaz/3270f012d0226150f170 to your computer and use it in GitHub Desktop.
Save fgaz/3270f012d0226150f170 to your computer and use it in GitHub Desktop.
Simple light/wave interaction generator in Haskell.
-- simple light/wave interaction generator
module Main where
-- depends on split and matrix packages
import Data.List.Split (chunksOf)
import Data.Matrix (Matrix, matrix, transpose, toList)
type P2 = (Int, Int)
type P3f = (Float, Float, Float)
type Light = Float
type Color = Int
type PGM = String
width = 2000
height = 3000
depth = 255
wavelength = 10
ampl = 100
sources = [ (400, 500, 100)
, (1600, 500, 100)
, (1000, 900, 100)
]
-- | interaction between n light sources
interact' :: P3f -> [P3f] -> Light
interact' point = abs . sum . map ((*ampl) . sin . (/wavelength) . dist3D point)
-- | 3D distance
dist3D :: P3f -> P3f -> Float
dist3D (x,y,z) (x',y',z') = sqrt $ ((x-x')**2) + ((y-y')**2) + ((z-z')**2)
-- | computes the color on a given 2D point
calc :: P2 -> Color
calc (x,y) = floor $ interact' (fromIntegral x, fromIntegral y, 0) sources
-- | the image
imgMatrix :: Matrix Color
imgMatrix = matrix width height calc
-- | ready for the final stringification
horribleListOfLists :: [[String]]
horribleListOfLists = chunksOf width $ fmap show $ toList $ transpose imgMatrix
-- | https://en.wikipedia.org/wiki/Netpbm_format#PGM_example
image :: PGM
image = "P2\n"
++ show width ++ " " ++ show height ++ "\n"
++ show depth ++ "\n"
++ (unlines $ fmap unwords horribleListOfLists)
main :: IO ()
main = writeFile "image.pgm" image
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment