00
Days
00
Hours
00
Mins
00
Secs
Discord Bots Challenge / Ends November 26
๐ŸŽ Prizes: Discord Swag, Hacker Plans, Repl Talk Cycles
Posts
Pinned
Discord Bot Competition
# In Partnership With Discord: Discord Bot Competition ![repl robot](https://i.imgur.com/91wYFfT.jpg) ## General Competition Information The way it works is that you build and deploy Discord bots with Repl.it and then submit your bot here on the challenge board. If you're new to building bots with Repl.it then start by reading one of the following guides: - [Building a Discord Bot with Python and Repl.it ](https://repl.it/talk/learn/Tutorial-Building-a-Discord-Bot-with-Python/6658) - [Building a Discord bot with Node.js and Repl.it ](https://repl.it/talk/learn/Tutorial-Building-a-Discord-bot-with-Nodejs/6659) - [Building a Discord bot in Ruby](https://repl.it/talk/learn/Making-a-Discord-bot-in-Ruby/8427) Or if you're impatient then start by forking [this example](https://repl.it/@amasad/discord-bot-example) and following the instructions in the comments. You can join the [Repl.it Discord Server](http://discord.gg/346Tapr) and ask the moderators to add your bot to develop it with other Repl.it users. Or you can develop it on your own server. Feel free to ask questions on the here on the [Ask](https://repl.it/talk/ask) board or in the Discord server #help channel. **Competition starts**: Monday, Nov 12 12:01 PM UTC **Competition ends**: Monday, Nov 26 12:01 PM UTC ## Prizes Instead of first, second, and third place prizes, this time, there will be **five winners** selected by the Repl.it team. Each winner will receive: * Discord swag (t-shirt and stickers) * Three months of [hacker plan](/pricing) for free (worth $21) * 100 extra cycles (upvotes) added to their account ![Bella+Canvas+3650+-+Discord+Logo+-+Black+(Front)](https://storage.googleapis.com/replit/images/1541901348125_b78ac87fafa512320da0951b12cddac8.pn) These five winners will be picked for these categories: * Fun (e.g. a game bot) * Utility (e.g. a bot that helps evaluate code) * Moderation (e.g. a bot that helps manage roles) ## Submission Criteria: In order to be considered, your submission: * Must be a discord bot * Must be hosted on Repl.it * Must be age-appropriate * Please include a gif of your bot in action
27
posted to Challenge by timmy_i_chen (423) 5 days ago
โ–ฒ
5
โŒTicTacToe โญ• ๐Ÿ’ปTerminal Edition โœจ
๐Ÿค”Ever wanted to play โŒTicTacToe โญ• in the terminal ๐Ÿ’ป? Me neither, but I made it anyway ๐Ÿคทbecause i want upvotesโฌ†! ๐ŸŽฎYou can [play it here](https://TicTacToe-Terminal-Edition.mat1.repl.run) or [view the source](https://repl.it/@mat1/TicTacToe-Terminal-Edition) ๐Ÿ–ฅ. ## How to play - uh just click on the blank spaces ๐Ÿ—… and stuff - i made this in like 30 minutes ๐Ÿ•’ - nope, no ai ๐Ÿค–. so if you have no friends then that's too bad - theres colors ๐ŸŽจ i guess - pls upvote ๐Ÿ‘ > โฌ† DON'T FORGET TO UPVOTE โฌ† > If you find a bug ๐Ÿ›, don't report it because I won't fix it
4
posted to Share by mat1 (281) about 4 hours ago
โ–ฒ
9
Starbot
Starbot adds support for appreciation in a discord community! You can give people who helped you stars, and the bot will note it - also creating a leaderboard, and some sort of karma points in the community. When you give a star - it reduces the number you have by one. But everyone starts off with `20` ๐Ÿ˜„ Here's a demo ๐Ÿ‘‡ ![](https://i.imgur.com/suV9ooj.gif) Send a message tagging user(s) like this: `Thanks @amasad and @hayaodeh for creating rep.it โญ` And send only a โญ to see the count ๐Ÿ† Try it out now in the [#bot-usage channel](https://discordapp.com/channels/437048931827056642/439586718681792552) ๐Ÿ’ฌ
0
posted to Challenge by jajoosam (93) about 19 hours ago
โ–ฒ
9
Making a Discord bot in Ruby!
# How to get started ### Step 1: install discordrb The discordrb gem (library) is required to make a discord bot in Ruby. You can install it by typing ``` `gem install discordrb` ``` or by using bundler. Then, in your code put `require "discordrb"` on the first line. ### Step 2: setup your bot Assuming that you have created your bot on Discord already, you need to create a bot by doing the following (of course, you can change the name): ```ruby @my_bot = Discordrb::Bot.new token: <my-token>, client_id: <my-id> @my_bot.run true # commands go here! @my_bot.join ``` And of course, `<my-token>` and `<my-id>` are replaced with your bot's token and id. `@my_bot.run true` and `@my_bot.join` help keep the bot running btw. If you want a predetermined prefix, add `, prefix: "<my-prefix>"` to the end of the first line (and `"<my-token>"` is replaced with your token). ### Step 3: adding commands to your bot #### If you have a prefix Having a prefix makes things easier (though a bit limited). To add a simple command, use the `command` method on your bot, followed by the command name (as a string or symbol), any options (will be described later), and the event block (like an anonymous function that looks like a control structure). Here's an example of a command that takes 2 or more numbers, and adds them up: ```ruby @my_bot.command :sum, min_args: 2 do |event, *args| numbers = args.collect &:to_i # turns each argument into a number sum = numbers.collect &:+ # adds up everything in "numbers" event.respond sum # I could have just done `event.respond args.collect(&:to_i).collect(&:+)` btw end ``` This would be used as `<my-prefix> sum num1 num2 [... num]`. #### If you don't have a prefix Not having a prefix is not a bad thing, it just means that you want your bot to do more. You can get every message by using the `message` command on your bot. For each message, you can specify options like: - `contains: "some text"` (searching for text) - `content: "some text"` (to match entire message) or `content: /some_regex/` (to match a pattern) - `starts_with: "text"` or `ends_with: "text"` (for matching the beginning or end of a message ...and other things. To create something like the previous example: ```ruby @my_bot.message content: /^<my\-prefix>\s+sum\s+.+$/ do |event| args = event.content.split " " # "event.content" is the message numbers = args.collect &:to_i # turns each string in "args" into a number sum = numbers.collect &:+ # adds up everything in "numbers" event.respond sum # I could have just done `event.respond event.content.split(" ").collect(&:to_i).collect(&:+)` btw end ``` This would be used as `<my-prefix> sum num1 num2 [... num]`. # Step 4: profit Because you made your bot in Ruby, everyone will love it. Eventually, your bot turns into a paid subscription service. Good night.
16
posted to Learn by theangryepicbanana (122) 3 days ago
โ–ฒ
5
Can you make the notifications page work?
There is a page [Notifications](https://repl.it/notifications), that does nothing. I think that it could have good potential if it was actually used. I think that you should get notifications when someone up votes your post, comments on your post, or pings you. Also, you could make it so that it told you when you moved a position on the leaderboard. It could also tell you whenever a new competition started, or when one of your posts got pinned. If anybody else has some ideas they want the page to say, comment below please! Thank you!
1
posted to Ask by fullern000 (647) about 19 hours ago
โ–ฒ
3
SNAKE GAME
Members: 1. Jassim Naeem (11828) 2. M.Hassan Farooq (11845) 3. M.Haseeb (11819) 4. M.Abbas (11831)
0
posted to Share by iamjassim (2) about 7 hours ago
โ–ฒ
7
HappyFakeBoulder Bot 2
HFBB2 is a Discord bot in Python 3 with miscellaneous commands, such as %illuminati (displaying a built-in ASCII art of the Illuminati icon), %say (repeating whatever you put after the command name), or %readf (allowing you to read one of the user files). You can enter the command "%help" (as shown in its playing status) to get a full list of commands. More commands might be added soonโ„ข. GIF of HFBB2 in action: https://gfycat.com/BestImpressionableJaeger
2
posted to Challenge by HappyFakeboulde (80) 2 days ago
โ–ฒ
17
๐Ÿ“ฑ Repl Talk ๐Ÿ’ฌ ๐Ÿ’ป **TERMINAL EDITION** ๐Ÿ’ป
# Repl Talk Terminal Edition yeah so basically it lets you view ๐Ÿ”ฅ [Repl Talk](https://repl.it/talk) ๐Ÿ”ฅ in the terminal - first you have to go to [repl-talk-terminal.mat1.repl.run](https://repl-talk-terminal.mat1.repl.run) ๐Ÿ”— for it to be fullscreen ๐Ÿ’ป - then you can scroll up โฌ† and down โฌ‡ with your scroll wheel or arrow keys - you can click ๐Ÿ–ฑ๏ธ on a post to view it - at the top you can click ๐Ÿ–ฑ๏ธ the board name to view the posts in that board - be weary of the bugs! ๐Ÿ› - ๐Ÿ‘ leave an upvote โฌ†๏ธ > DON'T FORGET TO โฌ†๏ธ UPVOTE โฌ†๏ธ > if you find a bug, please report it in the comments ๐Ÿ’ฌ
5
posted to Share by mat1 (281) 6 days ago
โ–ฒ
45
Building AI: Neural Networks for beginners ๐Ÿ‘พ
Teaching Machine to recognize Hand-written Numbers! I am excited to share some of my experience studying machine learning with you, guys! I'm not an expert but I'll try to explain it the way I see it myself. I'm going to try to give you some intuition about how Neural Networks work, omitting most of the math to make it more understandable but, for the most curious of you, I'll leave the links to complete explanations/courses in the end. ![Predicted class_ 4](https://storage.googleapis.com/replit/images/1541033154259_e80e9609e421c89077d1b92aa1d33f36.pn) In 29 mins, you'll be able to configure an algorithm that's going to recognize the written digits in python :) ## **๐Ÿง  What is a Neural Network?** Imagine Neural Network as an old wise wizard who knows everything and can predict your future by just looking at you. ![magicbox](https://storage.googleapis.com/replit/images/1541033176006_a6af80c5d6034944a58c1fc595834691.pn) It turns out that he manages to do so in a very non-magical way: 1. Before you visited him, he trained, carefully studied everything about many thousands of people who came to see him before you. 2. He now collects some data about what you look like (your apparent age, the website you found him at, etc). 3. He then compares it to the historical data he has about people that came to see him before. 4. Finally, he gives his best guess on what kind of person you are based on the similarities. ![nn](https://storage.googleapis.com/replit/images/1541033195545_03966c8b28c6a5a6e037593ca2d5fd2f.gi) In very general terms, it is the way many machine learning algorithms work. They are often used to predict things based on the history of similar situations: Amazon suggesting the product you might like to buy, or Gmail suggesting to finish the sentence for you, or a self-driving car learning to drive. ## **๐Ÿ“™ Part 1: Import libraries** Let's start! I have put together a class that is doing all the math behind our algorithm and I'd gladly explain how it works in another tutorial or you could go through my comments and try to figure it out yourself if you know some machine learning. **For now, create a file called `NN.py` and paste this code:** ```python import numpy as np from scipy.optimize import minimize class Neural_Network(object): def configureNN(self, inputSize, hiddenSize, outputSize, W1 = np.array([0]), W2 = np.array([0]), maxiter = 20, lambd = 0.1): #parameters self.inputSize = inputSize self.outputSize = outputSize self.hiddenSize = hiddenSize #initialize weights / random by default if(not W1.any()): self.W1 = np.random.randn( self.hiddenSize, self.inputSize + 1) # weight matrix from input to hidden layer else: self.W1 = W1 if (not W2.any()): self.W2 = np.random.randn( self.outputSize, self.hiddenSize + 1) # weight matrix from hidden to output layerself.W2 = W2 else: self.W2 = W2 # maximum number of iterations for optimization algorithm self.maxiter = maxiter # regularization penalty self.lambd = lambd def addBias(self, X): #adds a column of ones to the beginning of an array if (X.ndim == 1): return np.insert(X, 0, 1) return np.concatenate((np.ones((len(X), 1)), X), axis=1) def delBias(self, X): #deletes a column from the beginning of an array if (X.ndim == 1): return np.delete(X, 0) return np.delete(X, 0, 1) def unroll(self, X1, X2): #unrolls two matrices into one vector return np.concatenate((X1.reshape(X1.size), X2.reshape(X2.size))) def sigmoid(self, s): # activation function return 1 / (1 + np.exp(-s)) def sigmoidPrime(self, s): #derivative of sigmoid return s * (1 - s) def forward(self, X): #forward propagation through our network X = self.addBias(X) self.z = np.dot( X, self.W1.T) # dot product of X (input) and first set of 3x2 weights self.z2 = self.sigmoid(self.z) # activation function self.z2 = self.addBias(self.z2) self.z3 = np.dot( self.z2, self.W2.T) # dot product of hidden layer (z2) and second set of 3x1 weights o = self.sigmoid(self.z3) # final activation function return o def backward(self, X, y, o): # backward propgate through the network self.o_delta = o - y # error in output self.z2_error = self.o_delta.dot( self.W2 ) # z2 error: how much our hidden layer weights contributed to output error self.z2_delta = np.multiply(self.z2_error, self.sigmoidPrime( self.z2)) # applying derivative of sigmoid to z2 error self.z2_delta = self.delBias(self.z2_delta) self.W1_delta += np.dot( np.array([self.z2_delta]).T, np.array([self.addBias(X)])) # adjusting first set (input --> hidden) weights self.W2_delta += np.dot( np.array([self.o_delta]).T, np.array([self.z2])) # adjusting second set (hidden --> output) weights def cost(self, nn_params, X, y): #computing how well the function does. Less = better self.W1_delta = 0 self.W2_delta = 0 m = len(X) o = self.forward(X) J = -1/m * sum(sum(y * np.log(o) + (1 - y) * np.log(1 - o))); #cost function reg = (sum(sum(np.power(self.delBias(self.W1), 2))) + sum( sum(np.power(self.delBias(self.W2), 2)))) * (self.lambd/(2*m)); #regularization: more precise J = J + reg; for i in range(m): o = self.forward(X[i]) self.backward(X[i], y[i], o) self.W1_delta = (1/m) * self.W1_delta + (self.lambd/m) * np.concatenate( (np.zeros((len(self.W1),1)), self.delBias(self.W1)), axis=1) self.W2_delta = (1/m) * self.W2_delta + (self.lambd/m) * np.concatenate( (np.zeros((len(self.W2),1)), self.delBias(self.W2)), axis=1) grad = self.unroll(self.W1_delta, self.W2_delta) return J, grad def train(self, X, y): # using optimization algorithm to find best fit W1, W2 nn_params = self.unroll(self.W1, self.W2) results = minimize(self.cost, x0=nn_params, args=(X, y), options={'disp': True, 'maxiter':self.maxiter}, method="L-BFGS-B", jac=True) self.W1 = np.reshape(results["x"][:self.hiddenSize * (self.inputSize + 1)], (self.hiddenSize, self.inputSize + 1)) self.W2 = np.reshape(results["x"][self.hiddenSize * (self.inputSize + 1):], (self.outputSize, self.hiddenSize + 1)) def saveWeights(self): #sio.savemat('myWeights.mat', mdict={'W1': self.W1, 'W2' : self.W2}) np.savetxt('data/TrainedW1.in', self.W1, delimiter=',') np.savetxt('data/TrainedW2.in', self.W2, delimiter=',') def predict(self, X): o = self.forward(X) i = np.argmax(o) o = o * 0 o[i] = 1 return o def predictClass(self, X): #printing out the number of the class, starting from 1 print("Predicted class out of", self.outputSize,"classes based on trained weights: ") print("Input: \n" + str(X)) print("Class number: " + str(np.argmax( np.round(self.forward(X)) ) + 1)) def accuracy(self, X, y): #printing out the accuracy p = 0 m = len(X) for i in range(m): if (np.all(self.predict(X[i]) == y[i])): p += 1 print('Training Set Accuracy: {:.2f}%'.format(p * 100 / m)) ``` ## **๐Ÿ“Š Part 2: Understanding Data** Cool! Now, much like the wizard who had to study all the other people who visited him before you, we need some data to study too. Before using any optimization algorithms, all the data scientists first try to *understand* the data they want to analyze. **Download files `X.in` (stores info about what people looked like - question) and `y.in`(stores info about what kind of people they were - answer) from [here](https://www.dropbox.com/sh/b04b2xb5j3ncir3/AABlau8wnzWmuyekJ8iVlmPga?dl=0) and put them into folder `data` in your repl.** * X: We are given 5,000 examples of 20x20 pixel pictures of handwritten digits from 0 to 9 (classes 1-10). Each picture's numerical representation is a single vector, which together with all the other examples forms an array `X`. * Y: We also have an array `y`. Each column represents a corresponding example (one picture) from `X`. `y` has 10 rows for classes 1-10 and the value of only the correct class' row is one, the rest is zeros. It looks similar to this: ``` [0, 0, 0, 0, 0, 0, 0, 0, 0, 1] # represents digit 0 (class 10) [1, 0, 0, 0, 0, 0, 0, 0, 0, 0] # represents digit 1 (class 1) ...... [1, 0, 0, 0, 0, 0, 0, 0, 1, 0] # represents digit 9 (class 9) ``` Now, let's plot it! ![TrainingData](https://storage.googleapis.com/replit/images/1541033299328_0478599ab1b7884435cc3bf629b1edc1.pn) In the end, I'd want a function `displayData(displaySize, data, selected, title)`, where * `displaySize` - the numer of images shown in any one column or row of the figure, * `data` - our X array, * `selected` - an index (if displaying only one image) or vector of indices (if displaying multiple images) from X, * `title` - the title of the figure **Create a `plots` folder to save your plots to. Also, if you use repl, create some empty file in the folder so that it doesn't disappear.** **Create a `display.py` file and write the following code in there. Make sure to read the comments:** ```python import matplotlib.pyplot as plt # Displaying the data def displayData( displaySize, data, selected, title ): # setting up our plot fig=plt.figure(figsize=(8, 8)) fig.suptitle(title, fontsize=32) # configuring the number of images to display columns = displaySize rows = displaySize for i in range(columns*rows): # if we want to display multiple images, # then 'selected' is a vector. Check if it is here: if hasattr(selected, "__len__"): img = data[selected[i]] else: img = data[selected] img = img.reshape(20,20).transpose() fig.add_subplot(rows, columns, i+1) plt.imshow(img) # We could also use plt.show(), but repl # can't display it. So let's insted save it # into a file plt.savefig('plots/' + title) return None ``` Great, we are halfway there! ## **๐Ÿ’ช Part 3: Training Neural Network** Now, after we understand what our data looks like, it's time to train on it. Let's make that wizard study! It turns out that the results of the training process of the Neural Networks have to be stored in some values. These values are called *parameters* or *weights* of the Neural Network. If you were to start this project from scratch, your initial weights would be just some random numbers, however, it would take your computer forever to train to do such a complex task as recognizing digits. For this reason, I will provide you with the initial weights that are somewhat closer to the end result. **Download files `W1.in` and `W2.in` from [here](https://www.dropbox.com/sh/b04b2xb5j3ncir3/AABlau8wnzWmuyekJ8iVlmPga?dl=0) and put them into `data` folder.** We are now ready to write code to use our Neural Network library! ![training](https://storage.googleapis.com/replit/images/1541033327074_30bf734c3f1fa129d15be3285be6e453.gi) **Create a `train.py` file and write the following code in there. Make sure to read the comments:** ```python # This code trains the Neural Network. In the end, you end up # with best-fit parameters (weights W1 and W2) for the problem in folder 'data' # and can use them to predict in predict.py import numpy as np import display from NN import Neural_Network NN = Neural_Network() # Loading data X = np.loadtxt("data/X.in", comments="#", delimiter=",", unpack=False) y = np.loadtxt("data/y.in", comments="#", delimiter=",", unpack=False) W1 = np.loadtxt("data/W1.in", comments="#", delimiter=",", unpack=False) W2 = np.loadtxt("data/W2.in", comments="#", delimiter=",", unpack=False) # Display inputs sel = np.random.permutation(len(X)); sel = sel[0:100]; display.displayData(5, X, sel, 'TrainingData'); # Configuring settings of Neural Network: # # inputSize, hiddenSize, outputSize = number of elements # in input, hidden, and output layers # (optional) W1, W2 = random by default # (optional) maxiter = number of iterations you allow the # optimization algorithm. # By default, set to 20 # (optional) lambd = regularization penalty. By # default, set to 0.1 # NN.configureNN(400, 25, 10, W1 = W1, W2 = W2) # Training Neural Network on our data # This step takes 12 mins in Repl.it or 20 sec on your # computer NN.train(X, y) # Saving Weights in the file NN.saveWeights() # Checking the accuracy of Neural Network sel = np.random.permutation(5000)[1:1000] NN.accuracy(X[sel], y[sel]) ``` **Now, you have to run this code either from:** * **Repl.it** - but you would need to move code from `train.py` into `main.py`. Don't delete `train.py` just yet. It would also take approximately 12 minutes to compute. You can watch [this](https://www.youtube.com/watch?v=z-EtmaFJieY) Crash Course video while waiting :) * **Your own computer** - just run `train.py`, which takes 20 sec on my laptop to compute. If you need help installing python, watch [this](https://www.youtube.com/watch?v=LrMOrMb8-3s) tutorial. ![trained](https://storage.googleapis.com/replit/images/1541033350157_38c60efaabc74234ee72285f0e17048b.pn) ## **๐Ÿ”ฎ Part 4: Predicting!** By now, you are supposed to have your new weights (`TrainedW1.in`,`TrainedW2.in`) saved in `data` folder and the accuracy of your Neural Network should be over 90%. Let's now write a code to use the trained weights in order to predict the digits of any new image! ![giphy](https://storage.googleapis.com/replit/images/1541033387111_bcb40155cc2e8ef38749e91c207033d8.gi) **Create a `predict.py` file and write the following code in there. Make sure to read the comments:** ```python import numpy as np import display from NN import Neural_Network NN = Neural_Network() # Loading data X = np.loadtxt("data/X.in", comments="#", delimiter=",", unpack=False) y = np.loadtxt("data/y.in", comments="#", delimiter=",", unpack=False) trW1 = np.loadtxt("data/TrainedW1.in", comments="#", delimiter=",", unpack=False) trW2 = np.loadtxt("data/TrainedW2.in", comments="#", delimiter=",", unpack=False) # Configuring settings of Neural Network: NN.configureNN(400, 25, 10, W1 = trW1, W2 = trW2) # Predicting a class number of given input testNo = 3402; # any number between 0 and 4999 to test NN.predictClass(X[testNo]) # Display output display.displayData(1, X, testNo, 'Predicted class: ' + str(np.argmax(np.round(NN.forward(X[testNo]))) + 1) ) ``` **Change the value of `testNo` to any number between 0 and 4999. In order to get a digit (class) prediction on the corresponding example from array X, run the code from:** * **Repl.it** - but you would need to move code from `predict.py` into `main.py`. Don't delete `predict.py` just yet. * **Your own computer** - just run `predict.py`. Yay, you are officially a data scientist! You have successfully: 1. Analyzed the data 2. Implemented the training of your Neural Network 3. Developed a code to predict new testing examples ![congrats](https://storage.googleapis.com/replit/images/1541033425490_308fdfc015d494a8aeceae5564956f4b.gi) ## **๐Ÿš€ Acknowledgments** Hat tip to @shamdasani whose code I used as a template for Neural Network architecture and Andrew Ng from Stanford whose data I used. Plenty of things I told you are not completely correct because I rather tried to get you excited about the topic I am passionate about, not dump some math on you! If you guys seem to enjoy it, please follow through with studying machine learning because it is just an amazing experience. I encourage you to take [this free online course](https://www.coursera.org/learn/machine-learning) on it to learn the true way it works. Also, it's my first post here and I'd appreciate any feedback on it to get better. Keep me updated on your progress, ask any questions, and stay excited! โœจโœจโœจ
10
posted to Learn by ArtemLaptiev1 (44) 14 days ago
Pinned
โ–ฒ
8
Weekly Repls #9
Hello replitors! replit-goers? replitators.... we'll work on that. Anyways, we have some great news as the weekly repls are back again (surprise) and we have some great content to show you! @GrantKeo [Made an awesome 1 v E console game, and it's a ton of fun to play, with a great tutorial](https://repl.it/talk/share/Battlegrounds-Console-Edition/8296) @HappyFakeBoulde [Randomized input is very useful when testing things. With this Markov Chain, you can now make your own, sweet text!](https://repl.it/talk/share/Markov-Chain-thing/8340) @mat1 [Made this amazing terminal replica of Repl Talk! Complete with upvote counts and boards, scroll and click around to view posts in repl.run!](https://repl.it/talk/share/Repl-Talk-TERMINAL-EDITION/8380) @amasad [Created a wonderful, clean blog, that allows for a ton of customization! (Along with some great articles too)](https://repl.it/talk/share/Blog-in-Nodejs/8383) That's it for this week. Keep up the great work and we'll see you next time around, bye!
1
posted to Announcements by 21natzil (202) 2 days ago
โ–ฒ
6
Shakespeare
Shakespeare is a simple, fun bot with one core purpose: insulting people in Shakespearean English. At time of writing, it has over 20,000 different insults available, and is on over 75 servers with a combined total of over 70,000 users. It has an easily accessible help command, displayed as its status. Invite link: https://discordapp.com/oauth2/authorize?client_id=487305758875320332&permissions=0&scope=bot (It doesn't need any permissions other than posting messages) Repl: https://repl.it/@minx28/Shakespeare
2
posted to Challenge by minx28 (6) 2 days ago
โ–ฒ
1
.env Help
I'm using an .env file to do codes. It works fine for me but when another account uses the code it says that the .env file's contents are empty. https://repl.it/@LynnOng/ASL
2
posted to Ask by LynnOng (0) about 3 hours ago
โ–ฒ
78
Making a Phaser Game with HTML5 and JavaScript
# Making a Phaser Game with HTML5 and JavaScript Hi guys! Everybody likes to make games, right? And everybody has their own way of doing it. In this tutorial I wanted to share a very simple, yet effective way to make games in your browser! It should be easy enough for most people with javascript knowledge to follow along and, if you want to investigate further, there are endless possibilities out there! ![image](https://storage.googleapis.com/replit/images/1539468462288_75406edb94f04ca097cc5b4705ccbc85.pn) ### Phaser As Phaser describes itself it is a fast, free and fun open source framework for Canvas and WebGL powered browser games. And it really is! It is super simple to use and is quite easy to set up. No super extensive javascript knowledge is necessary and the process of making games is fun and rewarding. It also comes with tons of extra features that you may need in some more complicated games so while it caters to starters as well, it also does not lack depth if you want to look further. Anything from image editing to complex game mechanic mathematics is possible. ##### Sites to use The official Phaser website is [here](https://phaser.io). Additionally, because we are going to use Phaser 3, the latest release, the examples on the site will most probably not work for v3. If you want some examples of v3 features the link is [here](https://labs.phaser.io/). You should not need the examples during this tutorial but if you want to learn further that is where you start. Google works as well but be careful about which version is being discussed. Version 3 is relatively new and v2 has loads more documentation and examples and tutorials on it. However, I would recommend learning v3 because it is generally better in many ways and the knowledge will last you longer and it will be more current. #### Prerequisites (what you need before doing this tutorial) The pre-requisites are: * A basic understanding of HTML, CSS and Javascript. * Knowledge in Javascript about the `this` keyword. * Some time and patience. * 3 rolls of duct tape. * Lots of cardboard * Creativity ### Let's Get Started! The repl.it project that I will be using for this tutorial is [here](https://repl.it/@kaldisberzins/Phaser-Tutorial) and the website for it if you just wanna play the game is [here](https://phaser-tutorial.kaldisberzins.repl.co/). If you ever get stumped on a step that I take in this tutorial just check the repl and see how the code looks in it. If all else fails a bit of copy-paste will solve your issues. Make a new HTML/CSS/JS repl and follow along... So, first of all we need to include the Phaser script into our website. The only piece of HTML in this tutorial will be the following:`<script src="//cdn.jsdelivr.net/npm/[email protected]/dist/phaser.min.js"></script>`Just paste this into your project's HTML file right above your script tag that links to `script.js`. The order is important and if you get it wrong nothing will work. If your project is not working you should definitely have a look at the order of your scripts. The Phaser script should be first. With that out of the way, let's get into making our game! The first bit of code is a standard template that is in most simple Phaser games (more advanced ones may use a slightly different structure but the idea is the same). The code looks like this: ```javascript let config = { type: Phaser.AUTO, width: 800, height: 500, physics: { default: 'arcade', arcade: { debug: false } }, scene: { preload: preload, create: create, update: update } }; const game = new Phaser.Game(config); function preload(){ } function create(){ } function update(){ } ``` While this may look alien to you, don't stress. To follow along this tutorial you don't need to understand what everything does exactly. The main things you should pay attention to are: * The three functions at the bottom `preload`, `create` and `update`. These we will fill in with the game's code. * The `width` and `height` properties. You can set these to anything you like, I did not make it `window.innerWidth` and `window.innerHeight` because scaling can quickly become messy. It is easier to make it a fixed width for everybody. So now if you run your repl you should see a black square in your browser window. Success! If you do not, make sure you have the Phaser script in the right place and that you have the code in your `script.js` exactly like above. You should also get a message in the console, something like: ```%c %c %c %c %c Phaser v3.14.0 (WebGL | Web Audio) %c https://phaser.io background: #ff0000 background: #ffff00 background: #00ff00 background: #00ffff color: #ffffff; background: #000000 background: #fff``` This may look awful in the repl.it console but if you open it in a new tab and check the console it should be a colorful banner. ### Loading Assets The `preload` function that we are going to use for this section is where you load your assets. If you want some images or audio (Phaser does that as well) in your game you first have to load it here. This way you are loading all the required assets immediately and you can use them throughout the game. I have made some assets for this tutorial so that you do not need to find or make some yourself. Go [here](https://drive.google.com/drive/folders/1TzRicUBL8V0T_9fPMaNCL6M0UEV51irQ?usp=sharing) and click download like so to get the files: ![image](https://storage.googleapis.com/replit/images/1539468612344_eeb16f0a94e74fa401749d11f7b89333.pn) If you get the files in a `.zip` folder just unzip them and drop them into your repl. Once you have them in your repl we have to load them into our game. The following code in the `preload` function will do the trick: ```javascript this.load.atlas("player", "spritesheet.png", "sprites.json"); this.load.image("platform", "platform.png"); this.load.image("spike", "spike.png"); this.load.image("coin", "coin.png"); ``` The first parameter in all of the functions is the "key" for the image. This key you would use when you need to add the image into the game. You can put it as whatever you want but make sure it is descriptive of the image in some way. I suggest you keep them the same as mine so that later code in my tutorial works for you. The second parameter is the path to the image. Because I put the assets in the same folder as the html and js files the path is just the name of the image. If you put your assets in another folder the file path string would look like `"folder_name/file_name.png"`. You may also have noticed that the first command is a bit different. It loads an __atlas__ and not an image. An atlas is a collection of images put together to make a larger image accompanied by a file that states where all the smaller images are. If you open the file `sprites.json` in the assets I gave you you should see that it contains a bunch of named objects that have x, y, width and height properties among others. Each object is an image inside the larger image. In this tutorial we will use the atlas for the player animations. All of the frames for the player (in our case only three) are in the `spritesheet.png` file. The third parameter for the atlas is the path to the `.json` file which we looked at already. If you now run the current code the screen should remain black and no errors should be in the console. If you see a web audio warning that is fine, it does not mean anything important. It's just chrome messing with you. ### Adding Objects to Our Game The `create` function is where the building of our game happens. It is run right after `preload` and is run only once. If you want to add an object to the game, this is where you do it. If you want to repeatedly create some object. Make a function (read below) that creates the object and run that as may times as you like. So we now have loaded some images but we need to have something happen on the screen. Let's add a function in the `create` function that will spawn our player in. Add this code to the `create`function: ```javascript this.spawnPlayer = ()=>{ this.player = this.physics.add.sprite(400, 250, "player", "sprite_0"); } this.spawnPlayer(); ``` I put this in a seperate function so that we can spawn the player multiple times. We are saving the player to __`this`__ which is the Phaser game object so that we can access it from anywhere. The function itself creates a sprite (image/object) that is in the Phaser physics system. The parameters are: 1. X position 2. Y position 3. Image key 4. (optional) If the image is an atlas, which frame in the atlas. There may be a few more parameters but those are not important for this tutorial. The way we find out which frame is which in the atlas is by looking at the `sprites.json` file. Find an object and look at its x and y properties. For example `sprite_2` has the following object: ```javascript "sprite_2":{"frame":{"x":0,"y":0,"w":48,"h":64}... ``` We can see that the x and y coordinates of the frame are `0, 0`. This means that it will be in the top left corner. If you look at the top left corner of the `spritesheet.png` image you will see which frame is `sprite_2`. Try changing the last parameter in the add function to be `sprite_2`. You will see that it has changed. ##### Adding a Background If the only background color we could have would be black Phaser would look really bad. Luckily enough, Phaser has an easy way to add a background to our game. Just add this code to the top of your `create` function above the `spawnPlayer` function: ```javascript this.cameras.main.setBackgroundColor('#ffffff'); ``` This sets the background color for our main camera to white. If you have not used hex color codes before don't worry about it, just know that `#ffffff` is white. The only problem with that is that now we can't see where our canvas windw starts and ends. We can fix this with a little CSS: ```css canvas{ border: 1px solid black; } ``` Now if you run your code it should look something like this: ![image](https://storage.googleapis.com/replit/images/1539468654218_bf2de4d9dc55069fde105a14f6c9818a.pn) You can see we have our little character in the middle of the screen. The background is now white. You may have noticed that the character is not offset to a side even though we put in the coordinates for the center of the screen. This is because Phaser draws images from their center. This makes it easier to center images. Another simple thing we can add to the game is a camera that follows the player. This is quite easy to do in Phaser: ```javascript this.spawnPlayer = ()=>{ this.player = this.physics.add.sprite(400, 250, "player", "sprite_0"); this.cameras.main.startFollow(this.player); }; this.spawnPlayer(); ``` The function should be quite self-explanatory and if you run it you should see no change for now. As long as you do not get any errors you are fine. ### Adding Platforms Before we start I wanted to show you the most basic way to add an image to the game. The method used above has a very specific use case (only for sprites). Here is a more general use way of doing it: ```javascript // This goes beneath the spawnPlayer function call this.platform = this.add.image(404, 302, "platform"); ``` This is good for some simple use cases like for example a logo image in your title screen. However it has its shortcomings. Imagine you want to create a map of these platforms. You would have to add `platform1` `platform2` and so on... It would be a nightmare. Let's not get started on collisions. So by now you can see why we are not going to use this to add our platforms. Instead we will have a group. Defining a new group is easy. Remove the above code and add this instead. ```javascript this.platforms = this.physics.add.staticGroup(); ``` Currently we are just defining a new static (non-moving) group and assigning it to the variable `this.platforms`. If you run this now the platform image will disappear. That is because we need to add some platforms to the group. This can be done simply like this: ```javascript //Below the spawnPlayer function this.platforms = this.physics.add.staticGroup(); this.platfroms.create(404, 302, "platform"); ``` There we go! Now we have our platform back! But what is the benefit? In a moment when we deal with collisions you will see why. For now we will leave the platforms and get back to them later. ### Keyboard Inputs As you have probably gathered by now, Phaser has made its own version of everything you may need when developing games. Keyboard inputs are no exception. Phaser even supports many ways to do keyboard inputs. We are going to do the shortest and simplest. We are going to have a bunch of variables, one for each key. And we will check each frame if any of the keys are pressed and set velocities accordingly. The code for the keyboard variables in the `create` function looks like this: ```javascript this.key_W = this.input.keyboard.addKey(Phaser.Input.Keyboard.KeyCodes.W); this.key_A = this.input.keyboard.addKey(Phaser.Input.Keyboard.KeyCodes.A); this.key_D = this.input.keyboard.addKey(Phaser.Input.Keyboard.KeyCodes.D); ``` You do not need to understand this, just get the idea of what is happening. When a player presses a key the variable associated with that key will have `isDown` set to `true`. This makes adding keybinds really easy. Now for the rest of this section we are using the `update` function. `update` is your game loop. This function is run very fast repeatedly all throughout your game. This is where you would handle things like movement and other stuff you would want to check every frame. If you would be coding your own physics this would be where you do it. In the `update` function now let's check if the W key is pressed: ```javascript if(this.key_W.isDown){ this.player.setVelocityY(-50); }else{ this.player.setVelocityY(0); } ``` Instead of incrementing or decrementing the Y property of the player we set its velocity. We do this because it sets a velocity within Phaser which has some benefits. First of all Phaser object velocities take into account the frame rate. If every frame you increase the position X of a player, the higher the frame rate the faster the player moves. However, Phaser counteracts this. We do not need to know how, just that no matter the frame rate the player will always move at the same speed. The value we put into `setVelocityY` is the amount of pixels we want it to move in one second. If you run this now you will see that is you press the W key your character will move up. Success! Now let's add keybinds for A and D. This is only a few more lines of code: ```javascript if(this.key_A.isDown){ this.player.setVelocityX(-50); }else if(this.key_D.isDown){ this.player.setVelocityX(50); }else{ this.player.setVelocityX(0); } ``` We have this in an if/else if statement because we don't want to head left and right at the same time. We can only go in one direction or the other. And that's it! We now have linked up our keyboard keys to our Phaser game! Now it's time to deal with physics. ### Game Physics Phaser also has its own physics engine. In fact it has three but we will only use the most basic one for this tutorial. Just simple square and square collisions. Before we can do collisions, how about we add some gravity. We only need it on the player so it would look like this: ```javascript this.spawnPlayer = ()=>{ this.player = this.physics.add.sprite(400, 250, "player", "sprite_0"); this.player.body.setGravityY(800); this.cameras.main.startFollow(this.player); }; ``` Now if you run your game you will see that the player drops. But he is dropping very slowly. Why so? This is because each frame we are setting his velocity to 0 if the W key is not pressed. Previously that was needed so that he would not just fly away but now we need to remove that bit: ```javascript //In the update function if(this.key_W.isDown){ this.player.setVelocityY(-50); }/*else{ this.player.setVelocityY(0); } NO LONGER NEEDED*/ ``` Now if you run it the player falls a bit faster. You can still fly with W but we will change that in a second. #### Collisions Now that we have gotten gravity mostly out of the way let's make the player collide with the platform that we have. We can do this with one simple line of code. Add this to your `spawnPlayer` function: ```javascript this.physics.add.collider(this.player, this.platforms); ``` That's it. Just one line of code does everything. But if you run this now it will not work. The player will fall right through. And this is actually for a really stupid reason. We are running this code before we add the platforms. All you have to do is move the `spawnPlayer` function __call__ (not the function itself) below where we add the platforms. And Viola! We have the player not falling through the platform. There are some small problems that we should address before moving on. First of all, When we press W we can fly endlessly. That defeats the point of the game. To prevent this all we need to do is to only let us jump when we are on the ground. This is easy to do: ```javascript if(this.key_W.isDown && this.player.body.touching.down)... ``` When the key W is down and the player's body is touching a platform with its bottom it will jump. If you run this now you will see that the player now makes many little jumps if you press W. To make the jumps larger we have to increase the `setVelocitY`: ```javascript if(this.key_W.isDown && this.player.body.touching.down){ this.player.setVelocityY(-550); } ``` And also while we are at it we can make the left/right movement a bit faster: ```javascript if(this.key_A.isDown){ this.player.setVelocityX(-150); }else if(this.key_D.isDown){ this.player.setVelocityX(150); }else{ this.player.setVelocityX(0); } ``` So there we have it! A running and jumping player! Now let's give him a map to run around in. #### Map Building Phaser supports multiple ways to build a map (of course). However, I have decided that it would be better to cook up our own map builder that would work off of a string. Spaces would indicate that at that position there is no platform, 1 would mean that there is, 2 that this is a spawn point for the player and a dot(.) would mean that this is the end of a row. The map I designed looks something like this: ```javascript //At the top of your js file const map = '11111111111111111111111111.'+ '1 1.'+ '1 1.'+ '1 2 1 1 1 1 1.'+ '1 1 1 1 1 1.'+ '1 1.'+ '1 1.'+ '1 1 1 1 1 1.'+ '1 1 1 1 1 1.'+ '1 1.'+ '1 1.'+ '1 1 1 1 1 1.'+ '1 1 1 1 1 1.'+ '1 1.'+ '1 1.'+ '11111111111111111111111111'; ``` You can see that it is a box that is riddled with platforms. How do we turn this into a map? The parser for this that I made is only a few lines of code: ```javascript //Goes instead of the previous platform adding code this.platforms = this.physics.add.staticGroup(); let mapArr = map.split('.'); let drawX = 0; let drawY = 0; mapArr.forEach(row=>{ drawX = 0; for(let i = 0; i<row.length; i++){ if(row.charAt(i)==='1'){ this.platforms.create(drawX, drawY, "platform"); }else if(row.charAt(i)==='2'){ if(row.charAt(i+1)==='1'){ this.spawnPlayer(drawX-4, drawY-12); }else if(row.charAt(i-1)==='1'){ this.spawnPlayer(drawX+4, drawY-12); }else{ this.spawnPlayer(drawX, drawY-12); } } drawX+=40; } drawY+=40; }); ``` First we split the string that we have into an array of rows using the . that says that a row ends at that point. Then we loop through each row and at each row we loop through each character in the row. If the character is a 1, we add a platform at that place. If the character is 2 we spawn the player. I have a bit more code there that checks if there is a platform to the left or right and that nudges the character to a side just so that the player does not spawn in a platform. Also, you may have noticed that we are calling `spawnPlayer` here with some parameters. These are just x and y coordinates of where to spawn. To make that work we just have to edit the `spawnPlayer` function like so: ```javascript this.spawnPlayer = (x, y)=>{ this.player = this.physics.add.sprite(x, y, "player", "sprite_0"); this.player.body.setGravityY(800); this.cameras.main.startFollow(this.player); }; ``` Now if you run this you should get a map inside of which the player can run around. You can mess around with the map string if you want and design your own map. I would love to see what you come up with in the comments! ### Player Animations A while ago, I mentioned that we would use the atlas for player animations. Now is the time! We have three frames in our atlas and we have only used one. It's time to use the other two. Phaser has its own animation manager (by now you get the idea - Phaser === everything) that makes it super simple to do animations. First we have to set up our animations: ```javascript // At the bottom of the create function this.anims.create({ key:"walk", frames:[{key:"player", frame:"sprite_2"}, {key:"player", frame:"sprite_1"}], frameRate:10, repeat:-1 }); this.anims.create({ key:"stand", frames:[{key:"player", frame:"sprite_0"}], frameRate:1 }); ``` This creates an animation for our player that we can play when we want. The array `frames` is what Phaser will loop though and play. `frameRate` is quite self explanatory - the amount of frames that are played each second. `repeat` with the value -1 will make the animation loop again and again. Not specifying `repeat` will just make it run once. The key is the string that we can use to reference to the animation later. Just the same way as with images. Now let's run the animations when we walk right or left: ```javascript //In the update function if(this.key_A.isDown){ this.player.setVelocityX(-200); this.player.anims.play("walk", true); }else if(this.key_D.isDown){ this.player.setVelocityX(200); this.player.anims.play("walk", true); }else{ this.player.anims.play("stand", true); this.player.setVelocityX(0); } ``` The `true` parameter is just whether if there is already an animation running, should Phaser continue it? If you set this to false you will see that it will just freeze on a frame. That is because every frame it is checking if a key is pressed and then playing the animation. It will start again every frame making it look like it is frozen. Now if you run this you will see that we have a running animation with the legs moving and the hat bobbing up and down. There is only one more problem with the sprite. The player does not flip when he runs to the left. This is an easy fix: ```javascript //In the update function if(this.key_A.isDown){ this.player.setVelocityX(-200); this.player.anims.play("walk", true); this.player.flipX = true; }else if(this.key_D.isDown){ this.player.setVelocityX(200); this.player.anims.play("walk", true); this.player.flipX = false; }else{ this.player.anims.play("stand", true); this.player.setVelocityX(0); } ``` There we go! Now we have a map, player animations, keybinds, physics and most of all - a weird blob of a character who has a hat that flaps in the breeze! ### The Final Step - Spikes and Coins Now let's add some spikes that the player has to dodge and some coins that the player can collect. First, let's add a score counter in the top of the screen that displays our score: ```javascript this.spawnPlayer = (x, y)=>{ this.player = this.physics.add.sprite(x, y, "player", "sprite_0"); this.player.body.setGravityY(800); this.physics.add.collider(this.player, this.platforms); this.cameras.main.startFollow(this.player); //====================================== this.player.score = 0; this.scoreText = this.add.text(0, 0, "Score: "+this.player.score, { fill:"#000000", fontSize:"20px", fontFamily:"Arial Black" }).setScrollFactor(0).setDepth(200); }; ``` `setScrollFactor(0)` will make sure that when our camera moves, the text does not. This way it will always be in the same position in the top-left of the screen. Text is drawn from its top-left (don't ask me why it is one way for one thing and another for another) so drawing it at `0, 0` will put in the top-left corner. `setDepth(200)` will make sure the text always appears on top. We also make a variable for the score of the player that can be increased when we collect a coin. #### Coins Time to make an incentive to run and jump around. Coins will be a `c` in our map string. So, the map would now look like this: ```javascript const map = '11111111111111111111111111.'+ '1 c 1.'+ '1 c c c 1.'+ '1 2 1 1 c 1 c 1 1.'+ '1 1 1 1 1 1.'+ '1 1.'+ '1 c c 1.'+ '1 c 1 1 c 1 c 1 1.'+ '1 1 1 1 1 1.'+ '1 1.'+ '1 c c c 1.'+ '1 1 c 1 c 1 1 1.'+ '1 1 1 1 1 1.'+ '1 1.'+ '1 c c c c 1.'+ '11111111111111111111111111'; ``` Now to make this work we have to add an option of what to do if the current character is a `c` in our map parser. I added something like this: ```javascript this.platforms = this.physics.add.staticGroup(); //================================== this.coins = this.physics.add.group(); //================================= let mapArr = map.split('.'); let drawX = 0; let drawY = 0; mapArr.forEach(row=>{ drawX = 0; for(let i = 0; i<row.length; i++){ if(row.charAt(i)==='1'){ this.platforms.create(drawX, drawY, "platform"); }else if(row.charAt(i)==='2'){ if(row.charAt(i+1)==='1'){ this.spawnPlayer(drawX-4, drawY-12); }else if(row.charAt(i-1)==='1'){ this.spawnPlayer(drawX+4, drawY-12); }else{ this.spawnPlayer(drawX, drawY-12); } //================================= }else if(row.charAt(i)==='c'){ this.coins.create(drawX, drawY+10, "coin"); } //================================= drawX+=40; } drawY+=40; }); ``` If you run this you will see that a bunch of little coins appear. But we can't collect them! This is fairly easy to add: ```javascript // Add this after the map parsing code this.physics.add.overlap(this.player, this.coins, this.collectCoin, null, this); ``` This function will check if there is an overlap between two objects. The two objects are the first two parameters. If there is an overlap, it will run the function that is passed in with the third parameter. `null` is just there for reasons and `this` is just passing on the `this` value to the function. We now need to make a function `collectCoin` that will run if there is an overlap: ```javascript this.collectCoin = (player, coin)=>{ player.score+=10; this.scoreText.setText("Score: "+ this.player.score); coin.destroy(); }; ``` If you run this you will see that you can now collect coins and increase your score. Success! There is only one more step before we are done. #### Spikes Time to add some difficulty to the game. We are going to have spikes that if you step on they will clear your score and respawn you. Let's first add them to our map as an `s`: ```javascript const map = '11111111111111111111111111.'+ '1 c 1.'+ '1 c c s c 1.'+ '1 2 1 s 1 c 1 c 1 1.'+ '1 1 1 1 1 1.'+ '1 1.'+ '1 c c s s 1.'+ '1 c 1 s 1 c 1 c 1 1.'+ '1 1 1 1 1 1.'+ '1 1.'+ '1 c s c c 1.'+ '1 s 1 c 1 c 1 s 1 1.'+ '1 1 1 1 1 1.'+ '1 1.'+ '1 c c c c 1.'+ '11111111111111111111111111'; ``` And now we can render them into our game: ```javascript this.platforms = this.physics.add.staticGroup(); this.coins = this.physics.add.group(); //================================== this.spikes = this.physics.add.group(); //================================== let mapArr = map.split('.'); let drawX = 0; let drawY = 0; mapArr.forEach(row=>{ drawX = 0; for(let i = 0; i<row.length; i++){ if(row.charAt(i)==='1'){ this.platforms.create(drawX, drawY, "platform"); }else if(row.charAt(i)==='2'){ if(row.charAt(i+1)==='1'){ this.spawnPlayer(drawX-4, drawY-12); }else if(row.charAt(i-1)==='1'){ this.spawnPlayer(drawX+4, drawY-12); }else{ this.spawnPlayer(drawX, drawY-12); } }else if(row.charAt(i)==='c'){ this.coins.create(drawX, drawY+10, "coin"); //================================== }else if(row.charAt(i)==='s'){ this.spikes.create(drawX, drawY+10, "spike"); } //================================== drawX+=40; } drawY+=40; }); ``` Let's do what we did last time - add an overlap detector between the player and the spikes. The code is pretty much the same: ```javascript //Next to the other overlap checker for the coins this.physics.add.overlap(this.player, this.spikes, this.die, null, this); ``` And now we have to make a function `die` that will be run when the player hits the spike. All we will do is stop the game and display text saying **YOU DIED**: ```javascript this.die = ()=>{ this.physics.pause(); let deathText = this.add.text(0, 0, "YOU DIED", { color:"#d53636", fontFamily:"Arial Black", fontSize:"50px" }).setScrollFactor(0); Phaser.Display.Align.In.Center(deathText, this.add.zone(400, 250, 800, 500)); } ``` `this.physics.pause` is what stops the game. The text adding should be pretty self explanatory. The bit that may be confusing is the line after that. This is the code I used to center the text. It accepts two arguments - the object to center and the zone in which to center it in. `this.add.zone` in turn accepts four arguments - the x, y, width and height of the zone. The x and y are in the center of the screen and the width is the width of the screen and the same for the height. When you run this code and jump on a spike you will see that it shows some big red text saying __YOU DIED__. And there we have it! Our completed game! Make sure to celebrate by wrapping __lots__ of duct tape around some cardboard. That was what the duct tape and cardboard were for. Nothing, really :). ## Final Word Thank you for sticking to the end of this monster of a tutorial. I hope you are proud of what you have made. If you liked this tutorial, please show support by voting for it. If you have any questions, suggestions or if you found a typo don't hesitate to post it in the comments! Also, if you put a spin on the game or make a cool map that be sure to share it! I would love to see what you guys can make out of this :). If you are too lazy to scroll up, the link to the repl that I made is [here](https://phaser-tutorial.kaldisberzins.repl.co/). Also, if you would like me to make some follow up tutorials outside of the competition about some more advanced features like scenes and (multiplayer?) then be sure to leave a comment. If enough people want it I will be sure to make some more tutorials. ## __EDIT__ I made an additional demo that delves into some more complicated concepts but it looks a lot better (I stole some sprites off the internet). It is just some uncommented code that you can play around with and try and see if you can make anything out of it. If you want to check it out you can find it [here](https://repl.it/@kaldisberzins/Phaser-Demo). Just wanna play it? Go [here](https://phaser-demo--kaldisberzins.repl.co/). Also, thank you guys for all the support in the comments! So heartwarming to see that many people like it. [email protected]_
17
posted to Learn by kaldisberzins (176) about 1 month ago
โ–ฒ
70
Build a WhatsApp bot in 30 minutes ๐Ÿ•
A few months ago, I'd started making chatbots on [Telegram](https://t.me) - I'd seen APIs for WhatsApp but they were unoffical and there was a chance for getting your number blocked ๐Ÿ“ฑ โŒ A while ago, I saw that [Twilio](https://twilio.com) had an official WhatsApp API. 30 minutes later, I made a [Wikipedia bot on WhatsApp](https://wikibot.4ty2.fun) ๐Ÿ‘‡ ![](https://wikibot.surge.sh/Untitled-b9da3f92-94c0-4f97-8afb-787110d8a9d3.png) This is a tutorial to help you make a something like this, your own chatbots on WhatsApp - these bots are immediately available to 2 billion users, and there are so many things possible ๐ŸŽ“ I can't wait to see what you make! Now, let's get started ๐Ÿƒโ€โ™‚๏ธ ## ๐Ÿ”‘ Accounts and Keys First, Sign up for [Twilio](https://www.twilio.com/try-twilio) - it's free and you won't need a credit card ๐Ÿ’ณ ![](https://wikibot.surge.sh/screely-1535885763017-fc654067-9557-4bf7-98b5-4337911ff4ba.png) Once you're done verifying your phone number, select Procuts > Programmable SMS and then continue to name your project. ![](https://wikibot.surge.sh/screely-1535885937977-c5a924ec-8cc3-4430-9345-9b5e1dc74ef3.png) Feel free to skip steps for adding teammates - you won't need that for now. You must now take note of some authentication keys you'll need for building the WhatsApp bot ๐Ÿ‘‡ ![](https://wikibot.surge.sh/screely-1535886250966-f68b6cfb-c104-4adf-80e7-4e3f9bd15b5b.png) The final step - setup your WhatsApp Sandbox [here](https://www.twilio.com/console/sms/whatsapp/sandbox) - choose any number, and join your sandbox following instructions on the page. ![](https://wikibot.surge.sh/screely-1535886798623-1dac1ba9-c362-4e49-87ab-7bbb6138e8c7.png) Aaaaaand you're done with credential setup! Don't worry, that was the toughest part of this tutorial ๐Ÿ˜› ## ๐Ÿš€ Getting Started So that we don't spend too much time on setup, I've created an environment (with repl.it!) you can use within your browser. Head over [here](https://repl.it/@jajoosam/wikibot-start), and wait for a couple of seconds to fork it. Next, open up `server.js` and put in your Account SID and Auth Token, on lines `7` and `8` ```javascript const accountSid ="XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"; //Account SID const authToken ="XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"; // Auth Token ``` You can see, this environment already has dependencies installed, and an `express` server set up. We still need to give Twilio a URL to send incoming messages to, though ๐Ÿ”— Let's go back to the [WhatsApp Sandbox](https://www.twilio.com/console/sms/whatsapp/sandbox), and put in a webhook URL for incoming messages. ![](https://wikibot.surge.sh/Untitled-3ed5263b-c6d8-492b-ba08-b4644ab502cf.png) This URL must be what you see on the preview panel of your [repl.it](http://repl.it) project + `/incoming` ![](https://wikibot.surge.sh/Untitled-1779b21f-9100-4942-b732-320dc48c5f76.png) We can now finally read messages that are sent to the bot. Add a simple `console.log()` in your webhook handler ๐Ÿ‘‡ ```javascript app.post('/incoming', (req, res) => { console.log(req.body) }); ``` When you send a message to your bot, you should be able to see something like this in your repl console ๐Ÿ‘จโ€๐Ÿ’ป ![](https://wikibot.surge.sh/Untitled-163eb09e-e6ab-4910-badb-d8aa0aa789f7.png) Building an echo bot would look something like this, using `twiml` to write a message ๐Ÿ‘‡ ```javascript app.post('/incoming', (req, res) => { const twiml = new MessagingResponse(); twiml.message(req.body.Body); res.writeHead(200, {'Content-Type': 'text/xml'}); res.end(twiml.toString()); }); ``` But, since we're actually trying to build a useful bot - let's use informative APIs! ## ๐ŸŒ Fetching Information DuckDuckGo has an amazing, free instant answer API. It takes in a query and returns back a summary from WikiPedia and more. A few examples ๐Ÿ‘‰ [WikiPedia](https://api.duckduckgo.com/?skip_disambig=1&format=json&pretty=1&q=WikiPedia), [Macbook Air](https://api.duckduckgo.com/?skip_disambig=1&format=json&pretty=1&q=MacBook%20Air), [Twilio](https://api.duckduckgo.com/?skip_disambig=1&format=json&pretty=1&q=Twilio) I spent some time creating a decent parser which usually returns information from this API. Try pasting this code in your [repl.it](http://repl.it) project, and your [console](https://dsh.re/f7477c) should have stuff about Trump in it ๐Ÿ˜› ```javascript var base = 'https://api.duckduckgo.com/?skip_disambig=1&format=json&pretty=1&q='; var query = 'Donald Trump'; request(base + query, function (error, response, body) { body = JSON.parse(body) if(body["Abstract"] == ""){ body["Abstract"]= body["RelatedTopics"][0]["Text"] } var msg = body["Heading"]+"\n\n"+body["Abstract"]; console.log(msg) }); ``` Pretty straight forward, right? ๐Ÿ˜„ ## ๐Ÿ› ๏ธ Putting it all together To make our actual bot, all we need to do is get the query from our request - which we can get as `req.body.Body` - and use `twmil` to send across the data we collected in `msg` ```javascript app.post('/incoming', (req, res) => { const twiml = new MessagingResponse(); var base = 'https://api.duckduckgo.com/?skip_disambig=1&format=json&pretty=1&q='; var query = req.body.Body; request(base + query, function (error, response, body) { body = JSON.parse(body) if(body["Abstract"] == ""){ body["Abstract"]= body["RelatedTopics"][0]["Text"] } var msg = twiml.message(body["Heading"]+"\n\n"+body["Abstract"]); res.writeHead(200, {'Content-Type': 'text/xml'}); res.end(twiml.toString()); }); }); ``` You now have a fully functionaing WhatsApp bot! Send anything you want to know about your bot ๐Ÿค– and you should see it respond super fast ๐Ÿ’ฌ โšก Adding welcome messages and a little formatting is quite simple, look at the final [repl](https://repl.it/@jajoosam/wikibot) to see how I did it ๐Ÿ‘จโ€๐Ÿ’ป ## ๐Ÿ”— Sharing the bot For others to use this bot, they'll need to join your sandbox first - and send a message just like you did earlier ๐Ÿ‘‰ `join <two-words>` You can create links with this text too - For example this link lets you join my bot ๐Ÿ‘‡ ``` https://wa.me/14155238886?text=join ultramarine-tapir ``` `14155238886` is my bot's number, while `ultramarine-tapir` is the sandbox phrase. ## โšก What's next? Now that you know how to build a bot on WhatsApp, try sending notifications to yourself, and building more useful tools! Twilio has loads of [other mediums](https://www.twilio.com/channels) to message through too! All code for my WikiBot is on [Github](https://github.com/jajoosam/wikibot)! I'm a 15 year old maker ๐Ÿ‘จโ€๐Ÿ’ป For more cool things to make and to stay update with my progress, sign up for [my newsletter ๐Ÿ“ง](https://buttondown.email/jajoosam)
10
posted to Learn by jajoosam (93) 29 days ago
โ–ฒ
12
three lesson
my lesson
1
posted to Share by EnteFool (11) 6 days ago
โ–ฒ
27
Cookie Clicker: Terminal Edition
I'm still adding some things to it. You have to run it at https://jam4.pyelias.repl.run/ for it to work properly. EDIT: yay i won the code jam See the code jam grades at: https://docs.google.com/spreadsheets/d/1K_xkdKIcdFfAdaL3JbQ13h4BLT9VtIXgcQtJYPhnSTY/edit#gid=197356522
11
posted to Share by pyelias (569) 17 days ago
โ–ฒ
5
Omega Psi
# Omega Psi It's a nice bot with features being added every day that I have free time. ## What does it have? * Custom Prefixes (*you can have multiple prefixes in your server*) * Meme generator (*memes with your own text. you don't have to use Photoshop anymore*) * Server Moderation * Change your server name * Add / Remove Roles * Minigames (*it also has universal game stats; AKA your stats will be the same on every server Omega Psi is in and private messages*) * Connect Four * Hangman * Rock, Paper, Scissors * Tic-Tac-Toe * Private Message Support (*You can play minigames with the bot in a Private Message*[1]) * Math Commands * Gif Commands * Ranking System (*it is disabled by default*) ## Other Info If you are the server owner and someone adds the bot to your server, you are automatically given the bot's `server mod` permission. [1] - You and the bot must be in at least 1 server together for this to work
1
posted to Challenge by FellowHashbrown (4) 2 days ago
โ–ฒ
9
Blog in Node.js
Check out my blog that I wrote a while ago in Node.js. It used to be hosted somewhere else but now repl.it is powerful enough to host it for me. The way it works is that it has an `essays/` folder with markdown files and every file has a descriptor -- title, date, etc -- at the top. When the server starts it reads the essays directory, parses the files, and builds the index. It's simple, but I like the freedom it gives me to change it easily, unlike some static site generators where they can be really hard to change.
3
posted to Share by amasad (638) 6 days ago
โ–ฒ
2
Rock Paper Scissors Game in 60 lines (Python3)
To build our *Rock Paper Scissors* game we are going to use some elements of OOP, in fact, we are just going to create **one** `class` that is going to do all of it. So, without further ado... 1. `import` function `choice` from `random` module 2. declare `class RPS` 3. create an instance of this `class` called `game` ```python from random import choice class RPS: def __init__(self): pass # some more functions will go here game = RPS() ``` Inside the `__init__` function, we are going to have 4 variables: + `opt` is a `list` of options + `usr_score` and `cpu_score` are self-explanatory + `rules` is a `dict` that is going to help us decide who won without the need for extensive `if / else` statements The last line of `__init__` is going to be a call to some function `match` that also belongs to the `class RPS`. ```python # from now on we concentrate on the RPS class itself class RPS: def __init__(self): self.opt = ['rock', 'paper', 'scissors'] self.usr_score = 0 self.cpu_score = 0 self.rules = { 'rock' : 'scissors', 'paper' : 'rock', 'scissors' : 'paper' } self.match() # some more functions will go here def match(self): pass ``` Now, before we start implementing the `match` function, let's declare some useful 'helper' functions. I really like using functions in my code because they make debugging really easy, so do not be surprised when you see a function that is one line long... ```python # from now on we concentrate on the RPS class itself class RPS: def __init__(self): self.opt = ['rock', 'paper', 'scissors'] self.usr_score = 0 self.cpu_score = 0 self.rules = { 'rock' : 'scissors', 'paper' : 'rock', 'scissors' : 'paper' } self.match() def err(self, msg): print(f"ERROR: {msg}") def disp_scores(self): print(f"SCORES:\n\tYOU: {self.usr_score}\n\tCPU: {self.cpu_score}\n") def tie(self): print("It's a tie") self.usr_score += 1 self.cpu_score += 1 def usr_win(self): print("You won!") self.usr_score += 1 def cpu_win(self): print("CPU won!") self.cpu_score += 1 def ask(self): pass def match(self): pass ``` These 'helper' functions are going to be called each time we run the `match` function. You may have also noticed the `ask` function almost at the very end of the `class` definition. This function has to make sure that we get user input in the **correct** format before evaluating the results. This function, in case of invalid user input becomes *recursive*, so "Yaaay!". Let's see... First of all, in the `ask` function, we want to display the options. For user's convenience, we are going to enumerate them: ```python # now concentrating on the ask function def ask(self): for i in range( len(self.opt) ): print(f"{i + 1}. {self.opt[i]}") # it's incomplete, we're gonna write some more here! ``` Now, we are going to ask user for `input`: ```python # now concentrating on the ask function def ask(self): for i in range( len(self.opt) ): print(f"{i + 1}. {self.opt[i]}") usr = input("\nSelect one option: ") # it's incomplete, we're gonna write some more here! ``` We, as software developers, have to think ahead and always assume that user is an idiot who always makes mistakes (but we still love him). Therefore, next few lines are going to deal with `exception`s that may arise if an invalid input is given: ```python # now concentrating on the ask function def ask(self): for i in range( len(self.opt) ): print(f"{i + 1}. {self.opt[i]}") usr = input("\nSelect one option: ") try: usr = int(usr) - 1 except ValueError: self.err("INPUT INVALID! YOU MUST INPUT A NUMBER!\n") return self.ask() if -1 < usr < len(self.opt): return self.opt[usr] else: self.err( "INPUT INVALID! YOU MUST INPUT A NUMBER BETWEEN 1 AND {len(self.opt)}!\n" ) return self.ask() ``` Note that whenever we encounter an error, we let user know by displaying an error message and then we `return self.ask()`. This is because we want to run function `ask` again and again until user would be so kind as to provide us with a valid input value which we are then going to return. At this point, we have actually completed three fourth of our game! Congrats! Now the last bit: the `match` function. The `match` function is a lazy dude that uses other functions' labour to fulfill its own purpose, but we aren't angry at it... after all, we've designed it this way :) First two lines will select CPU's choice and `ask` user to input their answer. Let's also `print` those, so that the user knows what CPU's choice was. By the way, for those of you who don't know how `random.choice()` function works, it is a pseudo-random function that `return`s one value from a given `list` (in this case, the `opt` list). ```python # now concentrating on the match function def match(self): cpu = choice(self.opt) usr = self.ask() print(f"You chose {usr.upper()} and CPU chose {cpu.upper()}") ``` When we have those choices, we can evaluate and decide who is the winner. As I said earlier on, the `dict` called `rules` will help us with it. How does it work then? Well, if we take a look at the `rules`... ```python self.rules = { 'rock' : 'scissors', 'paper' : 'rock', 'scissors' : 'paper' } ``` ...we can see that item on the left always beats items on the right and this is very useful in this case. For every pair of choices, there are only 3 possible outcomes: 1. Both choices are the same and thus, it is a tie 2. User wins 3. CPU wins Therefore, logically, the first thing to do is to check whether it is a tie (it's also the easiest one). If we use user's choice as a key and request its value from the `rules` and this value is equal to CPU's choice then we know that user won since we've designed `rules` in such way the any key 'beats' its value. If it is not a tie and user didn't win, then we must give point to the CPU. This is how it looks in code: ```python # focusing on the match function def match(self): cpu = choice(self.opt) usr = self.ask() print(f"You chose {usr.upper()} and CPU chose {cpu.upper()}") if usr == cpu: self.tie() else: if self.rules[usr] == cpu: self.usr_win() else: self.cpu_win() ``` The `match` function is almost complete now: only 5 lines to go. We want to display scores, which is easily done using the `disp_scores` function. And the last bit: we want to know whether the user wants to play one more time or quit the game, so we declare a `bool` variable that is going to be the answer to this question and its value will, once more, depend on the user `input`. If it is `True`, we'll call our `match` function again, otherwise we'll `print("Bye-bye!")`. ```python # focusing on the match function def match(self): cpu = choice(self.opt) usr = self.ask() print(f"You chose {usr.upper()} and CPU chose {cpu.upper()}") if usr == cpu: self.tie() else: if self.rules[usr] == cpu: self.usr_win() else: self.cpu_win() self.disp_scores() endit = input("If you want to stop, enter 'q'. Otherwise, press ENTER. ").lower() == 'q' print() # this is just for spacing if not endit: self.match() else: print("Bye-bye!") ``` That's it fellas. We are officially done now. Hope it was fun. There you have the [Link to the Repl](https://repl.it/@sharpvik/Rock-or-Paper-or-Scissors) containing my source code for this game.
1
posted to Learn by sharpvik (29) about 5 hours ago
โ–ฒ
9
No Pressing Enter!
Get input from the user without pressing the enter key! Good for moving a player or a game of tetris! Or use [@pyelias's example](https://repl.it/@fullern000/Pyelias-No-Enter)
2
posted to Share by fullern000 (647) 6 days ago
โ–ฒ
48
How To Create A Black Hole Spiral in Python W/ Turtle
Hello Programmers, This is a innovative and creative way of showing of your programming skills in Python with Turtle by creating this Spiral which later centres into a Black Hole. Step 1 - Import and Name your turtle Step 2 - Create a for - in range and mark anything more than 100 Step 3 - Go forward by 180 or more Step 4 - Go left by 70 or more Step 5 - Go forward by 60 or more Step 6 - Go right by 40 or more Step 7 - Pen up Step 8 - Set position 0,0 Step 9 - Pen down Step 10 - Go right by 2 or more Challenge: Add Colour to make it a Rainbow Spiral There you have it Ten Easy Steps to make a pretty fascinating Black Hole Spiral and impress other programmers.
44
posted to Share by nothplus (56) about 1 month ago
โ–ฒ
3
Sign Bunny
A bot that generates a custom sign bunny whenever requested. All that you need to do is write `!bunny <message>` in a server where the bot is enabled and it generates somthing like: ``` |-------------| | THE QUICK | | BROWN FOX | | JUMPED OVER | | THE LAZY | | DOG | |-------------| (\__/) || (โ€ขใ……โ€ข) || / ใ€€ ใฅ ``` Add it to a sever [here](https://discordapp.com/api/oauth2/authorize?scope=bot&client_id=511688790994059267)
1
posted to Challenge by liamrosenfeld (2) about 19 hours ago
โ–ฒ
41
A Crash Course in LOLCODE ๐Ÿฑ
# A Crash Course in LOLCODE ___ OHAI! This is a crash course in the beautiful programming language known as LOLCODE! LOLCODE is a great language, and while it is similar to many other programming languages, trying to learn it may confuse some people because of the syntax. For this tutorial, any time I say `[variable1]`, `[variable2]`, or `[variable]`, as long as I'm not talking about initializing a variable, you can put a value instead. ### Creating a new program To begin a program, you need to have the line `HAI 1.2`. This will declare that it's a LOLCODE program that's written in LOLCODE 1.2. The last line in the program must be `KTHXBYE`. ### Comments There are two different ways of doing commenting - `BTW` and `OBTW`. The differences are shown below: ```lolcode BTW This is a one-line comment. OBTW This is a multi-line comment TLDR ``` The indentation is not necessary, but it makes it easier to read. ### Variables Variables are dynamically typed in LOLCODE, so you don't have to give them a type when declared. To declare a variable, use `I HAS A [variable]`. However, if you do want to give it a type, you can use `I HAS A [variable] ITZ A [type]`. There are 4 usable types of variables: - TROOF (a boolean - `WIN` or `FAIL`, corresponding to true or false.) - NUMBR (an integer - whole numbers) - NUMBAR (a float - decimal places) - YARN (a string - text, defined by "") Variable names are case-sensitive, so INT is different from Int. You can use capital and lowercase letters, underscores, and numbers - as long as neither underscores nor numbers begin the variable name. To assign one variable to another, use `[variable 1] R [variable 2]`. ### Concatenation It's very simple to concatenate YARNS in LOLCODE - you use `SMOOSH [variables to concatenate, seperated by AN] MKAY`. It will cast any input given to it to a YARN before concatenating. See below for an example. ```lolcode I HAS A VAR1 ITZ "Hi" I HAS A VAR2 ITZ 1234 I HAS A VAR3 ITZ WIN I HAS A VAR4 ITZ SMOOSH VAR1 AN VAR2 AN VAR3 MKAY VISIBLE VAR4 BTW The output will be Hi1234WIN ``` ### Casting There are a couple different ways of casting a variable from 1 type to another. The first is `MAEK [variable] A [type]`. This will attempt to cast from whatever type the variable is to the desired type. However, this will not work if it's illogical - for instance, trying to cast letters into a NUMBR or NUMBAR. To cast a variable to a different type and save the output in a different variable, use `[variable 1] R MAEK [variable 2] A [type]`. ### Expressions There are 3 different types of expressions in LOLCODE - **Math**, **Boolean**, and **Comparison**. The basic form for all expressions is either `[expression] [variable]` or `[expression] [variable1] AN [variable2]`. #### Math In LOLCODE, you have all the typical expression types - addition, subtraction, multiplication, division, and modulus (remainder), as well as some less-common ones - min (returns the value of the smaller of 2 variables) and max (returns the value of the larger of 2 variables). If either variable is a YARN and has a decimal, it is cast to a NUMBAR for the calculation. If it doesn't have a decimal, it's cast to a NUMBR. If both variables used are NUMBRs, then integer math is performed. If one or both are NUMBARS, floating floating point math is invoked. See below for a list of math expressions: ```lolcode SUM OF [variable 1] AN [variable 2] BTW This is addition DIFF OF [variable 1] AN [variable 2] BTW This is subtraction PRODUKT OF [variable 1] AN [variable 2] BTW This is multiplication QUOSHUNT OF [variable 1] AN [variable 2] BTW This is division MOD OF [variable 1] AN [variable 2] BTW This is modulus (remainder) BIGGR OF [variable 1] AN [variable 2] BTW This returns the bigger variable's value SMALLR OF [variable 1] AN [variable 2] BTW This returns the smaller variable's value ``` #### Boolean The boolean expressions work pretty much as you would expect, comparing WINs and FAILs. You can use and, or, xor, and not. Any value passed to this is cast to a TROOF. See below for the complete list: ```lolcode BOTH OF [variable 1] AN [variable 2] BTW This is an and statement EITHER OF [variable 1] AN [variable 2] BTW This is an or statement WON OF [variable 1] AN [variable 2] BTW This is an XOR statement NOT [variable] BTW This is a not statement ALL OF [variable 1] AN ... MKAY BTW This is an infinite and statement, keep adding variable names and ANs to check more ANY OF [variable 1] AN ... MKAY BTW This is an infinite or statement, see above ``` ### Comparisons This is very similar to boolean expressions - it takes in 2 variables and checks if they're either the same or different. However, it doesn't have to be 2 TROOFS, but they do have to be the same type. "9" and 9 will NOT be recognized as the same. See below for examples ```lolcode BOTH SAEM [variable 1] AN [variable 2] BTW returns WIN if variable 1 == variable 2 DIFFRINT [variable 1] AN [variable 2] BTW returns WIN if variable 1 != variable 2 BOTH SAEM [variable 1] AN BIGGR OF [variable 1] AN [variable 2] BTW variable 1 >= variable 2 BOTH SAEM [variable 1] AN SMALLR OF [variable 1] AN [variable 2] BTW variable 1 <= variable 2 DIFFRINT [variable 1] AN BIGGR OF [variable 1] AN [variable 2] BTW variable 1 > variable 2 DIFFRINT [variable 1] AN SMALLR OF [variable 1] AN [variable 2] BTW variable 1 < variable 2 ``` ### Printing To output text, you have to use the `VISIBLE [output]` command. This can also be used with variables by using `VISIBLE [variable]`. See below for examples: ```lolcode VISIBLE "Invisible" VISIBLE INT ``` ### Input To get input from the user, you can use `GIMMEH [variable]`. For this, you MUST specify a variable because that is where the output is stored. GIMMEH stores input as a YARN, so if you want to get a NUMBR or NUMBAR you have to cast it as such. ### Conditionals Creating conditionals is fairly straightforward in LOLCODE. There are 2 basic formats - one utilizing TROOFs, and one utilizing other types of variables. To create a conditional using TROOFs, use the following: ```lolcode [expression], O RLY? YA RLY BTW This code will execute if the result of [expression] is WIN NO WAI BTW This code will execute if the result of [expression] is FAIL OIC ``` To create a conditional using other variable types is a little more involved. Basically, `OMG [value]` is the same as checking if the expression is equal to [value], and `OMGWTF` is an else. To end a statement, you must put GTFO. ```lolcode [expression], WTF? OMG 5 BTW This code will execute if the result of [expression] is 5 GTFO OMG 91 OMG 21 BTW This code will execute if the result of [expression] is 91 or 21 GTFO OMGWTF BTW This code will execute if the result of [expression] is not 5, 91, or 21 OIC ``` ### Loops Loops are a somewhat confusing beast at first, but actually aren't that hard. First, you need `IM IN YR [label for the loop - I would recommend just calling it LOOP]`. Then, if you want to increase the iterator variable have `UPPIN YR [variable]`, and if you want to decrease the iterator variable have `NERFIN YR [variable]`. Finally, if you want to go until a certain value, use `TIL [expression]`, and if you want to go while a certain expression is true, use `WILE [expression]`. To end the loop, use `IM OUTTA YR [label]`. See below for an example: ```lolcode I HAS A ITERATOR ITZ 0 IM IN YR LOOP UPPIN YR ITERATOR TIL BOTH SAEM ITERATOR AN 9 VISIBLE ITERATOR IM OUTTA YR LOOP BTW This will output 0 through 8, and then stop before printing 9. ``` ### Conclusion Aaaand that's pretty much everything I could possibly find on the internet about LOLCODE... There is documentation for functions and BUKKITs (arrays), but I couldn't get them to work and so I decided against detailing them. If you still want MOAR LOLCODE documentation, go [here](https://github.com/justinmeza/lolcode-spec/blob/master/v1.2/lolcode-spec-v1.2.md), [here](https://esolangs.org/wiki/LOLCODE), or [here](https://learnxinyminutes.com/docs/LOLCODE/). If you want a fairly simple random python with turtle spiral generator, go check out my tutorial for that [here](https://repl.it/talk/challenge/Python-Turtle-Graphics-Random-Spirals/7651). If you want a super long tutorial about how to make your own game using only python with turtle graphics, go [here](https://repl.it/talk/challenge/How-to-make-a-fairly-basic-game-using-Python-with-Turtle-Graphics/8182). If you liked this tutorial, feel free to leave an upvote. Thanks! :)
9
posted to Learn by minermaniac447 (59) 28 days ago
โ–ฒ
30
Tutorials Challenge Results
## Congratulations to the winners! * 1st: [@kaldisberzins](https://repl.it/@kaldisberzins) for his tutorial on an [HTML5/Phaser.js game](https://repl.it/talk/learn/Making-a-Phaser-Game-with-HTML5-and-JavaScript/7593) * 2nd: [@jajoosam](https://repl.it/@jajoosam) for his [30 Minute WhatsApp Bot](https://repl.it/talk/learn/Build-a-WhatsApp-bot-in-30-minutes/7673) * 3rd: [@ArtemLaptiev1](https://repl.it/@ArtemLaptiev1) for his [Beginners Neural Networks Tutorial](https://repl.it/talk/learn/Building-AI-Neural-Networks-for-beginners/8156) Plus many other notable entries, which can be found on [Repl Talk Learn](https://repl.it/talk/learn/). ORIGINAL POST BELOW: --- ~The challenge has begun! Feel free to post your tutorials on the Challenge board! The competition will end on Monday, Nov 5th, 2018 at 12:01 EST.~ Requirements: * Your submission must be a tutorial. It can be a tutorial about anything - surprise us with your creativity. :) * It must use Repl.it. Attach the end result repl to the post. Prizes: * First Place: $100 Amazon Gift Card * Second Place: $50 Amazon Gift Card * Third Place: $25 Amazon Gift Card First, second, and third place prizes will be determined by the Repl.it team, who will take the following factors into consideration: * Quality of the submission * Number of upvotes it received * How many people engaged with it Additionally, the Repl.it Team will be awarding various prizes for quality submissions that went under the radar. We may even reach out to you for working with Repl.it further! Please remember that Repl Talk allows Markdown, so [style your tutorials](https://repl.it/talk/learn/A-Quick-Guide-to-Replit-Talk-Markdown/7448) for maximum readability!
100
posted to Challenge by timmy_i_chen (423) about 1 month ago
โ–ฒ
10
First Official Repl.it Art: MULTIPLAYER
We commissioned an artist to make something for the upcoming Multiplayer feature (renamed from "live-coding"). This is what he came up with -- what do you guys think? ![replit-3](https://storage.googleapis.com/replit/images/1541443245473_26de59e47478d2db85a79b2efe3b7bdb.jpe) ![replit-comingsoon](https://storage.googleapis.com/replit/images/1541740625199_6c805c431f2d3d00932296548fc2977a.jpe)
5
posted to Announcements by amasad (638) 9 days ago
โ–ฒ
9
Battlegrounds: Console Edition
Well, this is one of my first fighting games. Pretty simple, and basically a fungus compared to a videogame like Fortnite. But please try it. Although the instructions are in the game, here are the instructions: It is you versus the enemy. The enemy has attacked your hill. Your goal: _Defend your stand._ You take turns striking blows against each other. Here are actions you can do when it is your turn to strike: - Attack up (type, AU) - Attack down (type, AD) Once your turn has passed, it will be the opponents's turn to fight back. But you can defend yourself. - Block Attack (type, BL. Half of the damage is dealt.) - Dodge Up (type, DU. there is a 50% chance of being hit.) - Dodge Down (type, DD. there is a 50% chance of being hit.) A full hit = 20 damage A blocked hit = 10 damage A dodged hit = No damage You keep taking turns until one of you falls. Are you ready? Fight! (Press "Enter/Return" to continue...) ================================================================ My final words for you: "Enjoy the game!" (I admit, "My final words" doesn't sound very good.) P.S. The game looks best if you go to this link: http://battlegrounds.grantkeo.repl.run/ ![ASCII Soldier 1](https://storage.googleapis.com/replit/images/1541516425273_e9f81f262c7f30f35639a29e0376fa5b.pn)
5
posted to Share by GrantKeo (9) 8 days ago
Pinned
โ–ฒ
207
๐Ÿ‘‹โœจIntroduce yourself ๐ŸŽ‰๐Ÿ˜€
Hello everyone! Let's use this thread to get to know each other. Just say hi and a few words about who you are, maybe what are you building or learning with Repl.it. If you're not comfortable sharing anything then share something fun ๐Ÿ˜‰
646
posted to Announcements by amasad (638) 4 months ago
โ–ฒ
11
Weekly Repls #8
Welcome back to everyone's favorite article, the weekly repl highlights! This week we don't have that many, however each one is full of awesome stuff! @rafaelcastrocouto [With the power of node.js express, this person was able to make a sweet asteroids game!](https://repl.it/talk/share/Space-shooter/8214) @CodeRKane [Sorting is very important in programming. Here is a program that goes over them, and does a great job too.](https://repl.it/talk/share/First-Sorting-Library-Still-Incomplete/8176) @jajoosam [created a blog - only this time, it's completely terminal-based and uses Repl Run instead of any servers/web development.](https://repl.it/talk/share/A-blog-on-the-terminal/8256) See you guys next week, and keep up the great work!
2
posted to Announcements by 21natzil (202) 9 days ago
โ–ฒ
25
3D graphics, a beginners mind.
# Preface In this tutorial I would like to show how 3d graphics is done today, why it's important, and how it will change the way you see 3d graphics applications. To better understand, we'll end up creating a 3d engine with Python. # Requirements I expect you to be familiar with Python, if you understand what `class` means you're probably qualified in this department. I also expect you to understand what the terms fov (field of view), vertex, mesh..etc. mean. # But 3d graphics is hard! No, it's not. This is an awesome area of programming you'll be able to show to your friends, there *will* be math(s) involved, so strap in, but it'll all be explained. If there are aspects you do not understand, simply copy my solution. # Fundamentals To start, let's go through the basic building blocks. Imagine we have a simple object, a cube. ![blender_2018-10-24_10-42-00](https://image.ibb.co/b5RdgV/blender-2018-10-24-10-42-00.png) There's more going on under the hood, this cube is made up of two things, *vertexes* and *triangles*. Vertexes are essentially points in 3d space. Look around your room, and imagine a speck of dust, a single point in 3d space. Triangles are, well just triangles, normal 2d flat triangles. However their three points are connected to specific vertexes. Let's look at the vertexes. ![blender_2018-10-24_10-43-32](https://image.ibb.co/dtgpoA/blender-2018-10-24-10-43-32.png) On the above image of a cube, you can see there are eight points, these are the points which make up the cube. In memory, these points each have a 3d coordinate: X, Y, Z axis. however when we go to *render* the cube, we map each 3d coordinate to 2d screen space. And the way we do that is surprisingly simple. Next, let's look at the triangles. ![blender_2018-10-24_10-43-33](https://image.ibb.co/fMqh8A/blender-2018-10-24-10-43-33.png) As you can see, a triangle is now connected to three of the points. Do this 12(*) times and you'll get a cube. *: A cube is made up of 6 faces, however to make a face with a triangle, you must use two triangles, so it ends up being 12 triangles. # Enough "fundamentals", more coding! Alright, now that we understand the basic structure for rendering 3d shapes. Let's get more technical. We'll be doing this in `Python (with Turtle)`. First, we import Turtle, I will assume you already know how to use Turtle and are familiar with it's functionality. In short, it's just a graphics library aimed at kids learning how to code with graphics, and making flowers and all sorts of things... Except we'll be going much further than flowers. ```python import turtle ``` Next we need to store our object data. We need to store all our vertexes and triangles. ```python VERTEXES = [(-1, -1, -1), ( 1, -1, -1), ( 1, 1, -1), (-1, 1, -1), (-1, -1, 1), ( 1, -1, 1), ( 1, 1, 1), (-1, 1, 1)] TRIANGLES = [(0, 1, 2)] ``` For now, we only have one triangle connected to the first three points. # Our basic main loop We want to simulate a normal graphics library with turtle. Our program will follow this structure: ```python # Create turtle, pointer = turtle.Turtle() # Turn off move time, makes drawing instant, turtle.tracer(0, 0) pointer.up() while True: # Clear screen, pointer.clear() # Draw, # ... # Update, turtle.update() ``` # Rendering Alright, now we need to somehow map these 3d vertex coordinates to 2d screen coordinates. To do this, let's use the *Perspective Formula*. Before we dive into the details of what exactly this formula does, let's start with an observation. Place an object in front of you, for instance a cup. As you move away, the cup shrinks; now this is all very obvious, but it is an essential property of 3d space we must consider. When we're creating a 3d engine, what we're doing is simulating this observation. When we move away from our objects, that is - the Z axis, we're essentially *converging* the X and Y axis toward zero. Look at this front-view of a cube, you can see the back vertexes are closer to the center (zero). ![blender_2018-10-24_19-01-34](https://image.ibb.co/kzOfvq/blender-2018-10-24-19-01-34.png) # So what is this "formula"? ```python f = field_of_view / z screen_x = x * f screen_y = y * f ``` Where x, y, z are vertex coordinates. We can simplify this to: ```python f = fov / z sx, sy = x * f, y * f ``` Easy right? So let's add `FOV` at the top of the file: ```python FOV = 100 ``` # Drawing the points Let's iterate through each vertex: ```python # Draw, for vertex in VERTEXES: # Get the X, Y, Z coords out of the vertex iterator, x, y, z = vertex # Perspective formula, f = FOV / z sx, sy = x * f, y * f # Move to and draw point, pointer.goto(sx, sy) pointer.dot(3) ``` What we get is: ![chrome_2018-10-24_19-45-21](https://image.ibb.co/kONUoA/chrome-2018-10-24-19-45-21.png) But where are our four other points from before? The ones behind? The issue is we're inside the cube, we need to move the camera out. # The camera Alright, I won't go into the camera in this tutorial, you can look at my repl at the bottom to see how to properly implement a 3d engine, but we're taking baby steps here. When we think of moving the camera, we think of the camera object moving, simple right? Well that's not easy to implement in a rasterized renderer. However what's easier is to move the *world* around it. Think about it, either you can move the camera, or move the world; it's the same effect. As it turns out, it's a lot easier to offset the vertex positions than somehow change the perspective formula to equate the position; it would be a whole lot more complex. So quickly solve this, let's move the camera out: ```python # Perspective formula, z += 5 f = FOV / z sx, sy = x * f, y * f ``` ![chrome_2018-10-24_19-52-05](https://image.ibb.co/ceSJgV/chrome-2018-10-24-19-52-05.png) And adjust the `FOV` to say, `400`. ![chrome_2018-10-24_19-53-04](https://image.ibb.co/i62jMV/chrome-2018-10-24-19-53-04.png) Nice! # Drawing triangles To draw triangles, consider this code. By this point you should be able to understand it: ```python # Draw, for triangle in TRIANGLES: points = [] for vertex in triangle: # Get the X, Y, Z coords out of the vertex iterator, x, y, z = VERTEXES[vertex] print(x, y, z) # Perspective formula, z += 5 f = FOV / z sx, sy = x * f, y * f # Add point, points.append((sx, sy)) # Draw trangle, pointer.goto(points[0][0], points[0][1]) pointer.down() pointer.goto(points[1][0], points[1][1]) pointer.goto(points[2][0], points[2][1]) pointer.goto(points[0][0], points[0][1]) pointer.up() ``` # Rotation To rotate our object, we'll be using the *Rotation Matrix*. It sounds scary, right? If you're familiar with linear algebra, you should already know this, but the rotation matrix is commonly defined as: ``` [x'] = [cos(0), -sin(0)] [y'] = [sin(0), cos(0)] ``` *using `0` as theta* I won't go into detail of the matrix. If you're unfamiliar, feel free to either research or copy & paste. To implement this, we'll first need the `math` library: ```python from math import sin, cos ``` Let's make a function to rotate: ```python def rotate(x, y, r): s, c = sin(r), cos(r) return x * c - y * s, x * s + y * c ``` Then let's place this before we do our perspective formula calculations: ```python # Rotate, x, z = rotate(x, z, 1) ``` As you can see the triangle is now rotated: ![chrome_2018-10-24_20-21-51](https://image.ibb.co/n60tFq/chrome-2018-10-24-20-21-51.png) Let's make the rest of the triangles: ```python TRIANGLES = [ (0, 1, 2), (2, 3, 0), (0, 4, 5), (5, 1, 0), (0, 4, 3), (4, 7, 3), (5, 4, 7), (7, 6, 5), (7, 6, 3), (6, 2, 3), (5, 1, 2), (2, 6, 5) ] ``` ![chrome_2018-10-24_20-23-06](https://image.ibb.co/k3Knaq/chrome-2018-10-24-20-23-06.png) Awesome! Let's initialize a counter at the start of the file: ```python counter = 0 ``` and increment this at the end of every loop: ```python # Update, turtle.update() counter += 0.025 ``` And replace our rotation function: ```python x, z = rotate(x, z, counter) ``` It's rotating, awesome! To rotate on the X, Y and Z axis: ```python x, z = rotate(x, z, counter) y, z = rotate(y, z, counter) x, y = rotate(x, y, counter) ``` We're done! # Complete code Before you read, I recommend you do read through the above, I know it's easier to just skip down to the bottom for the solutions. However, if you're here after reading through the above, feel free to post `Full read` in the comments as a token of my respect, and feel free to copy this code =) ```python from math import sin, cos import turtle VERTEXES = [(-1, -1, -1), ( 1, -1, -1), ( 1, 1, -1), (-1, 1, -1), (-1, -1, 1), ( 1, -1, 1), ( 1, 1, 1), (-1, 1, 1)] TRIANGLES = [ (0, 1, 2), (2, 3, 0), (0, 4, 5), (5, 1, 0), (0, 4, 3), (4, 7, 3), (5, 4, 7), (7, 6, 5), (7, 6, 3), (6, 2, 3), (5, 1, 2), (2, 6, 5) ] FOV = 400 # Create turtle, pointer = turtle.Turtle() # Turn off move time, makes drawing instant, turtle.tracer(0, 0) pointer.up() def rotate(x, y, r): s, c = sin(r), cos(r) return x * c - y * s, x * s + y * c counter = 0 while True: # Clear screen, pointer.clear() # Draw, for triangle in TRIANGLES: points = [] for vertex in triangle: # Get the X, Y, Z coords out of the vertex iterator, x, y, z = VERTEXES[vertex] # Rotate, x, z = rotate(x, z, counter) y, z = rotate(y, z, counter) x, y = rotate(x, y, counter) # Perspective formula, z += 5 f = FOV / z sx, sy = x * f, y * f # Add point, points.append((sx, sy)) # Draw trangle, pointer.goto(points[0][0], points[0][1]) pointer.down() pointer.goto(points[1][0], points[1][1]) pointer.goto(points[2][0], points[2][1]) pointer.goto(points[0][0], points[0][1]) pointer.up() # Update, turtle.update() counter += 0.025 ``` # Conclusion If you want to see an expanded and better written version: https://repl.it/@CoolqB/3D-Engine If there's demand I will perhaps dive into shading, lighting, culling, clipping and even texturing. If you've got any questions, fire away in the comments. Good luck!
2
posted to Learn by CoolqB (54) 22 days ago
โ–ฒ
11
My first coding class with Tim. thoughts?
I'm learning more how to code with @timmy_i_chen what do you think I should learn?
13
posted to Ask by hayaodeh (53) 15 days ago
Load more