How Pathfinding Works in Games!

Поделиться
HTML-код
  • Опубликовано: 24 ноя 2024

Комментарии • 156

  • @TottyRops
    @TottyRops 8 лет назад +17

    We learned about this in the Artificial Intelligence module of my degree. One of the assignments was to solve the Travelling Salesman Problem (TSP) using a genetic algorithm. I wrote a solution in Javascript so it can run on almost anything that has a browser. Genetic Algorithms are also used in game path finding, as they can be quite fast and pretty accurate!

    • @YEASTY_COMMIE
      @YEASTY_COMMIE 8 лет назад +2

      genetic algorithm ? you mean trying random path and keeping the best ones ?

  • @henriklarsen8193
    @henriklarsen8193 8 лет назад +54

    Very good stuff! More detail would be welcome, I think this kind of video can be a lot longer without loss of interest!

  • @emessar
    @emessar 3 года назад

    Thank you. This is one of the better videos on how pathfinding actually works. Most videos are just tutorials of how to utilize a nav mesh in game engine X. Having taken discrete math, the idea of boiling a surface down to a series of nodes makes a lot of sense. Thank you.

  • @janglaser6130
    @janglaser6130 6 лет назад

    I would like to add, that dijkstra's algo can be used to precompute graph for start node A. Then, any query that starts in path node A but ends whereever you want, can use the precomputed graph. Like this, you can keep list of precomputed graphs for various start nodes. (depends on game / situations). :)

  • @llywyllngryffyn8053
    @llywyllngryffyn8053 8 лет назад

    Watching your videos is like reliving my CSI classes vicariously.

  • @ianmclean9382
    @ianmclean9382 7 лет назад +1

    great explanation! I adore your very real world examples for explaining different mechanisms.

  • @KilnFirelink
    @KilnFirelink 9 лет назад

    You slightly simplified the darkroot garden glitch as it is because the AI (In this case the humanoid AI meant to act like a player as most enemies in the game have different aggro and behaviour) knows you have bottleneck it so it is trying to get the jump on you as by driving to its death. If you don't break off from the enemies when running they will simple follow you inside of trying to find a way to sneak up on you so this is more a behavioural exploit than path finding after for the crystal golems they use a very simple shortest route to the player method so they only use one path finding method as like most simple enemies they only attack forward withing aggro range and cannon leave it to find away around as they would break aggro, This is beast found with the "super aggressive mod" that would stops this problem to only increasing agrro range. Ever way great video and subbed, keep up the great work.

  • @FSF87
    @FSF87 8 лет назад

    Subway stations in GTAV (particularly Portola Drive) is a great example of this. You can stand in the tunnels, take shots at passengers on the platform with a sniper rifle, and the police gather around the street above you, allowing you to rack up kills to increase the amount of ammo you can carry without the inconvenience of getting arrested or killed, or having to outrun the police.

  • @ElboxD
    @ElboxD 8 лет назад +1

    and just 14k views? You deserve way more... Thanks for making these absolutely amazing videos!

  • @algi1
    @algi1 8 лет назад +5

    OMG, the Dragoons of StarCraft 1 waiting for each other at bridges! :O

  • @lucetubegplusstillsux2678
    @lucetubegplusstillsux2678 8 лет назад +3

    There's also the Pad/preset system that Perfect Dark, and some other Nintendo 64 games used. Where there would be hundreds of points on a map and the AI would run to the point, then move to the next one.
    The unique thing is the navigation presets would be manually programmed, so that if there was a preset running into a wall, there'd be no direct path to it, so the AI never ran off cliffs, since someone on the dev team specifically ensured they couldn't.

    • @kollerjon
      @kollerjon 8 лет назад

      +Lucetube GPlusStillSux Is that implementation similar to Half Life 2?

    • @lucetubegplusstillsux2678
      @lucetubegplusstillsux2678 8 лет назад

      Probably, I'm not quite familiar with HL2's system though

    • @seigeengine
      @seigeengine 6 лет назад

      And how is that different? It's the same idea: a graph is constructed than an algorithm searches to find a path across.

  • @Sangheilitat117
    @Sangheilitat117 9 лет назад +5

    VaatiVidya brought me here, and I was not disappointed. This is an insightful look into an often poorly understood mechanic.

    • @TheHappieCat
      @TheHappieCat  9 лет назад

      Sangheilitat117 From where did this get linked by VaatiVidya? Or did you find it from the subreddit?

    • @Sangheilitat117
      @Sangheilitat117 9 лет назад +2

      Ah, he linked it on his tumblr actually.

    • @TheHappieCat
      @TheHappieCat  9 лет назад

      Sangheilitat117 Woah!

    • @MRabbitFrog
      @MRabbitFrog 9 лет назад

      Sangheilitat117 Was it before all the plagiarism stuff flooded or after?

    • @Sangheilitat117
      @Sangheilitat117 9 лет назад

      I honestly have no idea what you're talking about.

  • @colepeterson5392
    @colepeterson5392 8 лет назад

    you should make a Dijkstra's algorithm explanation video please!!! all the ones on youtube are weird and you explain things so well! thanks.

  • @CiaphasKirby
    @CiaphasKirby 9 лет назад +1

    Fascinating stuff, I would love to see more of these.

  • @alekxsander
    @alekxsander 9 лет назад +2

    through "nodes", it became much easier to understand! thanks mis!! :)

    • @TheHappieCat
      @TheHappieCat  9 лет назад +3

      alekxsander eduardo Glad it helped! Thanks for watching!

    • @Gizego
      @Gizego 7 лет назад

      For my game, i am going to use an easier system. Its a tile mapping game so, it determines the distance to the player, it checks for obstacles and if it finds one it tries to go around it

  • @DanielPerez-fm9vy
    @DanielPerez-fm9vy 7 лет назад

    When it comes about this topic, it's impossible not to mention StarCraft. Nice presentation, with examples and hilarious bugs from Dark Souls. That's the dream!

  • @magnusm4
    @magnusm4 4 года назад

    There's a fun video with a developer of C&C Tiberian Sun where he explains that the way they made the ai more efficient for processors was to not put allies into account and simply tell them to move if they collide. Thought of this when you said they just wait until the unit moves to continue.

  • @glez5288
    @glez5288 8 лет назад

    just found this channel, its amazing! much love from Mexico

  • @briansmith1288
    @briansmith1288 9 лет назад +1

    That was pretty interesting. It is fun to know the underlying principles. I just know a few places in the game where pathing is lethal. Much to my delight.

  • @sagarpatel2630
    @sagarpatel2630 8 лет назад

    This is my first comment on youtube. Saw 2-3 videos of this channel, and I am in love with you 😀.

  • @MrDrescher86
    @MrDrescher86 8 лет назад

    I have only 2 things to say. 1 your videos are amazing. I can only imagine how good they are for people without prior knowledge. 2 Dammit! I thought my idea of making simple instructional game development videos were unique 😄 guess it is good I didn't start yet

  • @mintyjodpuhrs
    @mintyjodpuhrs 9 лет назад

    Really interesting, definitely looking forward to the next one!

  • @moodyplus
    @moodyplus 8 лет назад

    this channel is everything

  • @nosh247
    @nosh247 8 лет назад +1

    wow happie cat your videos are very educational!
    Great Job explaining programming principles and how things work...i have a new perspective on some of those subjects thanks to you :D Finite State machine explanation was excellent :D

  • @JoSaLoFoPoT
    @JoSaLoFoPoT 9 лет назад

    That was really interesting! The cost based system reminds me of link state routing over computer networks, it's cool to see it applied here. I think I'll peruse this channel further :)

  • @medimadeddineboubekeur8058
    @medimadeddineboubekeur8058 Год назад

    Thank you sm I’ve been searching for ages to this answer

  • @AymanJundi
    @AymanJundi 8 лет назад +1

    gosh that was so neatly explained.. great channel.

  • @MarcusNorton1024
    @MarcusNorton1024 8 лет назад

    Thanks for creating this video! It is very interesting / enlightening!

  • @winterfallgame
    @winterfallgame 8 лет назад +1

    Very disturbing: we have the same handwriting, including irregularly written e or a. That aside, this is a very nice video, as a game designer I enjoyed it very much. Very educatively put!

    • @snowy8321
      @snowy8321 8 лет назад

      LOL, compare it to Me and tekking101, he's eerily similar to me. He looks like me, acts like me, and even a bit of his life stories are like mine.

  • @zzzzzmmm6539
    @zzzzzmmm6539 9 лет назад +4

    that graph u drew, reminded of the Signal-Flow Graph in control theory, the only difference being what u call edges r actually called paths in SFG

    • @TheHappieCat
      @TheHappieCat  9 лет назад +5

      Rebel Raime Yeah, high-level and low-level stuff share many of the same models. It's pretty cool.

  • @Noobwarriking
    @Noobwarriking 9 лет назад +1

    very cool video
    more please!

  • @portnoy256
    @portnoy256 8 лет назад +1

    Snake! :)
    Thank you for the unique MGS alert sound!

  • @p3rcey
    @p3rcey 9 лет назад +1

    Really interesting from a development perspective

  • @pokashine
    @pokashine 9 лет назад +10

    I came for the cat. Subscribed for the cat. And will stay for the cat.
    Oh, and videos!
    ...like this one. Good stuff!

  • @ayushman_sinhaa
    @ayushman_sinhaa 3 года назад

    Finally I learnt to pronounce Dijkstra's algorithm

  • @Aikaosu
    @Aikaosu 9 лет назад +3

    Yo that cat graph was rad as shit.

    • @ReyndommVideos
      @ReyndommVideos 9 лет назад

      Krasnoya Ronin Your avatar is also rad as shit.

    • @lu-chan1745
      @lu-chan1745 7 лет назад +1

      shit is not red 😡

    • @lu-chan1745
      @lu-chan1745 7 лет назад +1

      shit is not red 😡

    • @Manas-co8wl
      @Manas-co8wl 7 лет назад +1

      shit is brown... and rad

  • @2sahn234
    @2sahn234 6 лет назад

    well Pathfinind Algorithm has been imporeved now. since then its not completlty hardcoded anyway.. it just takes a simplified version of mesh with places marked as allowable and forbidden which can dynamically be triggered or switched.and then bots are configured with set of automated queries with a different buffer, that makes them aware of possible routes it has to reach , since path distance has already be calculated, hence so itll move like there . And yes noth everytime we need it to trace the shortest path and so its upto game logic ;) to mark places as forbidden forcing system to use longest path.

  • @glouburgorilla2401
    @glouburgorilla2401 3 года назад

    That was really helpful ; I am doing college project about pathfinding Visualizer I don't know the Topic is something just deep ;
    Thanks video just help me to understand pathfinding more effective ;

  • @danroamer
    @danroamer 9 лет назад

    She got my like at: "Obligatory Praise the sun", but seriously, cool stuff in the vid.

  • @xiangzhang8508
    @xiangzhang8508 8 лет назад

    love your explanation.

  • @ZaphyrVonGenevese
    @ZaphyrVonGenevese 8 лет назад

    Awesome video. You are great! Thank you

  • @gophermaster
    @gophermaster 9 лет назад

    Super informative, thanks!

  • @virtualcosmos2340
    @virtualcosmos2340 8 лет назад

    i know the* algorithm but the pathfinding in starcraft 2 follow surprise me, It's so smooth and precise... how could the modules are disposed in the map? are there thousands of very little modules for everywhere or could have another system like modules inside of modules?

  • @rock00dom
    @rock00dom 9 лет назад

    You've explained it very well, thank you! ^^

  • @isaiaslafon9329
    @isaiaslafon9329 8 лет назад

    I find your videos, Ur so awesome. THX for doing this videos. (I'm not a native speaker, so sorry if I make some mistake in my text)

  • @Personincrowd
    @Personincrowd Год назад

    Cool and informative vid. Thanks

  • @xdario10
    @xdario10 9 лет назад +1

    Loved this thanks!!

  • @menosferato
    @menosferato 9 лет назад +1

    I knew about the A* algorithm, but I think it's not doable for large scale games to run it in runtime for several units at once. Great tutorial.

    • @TheHappieCat
      @TheHappieCat  9 лет назад +3

      menosferato Many games do use A*, it's Dijkstra's that would take awhile for each unit :) Thank you!

    • @luisoncpp
      @luisoncpp 8 лет назад

      A* is pretty useful even for large games, and the path finding algorithm in the graph usually is not the big challenge for the path finding AI.
      Both A* and Dijkstra can process only few of the nodes in each iteration of the gameloop.
      Bigger challenges is choose how to create the navigation map, how often recalculate the path finding in case that the target moves, what to do if the agent find an obstacle in an already planned path or how to deal with the momentum.
      A different algorithm may be required if there are a lot of agents moving at the same time (for example, the Zerg).

  • @RadCommieGamer
    @RadCommieGamer 8 лет назад

    I like your videos so much! Thank you!

  • @Karvistico
    @Karvistico 9 лет назад

    Thank you for doing this!

  • @sarthakshah77
    @sarthakshah77 7 лет назад

    I didn't find "Computer architecture" Playlist in your play list.

  • @henbomb9826
    @henbomb9826 6 лет назад

    The most accurate and fastest pathfinding algorithm is A* with Euclidean distance

  • @BruceWayne-gv9zs
    @BruceWayne-gv9zs 8 лет назад

    Ive noticed bethesda games dont have this problem despite being much larger. Ai routines must account for things like height. If you run up some stairs the enemies always run up after you, not into a wall below youm

  • @Randall_Kildare
    @Randall_Kildare 8 лет назад

    would it be conceivable to program mob AI to work 'clairvoyantly' in reverse from the target destination, eliminating path selection backwards. Ideally, this would not only make MUCH smarter mobs, but allow for some very complex mechanics to be selected between confrontation & aggro.
    thoughts on this..?

  • @Lobbogurke
    @Lobbogurke 8 лет назад

    :'D I was already in the act of grabing my mouse and twitched back at the "BUT WAIT" :'D

  • @kim15742
    @kim15742 8 лет назад +1

    Yay, A*, that is what I will be writing a school paper about!

    • @liesdamnlies3372
      @liesdamnlies3372 8 лет назад +1

      Mein Kanal! Just stay a healthy distance away from the event horizon.

    • @kim15742
      @kim15742 8 лет назад

      ***** That means?

    • @liesdamnlies3372
      @liesdamnlies3372 8 лет назад +1

      Mein Kanal!
      Well, -10 nerd cred for you: en.wikipedia.org/wiki/Sagittarius_A*

    • @kim15742
      @kim15742 8 лет назад

      ***** Ah! Also, when you search for D*, you get you get some sort of radios :)

  • @Hlidskialf
    @Hlidskialf 9 лет назад +1

    Great video

  • @Felhek
    @Felhek 8 лет назад

    awesome channel. thank you.

  • @Beatsbasteln
    @Beatsbasteln 3 года назад

    programming tutorials with cat drawings? fuck yeah!

  • @16dancechik
    @16dancechik 9 лет назад

    You're amazing! Thank you :)

  • @89elmonster
    @89elmonster 9 лет назад

    Can you explain to me how people find glitches in games like call of duty? In multilayer maps people find the weirdest things that I wouldn't even come close to finding out. How do people do this? Do they know where the grid mesh for the AI is(For zombie mode)?

  • @KaletheQuick
    @KaletheQuick 7 лет назад +2

    PRAISE THE SUN!
    More dark souls plz.

  • @imrequael
    @imrequael 8 лет назад

    you are so talented

  • @ethanwasme4307
    @ethanwasme4307 8 лет назад +3

    Reminds me of gta 3 where you could get 6 stars, go onto the container ship and just watch the cop cars drive into the water, provided lots of laughs

  • @revolutionnetwork7709
    @revolutionnetwork7709 8 лет назад

    Amazing video

  • @RaidenHeaven
    @RaidenHeaven 8 лет назад

    6:00 actually no. It just doesn't calculate the collusion that happens. If there was no collusion the AI would jumped down without falling off the edge. As the enemy is jumping down it steps on the characters head and then it's forced keep on walking forward.

  • @Ruftinator
    @Ruftinator 7 лет назад

    What happens when you put an NPC on a Mesh that isn't a NavMesh?

  • @OthmanAlikhan
    @OthmanAlikhan 8 лет назад

    Thanks for the video =)

  • @huizhou47
    @huizhou47 9 лет назад

    The devs didn't patch this, because it is useful for bad players or players that need lots of souls. They could easily have patched it so that they back away from the corners of the map.

  • @shun2240
    @shun2240 7 лет назад

    hey happie cat can you do a video on total war eats so much compute power

  • @abetry
    @abetry 8 лет назад

    Excellent

  • @NikhilKumar-fj2dg
    @NikhilKumar-fj2dg 7 лет назад

    I got it!!!!
    Thanks for making things easier to understand
    #TheHappieCat
    :-)

  • @Zydraxis
    @Zydraxis 8 лет назад

    you should do gameplay!

  • @kanseidorifto2430
    @kanseidorifto2430 6 лет назад

    MY TIMESKIP IS UNBEATABLE!
    MY TIMESKIP IS UNBEATABLE!
    MY TIMESKIP IS UNBEATABLE!
    MY TIMESKIP IS UNBEATABLE!
    MY TIMESKIP IS UNBEATABLE!
    MY TIMESKIP IS UNBEATABLE!
    MY TIMESKIP IS UNBEATABLE!
    MY TIMESKIP IS UNBEATABLE!
    ....."Time to make the donuts."

  • @MrChaitanaya
    @MrChaitanaya 6 лет назад

    Great vid

  • @tanan1771
    @tanan1771 7 лет назад +2

    Or... just go directly to the player.
    if (botX < X) {
    botX++;
    } else {
    botX--;
    }
    if (botY < Y) {
    botY++;
    } else {
    botY--;
    }
    better?

  • @jensons88
    @jensons88 9 лет назад

    Very informative. Graphics today in video games are very advanced and more realistic. In my opinion, pathfinding is still way too far complicated as compared to how a person does it.

  • @Sirtuta1
    @Sirtuta1 8 лет назад

    could you explain why blighttown has frame rate issues?

    • @MadDeuceJuice
      @MadDeuceJuice 8 лет назад +1

      +Arthur Ferreira they crammed it with particle effects that the engine couldn't handle

  • @Toudreyte6501
    @Toudreyte6501 8 лет назад +5

    I didn't understand how the path is found by the second way to do :c

    • @kohtlajarve7703
      @kohtlajarve7703 8 лет назад +4

      A-star algorythm uses array structure. There we check all array points, and then find the way. Some books can understand it better than me.

    • @YEASTY_COMMIE
      @YEASTY_COMMIE 8 лет назад +2

      each node have it's own "distance traveled to reach it" variable, when 2 path lead to the same node the path with the highest "dttri" is removed

    • @prohacker5086
      @prohacker5086 7 лет назад

      Each box has their own "cost" (distance between 'start' and 'end'). If 2 path leads to same box, the one with lowest Start Distance (G Cost) gets choosed.

    • @JoseTorres-tr6od
      @JoseTorres-tr6od 6 лет назад +1

      A* is extremely useful for spatial distance since the "straight line" heuristic with respect to the space has the property of consistency ( therefore also admissible ) and you can ignore repeated nodes ( by different path ) and assume smallest cost node contains the best solution.
      Edit:
      With that assumption you don't have to check every node in the graph which otherwise for infinite ( or really big ) search spaces would take a long time.
      However if you are not sure you heuristic is consistent it is rather difficult to proof it is, and even more so to find one.

  • @takealook5012
    @takealook5012 7 лет назад

    Very Nice You have saved my day beautifull

  • @dailydols
    @dailydols 8 лет назад

    That Dijkstra's looks like Viterby's.

  • @StrongJoshua
    @StrongJoshua 9 лет назад

    A* is so useful

  • @muhammedabdul-ghaffar8765
    @muhammedabdul-ghaffar8765 8 лет назад

    This is interesting.

  • @moviesynopsis001
    @moviesynopsis001 5 лет назад

    You have restored my faith in women, thank you.

  • @andreatucci6356
    @andreatucci6356 8 лет назад

    awesome.

  • @bharathmettu4252
    @bharathmettu4252 6 лет назад

    You are awesome

  • @ErickTG
    @ErickTG 9 лет назад

    You made the Golems look like idiots! lol Nice video! =D

  • @put_istine
    @put_istine 8 лет назад +14

    Problem with pathfinding algorithm in 3D games is that they are using 2D algorithm for pathfinding.
    Two guys have fallen off a cliff not because of pathfiniding (which is fine in this case), but because they are not aware of the cliff (which is AI issue, not just pathfinding).
    Solution for 3D pathfinding is to use "regions", and mark node for height difference, so pathfinding will include 3rd parent node (difference between 2 levels in height or walkable path for high/low ground). But this algorithm could be very expensive so it's best to mark (by mapping) floors/spots.
    However, illustrations for Dijkstra and A* algorithm is wrong. Node 2 and 4 is on the wrong side for A* example, and Dijakstra algorithm is not faster and harder for "us programmers". It's pretty much opposite, because Dijkatra algorithm explores a much more nodes which is not faster (which depence of A heuristics).

    • @luisoncpp
      @luisoncpp 8 лет назад +2

      Actually both Dijkstra and A* are not dependent if the geometry is 2D or 3D and they can even be used for path findings for more than 3 dimensions.
      The main difference is about how to create the graph in both algorithms and in the case of A* is also which heuristic choose for distance estimation.
      Once the graph is created both algorithms don't care about the geometry of the original space.
      Also, when she said that Dijkstra is faster and harder, she was comparing Dijkstra to brute force, not to A*.
      EDIT: Just another point: the exploit that she showed in Dark Souls was not only about 2D vs 3D, I think was more about creating the nodes only representing the positions and ignoring the momentum.
      Take in account the momentum it's a huge problem in the path finding for videogames and there is not a clear solution (as I understand, most times the solution used is to create one navigation map with very few nodes, find the path in that graph and then between each pair of nodes do a completely different algorithm that takes in account the momentum(they call it "the local planner").

    • @put_istine
      @put_istine 8 лет назад

      That is why I mention regions mapping with height difference, walkable ground, including 3rd node. Currently, this is the best (and almost bug free) algorithm.

    • @hansmeier2802
      @hansmeier2802 8 лет назад

      I also thought that it is the momentums falt in the darksouls example. I think that stff like that is really difficult to programm. for example:
      you have a cliff and you can fall if you have enoth momentum to a ledge on the other side. it would be really hard for an Ai to realise that the fastest way is to first go a step back in order to exelerate longer. that is hard but possible. now emagine there is also wind changing in intensety and changing the momentum of the ai.
      As a sidenote: I love mincrafts zombie Ai, there are so many ways to make it run away from you just to walk into an obsticle ;-)

    • @seigeengine
      @seigeengine 6 лет назад

      The problem, as mentioned, seemed more like it was that the enemies will try to go at you for an attack within a certain distance, and that this movement trips them off the edge. It's not a part of normal path-finding. I'd imagine the graph isn't actually linked across those height differences.

  • @rodrigoappendino
    @rodrigoappendino 8 лет назад

    What about GTA GPS pathfinding?

    • @uberdude8529
      @uberdude8529 8 лет назад

      The method she explained isn't limited to Dark Souls, so GTA probably uses a similar system.

    • @ImperativeGames
      @ImperativeGames 8 лет назад

      Most games use similar approach, but it's not the only one..

    • @luisoncpp
      @luisoncpp 8 лет назад

      I'm almost sure that GTA GPS uses A*, mainly because it's a very standard algorithm and I don't find any reason for trying another approach.

  • @sleeping_ghxst
    @sleeping_ghxst 8 лет назад

    subbed

  • @TheBcoolGuy
    @TheBcoolGuy 8 лет назад +1

    I like your videos so far! You're also absolutely gorgeous! :D

    • @ashleyketchum2739
      @ashleyketchum2739 8 лет назад

      TheBcoolGuy go away shes mine.

    • @TheBcoolGuy
      @TheBcoolGuy 8 лет назад

      Ryan Noble Hahaha. She's neither of us', mate. I just wanted to tell her that. I know you know this, but whatever, man.

  • @DivusMeta
    @DivusMeta 8 лет назад

    Dark Souls Forever! (You Died!)

  • @gundam7463
    @gundam7463 8 лет назад

    Legal, Cool :)

  • @anonymousnearseattle2788
    @anonymousnearseattle2788 6 лет назад

    Nah, what's really happening here is that the NPCs realized their existence was pointless, so they committed suicide by jumping off the ledge. :-)

  • @papachanka658
    @papachanka658 7 лет назад

    Damn right dark souls is a good game. I made it.

  • @jayp1206
    @jayp1206 9 лет назад

    I wish I had a cat

  • @Vesperon
    @Vesperon 8 лет назад

    zoink!!

  • @OwO-
    @OwO- 8 лет назад +3

    3:00 "much more faster" xD

  • @TechXSoftware
    @TechXSoftware 8 лет назад

    Just because your a girl and u like tech stuff doesn't mean, never mind, date me.

  • @dusty_fusty3568
    @dusty_fusty3568 8 лет назад

    i think im in love, haha
    way to go lady!!