(ns advent.screens.rooms.outside-castle (:require [advent.screens.items :as items] [advent.screens.rooms :as rooms] [advent.screens.rooms.common :as common] [advent.screens.rooms.castle-gate :as castle-gate] [advent.actions :as actions] [advent.utils :as utils] [clojure.zip :as zip] [play-clj.core :refer :all] [play-clj.ui :refer :all] [play-clj.utils :refer :all] [play-clj.math :refer :all] [play-clj.g2d :refer :all])) (defn flies-vol [entities] (utils/proximity-volume entities [201 175] :scale 0.20)) (defn do-peddler-tree [entities] (actions/present-choices entities {:choices ["What \"wares\" are you selling?" {:run #(actions/respond entities % :peddler "The choicest of questions, sir!" :peddler "I have the choicest of all types of wares..." :peddler "...I'm well stocked on used earplugs..." :peddler "...glass eyes..." :peddler "... and motivational tapes." :peddler "And today, I have a one day special!" :peddler "Every purchase comes with the choicest of balloons!") :choices ["I'm interested in your earplugs." {:run #(do (actions/respond entities % :peddler "A choice choice, sir!" :peddler "These earplugs have been used by the choicest of wearers." :peddler "I can see a young man like yourself enjoying these choice earplugs for ages to come!" :peddler "And remember, every purchase comes with the choicest of balloons!" ) (if (get-in @entities [:state :wants-toy]) (actions/do-dialogue entities :peddler "I will give them to you if you bring me the choicest of toys.") (actions/do-dialogue entities :peddler "That'll just be 10 sheckles." :ego "But I haven't got any money!" :peddler "Well, I'm afraid you won't have the choicest of earplugs." :ego "Can't I give you something else for them?" :peddler "I'll tell you what, I don't have anything for the kids that come to my stand." :peddler "If you can bring me the choicest of toys..." :peddler "... and I mean the choicest of toys... " :peddler "I will give you the earplugs.")) (actions/update-state entities (fn [state] (assoc state :wants-toy true))) ) :choices actions/previous-choices} "I'm interested in a glass eye." {:run #(do (actions/respond entities % :peddler "The choicest choice, young man!" :peddler "This glass eye is made out of the choicest glass from across the sea." :peddler "And remember, every purchase comes with the choicest of balloons!" ) (if (get-in @entities [:state :wants-toy]) (actions/do-dialogue entities :peddler "I will give it to you if you bring me the choicest of toys.") (actions/do-dialogue entities :peddler "That'll just be 95 sheckles." :ego "But I haven't got any money!" :peddler "Well, I'm afraid you won't have the choicest of glass eyes." :ego "Can't I give you something else for them?" :peddler "I'll tell you what, I don't have anything for the kids that come to my stand." :peddler "If you can bring me the choicest of toys..." :peddler "... and I mean the choicest of toys... " :peddler "Then I'll give you the glass eye.")) (actions/update-state entities (fn [state] (assoc state :wants-toy true)))) :choices actions/previous-choices} "I'm interested in the motivational tapes." {:run #(do (actions/respond entities % :peddler "Sure thing!" :peddler "Has your luck got you down? Feeling pathetic?" :peddler "These choicest of motivation tapes will convince you that life isn't so bad.") (if (get-in @entities [:state :wants-toy]) (actions/do-dialogue entities :peddler "I will give them to you if you bring me the choicest of toys.") (actions/do-dialogue entities :peddler "For only 3 easy payments of 29.99 scheckles, they're yours!" :ego "But I'm broke!" :peddler "Well, I'm afraid you won't have the choicest of motivational tapes." :ego "Is there anything else you'd take instead?" :peddler "I'll tell you what, I don't have anything for the kids that come to my stand." :peddler "If you can bring me the choicest of toys..." :peddler "... and I mean the choicest of toys... " :peddler "Then I'll give you the motivational tapes.")) (actions/update-state entities (fn [state] (assoc state :wants-toy true)))) :choices actions/previous-choices} "Something else." {:choices actions/something-else}]} (when (get-in @entities [:state :wants-toy]) "Tell me again about the toy you want.") {:run #(actions/respond entities % :peddler "But of course, sir!" :peddler "I want a toy for the children who come by my stand." :peddler "And I don't mean any toy." :peddler "I need the choicest of toys!" :peddler "If you bring me one, I'll give you any of my choicest of wares." :peddler "And I'll throw in a balloon, free of charge!") :choices actions/previous-choices} "How's business?" {:run #(actions/respond entities % :peddler "Excellent, sir!" :peddler "This is the choicest location to find schmucks-" :peddler "Err, customers, for my choicest of wares!") :choices actions/previous-choices} "See you later." {:run #(actions/respond entities % :peddler "Goodbye, sir!" :peddler "May today be the choicest day!")}]})) (defn give-teddy [entities] (actions/remove-item entities :teddy) (actions/do-dialogue entities :peddler "That is the choicest of teddy bears!" :peddler "True to my word, I will give you one of my wares." :peddler "What would you like?") (actions/present-choices entities {:choices ["The glass eye." {:run #(do (actions/respond entities % :peddler "Of course, sir. Here you go.") (actions/give entities :glass-eye))} "The motivational tapes." {:run #(do (actions/respond entities % :peddler "Of course, sir. Here you go.") (actions/give entities :motivational-tapes))} "The used earplugs." {:run #(do (actions/respond entities % :peddler "Of course, sir. Here you go.") (actions/give entities :used-earplugs))}]}) (actions/talk entities :peddler "And, of course, here is your balloon.") (actions/give entities :balloon) (actions/talk entities :peddler "Thank you for your business!")) (defn do-completed-peddler-conversation [entities] (actions/do-dialogue entities :ego "Hello there, peddler." :peddler "Well, well!" :peddler "If it isn't my choicest of customers!" :peddler "I trust you are enjoying your choicest of wares?" :ego "... I sure am." :peddler "I thought so!")) (defn do-wants-toy-conversation [entities] (actions/do-dialogue entities :ego "Hello there, peddler." :peddler "Hello again, sir!" :peddler "Have you found me the choicest jack-in-the box yet?" :ego "... erm, no." :peddler "Oh, well how about the choicest bouncy ball?" :ego "... not quite yet." :peddler "Marionette? Teddy bear? Building blocks?") (if (actions/has-item? entities :teddy) (do (actions/do-dialogue entities :ego "Well, I have this teddy bear.") (give-teddy entities)) (do (actions/do-dialogue entities :ego "No, no, and no.") (do-peddler-tree entities)))) (defn walk-to-peddler [entities] (actions/walk-to entities :ego [191 90] :face :left)) (defn no-returns [entities] (walk-to-peddler entities) (actions/do-dialogue entities :ego "Can I return this?" :peddler "Sorry, no refunds.")) (defn do-peddler-dialogue [entities] (cond (actions/has-obtained? entities :balloon) (do-completed-peddler-conversation entities) (get-in @entities [:state :wants-toy]) (do-wants-toy-conversation entities) :else (do (actions/do-dialogue entities :ego "Hello there, peddler." :peddler "Good day, sir! Care to see any of my wares?" :peddler "I have only the choicest of wares.") (do-peddler-tree entities)))) (defn should-block? [entities] (and (= :night (get-in @entities [:state :time])) (actions/has-obtained? entities :flask-2) (not (actions/has-item? entities :magic-slingshot)))) (defn frankie-comment-on-item [entities] (cond (actions/has-item? entities :glass-eye) (do (actions/remove-item entities :glass-eye) (actions/do-dialogue entities :frankie "And how about that? A glass eye." :frankie "And not only that, it's the choicest of glass eyes!" :frankie "It must be made of the choicest glass from across the sea!" :frankie "This'll be perfect for when I punch your eye out, Dipstick." :frankie "Or, I could fetch some real good dough for this." :frankie "What would you say, boys?") (actions/play-animation entities :frankie :glance) (actions/do-dialogue entities :frankie "95 sheckles?")) (actions/has-item? entities :used-earplugs) (do (actions/remove-item entities :used-earplugs) (actions/do-dialogue entities :frankie "And how about that? Some used earplugs." :frankie "Wow! These are the choicest of earplugs!" :frankie "They're great for tuning out your voice, Dipstick!" :frankie "But, I could fetch some real good dough for them." :frankie "What would you say, boys?") (actions/play-animation entities :frankie :glance) (actions/do-dialogue entities :frankie "10 sheckles?")) (actions/has-item? entities :motivational-tapes) (do (actions/remove-item entities :motivational-tapes) (actions/do-dialogue entities :frankie "And how about that? Some motivational tapes." :frankie "Wow! These are the choicest of motivational tapes!" :frankie "But, I could fetch some real good dough for them." :frankie "What would you say, boys?") (actions/play-animation entities :frankie :glance) (actions/do-dialogue entities :frankie "3 easy payments of 29.99 sheckles?")))) (defn block-entrance [entities] (actions/transition-background entities :castle-gate [340 40]) (actions/walk-straight-to entities :ego [300 45]) (if (get-in @entities [:state :seen-frankie?]) ((rand-nth [#(do (actions/do-dialogue entities :frankie "Well, well, well. What have we here, boys?" :frankie "It's good ol' Dipstick again.") (actions/play-animation entities :frankie :laugh)) #(do (actions/do-dialogue entities :frankie "Quiet, boys." :frankie "Dipstick's here.") )])) (do (actions/do-dialogue entities :frankie "Well, well, well. What have we here, boys?") (actions/play-animation entities :frankie :glance) (actions/do-dialogue entities :frankie "It's good ol' Dipstick.") (actions/play-animation entities :frankie :laugh) (actions/do-dialogue entities :ego "Oh no! Frankie Rockfist!" :ego "Listen, I don't want any trouble." :frankie "Well you found it tonight, Dipstick." ) (actions/play-animation entities :frankie :flex) (actions/talk entities :frankie "Am I right, boys?") (actions/play-animation entities :frankie :glance) (actions/do-dialogue entities :frankie "You looking for another beat down, Dipstick?") (actions/play-animation entities :frankie :laugh) (actions/do-dialogue entities :ego "The name's \"Tick\"..." :ego "... and I'm just passing through..." :frankie "Not tonight you're not." :frankie "Unless, of course, you can pay the toll." :frankie "Come here, Dipstick." :ego "Umm, err, I'd rather not." :frankie "I said, come here." :frankie "Now.") (actions/walk-straight-to entities :ego [254 80]) (actions/do-dialogue entities :frankie "Now what have we got to give us today, Dipstick?") (actions/play-animation entities :frankie :reach) (actions/do-dialogue entities :frankie "A strength potion, oh very nice!" :frankie "And some gold..." :frankie "And what's this?") (actions/play-animation entities :frankie :reach) (actions/do-dialogue entities :frankie "The Slinger's Shot?" :ego "No, not the Slinger's Shot!" :frankie "Looks like we hit the jackpot tonight, boys!") (frankie-comment-on-item entities) (actions/update-state entities #(assoc % :bubba-gone? true)) (actions/do-dialogue entities :frankie "Bubba, put this stuff in the secret stash." :goon-2 "You got it, boss.") (actions/remove-entity entities :coin-flip) (actions/walk-straight-to entities :goon-2 [0 100]) (actions/do-dialogue entities :frankie "Now move along." :frankie "Before we decide to take all of your stuff." :ego "But I need that slingshot!" :frankie "Too bad. Move along.") (actions/remove-item entities :flask-1-strength) (actions/remove-item entities :medal) (actions/remove-item entities :trophy) (actions/remove-item entities :slingshot) (actions/walk-to entities :ego [181 79]) (actions/do-dialogue entities :ego "Now what am I going to do?" :ego "How will I break the news to Gandarf that I lost the Slinger's Shot?" :ego "My sweet Georgia McGorgeous, I will find a way to save you!"))) (actions/update-state entities #(assoc % :seen-frankie? true))) (defn go-through-gate [entities & {:keys [skip-type stop?] :or {skip-type :end stop? true}}] (if (should-block? entities) (do (actions/walk-to entities :ego [82 180] :face :left :skip-type skip-type) (block-entrance entities)) (do (actions/walk-to entities :ego [82 180] :skip-type skip-type :stop? false) (actions/walk-straight-to entities :ego [61 182]) (actions/transition-background entities :inside-castle [295 145]) (actions/walk-to entities :ego [245 90] :skip-type skip-type :stop? stop?)))) (defn add-note-if-necessary [entities] (if (and (actions/has-obtained? entities :spell-component) (not (actions/has-item? entities :spell-component)) (not (actions/has-obtained? entities :note-2))) (update-in entities [:room :entities] #(assoc % :note (get-in entities [:room :note]))) entities)) (defn make-night [entities] (-> entities (update-in [:room :entities] #(dissoc % :peddler)) (update-in [:room :entities] #(dissoc % :balloons)) (utils/remove-interaction :wares) add-note-if-necessary)) (defn feed-bull [entities] (actions/walk-to entities :ego [168 150] :face :right) (actions/play-animation entities :ego :reach) (actions/remove-item entities :grass) (actions/talk entities :ego "Eww! He slobbered on my hand.") (actions/give entities :slobber)) (defn make [screen] (let [peddler-sheet (texture! (utils/get-texture "outside-castle/peddler-talk.png" ) :split 18 36) peddler-talk (animation 0.18 (for [i (flatten [2 3 2 3 2 3 6 1 0 1 0 1 0 1 0 1 2 3 2 3 2 3 6 4 5 4 5 4 5 4 5])] (aget peddler-sheet 0 i))) peddler-stand (animation 0.2 (for [i (flatten [(repeat 8 0) 6 (repeat 15 0) 6 (repeat 5 0) 4 5 4 5 4 5 (repeat 10 0)] )] (aget peddler-sheet 0 i))) balloon-sheet (texture! (utils/get-texture "outside-castle/balloons.png") :split 20 36) balloon-stand (animation 0.25 (for [i [1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 1 0 1 2 1 0 1 2 1 0 1 2 1 0 1 2]] (aget balloon-sheet 0 i))) steer-sheet (texture! (utils/get-texture "outside-castle/steer.png") :split 50 35) steer-stand (animation 0.2 (for [i [0 0 0 0 0 0 0 0 0 1 0 2 0 1 0 2 0 1 0 2 0 0 0 0 0 0 0 0 0 0 0 0 0 3 3 3 3 3 3 3 3 3 0 0 0 0]] (aget steer-sheet 0 i))) flies-stand (utils/make-anim "outside-castle/flies.png" [15 15] 0.075 (flatten (repeat 2 [0 1 2 1])))] (rooms/make :music {:day :town-2 :night :night :sunrise :night} :name "Outside castle" :interactions {:right-dir {:box [280 40 320 140] :script (actions/get-script entities (actions/walk-to entities :ego [310 80] :stop? false :skip-type :end) (actions/walk-straight-to entities :ego [340 80]) (actions/transition-background entities :outside-house [-10 80]) (actions/walk-straight-to entities :ego [30 80])) :cursor :right} :door {:box [66 180 85 195] :script (actions/get-script entities (go-through-gate entities)) :cursor :left} :castle {:box [0 181 100 240] :script (actions/get-script entities (actions/do-dialogue entities :ego "That's the town of Remington in the distance."))} :wares {:box [69 75 97 110] :script (actions/get-script entities (actions/talk entities :ego "That peddler has all kinds of strange trinkets."))} :garden {:box [103 170 178 200] :script (actions/get-script entities (if (actions/has-obtained? entities :carrot) (actions/talk entities :ego "If I steal any more, I might get caught.") (do (actions/walk-to entities :ego [128 180]) (actions/talk entities :ego "Hey! Carrots.") (actions/play-animation entities :ego :squat) (actions/talk entities :ego "No one will notice one missing.") (actions/give entities :carrot))))}} :flies-sound {:sound (utils/load-sound "outside-castle/flies2.ogg") :id nil} :layers {:day [(assoc (utils/get-texture "outside-castle/background.png") :x 0 :y 0 :baseline 0) (assoc (utils/get-texture "outside-castle/blanket.png") :x 60 :y (- 240 173) :baseline 1) (assoc (utils/get-texture "outside-castle/brush-bl.png") :origin-x 25 :origin-y 20 :scale-x 1.0 :scale-y 1.0 :x 25 :y 0 :baseline 240 :parallax 1.2) (assoc (utils/get-texture "outside-castle/brush-br.png") :origin-x 88 :origin-y 20 :scale-x 1.0 :scale-y 1.0 :x 315 :y 0 :baseline 240 :parallax 1.2) (assoc (utils/get-texture "outside-castle/walk-behind.png") :x 0 :y 0 :baseline 69)] :night [(assoc (utils/get-texture "outside-castle/background.png") :x 0 :y 0 :baseline 0) (assoc (utils/get-texture "outside-castle/brush-bl.png") :origin-x 25 :origin-y 20 :scale-x 1.0 :scale-y 1.0 :x 25 :y 0 :baseline 240 :parallax 1.2) (assoc (utils/get-texture "outside-castle/brush-br.png") :origin-x 88 :origin-y 20 :scale-x 1.0 :scale-y 1.0 :x 315 :y 0 :baseline 240 :parallax 1.2) (assoc (utils/get-texture "outside-castle/walk-behind.png") :x 0 :y 0 :baseline 69)] :sunrise [(assoc (utils/get-texture "outside-castle/background.png") :x 0 :y 0 :baseline 0) (assoc (utils/get-texture "outside-castle/brush-bl.png") :origin-x 25 :origin-y 20 :scale-x 1.0 :scale-y 1.0 :x 25 :y 0 :baseline 240 :parallax 1.2) (assoc (utils/get-texture "outside-castle/brush-br.png") :origin-x 88 :origin-y 20 :scale-x 1.0 :scale-y 1.0 :x 315 :y 0 :baseline 240 :parallax 1.2) (assoc (utils/get-texture "outside-castle/walk-behind.png") :x 0 :y 0 :baseline 69)]} :entities {:peddler (actions/start-animation screen (assoc (utils/get-texture "outside-castle/peddler.png") :x 110 :y 90 :baseline 150 :anim nil :anim-sound-frames {peddler-stand {8 [:blink 0.3 0.8] 24 [:blink 0.3 0.8] 30 [:scratch 0.15]} peddler-talk {23 [:scratch 0.15] 6 [:blink 0.3 0.8] 22 [:blink 0.3 0.8]}} :scratch (utils/load-sound "outside-castle/scratch.ogg") :talk peddler-talk :stand peddler-stand :talk-color (color 1.0 0.9 0.4 1.0) :script (actions/get-script entities (walk-to-peddler entities) (do-peddler-dialogue entities)) :scripts #(condp = % :teddy (actions/get-script entities (walk-to-peddler entities) (give-teddy entities)) :glass-eye (actions/get-script entities (no-returns entities)) :motivational-tapes (actions/get-script entities (no-returns entities)) :used-earplugs (actions/get-script entities (no-returns entities)) :balloon (actions/get-script entities (no-returns entities)) (actions/get-script entities (walk-to-peddler entities) (actions/do-dialogue entities :ego "Are you interested in this?" :peddler "No, I have no use for it.")))) :stand) :steer (actions/start-animation screen (assoc (animation->texture screen steer-stand) :x 203 :y 155 :baseline 80 :stand steer-stand :night-profile :sprite :moo (utils/load-sound "outside-castle/moo.ogg") :anim-sound-frames {steer-stand {10 [:moo 0.2]}} :script (actions/get-script entities (actions/walk-to entities :ego [168 150] :face :right) (actions/do-dialogue entities :ego "It's Angus, Remington's buff bull." :ego "He's used in all of the town's rodeos." :ego "Farmer Doug feeds him a wild high-protein grass diet to keep him in tiptop shape." :ego "Phew! His stench has attracted a lot of flies.")) :scripts #(condp = % :grass (actions/get-script entities (feed-bull entities)) :carrot (actions/get-script entities (actions/walk-to entities :ego [168 150] :face :right) (actions/do-dialogue entities :ego "I don't think Angus is interested." :ego "Farmer Doug only feeds him a wild high-protein grass.")) :sack-lunch (actions/get-script entities (actions/walk-to entities :ego [168 150] :face :right) (actions/do-dialogue entities :ego "I don't thing Angus is interested." :ego "Those flies sure seem to like the stench!")) :flask-1-strength (actions/get-script entities (actions/do-dialogue entities :ego "He's buff enough as it is!" :ego "Any more muscles and I think he'll explode.")) nil)) :stand) :balloons (actions/start-animation screen (assoc (animation->texture screen balloon-stand) :x 75 :y 100 :baseline 140 :stand balloon-stand :script (actions/get-script entities (actions/talk entities :ego "Those look like the choicest of balloons."))) :stand) :bird (utils/make-bird screen (as-> [[82 235] [134 215] [185 235] [165 238] [220 225] [210 230] [250 235]] p (concat p (reverse p)))) :outside-particles (common/make-outside-particles) :flies (assoc (animation->texture screen flies-stand) :x 201 :y 175 :anim flies-stand :anim-start 0 :baseline 240 :scripts {:grass (actions/get-script entities (feed-bull entities)) :sack-lunch (actions/get-script entities (actions/walk-to entities :ego [168 150] :face :right) (actions/talk entities :ego "Maybe I can catch some of these flies.") (actions/remove-item entities :sack-lunch) (actions/play-animation entities :ego :squat) (actions/talk entities :ego "I think it's working!") (actions/play-animation entities :ego :squat) (actions/give entities :flies) (actions/talk entities :ego "Hopefully, they won't fly out of my backpack.")) :frog-legs (actions/get-script entities (actions/do-dialogue entities :ego "It's a little late for a last meal." :ego "Plus, these are just legs. This frog doesn't even have a mouth."))} :script (actions/get-script entities (actions/talk entities :ego "Those flies seem to be attracted to Angus' stench.")) )} :note (rooms/make-entity :note (assoc (utils/get-texture "outside-castle/note.png") :x 198 :y 66 :baseline 174 :script (actions/get-script entities (actions/walk-to entities :ego [210 79] :face :left) (actions/play-animation entities :ego :squat) (actions/give entities :note-2) (actions/remove-entity entities :note) (common/read-note-2 entities)))) :collision "outside-castle/collision.png" :scale-fn (utils/scaler-fn-from-image "outside-castle/scale-map.png" 0.20 1.00) :start-pos [259 80] :apply-state (fn [screen entities] (utils/fast-forward-particle (get-in entities [:room :entities :outside-particles])) (as-> entities entities (if (#{:night :sunrise} (get-in entities [:state :time])) (make-night entities) entities) (utils/play-sound! screen entities (get-in entities [:room :flies-sound :sound]) flies-vol 0.5 :loop))))))