(define num-plants 1000) (define-struct plant (root shape widths (start-time #:mutable) (started #:mutable) (seed #:mutable))) (define (choose l) (list-ref l (random (length l)))) (define (build-plant size) (make-plant (with-state (translate (vector 1000 0 0)) ;(shader "simple.vert.glsl" "simple.frag.glsl") ;(hint-none) ;(hint-wire) (hint-unlit) ; (hint-ignore-depth) (build-ribbon size)) (let ((r (* 50 (crndf))) (d (vmul (vector 0 0.5 0.2) (* (rndf) 1))) (p (vector 0 0 0)) (w (* 5 (rndf))) (off (crndf))) (build-list size (lambda (i) (set! p (vadd p d)) (set! d (vtransform d (mrotate (vector 0 0 (* r (+ off (* 1 (sin (* i w))))))))) (set! d (vmul d 0.9)) p))) (build-list size (lambda (i) (let ((t (/ i size))) (* 1 t t (* 0.3 (+ 1 (cos (* t 3.141)))))))) (time) #f (* (rndf) 10))) (define (reset-plant plant pos col tex) (with-primitive (plant-root plant) (identity) (colour col) (texture (load-texture tex)) ;(shader-set! (list "ColourMap" 0)) (translate pos) (pdata-map! (lambda (p) (vector 0 0 0)) "p") (pdata-index-map! (lambda (i w) (list-ref (plant-widths plant) i)) "w")) (set-plant-start-time! plant (time)) (set-plant-started! plant #t)) (define (plant-update plant) (let ((t (* (- (time) (plant-start-time plant)) 2.5))) (with-primitive (plant-root plant) ;(shader-set! (list "Time" (* 10 (time)))) (rotate (vector 0 0 (* 0.05 (sin (+ (plant-seed plant) (- (time) (plant-start-time plant))))))) (when (< t (pdata-size)) (pdata-index-map! (lambda (i p) (let ((t (- t i))) (if (> t 0) (vmix p (list-ref (plant-shape plant) (inexact->exact (floor t))) 0.9) p))) "p"))))) (define (plant-destroy plant) (destroy (plant-root plant))) ;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ (define (random-pos i) (let* ((t (* (random (inexact->exact (floor (/ (length i) 3)))) 3)) (b (rndbary))) (vadd (vmul (pdata-ref "p" (list-ref i t)) (vx b)) (vmul (pdata-ref "p" (list-ref i (+ t 1))) (vy b)) (vmul (pdata-ref "p" (list-ref i (+ t 2))) (vz b))))) (define (get-line-from-mouse) (let* ((ndcpos (vector (* (- (/ (mouse-x) (vx (get-screen-size))) 0.5) 1.25) ; 2 (* (- (- (/ (mouse-y) (vy (get-screen-size))) 0.5)) 1) -1)) ;1.5 (scrpos2 (vtransform (vmul ndcpos 500) (minverse (get-camera-transform)))) (scrpos (vtransform ndcpos (minverse (get-camera-transform))))) (list scrpos scrpos2))) (define (pos-from-mouse line) (let ((i (geo/line-intersect (car line) (cadr line)))) (cond ((not (null? i)) (cdr (assoc "p" (car i)))) (else #f)))) ;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ (define (setup-flowers flowers) (with-primitive flowers (translate (vector 0 0 0.1)) (hint-depth-sort) (pdata-add "plant" "f") (pdata-add "vert" "f") (pdata-add "max-size" "f") (pdata-map! (lambda (c) (vector (+ 0.5 (* 0.5 (rndf))) (* 0.5 (rndf)) (rndf))) "c") (pdata-map! (lambda (c) (vector 0 0 0)) "s") (pdata-map! (lambda (c) (* (rndf) 0.6)) "max-size"))) (define (update-flowers flowers plants) (with-primitive flowers (pdata-map! (lambda (p plant vert) (if (zero? vert) p (with-primitive (plant-root (list-ref plants (inexact->exact plant))) (vtransform (pdata-ref "p" (inexact->exact vert)) (get-transform))))) "p" "plant" "vert") (pdata-map! (lambda (s max-size) (if (or (> (vx s) max-size) (< (vx s) 0.005)) s (vadd s (vector 0.001 0.001 0.001)))) "s" "max-size") (when (zero? (random 10)) (let ((f (random (pdata-size)))) (when (zero? (vx (pdata-ref "s" f))) (let* ((plant-num (random (length plants))) (plant (list-ref plants plant-num))) (when (plant-started plant) (pdata-set! "plant" f (random (length plants))) (pdata-set! "vert" f (+ 5 (random 10))) (pdata-set! "s" f (vector 0.01 0.01 0.01)) (pdata-set! "p" f (vector 1000 0 0))))))))) ;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ (clear) (set-screen-size (vector 1024 768)) (set-camera-transform #(1.0 0.0 0.0 0.0 0.0 1.0 0.0 0.0 0.0 0.0 1.0 0.0 0.36000001430511475 0.41999998688697815 -9.279999732971191 1.0)) ;(define img (build-image (load-texture "textures/tyki.png") (vector 0 0) (get-screen-size))) (set-fov 50 1 1000) (light-diffuse 0 (vector 0 0 0)) (let ((l (make-light 'point 'free))) (light-diffuse 1 (vector 1 1 1)) (light-position l (vector 0 100 100))) (define bg (with-state (opacity 0.2) (translate (vector 0 3 -6)) (rotate (vector 0 180 0)) (hint-wire) (wire-colour (vector 0 0 1)) (colour (vector 0 0 0.5)) (load-primitive "meshes/k.obj"))) (with-primitive bg (hide 1)) (define shape (load-primitive "meshes/proc3.obj")) (define flowers (with-state (hint-unlit) (texture (load-texture "textures/flower2.png")) (build-particles 400))) (setup-flowers flowers) (define plants (build-list num-plants (lambda (_) (build-plant 20 )))) (define cur 0) (define i (with-primitive shape (hint-wire) (hint-unlit) (colour 0.2) (wire-colour 0.5) (backfacecull 0) (translate (vector 0 3 -6)) (rotate (vector 0 180 0)) (scale 10) (hide 1) (apply-transform) ;(poly-convert-to-indexed) (poly-indices))) (define (plants-cons plants pos col tex) (reset-plant (list-ref plants cur) pos col tex) (set! cur (modulo (+ cur 1) (length plants)))) (define (plants-update) (when (key-pressed "b") (with-primitive bg (hide 0))) (when (key-pressed "c") (with-primitive bg (hide 1))) (let ((line (get-line-from-mouse)) (hit #f)) (when (mouse-button 1) #;(key-pressed " ") (with-primitive shape (let ((p (pos-from-mouse line))) (when (and p (not (zero? (vx p)))) (set! hit #t) (let ((col (hsv->rgb (vector 0.25 (rndf) (+ 0.5 (* 0.5 (rndf)))))) (tex (choose (list "textures/leaf-01.png" "textures/leaf-02.png" "textures/leaf-03.png")))) (for ((i (in-range 0 6))) (plants-cons plants p col tex))))))) (with-state (translate (vadd (vmul (car line) 0.99) (vmul (cadr line) 0.01))) (if hit (scale 0.04) (scale 0.02)) (hint-unlit) (colour (vector 0.7 0.7 0)) (draw-sphere))) (for-each (lambda (plant) (plant-update plant)) plants) (update-flowers flowers plants)) (show-axis 0) (every-frame (plants-update))