{"id":15160107,"url":"https://github.com/itsvaibhavk/pong-variants","last_synced_at":"2026-01-19T06:34:00.260Z","repository":{"id":209464331,"uuid":"724128036","full_name":"ItsVaibhavK/Pong-Variants","owner":"ItsVaibhavK","description":"Variants of Pong (the game that is the subject of Week 0 of CS50G and the first assignment) that I made while experimenting with the base game code.","archived":false,"fork":false,"pushed_at":"2023-12-01T14:35:28.000Z","size":95,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-02-13T20:33:47.559Z","etag":null,"topics":["cs50","cs50g","edx","game","game-development","love2d","lua","pong","pong-game"],"latest_commit_sha":null,"homepage":"","language":"Lua","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/ItsVaibhavK.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-11-27T13:04:45.000Z","updated_at":"2023-11-30T15:32:18.000Z","dependencies_parsed_at":"2023-12-01T15:45:33.032Z","dependency_job_id":null,"html_url":"https://github.com/ItsVaibhavK/Pong-Variants","commit_stats":null,"previous_names":["itsvaibhavk/pong-variants"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ItsVaibhavK%2FPong-Variants","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ItsVaibhavK%2FPong-Variants/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ItsVaibhavK%2FPong-Variants/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ItsVaibhavK%2FPong-Variants/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/ItsVaibhavK","download_url":"https://codeload.github.com/ItsVaibhavK/Pong-Variants/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247712338,"owners_count":20983675,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["cs50","cs50g","edx","game","game-development","love2d","lua","pong","pong-game"],"created_at":"2024-09-26T22:21:31.627Z","updated_at":"2026-01-19T06:34:00.231Z","avatar_url":"https://github.com/ItsVaibhavK.png","language":"Lua","funding_links":[],"categories":[],"sub_categories":[],"readme":"# PONG VARIANT DEMOS\n1. [DONG - Demo video on YouTube](https://youtu.be/k3hmONNfAvk)\n2. [WRONG - Demo video on YouTube](https://youtu.be/RISLevwBapw)\n3. [DEAD WRONG - Demo video on YouTube](https://youtu.be/cNqA6Q7hTE4)\n\n# PREFACE\nI had been on a roll of completing [CS50](https://pll.harvard.edu/course/cs50-introduction-computer-science)'s courses on the [edX](https://www.edx.org/) platform, and had picked up skills in a variety of programming concepts, languages and applications.\u003cbr\u003eThat is when I came across [CS50G - CS50’s\nIntroduction to Game Development](https://cs50.harvard.edu/games/2018/).\n\nLike a lot of people, I do enjoy gaming here and there, but I had never really thought of peeking behind the curtain of what made games run underneath the hood.\u003cbr\u003eThis course and its teachers absolutely BLEW my mind.\n\nThe first week of this course covered [Pong](https://en.wikipedia.org/wiki/Pong), the famous 1972 arcade game. We were introduced to [Lua](https://www.lua.org/) and [LÖVE](https://love2d.org/), and a whole host of concepts\u003cbr\u003ethat are important to game development. The first assignment tasked us with making either of the paddles, or both, a \"computer-controlled\" paddle.\u003cbr\u003eUpon completing [this assignment](https://github.com/ItsVaibhavK/CS50G-2023/blob/main/pong/main.lua) successfully, I was left wanting... more. And so I decided I would tinker around with the game's base code that was provided to us\u003cbr\u003eand make my own variants of [Pong](https://en.wikipedia.org/wiki/Pong).\n\nMy first attempt resulted in [Dong - Death Pong](https://github.com/ItsVaibhavK/Pong-Variants.git). My second attempt gave rise to [Wrong](https://github.com/ItsVaibhavK/Pong-Variants.git). Here's how I executed the two variants.\n\n# DONG - DEATH PONG\nThe idea was simple. Using what we had learned so far in the first week, I would introduce a second ball into the game. Since we hadn't learnt how to add colors to sprites,\u003cbr\u003eI differentiated this second ball by turning it into an *outline* of a ball, instead of the regular filled-in ball. This ball was the DEATH BALL.\n\nA regular game of [Pong](https://en.wikipedia.org/wiki/Pong) ends when a player gets to the target score first. Players score when their opponents miss the ball.\u003cbr\u003eHowever, if a player made contact with the DEATH BALL, they would lose the game instantly via \"sudden death.\"\u003cbr\u003eHere's how I turned that logic into code.\n\n## EXECUTION\n*Note: Players can control the paddles using W and S keys for Player 1, and the up and down arrow keys for Player 2.*\n\n### APPEARANCE\nI needed the DEATH BALL to be distinguishable from the regular ball. I achieved this by turning the DEATH BALL into its own class,\u003cbr\u003ewhere I could then add the following to its render function to get an *outline* ball instead of a *fill-in* ball:\u003cbr\u003e`love.graphics.rectangle('line', self.x, self.y, self.width, self.height)`\n\n### WALL COLLISION\nThe regular ball only \"bounced\" back from the vertical edges, as if it went past the horizontal edges, that meant a point for one of the players.\u003cbr\u003eI needed the DEATH BALL to keep bouncing around all 4 edges **until** it made contact with one of the players' paddles.\u003cbr\u003eSo I modified its collision behavior along the X axis using:\n```\nif deathball.x \u003c= 0 then\n    deathball.x = 0\n    deathball.dx = -deathball.dx\nend\n```\nfor the left edge, and:\n```\nif deathball.x \u003e= VIRTUAL_WIDTH - 4 then\n    deathball.x = VIRTUAL_WIDTH - 4\n    deathball.dx = -deathball.dx\nend\n```\nfor the right edge.\n\n### SUDDEN DEATH\nNow, for how the game would conclude via sudden death. The game could still end via the normal fashion if both players successfully avoided the DEATH BALL\u003cbr\u003ethroughout their playthrough and one of the player scored the game-ending 10 points.\u003cbr\u003eBut **if** one of the players made contact with the DEATH BALL, the opponent's score would instantly be set to 10, triggering the game-ending condition of a winning score.\u003cbr\u003e\nThis was executed with the following block of code:\n```\nif deathball:collides(player1) then\n    player2Score = 10\n    winningPlayer = 2\n    sounds['score']:play()\n    gameState = 'sudden death'\nend\n```\nand a similar code block from the other player's perspective.\u003cbr\u003eI also wanted a different game-over screen if a player won via sudden death, compared to the regular game-over screen. That screen was accomplished using:\n```\nelseif gameState == 'sudden death' then\n    love.graphics.clear(1, 0, 0, 255/255)\n    love.graphics.setFont(largeFont)\n    love.graphics.printf('Player ' .. tostring(winningPlayer) .. ' wins!',\n        0, 10, VIRTUAL_WIDTH, 'center')\n    love.graphics.printf('SUDDEN DEATH',\n        0, 30, VIRTUAL_WIDTH, 'center')\n    love.graphics.setFont(smallFont)\n    love.graphics.printf('Press Enter to restart!', 0, 50, VIRTUAL_WIDTH, 'center')\n```\n\n## CONCLUSION\nAnd there it was! My first attempt at experimenting and modifying a game to execute my own ideas!\u003cbr\u003e*What a RUSH.*\n\n# WRONG\nAfter successfully creating [Dong - Death Pong](https://github.com/ItsVaibhavK/Pong-Variants.git), I wanted to create a [Pong](https://en.wikipedia.org/wiki/Pong) variant whose gameplay would be... *unhinged*. The gameplay was so \"broken\",\u003cbr\u003eI decided to name this variant [Wrong](https://github.com/ItsVaibhavK/Pong-Variants.git). Here's how it works:\n1. There is only one ball in play.\n2. The only sprites that get affected in this variant are the players' paddles.\n3. When the ball makes contact with a player's paddle, it **MAY** trigger a random side effect.\n4. The side effects can be either a positive effect on self, or a negative effect on the opponent.\n5. The side effects are selected at random and cannot be chosen by the players.\n6. All side effects are reset at the **END** of a game only.\n7. It is not necessary that a side effect is triggered on every collision, gameplay may also proceed normally without side effects.\n8. Side effects can stack (for example, paddle size gets halved **AND** paddle movement controls get inverted).\n9. A side effect will continue as long as a new side effect is not triggered, or the game has not ended.\n\nThe side effects (or power-ups, whatever you'd like to call them) are:\n1. Your own paddle becomes larger, twice the original height.\n2. The opponent's paddle becomes smaller, half the original height.\n3. The opponent's paddle controls are inverted (up becomes down, down becomes up).\n4. The opponent's paddle speed is halved.\n\n## EXECUTION\n*Note: Players can control the paddles using W and S keys for Player 1, and the up and down arrow keys for Player 2.*\n\nFirst, I abstracted away the logic behind how the ball moves after colliding with a paddle into two separate functions to avoid cluttering up `love.update(dt)`.\n```\nfunction player1CollisionBallMovement()\n    ball.dx = -ball.dx * 1.03\n    ball.x = player1.x + 5\n    if ball.dy \u003c 0 then\n        ball.dy = -math.random(10, 150)\n    else\n        ball.dy = math.random(10, 150)\n    end\n    sounds['paddle_hit']:play()\nend\n\nfunction player2CollisionBallMovement()\n    ball.dx = -ball.dx * 1.03\n    ball.x = player2.x - 4\n    if ball.dy \u003c 0 then\n        ball.dy = -math.random(10, 150)\n    else\n        ball.dy = math.random(10, 150)\n    end\n    sounds['paddle_hit']:play()\nend\n```\nNext, I used `math.random(0, 4)` to decide what side effect needed to be triggered. I stored this result in two variables, `deranged1` and `deranged2`,\u003cbr\u003eto have better control over side effects that were to be triggered on self, and side effects that were to be triggered on the opponent.\n### PADDLE SIZE EFFECTS\nHere's the code snippet of how paddle size changes were decided from the perspective of Player 1:\n```\nif ball:collides(player1) then\n    deranged1 = math.random(0, 4)\n    -- normal play\n    if deranged1 == 0 then\n        player1CollisionBallMovement()\n    -- player1 gets large paddle\n    elseif deranged1 == 1 then\n        player1.height = 40\n        player1CollisionBallMovement()\n    -- player2 gets small paddle\n    elseif deranged1 == 2 then\n        player2.height = 10\n        player1CollisionBallMovement()\n    -- these effects are programmed into the paddle movement\n    -- section of the code\n    else\n        player1CollisionBallMovement()\n    end\nend\n```\n* If `deranged1` == 0, gameplay was normal with no side effects.\n* If `deranged1` == 1, then Player 1's paddle would become twice as large.\n* If `deranged1` == 2, Player 2's paddle would become half its original size.\n* If `deranged1` == 3 or 4, gameplay with respect to paddle size remained unchanged. This was used to change paddle movement.\n\nA similar block of code controlled side effects from the perspective of Player 2.\n\n### PADDLE MOVEMENT EFFECTS\nHere's how paddle movement effects were decided, from the perspective of Player 1:\n```\n-- player1's controls get inverted\nif deranged2 == 3 then\n    if love.keyboard.isDown('s') then\n        player1.dy = -PADDLE_SPEED\n    elseif love.keyboard.isDown('w') then\n        player1.dy = PADDLE_SPEED\n    else\n        player1.dy = 0\n    end\n-- player1's paddle speed is halved\nelseif deranged2 == 4 then\n    if love.keyboard.isDown('w') then\n        player1.dy = -PADDLE_SPEED / 2\n    elseif love.keyboard.isDown('s') then\n        player1.dy = PADDLE_SPEED / 2\n    else\n        player1.dy = 0\n    end\n-- player1's movements are normal\nelse\n    if love.keyboard.isDown('w') then\n        player1.dy = -PADDLE_SPEED\n    elseif love.keyboard.isDown('s') then\n        player1.dy = PADDLE_SPEED\n    else\n        player1.dy = 0\n    end\nend\n```\nNotice how paddle movement effects for Player 1 were decided using Player 2's `deranged 2 = math.random(0, 4)` values.\n* If `deranged2` == 3, Player 1's paddle controls were inverted (up is down, down is up).\n* If `deranged2` == 4, Player 1's paddle speed was halved.\n* For all other values, Player 1's paddle movement was left unchanged.\n\nA similar block of code controlled side effects from the perspective of Player 2.\n\n## CONCLUSION\nThis was only the first version of the variant [Wrong](https://github.com/ItsVaibhavK/Pong-Variants.git). I think it would truly make the game *intense* if I were to add in the DEATH BALL element to [Wrong](https://github.com/ItsVaibhavK/Pong-Variants.git)\u003cbr\u003efrom my first variant, [Dong - Death Pong](https://github.com/ItsVaibhavK/Pong-Variants.git). Just *imagine*.\n\n*Update! I did finally make the variant I was talking about. Check it out in the section below!*\n\n# DEAD WRONG\n\nThere is not much to explain for this variant, it combines the concepts and rules I came up with when I created [Dong - Death Pong](https://github.com/ItsVaibhavK/Pong-Variants.git) and [Wrong](https://github.com/ItsVaibhavK/Pong-Variants.git) (hence the name, [DEAD WRONG](https://github.com/ItsVaibhavK/Pong-Variants.git)).\n\nTo understand how [DEAD WRONG](https://github.com/ItsVaibhavK/Pong-Variants.git) works, you can read up on the mechanics that I've detailed above in the first two [Pong](https://en.wikipedia.org/wiki/Pong) variants I created.\n\nThe only change I made has to do with the DEATH BALL's appearance. I set its color to red using `love.graphics.setColor(1, 0, 0, 1)`,\u003cbr\u003eand instead of it being an *outline* like it was in [Dong - Death Pong](https://github.com/ItsVaibhavK/Pong-Variants.git), I turned it into a *filled-out* ball using\u003cbr\u003e`love.graphics.rectangle('fill', self.x, self.y, self.width, self.height)`.\u003cbr\u003eThese changes are visible in the `Death.lua` file.\n\nNow, *this* is a *frustratingly* fun game to mess about on!\n\n\n# NOTES\nThe files for the variants do not contain comments explaining what the rest of the code is doing, only comments pointing out the parts I had added for my idea.\u003cbr\u003eThis is by design, to keep the code as neat as possible. If you're interested in the fully commented version of the code, or if you'd like to watch the lecture\u003cbr\u003ethat explains the original base code in depth, allow me to point you in the right direction:\u003cbr\u003e\n1. [Pong code with comments](https://github.com/ItsVaibhavK/CS50G-2023/blob/main/pong/main.lua)\n2. [Lecture](https://cs50.harvard.edu/games/2018/weeks/0/)\n\n# CREDITS\nAs always, I cannot begin to express my gratitude for the people behind all the [CS50](https://pll.harvard.edu/course/cs50-introduction-computer-science) courses.\u003cbr\u003eIn less than a year, I have gone from knowing nothing about programming to being able to write my own programs, web apps, create my own databases, and now - GAMES!\n\nThank you, [Colton Ogden](https://www.linkedin.com/in/colton-ogden-0514029b), for taking us through this course, and all the staff members at [CS50](https://pll.harvard.edu/course/cs50-introduction-computer-science), for instilling the love of programming in us!\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fitsvaibhavk%2Fpong-variants","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fitsvaibhavk%2Fpong-variants","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fitsvaibhavk%2Fpong-variants/lists"}