#lang scheme ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; RPG Combat System ;; ;; Stefan Terry ;; ;; *just hit run* ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;stat holders;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;elemental info;;;;;;;;;;;;;;;;;;;;;;; ;wood (wd), water (wt), metal (mt), earth (er), fire (fr); ; wd trumps er trumps wt trumps fr trumps mt trumps wd ; ; wd heals fr heals er heals mt heals wt heals wd ; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (define playerbase '(1 5 5 5 5 5 n)) ;(lvl atk def mag res spd element) (define playerbasehp 25) (define playerbasemp 20) (define player playerbase) (define playerhp playerbasehp) (define playermp playerbasemp) (define enemybase '(0 1 1 1 1 1 n)) (define enemybasehp 1) (define enemybasemp 1) (define enemy '(0 1 1 1 1 1 n)) (define enemyhp 1) (define enemymp 1) (define pturn #f) (define eturn #f) (define slimebase '(1 2 2 2 3 3 wt)) ;(mnumber atk def mag res spd element) (define slimebasehp 30) (define slimebasemp 10) (define slime slimebase) (define slimehp slimebasehp) (define slimemp slimebasemp) (define gablinbase '(2 4 3 2 3 4 er)) ;(mnumber atk def mag res spd) (define gablinbasehp 30) (define gablinbasemp 10) (define gablin gablinbase) (define gablinhp gablinbasehp) (define gablinmp gablinbasemp) (define lizardmanbase '(3 4 4 2 3 5 er)) ;(mnumber atk def mag res spd) (define lizardmanbasehp 45) (define lizardmanbasemp 15) (define lizardman lizardmanbase) (define lizardmanhp lizardmanbasehp) (define lizardmanmp lizardmanbasemp) (define survival? #f) ;;;;;;;;;;game start;;;;;;;;;; (define pickfight (lambda () (printf "what do you want to fight: slime, gablin, lizardman, survival \n") (let ((a (read))) (cond ((equal? a 'exit) "game over") ((equal? a 'slime) (startbattle 1)) ((equal? a 'gablin) (startbattle 2)) ((equal? a 'lizardman) (startbattle 3)) ((equal? a 'survival) (survivalmode 1)) (else (printf "invalid entry") (pickfight)))) )) (define survivalmode (lambda (monnum) (when (equal? monnum 1) (set! playerhp playerbasehp)) (set! survival? #t) (cond ((equal? monnum 4) (when (> playerhp 0) (printf "Incredible! \n")) (set! survival? #f) (endgame)) (else (printf "You are fighting a ~A \n" (ename monnum)) (startbattle monnum))))) (define startbattle (lambda (b) (when (equal? survival? #f) (set! playerhp playerbasehp)) (cond ((equal? b 1) (set! enemybase slimebase) (set! enemybasehp slimebasehp) (set! enemybasemp slimebasemp) (set! enemy slimebase) (set! enemyhp slimebasehp) (set! enemymp slimebasemp)) ((equal? b 2) (set! enemybase gablinbase) (set! enemybasehp gablinbasehp) (set! enemybasemp gablinbasemp) (set! enemy gablinbase) (set! enemyhp gablinbasehp) (set! enemymp gablinbasemp)) ((equal? b 3) (set! enemybase lizardmanbase) (set! enemybasehp lizardmanbasehp) (set! enemybasemp lizardmanbasemp) (set! enemy lizardmanbase) (set! enemyhp lizardmanbasehp) (set! enemymp lizardmanbasemp))) (if (< (list-ref player 5) (list-ref enemy 5)) (enemyturn) (playerturnstart)))) ;(define turnorder ; (lambda (pspd 1spd (2spd 0) (3spd 0)) ; (cond ;;;;;;;;;;player turn;;;;;;;;;; (define playerturnstart (lambda () (set! pturn #t) (set! eturn #f) (set! player playerbase) (mprecovery 3 'player) (playerturn))) (define playerturn (lambda () (printf "attack, defend, magic, health, flee, exit \n") (let ((c (read))) (cond ((equal? c 'exit) "game over") ((equal? c 'attack) (physattack)) ((equal? c 'defend) (defend)) ;defend incomplete, but runable ((equal? c 'magic) (magic)) ;magic incomplete, but runable ((equal? c 'health) (showhp)) ((equal? c 'stats) (showstats)) ((equal? c 'scan) (scan)) ((equal? c 'flee) (runaway)) ((equal? c 'bjork) (printf "bjork! \n") (playerturn)) (else ((printf "invalid entry \n") (playerturn))))) )) (define physattack (lambda () (cond ((physhit (list-ref player 5) (list-ref enemy 5)) (let ((dmg (physdamage (list-ref player 1) (list-ref enemy 2)))) (printf "you deal ~A damage \n" dmg) (dealdamage dmg))) (else (printf "miss \n"))) (when (and (> enemyhp 0) (> playerhp 0)) (enemyturnstart)) )) (define defend (lambda () (defenseup 'player (/ 3 2)) (resup 'player (/ 3 2)) (printf "you are defending \n") (enemyturnstart))) ;(define magic ; (lambda () ; (printf "you have no magic \n") ;currently does nothing ; (playerturn))) (define magic (lambda () (printf "ember, growth, quake, tide, shard, back \n") (let ((choice (read))) (cond ((equal? choice 'ember) ;ember (if (>= playermp 5) (begin (let ((dmg (magdamage (list-ref player 3) (list-ref enemy 4) 'fr (list-ref enemy 6)))) (printf "you deal ~A damage \n" dmg) (dealdamage dmg) (set! playermp (- playermp 5)))) (begin (printf "not enough mp") (magic)))) ((equal? choice 'growth) ;growth (if (>= playermp 5) (begin (let ((dmg (magdamage (list-ref player 3) (list-ref enemy 4) 'wd (list-ref enemy 6)))) (printf "you deal ~A damage \n" dmg) (dealdamage dmg) (set! playermp (- playermp 5)))) (begin (printf "not enough mp") (magic)))) ((equal? choice 'quake) ;quake (if (>= playermp 5) (begin (let ((dmg (magdamage (list-ref player 3) (list-ref enemy 4) 'er (list-ref enemy 6)))) (printf "you deal ~A damage \n" dmg) (dealdamage dmg) (set! playermp (- playermp 5)))) (begin (printf "not enough mp") (magic)))) ((equal? choice 'tide) ; tide (if (>= playermp 5) (begin (let ((dmg (magdamage (list-ref player 3) (list-ref enemy 4) 'wt (list-ref enemy 6)))) (printf "you deal ~A damage \n" dmg) (dealdamage dmg) (set! playermp (- playermp 5)))) (begin (printf "not enough mp") (magic)))) ((equal? choice 'shard) ;shard (if (>= playermp 5) (begin (let ((dmg (magdamage (list-ref player 3) (list-ref enemy 4) 'mt (list-ref enemy 6)))) (printf "you deal ~A damage \n" dmg) (dealdamage dmg) (set! playermp (- playermp 5)))) (begin (printf "not enough mp") (magic)))) ((equal? choice 'back) ;back (playerturn)) (else (printf "that's not a spell \n") (magic))) (when (and (> enemyhp 0) (> playerhp 0)) (enemyturnstart)) ))) (define showhp (lambda () (printf "hp is ~A \n" playerhp) (printf "mp is ~A \n" playermp) (playerturn))) (define showstats (lambda () (printf "yours: ~A \n" player) (printf "enemy's: ~A \n" enemy) (playerturn))) (define scan (lambda () (printf "foe hp is ~A \n" enemyhp) (printf "foe mp is ~A \n" enemymp) (playerturn))) (define runaway (lambda () (cond ((escape (list-ref player 5) (list-ref enemy 5)) (display "got away safely \n") (pickfight)) (else (enemyturnstart)) ))) ;;;;;;;;;;enemy turn;;;;;;;;;; (define enemyturnstart (lambda () (set! eturn #t) (set! pturn #f) (mprecovery 3 'enemy) (set! enemy enemybase) (enemyturn))) (define enemyturn (lambda () (let ((z (random 100))) (cond ((< z 75) (ephysattack)) (else (edefend)))) )) (define ephysattack (lambda () (printf "~A attacks \n" (ename (car enemy))) (cond ((physhit (list-ref enemy 5) (list-ref player 5)) (let ((dmg (physdamage (list-ref enemy 1) (list-ref player 2)))) (printf "you take ~A damage \n" dmg) (takedamage dmg))) (else (printf "miss \n"))) (when (and (> playerhp 0) (> enemyhp 0)) (playerturnstart)))) (define edefend (lambda () (defenseup 'enemy (/ 3 2)) (resup 'enemy (/ 3 2)) (printf "~A is defending \n" (ename (car enemy))) (playerturnstart))) ;;;;;;;;;;formulas;;;;;;;;;; (define physhit (lambda (atkspd enmspd) (> (- (+ (/ atkspd 2) (random 100)) enmspd) 0) )) ;divides player attack by two and adds it to a random number between 0 and 99, then subtracts the enemy spd from it and compares it to 0 (define physdamage (lambda (atk enmdef) (floor (* (+ (* (/ (* atk 3) enmdef) (/ (+ (random 50) 71) 100)) 1) (crit))))) ; (atk*3)/enemydefense)*(random number between 0.7 and 1.2) +1 (define crit (lambda () (let ((chance (random 20))) (if (equal? chance 19) (begin (printf "critical hit! \n") 2) 1)))) (define magdamage (lambda (mag enmres elmt defelmt) (floor (+ (* (* (/ (* mag 3) enmres) (/ (+ (random 50) 71) 100)) (typemultiplier elmt defelmt)) 1)))) ; same as phys damage formula, almost (define typemultiplier ;compares attack type to defender's element and determines if it trumps or "heals" (lambda (element defender) (cond ((and (equal? element 'wd) (equal? defender 'er)) (printf "weak! \n") 2) ;weak ((and (equal? element 'fr) (equal? defender 'mt)) (printf "weak! \n") 2) ((and (equal? element 'er) (equal? defender 'wt)) (printf "weak! \n") 2) ((and (equal? element 'mt) (equal? defender 'wd)) (printf "weak! \n") 2) ((and (equal? element 'wt) (equal? defender 'fr)) (printf "weak! \n") 2) ((and (equal? element 'wd) (equal? defender 'fr)) (printf "resist! \n") (/ 1 2)) ;resistant ((and (equal? element 'fr) (equal? defender 'er)) (printf "resist! \n") (/ 1 2)) ((and (equal? element 'er) (equal? defender 'mt)) (printf "resist! \n") (/ 1 2)) ((and (equal? element 'mt) (equal? defender 'wt)) (printf "resist! \n") (/ 1 2)) ((and (equal? element 'wt) (equal? defender 'wd)) (printf "resist! \n") (/ 1 2)) (else 1)))) ;neutral (define escape (lambda (spd enmspd) (> (- (+ (/ spd 2) (random 100)) (* enmspd 2)) 0) )) ;same as hit formula, but the enemy speed gets doubled. (define dealdamage (lambda (damage) (set! enemyhp (- enemyhp damage)) (when (<= enemyhp 0) (begin (printf "victory! \n") (endgame))) )) (define takedamage (lambda (damage) (set! playerhp (- playerhp damage)) (when (<= playerhp 0) (begin (printf "game over \n") (endgame))) )) (define defenseup ;recreates either the player or enemy list with the defense slot increased (lambda (who multiplier) (when (equal? who 'player) (set! player (list (first player) (second player) (round (* (third player) multiplier)) (fourth player) (fifth player) (sixth player) (seventh player)))) (when (equal? who 'enemy) (set! enemy (list (first enemy) (second enemy) (round (* (third enemy) multiplier)) (fourth enemy) (fifth enemy) (sixth enemy) (seventh enemy)))))) (define resup ;same as defenseup, but with the res slot (lambda (who multiplier) (when (equal? who 'player) (set! player (list (first player) (second player) (third player) (fourth player) (round (* (fifth player) multiplier)) (sixth player) (seventh player)))) (when (equal? who 'enemy) (set! enemy (list (first enemy) (second enemy) (third enemy) (fourth enemy) (round (* (fifth enemy) multiplier)) (sixth enemy) (seventh enemy)))))) (define hprecovery ;makes sure recovery isn't bigger than max hp, then adds it to hp (if bigger is #t, it just sets it to max) (lambda (rec who) (cond ((equal? who 'player) (if (>= (+ playerhp rec) playerbasehp) (set! playerhp playerbasehp) (set! playerhp (+ playerhp rec)))) ((equal? who 'enemy) (if (>= (+ enemyhp 3) enemybasehp) (set! enemyhp enemybasehp) (set! enemyhp (+ enemyhp 3))))))) (define mprecovery ;same as hp recovery, but with mp (lambda (rec who) (cond ((equal? who 'player) (if (>= (+ playermp rec) playerbasemp) (set! playermp playerbasemp) (set! playermp (+ playermp rec)))) ((equal? who 'enemy) (if (>= (+ enemymp 3) enemybasemp) (set! enemymp enemybasemp) (set! enemymp (+ enemymp 3))))))) (define ename (lambda (q) (cond ((equal? q 1) 'slime) ((equal? q 2) 'gablin) ((equal? q 3) 'lizardman) (else 'enemy)))) (define endgame (lambda () (cond ((equal? survival? #t) (survivalmode (+ (car enemybase) 1))) (else (printf "another? (y/n) \n") (let ((choice (read))) (cond ((equal? choice 'y) (pickfight)) ((equal? choice 'n) (printf "game over")) (else (printf "It's a yes or no question \n") (endgame)))))))) ;;;;;;;;;;aaahhhhhhhh!;;;;;;;;;; (pickfight)