Python Lesson 33: Stopwords (NLP pt.2)

Advertisements

Hello everybody,

Michael here, and today’s post will be on stopwords in Python NLP-part 2 in my NLP series.

What are stopwords? Simply put, stopwords are words you want to ignore when tokenizing a string. Oftentimes, stopwords are common English words like “a”, “the”, and “is” that are so commonly used in English that they don’t add much meaning in text.

  • Stopwords can be found for any language, but for this series of NLP lessons, I’ll focus on English words.

Now that I’ve explained the basics of stopwords, let’s see them in action:

import nltk
nltk.download('punkt')
nltk.download('stopwords')
from nltk.corpus import stopwords

test = input('Please type in a string: ')
testWords = nltk.word_tokenize(test)

stopwordsList = set(stopwords.words('english'))

filteredList = []

for t in testWords:
    if t.casefold() not in stopwordsList:
        filteredList.append(t)

print(filteredList)

Please type in a string: The puppies and the kitties played in their playpen on the hot summer afternoon.
['puppies', 'kitties', 'played', 'playpen', 'hot', 'summer', 'afternoon', '.']

To utilize NLTK’s stopwords module, you’ll need to run the nltk.download(stopwords) command and import the stopwords module from the nltk.corpus package.

  • Yes, you’ll still need to download the punkt module, as it will enable easy tokenization, which is important to have when working with stopwords.

To store the list of tokens in the string you input, create a testWords variable that stores the output of the nltk.word_tokenize function. To get a list of NLTK’s English stopwords, use the line of code set(stopwords.words('english'))-this line of code creates a set from the list of NLTK’s English stopwords. Recall that sets are like lists, except without duplicate elements.

To gather a list of stopwords in the input string, you’d need to first create an empty list-filteredList in this case-that you’ll need to filter the stopwords out of the list of tokens (testWords in this case). To remove the stopwords, you’ll need to iterate through the list of tokens (again, testWords in this case), check if each token is in the list of stopwords and if not, add the token to the empty list you created earlier (filteredList in this case).

As you can see in the example above, the input string I used has 15 tokens (the punctuation at the end of the sentence counts as a token). After filtering out the stopwords, the resulting list only contains 8 tokens, as 7 tokens have been filtered out-The and the in their on the. Yes, even though I am iterating though a UNIQUE list of stopwords, the loop I am running will check for all instances of a stopword and exclude them from the filtered list (after all, there were three instances of the word “the” in the input string).

Ever want to see all of the words included in NLTK’s English stopwords list? Run the command print(stopwords.words('english') and you’ll see all the stopwords NLTK uses in English:

['i', 'me', 'my', 'myself', 'we', 'our', 'ours', 'ourselves', 'you', "you're", "you've", "you'll", "you'd", 'your', 'yours', 'yourself', 'yourselves', 'he', 'him', 'his', 'himself', 'she', "she's", 'her', 'hers', 'herself', 'it', "it's", 'its', 'itself', 'they', 'them', 'their', 'theirs', 'themselves', 'what', 'which', 'who', 'whom', 'this', 'that', "that'll", 'these', 'those', 'am', 'is', 'are', 'was', 'were', 'be', 'been', 'being', 'have', 'has', 'had', 'having', 'do', 'does', 'did', 'doing', 'a', 'an', 'the', 'and', 'but', 'if', 'or', 'because', 'as', 'until', 'while', 'of', 'at', 'by', 'for', 'with', 'about', 'against', 'between', 'into', 'through', 'during', 'before', 'after', 'above', 'below', 'to', 'from', 'up', 'down', 'in', 'out', 'on', 'off', 'over', 'under', 'again', 'further', 'then', 'once', 'here', 'there', 'when', 'where', 'why', 'how', 'all', 'any', 'both', 'each', 'few', 'more', 'most', 'other', 'some', 'such', 'no', 'nor', 'not', 'only', 'own', 'same', 'so', 'than', 'too', 'very', 's', 't', 'can', 'will', 'just', 'don', "don't", 'should', "should've", 'now', 'd', 'll', 'm', 'o', 're', 've', 'y', 'ain', 'aren', "aren't", 'couldn', "couldn't", 'didn', "didn't", 'doesn', "doesn't", 'hadn', "hadn't", 'hasn', "hasn't", 'haven', "haven't", 'isn', "isn't", 'ma', 'mightn', "mightn't", 'mustn', "mustn't", 'needn', "needn't", 'shan', "shan't", 'shouldn', "shouldn't", 'wasn', "wasn't", 'weren', "weren't", 'won', "won't", 'wouldn', "wouldn't"]

In total, NLTK has 179 stopwords in English, which consist of common English pronouns (I, my, you), commonly used English contracations (don’t, isn’t), conjungations of common English verbs (such as be and have), and surprisingly, contractions that you don’t hear most people use nowadays (be honest, when was the last time you heard someone use a word like shan’t or mightn’t).

  • Of course, you can always append words to NLTK’s stopwords list as you see fit, but when working with stopwords in English (or any language), I’d suggest sticking with the default stopwords list.

Now, I know I mentioned that I’ll mostly be working with English throughout my NLP lessons, but let’s explore stopwords in other languages. For this example, I’ll use the same code and same input string I used in the previous example, except this time use Spanish:

Please type in a string: Los cachorros y los gatitos jugaban en su corralito en la calurosa tarde de verano.
['cachorros', 'gatitos', 'jugaban', 'corralito', 'calurosa', 'tarde', 'verano', '.']

So, the Spanish-translated version of my previous example has 16 tokens, 8 of which appear on the filtered list. Thus, there were 8 stopwords that were removed from the testWords list.

Want to see the Spanish list of stopwords? Run the command print(stopwords.words('spanish') and take a look:

['de', 'la', 'que', 'el', 'en', 'y', 'a', 'los', 'del', 'se', 'las', 'por', 'un', 'para', 'con', 'no', 'una', 'su', 'al', 'lo', 'como', 'más', 'pero', 'sus', 'le', 'ya', 'o', 'este', 'sí', 'porque', 'esta', 'entre', 'cuando', 'muy', 'sin', 'sobre', 'también', 'me', 'hasta', 'hay', 'donde', 'quien', 'desde', 'todo', 'nos', 'durante', 'todos', 'uno', 'les', 'ni', 'contra', 'otros', 'ese', 'eso', 'ante', 'ellos', 'e', 'esto', 'mí', 'antes', 'algunos', 'qué', 'unos', 'yo', 'otro', 'otras', 'otra', 'él', 'tanto', 'esa', 'estos', 'mucho', 'quienes', 'nada', 'muchos', 'cual', 'poco', 'ella', 'estar', 'estas', 'algunas', 'algo', 'nosotros', 'mi', 'mis', 'tú', 'te', 'ti', 'tu', 'tus', 'ellas', 'nosotras', 'vosotros', 'vosotras', 'os', 'mío', 'mía', 'míos', 'mías', 'tuyo', 'tuya', 'tuyos', 'tuyas', 'suyo', 'suya', 'suyos', 'suyas', 'nuestro', 'nuestra', 'nuestros', 'nuestras', 'vuestro', 'vuestra', 'vuestros', 'vuestras', 'esos', 'esas', 'estoy', 'estás', 'está', 'estamos', 'estáis', 'están', 'esté', 'estés', 'estemos', 'estéis', 'estén', 'estaré', 'estarás', 'estará', 'estaremos', 'estaréis', 'estarán', 'estaría', 'estarías', 'estaríamos', 'estaríais', 'estarían', 'estaba', 'estabas', 'estábamos', 'estabais', 'estaban', 'estuve', 'estuviste', 'estuvo', 'estuvimos', 'estuvisteis', 'estuvieron', 'estuviera', 'estuvieras', 'estuviéramos', 'estuvierais', 'estuvieran', 'estuviese', 'estuvieses', 'estuviésemos', 'estuvieseis', 'estuviesen', 'estando', 'estado', 'estada', 'estados', 'estadas', 'estad', 'he', 'has', 'ha', 'hemos', 'habéis', 'han', 'haya', 'hayas', 'hayamos', 'hayáis', 'hayan', 'habré', 'habrás', 'habrá', 'habremos', 'habréis', 'habrán', 'habría', 'habrías', 'habríamos', 'habríais', 'habrían', 'había', 'habías', 'habíamos', 'habíais', 'habían', 'hube', 'hubiste', 'hubo', 'hubimos', 'hubisteis', 'hubieron', 'hubiera', 'hubieras', 'hubiéramos', 'hubierais', 'hubieran', 'hubiese', 'hubieses', 'hubiésemos', 'hubieseis', 'hubiesen', 'habiendo', 'habido', 'habida', 'habidos', 'habidas', 'soy', 'eres', 'es', 'somos', 'sois', 'son', 'sea', 'seas', 'seamos', 'seáis', 'sean', 'seré', 'serás', 'será', 'seremos', 'seréis', 'serán', 'sería', 'serías', 'seríamos', 'seríais', 'serían', 'era', 'eras', 'éramos', 'erais', 'eran', 'fui', 'fuiste', 'fue', 'fuimos', 'fuisteis', 'fueron', 'fuera', 'fueras', 'fuéramos', 'fuerais', 'fueran', 'fuese', 'fueses', 'fuésemos', 'fueseis', 'fuesen', 'sintiendo', 'sentido', 'sentida', 'sentidos', 'sentidas', 'siente', 'sentid', 'tengo', 'tienes', 'tiene', 'tenemos', 'tenéis', 'tienen', 'tenga', 'tengas', 'tengamos', 'tengáis', 'tengan', 'tendré', 'tendrás', 'tendrá', 'tendremos', 'tendréis', 'tendrán', 'tendría', 'tendrías', 'tendríamos', 'tendríais', 'tendrían', 'tenía', 'tenías', 'teníamos', 'teníais', 'tenían', 'tuve', 'tuviste', 'tuvo', 'tuvimos', 'tuvisteis', 'tuvieron', 'tuviera', 'tuvieras', 'tuviéramos', 'tuvierais', 'tuvieran', 'tuviese', 'tuvieses', 'tuviésemos', 'tuvieseis', 'tuviesen', 'teniendo', 'tenido', 'tenida', 'tenidos', 'tenidas', 'tened']

In comparison to the English stopwords list, the Spanish list has 313 stopwords. However, both the English and Spanish lists have the same type of elements, such as conjugations of commonly used verbs (such as ser and estar), common pronouns and prepositions (yo, tu, para, contra), among other things. What you don’t see much of in the Spanish stopwords list are contractions, and that’s because there are only two knwon contractions in Spanish (al and del-both of which are on this list) while English has plenty of contractions.

Now, one cool thing about working with stopwords (and NLP in general) is that you can play around with several foreign languages. Run the command print(stopwords.fileids()) to see all the languages you can play with when working with stopwords:

['arabic', 'azerbaijani', 'bengali', 'danish', 'dutch', 'english', 'finnish', 'french', 'german', 'greek', 'hungarian', 'indonesian', 'italian', 'kazakh', 'nepali', 'norwegian', 'portuguese', 'romanian', 'russian', 'slovene', 'spanish', 'swedish', 'tajik', 'turkish']

In total, you can use 24 languages when working with stopwords-from common languages like English, Spanish and French to more interesting options like Kazakh and Turkish. Interestingly, I don’t see an option to use Mandarin on here, as it’s a commonly spoken language worldwide.

Thank you,

Michael

It’s Our Fourth Anniversary Everybody!!!

Advertisements

Hello readers,

Michael here, and today I thought I’d celebrate the blog’s fourth anniversary (yes, I’ve been active for that long) to introduce more exciting updates to my blog (and no, there won’t be a third home). Yes, I’m still keeping my tradition of anniversary posts every June 13.

If you’ve been reading my WordPress site throughout the years, you’ll notice that not much has changed. From the blog’s name, layout, and content, not much has changed at all-after all, I’ve strived (and will continue to strive) to give you all great programming content. Hey, if it ain’t broke, don’t fix it.

But as the years have gone by, I’ve realized that this little blog of mine could use a little revamping every now and then-and to be honest, this blog is looong overdue for a little facelift.

First off, let’s start with the About Me page. Hoo boy, this may have worked when I launched this blog in 2018, but it looks awfully dated now. After all, I’m no longer a 22-year-old recent college graduate but now a 26-year-old working professional who now has had almost three years of programming job experience under his belt (when I launched this blog, I had no programming job experience, just some coding knowledge from courses I took in my last year of undergrad). Plus, I’ve been out of school for four years now-I started this blog about a month and a half after college graduation.

Now, after a little tweaking, let’s see the new About Me page:

OK, so I couldn’t capture the whole about me page in a single screenshot, but wouldn’t you say this looks much better. I describe myself and give a little more background as to why I pursued a career in coding so that you all can know why I do what I do. I also included a link to my Medium account-as many of you know, I started publishing my blogs to Medium as well as WordPress beginning in October 2021.

I also include a picture of myself, just so you-the readers-know what I look like.

  • Also, for those who may be wondering, I took this picture in June 2021 at Radnor Lake State Park in Nashville, TN. Perfect outdoor area to visit if you’re ever in Nashville.

Now, the next major update I made is post-tagging. As you readers likely have noticed, I tend to jump back and forth between programming tools a lot in my posts (e.g. in 2018, I jumped from a series of R lessons to a series of MySQL lessons and back to another series of R lessons). The reason I do this is because I like to cover a variety of programming tools to keep this blog interesting-after all, I’ve covered SEVEN different programming tools (GitHub, Python, Java, MySQL, R, HTML, and CSS) over the course of this blog’s four-year run. Since I’ve covered so many different programming tools, I know it can get messy if you’re looking for lessons pertaining to a certain tool (such as R). That’s why I’m going back and tagging all 126 of my posts (including this post). Take a look at my first R lesson from June 25, 2018:

Notice something different on the bottom? If you’ve visited my blog, you’ll notice that I didn’t have tags on my posts up until now. In this post, I just have a single tag-R-which if you click on it, you’ll see all the R posts I’ve written on this blog (well, all the R posts I’ve tagged so far):

Programming tools like R and MySQL aren’t the only things to get their own tags. Let’s say you wanted to find posts that use music-related datasets. Well, click on any post that has a music tag and watch what happens:

In this example, after I clicked on a post with a music tag, I can see all my posts that have a music tag-most of which are also MySQL lessons. For those that have read my blog for a long time, you’ll likely remember that I utilized a dataset of American music from 2000-2018 when I published my MySQL lesson series in the summer and fall of 2018.

Also, even though this is not an update, I just wanted to remind you all that, if you ever wanted to reach out to me directly, I’ve had a handy-dandy contact form on my blog since Day 1:

Hey, it’s simple, but it works. Plus, anything you post on this form will go to an e-mail account I actually check, not a throwaway account. I’d love to answer some of your coding/programming questions.

Also, last but not least, the biggest update I have for you all. You ready?

I’m changing the name of the blog! Yes, when I first created this blog, I settled on the name Michael’s Analytics Blog because, after all, my name is Michael and I was going to share solely data analytics lessons with you all (I was in the midst of a marathon of a post-college job hunt in data analytics when I launched this blog). However, throughout the years, my blog’s focus has certainly broadened from just data analytics to more programming tools such as Python, web development (with HTML and CSS) and even GitHub (recall my celebratory 100th post A Very Special 100th Post: The Basics of Git & GitHub).

So without further ado, here’s my new blog name:

Yes, this blog will now be known as Michael’s Programming Bytes. I also now have a tagline-Byte sized programming classes for all coding learners.

Honestly, with the direction the blog has taken over the last several years, I thought it was fitting to retire the Michael’s Analytics Blog name (not that there was anything wrong with it) and introduce the Michael’s Programming Bytes name. How did I land on this name? Well, think about this, dear readers. Over the last four years, I’ve given you all “bytes” of programming knowledge in seven different programming tools with each post. Plus, bytes are the smallest units of computer memory storage, and this is a programming blog after all, so I thought the name fit well.

As I just mentioned, I also have a blog tagline now-Byte sized programming classes for all coding learners. I am giving you all “byte”-sized programming “classes” with each post (hey, two programming puns in one).

  • Yes, I wanted to go all-in on the programming wordplay with the new blog name & tagline. I think you coders will get a kick out of it. Still keeping the red border on my blog-red is my favorite color after all.
  • Now that I have a new blog name, I’ll change the blog domain as well. Will keep you posted on that.

Thanks for reading these last four years! Here’s to many many more years of providing great programming content for you all.

Michael

Python Lesson 32: Intro to Python NLP (NLP pt. 1)

Advertisements

Hello everybody,

Michael here, and today I thought I’d get back into some Python lessons-particularly, I wanted to start a new series of Python lessons on a topic I’ve been wanting to cover, NLP (or natural language processing).

See, Python isn’t just good for mathematical operations-there’s so much more you can do with it (computer vision, natural language processing, graphic design, etc.). Heck, if I really wanted to, I could post only Python content on this blog and still have enough content to keep this blog running for another 6-10 years.

In the context of Python, what is natural language processing? It’s basically a concept that encompasses how computers process natural language. Natural language is basic, conversational language (whether English, Spanish, or any other language on the planet), much like what you’d use when talking to your buddies or writing a job resume.

See, when you’re writing a Python program (or any program really) you’re not feeding natual language to the computer for processing. Rather, what you feed to the computer are programming instructions (loops, conditions, print statements-they all count as programming instruction). Humans don’t speak in code, and computers don’t process instructions in “people-talk”, if you will. This is where natural language processing comes in, as developers (depending on the program being created) sometimes want to process natural language in their programs for a variety of purposes, such as data anaylsis, finding certain parts-of-speech, etc.

Now that I’ve given you a basic NLP intro, let’s dive into some coding! To start exploring natural language processing with Python, let’s first pip install the NLTK package by running this line on our command prompts (the regular command prompt, not the Anaconda prompt-if you happen to have that)-pip install nltk.

  • Remember to run the pip list command to see if you already have the nltk package installed on your device.

Once you get the NLTK package installed on your device, let’s start coding!

Take a look at this code below-I’ll dicuss it after I show you the example:

import nltk
nltk.download('punkt')

test = input('Please type in a string: ')

nltk.word_tokenize(test)

Please type in a string: Don't worry I won't be going anywhere.
['Do', "n't", 'worry', 'I', 'wo', "n't", 'be', 'going', 'anywhere', '.']

In this example, I was demonstrating one of the most basic concepts of NLP-tokenization. Tokenization is simply the process of splitting up text strings-either by word or by sentence (and more on the sentence thing later).

For this example to work, I imported the nltk package and downloaded NLTK’s punkt module-reasons for doing this are that punkt is a good pre-trained tokenizer model and in order for the tokenization process to work, you’ll need to install a pre-trained model (which doesn’t come with the NLTK package’s pip installation, sadly).

After importing the NLTK package and installing the pre-trained model, I then typed in a sentence that I wanted to toeknize and then ran the NLTK package’s word_tokenize method on the sentence. The last line of code in the example contains the output after the text is tokenized-as you can see, the tokenized output is displayed as a list of the words in the input sentence (denoted by the test variable).

Pay attention to the list of words that was generated. With words like be, going, and worry-nothing too remarkable, right? However, pay attention to the way the two contractions in the test sentence were tokenized. Don’t was tokenized as do and n't while won’t was tokenized as wo and n't. Why might that be? Well, the pre-trained NLTK model we downloaded earlier (punkt) is really good at recognizing common English contractions as two separate words-don’t is shorthand for “do not” and won’t is shorthand for “will not”. However, just because a word in the string has an apostrophe doesn’t mean it will automatically be split in two-for instance the word “Cote D’Ivore” (the Ivory Coast nation in Africa) wouldn’t be split as it’s not a common English contraction.

Pretty neat stuff right? Now, let’s take a look at sentence-based tokenization:

import nltk
nltk.download('punkt')

test = input('Please type in a string: ')

nltk.sent_tokenize(test)

Please type in a string: How was your Memorial Day weekend? Mine was fun. Lots of sun!

['How was your Memorial Day weekend?', 'Mine was fun.', 'Lots of sun!']

In order to perform sentence-based tokenization, you’d need to utilize NLTK’s sent_tokenize model (just as you would utilize word_tokenize for word-based tokenization). Just like the word_tokenize module, the sent_tokenize module returns a list of strings that were derived from the larger string but in this case, sent_tokenize splits the string based on sentences rather than individual words. Notice how sent_tokenize perfectly notices where the punctuation is located in order to split the string based on sentences.

Thanks for reading,

Michael

CSS Lesson 5: Webpage Margins and Padding

Advertisements

Hello everybody,

Michael here, and today’s post will discuss how to incorporate CSS margins and padding into your webpage.

What do margins and padding do, exactly? Well, in the context of CSS development, margins are used to create space around webpage elements outside of predefined borders. In other words, if there are some elements that you’d like to surround with some whitespace, using a margin would be perfect.

Let’s explore how margins work by first taking a look at the HTML form code we’ve used for every CSS lesson in this series thus far (the CSS stylings not including the borders from the previous lesson will remain intact here):

<!DOCTYPE html>
<html lang="es-US" dir="ltr">
  <head>
    <meta charset="utf-8">
    <link rel="stylesheet" href="Form.css">
    <link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Press+Start+2P">
    <title></title>
  </head>
  <body>
    <h1>Flight finder:</h1>
    <form action="Submitted.html" method="POST">
      <label for="datepicker1">Pick the date you want to depart for your vacation</label><br>
      <input type="date" id="datepicker1" name="datepicker1" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="datepicker2">Pick the date you want to return from your vacation</label><br>
      <input type="date" id="datepicker2" name="datepicker2" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="time1">What time would you like to depart? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time1" name="time1"><br>
      <br>
      <label for="time2">What time would you like to return? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time2" name="time2"><br>
      <br>
      <label for="layover">How many layovers do you want?</label><br>
      <input type="number" id="layover" name="layover" min="0" max="3"><br>
      <br>
      <input type="submit" value="Submit">
    </form>
    <div class="container">
     <p>Thank you for booking your next trip with XYZ Airlines!!</p>
     <p>Can't wait to see you on your travels!!</p>
   </div>
  </body>
</html>

Great. Now let’s say we wanted to add a little margin to the Flight finder: header. Take a look at the highlighted line of CSS code to see how you can accomplish this:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center;
  margin: 30px;
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
}

input{
  background-color: #00FFFF
}

To add a margin to the Flight finder: header, I added a styling call to the h1 declaration that uses the margin property and sets the value to 30px-this adds a 30px margin around all sides of the Flight finder: header.

Look, I know margins aren’t as obvious to detect as borders but trust me, they’re there. If it helps, think of margins as a sort of invisible border around a certain HTML element(s).

  • Margins are always measured in px (pixels). Always append the px suffix to whatever you want to use for the margin measurement.
  • Also, even though I mentioned that you could think of margins as “invisible borders”, you can’t set colors or line styles for margins (after all, margins are invisible, so therefore you won’t even see any colors/line styles). However, margins, like borders, have four sides-you can have four different margin sizes if you so choose (just like you can have four different border line stylings). More on this point later.

So, know how I mentioned that similar to how you can have up to four different border line stylings, you can also have up to four different margin sizes. Let’s see an example of this in the highlighted line of CSS code below:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center;
  margin: 30px 10px 20px 40px;
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
}

input{
  background-color: #00FFFF
}

In this example, I used four different margin lengths-30px 10px 20px 40px-to denote the four different margin sizes I’d like to use. Notice anything familiar about the highlighted styling call? The way I listed the margin lengths is the same way I used to list different border stylings in the previous lesson (CSS Lesson 4: Webpage Borders)

Just to reiterate the logic I used in the previous post (but in the context of margins):

  • If margin has four values:
    • Example: margin: 10px 50px 20px 40px
    • How it would work: top margin of 10px, right margin of 50px, bottom margin of 20px, left margin of 40px
  • If margin has three values:
    • Example: margin: 10px 50px 20px
    • How it would work: top margin 10px, right and left margins 50px, bottom margin 75px
  • If margin has two values:
    • Example: margin: 10px 50px
    • How it would work: top and bottom margins 10px, right and left margins 50px
  • If margin has one value:
    • Example: margin: 10px
    • How it would work: all margins 10px
  • Ideally, try to maintain even margins for your elements. Having all margins the same length is fantastic, but the 2-2 rule (which I made up) works just as well-top and bottom margins set to the same length, and left and right margins set to the same length but different than the length of the top and bottom margins.
  • If you want to set margin lengths for each side of a margin around an element, using the margin-top, margin-bottom, margin-left and margin-right properties would work too; however, this is less efficient than utilzing the multiple margin lengths logic I discussed above.

Sounds pretty easy, right? However, keep in mind that there’s another possible value for margins-auto. Using the auto value on an element will horizontally center it. Take a look at how it’s used (through the highlighted line of code):

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center;
  margin: auto;
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
}

input{
  background-color: #00FFFF
}

In this example, I set the value of the h1 element’s margins property to auto, which automatically horizonatally centers the h1 element in the webpage.

  • Personally, if you want the webpage looking as neat as possible, auto would be the way to go when working with your margins. Also, unlike with prespecified margin lengths (e.g. 10px, 50px), you can’t repeat auto several times. So a styling call like margins: auto auto auto auto won’t work.

Now that we’ve explored margins, let’s take a look at padding. Padding and margins are conceptually similar since both features are meant to create space around an element (or elements) in your webpage. However, margins create space around an element outside of a defined border, while padding creates space around an element INSIDE of a defined border. Let’s take a look at a basic example of padding (using the highlighted line of code below):

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center;
  margin: auto;
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
  border-style: solid;
  border-color: green;
  border-width: 6px;
  padding: 30px
}

input{
  background-color: #00FFFF
}

In this example, I applied a padding of 30px (like margins, padding values are also specified in px or pixels) to the elements in the .container class-the last two lines of text on the webpage. This creates whitespace of 30px between the elements and each side of the border.

Now, can you specify multiple padding lengths similar to how you can specify multiple border stylings or margin lengths? Yes. Does the logic for specifying mutliple padding lengths work the same as it would for specifying multiple border stylings or margin lengths? Also yes. Let me explain below:

  • If padding has four values:
    • Example: padding: 25px 30px 10px 50px
    • How it would work: top padding 25px, right padding 50px, bottom padding 10px, left padding 50px
  • If padding has three values:
    • Example: padding: 25px 30px 10px
    • How it would work: top padding 25px, right and left paddings 30px, bottom padding 10px
  • If padding has two values:
    • Example: padding: 25px 30px
    • How it would work: top and bottom paddings 25px, right and left paddings 30px
  • If padding has one value:
    • Example: padding: 25px
    • How it would work: all paddings 25px

While discussing CSS margins, I did mention another approach to setting multiple margin lengths-using the margin-top, margin-left, margin-bottom, and margin-right properties to set the top, left, bottom, and right margin lengths, respectively. You can do something similar with padding lengths using the padding-top, padding-left, padding-bottom, and padding-right properties, respectively, but it would be much more efficient to use the multiple-padding-lengths-in-a-single-line approach that I discussed above.

  • Just like with margin lengths, I don’t recommend setting four (or even three) different padding lengths, as this would make the element spacing look really uneven. One or two padding lengths would work just fine (preferably a single padding length).
    • You may be able to hide uneven margin lengths better than you can hide uneven padding lengths, as margins are utilized outside of defined borders while padding is utilized inside of defined borders. Therefore, uneven padding is more obvious to see to visitors of your website.
  • Lo and behold, you can utilize the auto property on padding too in order to horizontally center your element withing a border. Same rules from applying the auto property to margins are in place here (e.g. the styling call padding: auto auto auto auto) won’t work. Here’s how utilizing the auto property for padding would work here (pay attention to the highlighted line of code):
h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center;
  margin: auto;
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
  border-style: solid;
  border-color: green;
  border-width: 6px;
  padding: auto
}

input{
  background-color: #00FFFF
}

Thanks for reading,

Michael

CSS Lesson 4: Webpage Borders

Advertisements

Hello everybody,

Michael here, and today’s lesson will cover how to use CSS borders on your webpage.

When you are designing your HTML website, borders are crucial design elements.

First off, let’s start by exploring CSS borders. To do that, let’s use the form we’ve been using for my CSS lessons (minus the background image from the previous lesson):

<!DOCTYPE html>
<html lang="es-US" dir="ltr">
  <head>
    <meta charset="utf-8">
    <link rel="stylesheet" href="Form.css">
    <link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Press+Start+2P">
    <title></title>
  </head>
  <body>
    <h1>Flight finder:</h1>
    <form action="Submitted.html" method="POST">
      <label for="datepicker1">Pick the date you want to depart for your vacation</label><br>
      <input type="date" id="datepicker1" name="datepicker1" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="datepicker2">Pick the date you want to return from your vacation</label><br>
      <input type="date" id="datepicker2" name="datepicker2" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="time1">What time would you like to depart? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time1" name="time1"><br>
      <br>
      <label for="time2">What time would you like to return? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time2" name="time2"><br>
      <br>
      <label for="layover">How many layovers do you want?</label><br>
      <input type="number" id="layover" name="layover" min="0" max="3"><br>
      <br>
      <input type="submit" value="Submit">
    </form>
    <div class="container">
     <p>Thank you for booking your next trip with XYZ Airlines!!</p>
     <p>Can't wait to see you on your travels!!</p>
   </div>
  </body>
</html>

Great, so we have the form webpage (along with the corresponding code) here. Now, let’s say we wanted to add a simple CSS border to the last two lines of text (the ones in red). How would we do so? Take a look at the highlighted line of CSS code below:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
  border-style: solid
}

input{
  background-color: #00FFFF
}

To add a CSS border to an element on the form, simply add a border-style styling call and set any of the following values for border-style:

  • dotted-creates a dotted line border
  • dashed-creates a dashed line border
  • solid-creates a solid line border
  • double-creates a double border
  • groove-creates a 3D grooved border
  • ridge-creates a 3D ridged border
  • inset-creates a 3D inset border
  • outset-creates a 3D outset border
  • none-creates no border
  • hidden-creates a hidden line border

In this example, I set the value of the border-style property to solid, which creates a solid red border on the last two lines of text on this webpage.

Now, what if you wanted a thicker or thinner border? Let’s see how we can change border thickness (look at the highlighted section of code below):

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
  border-style: solid;
  border-width: 6px
}

input{
  background-color: #00FFFF
}

As you can see, I managed to make the border slightly thicker than it was before. How did I manage to do this? I added another styling call to the .container declaration that contains the property border-width and has a value of 6px (border thickness in CSS is always measured in px or pixels).

  • Remember that the value of the border-width property must always contain px at the end and a number at the beginning (e.g. 6px in this example). And don’t wrap this value in quotes-it’s not a string!

Now, as you may have noticed from the previous two examples, the border around the last two lines of text is red-this is because the border color will default to the color of the elements it contains, and since the text inside the border is red, the border itself will also be red.

Let’s say we wanted to change the aforementioned border’s color from red to green. How would we accomplish this? Take a look at the highlighted line of code below:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
  border-style: solid;
  border-width: 6px;
  border-color: green
}

input{
  background-color: #00FFFF
}

To change the border’s color, I simply added another styling call to the .container declaration; in this call, I used the border-color property and set this property’s value to green to change the border from red to green.

  • Using a HEX code, RGB code, HSL code, or the keyword transparent would have worked here too. However, using simple color names (e.g. red, blue, orange) always works with the border-color property, especially if you want a basic color.

So, having fun exploring the several different ways we can play with CSS borders? If so, great, but we’ve got one more thing to explore.

In case you weren’t aware, you can apply more than one styling to a border. Curious? Well check out the highlighted line of code below to see how you can apply multiple different stylings to a CSS border:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
  border-style: solid dashed;
  border-width: 6px
}

input{
  background-color: #00FFFF
}

As you can see here, I created a border with two different stylings (solid on the top and bottom and dashed on the left and right). How did I accomplish this? I set the value of the border-style property to solid dashed, which will tell CSS to create a border that is dashed on two sides and solid on the other two sides. To set multiple different stylings for the border, simply list the styles you want for the border and separate the names of each style with a space. That’s it-and you can have between one and four styles for your border. Here’s how the multiple border stylings trick works in CSS:

  • Four border stylings:
    • example: border-style: dotted dashed solid ridge
    • how it works: top border dotted, right border dashed, bottom border solid, left border ridge
  • Three border stylings:
    • example: border-style: dotted solid groove
    • how it works: top border dotted, right and left borders solid, bottom border groove
  • Two border stylings:
    • example: border-style: solid dashed
    • how it works: top and bottom borders solid, left and right borders dashed
  • One border styling:
    • example: border-style: solid
    • how it works: all borders solid

Pretty neat stuff right? Just wait until you see that similar logic for the multiple border stylings trick also works to apply multiple border colors. Check out the highlighted line of code below:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center;
  border-style: solid dashed;
  border-color: red green;
  border-width: 6px
}

input{
  background-color: #00FFFF
}

And here’s what the webpage looks like with the multiple border colors applied:

How did I generate a red and green border? I simply added another styling call to the .container declaration that used the border-color property along with two color values separated by a space-red green (similar to what I did with the multiple values for the border-style property). The highlighted line of code above tells CSS to make the top and bottom borders red and the left and right borders green.

  • You’ll notice that I used both the border-color and color properties in the .container declaration. Note that you can’t use these properties interchangeably-color sets the color of the elements in the .container declaration (the last two lines of text on this webpage) while border-color sets the color of the border around the aforementioned elements.

Also, just as with multiple CSS borders, you can apply between one and four different border colors to your border. Here’s how the multiple border colors trick would work in CSS:

  • Four border colors:
    • example: border-color: red orange green blue
    • how it works: top border red, right border orange, bottom border green, left border blue
  • Three border colors:
    • example: border-color: red orange green
    • how it works: top border red, right and left borders orange, bottom border green
  • Two border colors:
    • example: border-color: red orange
    • how it works: top and bottom borders red, left and right borders orange
  • One border color:
    • example: border-color: red
    • how it works: all borders red

Thanks for reading,

Michael

CSS Lesson 3: The Basics of Backgrounds

Advertisements

Hello everybody,

Michael here, and today’s lesson will cover basic principles of using backgrounds in CSS.

Just as I did for my previous CSS lessons, I’ll use the sample form I created in HTML for this lesson. Here’s the code for the form:

<!DOCTYPE html>
<html lang="es-US" dir="ltr">
  <head>
    <meta charset="utf-8">
    <link rel="stylesheet" href="Form.css">
    <link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Press+Start+2P">
    <title></title>
  </head>
  <body>
    <h1>Flight finder:</h1>
    <form action="Submitted.html" method="POST">
      <label for="datepicker1">Pick the date you want to depart for your vacation</label><br>
      <input type="date" id="datepicker1" name="datepicker1" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="datepicker2">Pick the date you want to return from your vacation</label><br>
      <input type="date" id="datepicker2" name="datepicker2" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="time1">What time would you like to depart? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time1" name="time1"><br>
      <br>
      <label for="time2">What time would you like to return? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time2" name="time2"><br>
      <br>
      <label for="layover">How many layovers do you want?</label><br>
      <input type="number" id="layover" name="layover" min="0" max="3"><br>
      <br>
      <input type="submit" value="Submit">
    </form>
    <div class="container">
     <p>Thank you for booking your next trip with XYZ Airlines!!</p>
     <p>Can't wait to see you on your travels!!</p>
   </div>
  </body>
</html>

And here’s the CSS styling code we’ll use (I’ll keep the styling I applied at the end of CSS Lesson 2: Fun with Fonts):

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center
}

Here’s what the webpage looks like with the current styling:

Now, how would we add some background styling to the webpage. Take a look at the highlighted segment of code below:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center
}

body{
  background-color: #87CEEB
}

To set a background color for the webpage, use the body selector and inside the selector, call the background-color property and set the value of this property to a certain color, which can take one of these three forms:

  • a conventional color name (e.g. red, yellow, green)
  • a color HEX code (e.g. #87CEEB)
  • a color RGB code (e.g. rgb(123, 10, 88))

In this example, I specified the backround color with a hex code-#87CEEB. In case you’re wondering, this hex code produces a sky-blue background (heck, I thought it was appropriate given that this a form for an imaginary airline). Here’s what the webpage looks like with the background styling applied:

  • If you want to apply a background color to the entire webpage, always use the body selector!
  • When specifying a HEX code color, don’t wrap it in quotation marks.

So, the background looks great, but all the input elements in the form could use some more styling as well. How should we approach this? Take a look at the CSS code below and pay attention to the highlighted section:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center
}

body{
  background-color: #87CEEB
}

input{
  background-color: #00FFFF
}

Here’s what the webpage looks like with the additional styling:

Yes, you can give background stylings to elements other than the main webpage as I did here with the input elements. To style the input elements, I created a CSS styling call with input as the selector and background-color: #00FFFF as the styling call that will change the background color of the input elements.

  • #00FFFF refers to cyan by the way. I thought it would be an appropratie color given that this is a form for an (imaginary) airline.

Alright, the webpage looks great so far! However, what if you wanted to use a picture for the background rather than a color? How would you go about doing this? Take a look at the highlighted section of the code below:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center
}

body{
  background-image: url('stock photo.jpg')
}

input{
  background-color: #00FFFF
}

So, how did I get the result for my webpage that you see above? Well, I first obtained a stock photo from a stock photo website (https://shop.stockphotosecrets.com/index.cfm?/home_EN&CFID=351309901&CFTOKEN=65225479 for those curious). I then saved the stock photo to the same directory where my form HTML and CSS code is located.

To add the stock photo to the website, use CSS’s background-image property and set the value of this property to url(image name.image extension); in this example, the value of the background-image property was url('stock photo.jpg'), since I had saved this stock photo of a plane onto my computer as stock photo.jpg (creative, I know).

  • If you want to succesfully connect your chosen background image to your HTML webpage, wrap the name of your image (as it’s saved on your computer) inside a url() function. Also, wrap the name of your image in quotes (whether single quotes or double quotes) as I did in the above example.

Once I set the form’s background-image property, the webpage’s background image changes to the stock photo of a plane I saved onto my computer.

Looks pretty good, right? Well, there’s one thing we can fix-if you’re thinking of the fact that the stock photo is repeated several times throughout the webpage (both vertically and horizontally), you’d be right. Yes, there’s a simple fix to the repeating background image issue, and all it takes is a single line of code. Check out the highlighed section of the code below:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center
}

body{
  background-image: url('stock photo.jpg');
  background-repeat: no-repeat;
}

input{
  background-color: #00FFFF
}

To ensure the background image doesn’t repeat, I added the background-repeat property to the body styling call in the CSS file and set this property’s value to no-repeat to tell my CSS code to only display the background image once.

  • If I only wanted to repeat the background image horizontally, I could set the value of the background-repeat property to repeat-x. Likewise, if I only wanted to repeat the background image vertically, I could set the value of the background-repeat property to repeat-y.

Alright, the webpage is looking better, but we’ve still got another issue-the background image only covers the top-left corner of the webpage when it should ideally cover the whole webpage. How would we fix this issue? Take a look at the highlighted section of the CSS code below:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center
}

body{
  background-image: url('stock photo.jpg');
  background-repeat: no-repeat;
  background-size: cover;
}

input{
  background-color: #00FFFF
}

Just as I did with the background-repeat property, I managed to fix the background image display issue with a single line of code-in this case, background-size: cover. What this single line of code does is utilize CSS’s background-size property to change the size of the background image to cover, which will stretch the background image to cover the whole webpage. Pretty neat what you can do with a single line of code is CSS, amirite?

  • If you set the size of a background image to cover keep in mind that the image will likely either stretch or be slightly cut off.

So, the webpage is looking a lot nicer! However, before I go, let me leave you with these web background design tips:

  • When picking a background (whether its a color or an image), pick something that doesn’t clash with the webpage’s text too much. If you like your choice of background but find that it clashes with the text too much, change the color scheme of the text.
    • Now that I think of it, the last two lines of text on this webpage somewhat clash with the background image. But then again, this is for a programming lesson, not a production-ready website.
  • Also, if you’re creating a webpage for a business (not for a programming lesson), PLEASE PLEASE PLEASE don’t use stock photos. It just looks unprofessional and fakey.

Thanks for reading,

Michael

CSS Lesson 2: Fun with Fonts

Advertisements

Hello everybody,

Michael here, and today’s lesson will explore working with fonts in CSS.

Choosing the right font, just like choosing the right colors, is an important element in website styling. For our exploration of CSS fonts, let’s take a look at the form we styled in CSS Lesson 1: Introduction to CSS Styling. Here’s the form’s HTML code along with the screenshot of the form (keep in mind that this form code isn’t connected to a CSS file):

<!DOCTYPE html>
<html lang="es-US" dir="ltr">
  <head>
    <meta charset="utf-8">
    <title></title>
  </head>
  <body>
    <h1>Flight finder:</h1>
    <form action="Submitted.html" method="POST">
      <label for="datepicker1">Pick the date you want to depart for your vacation</label><br>
      <input type="date" id="datepicker1" name="datepicker1" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="datepicker2">Pick the date you want to return from your vacation</label><br>
      <input type="date" id="datepicker2" name="datepicker2" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="time1">What time would you like to depart? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time1" name="time1"><br>
      <br>
      <label for="time2">What time would you like to return? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time2" name="time2"><br>
      <br>
      <label for="layover">How many layovers do you want?</label><br>
      <input type="number" id="layover" name="layover" min="0" max="3"><br>
      <br>
      <input type="submit" value="Submit">
    </form>
    <div class="container">
     <p>Thank you for booking your next trip with XYZ Airlines!!</p>
     <p>Can't wait to see you on your travels!!</p>
   </div>
  </body>
</html>

OK, so now that we know what the unstyled version of the form looks like, let’s start having some fun with (CSS) fonts. Just as we did for the previous CSS lesson, I’d suggest creating a new CSS file and giving it the same name as your HTML file-in this case, I’ll call the CSS file Form.css since my HTML file is called Form.html.

Before we start examining how to work with fonts in CSS, let’s familiarize ourselves with the concept of font families. CSS has five different font families, which are categories of fonts with their own distinct features; here are the five different font families:

  • Serif-these fonts have a small stroke at the edge of each letter (example: Times New Roman-the font I’m using for this blog)
  • Sans-serif-these fonts have no small strokes at the edge of each letter (example: Arial)
  • Monospace-these fonts have letters of equal width (example: Courier New)
  • Cursive-these fonts are meant to look like human handwriting, namely cursive handwriting-remember learning that in school? (e.g. Comic Sans)
  • Fantasy-these fonts are meant to be decorative (e.g. Papyrus)

For those of you who’d like a visual depiction of the five CSS font families, refer to the picture below:

https://renenyffenegger.ch/notes/development/web/CSS/properties/font-family

Now that we discussed the five CSS font families, let’s see how we can apply font stylings to our webpage. Let’s start the font styling by first changing the font of the top header (Flight finder:)

h1{
  color: green;
  font-family: "Comic Sans MS";
  text-align: center
}

To style the top header, I applied a series of CSS styling calls to the <h1> tag, as it contained the Flight finder: header. Aside from changing the font of the <h1> tag, I also changed the tag’s color and center-aligned the text. Take a look at the series of CSS styling calls I applied to the <h1> tag. Which styling call do you think changes the font? If you thought it was the styling call with the font-family property, you’d be right. In order to change the font of a certain element, you’d need to make this styling call: font-family: "[font you'd like to use]". Yes, you would need to wrap the name of the font you’d like to use inside double quotes as I did for the font name I used in this example.

  • When deciding on font stylings for your webpage, Comic Sans is the last font I’d use if I was designing a webpage for a business since Comic Sans is generally seen as unprofessional. However, if you’re just designing a webpage to follow along with my tutorial, let your imagination run wild with the font stylings!

Now, what if you wanted to change the font size of the <h1> tag? Take a look at this series of styling calls below:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

In this example, I used the font-size property to change the font size of the <h1> tag to 40px (40 pixels). Whenever specifying a font size, always follow this syntax-font size + px. Don’t forget to put the px after the number!

Now, let’s change the font of the last two lines of text on this page. Here’s how to do so (in this example, we’ll change the font to Century Gothic):

.container{
  color: red;
  font-family: "Century Gothic";
  font-size: 30px;
  text-align: center
}

In this example, note that I kept the same font styling for <h1> that I had applied in the previous example. Aside from that, pay attention to the code above that I used to change the styling for the last two lines. Recall that from my previous CSS lesson (CSS Lesson 1: Introduction to CSS Styling) that the dot (.) is used as one of the main selectors in CSS; selectors tell CSS to select a certain element to style. In this example, the dot selector tells CSS to style all elements within a container class-if you take a look at the form code that I shared at the beginning of this post, you’ll notice that the last two lines of the webpage are contained in a <div> tag with the class container. Thus, when I applied the series of CSS styling calls to the container class, the stylings were applied to the last two lines of text on this webpage.

As for the stylings I applied, I simply made the text red and center-aligned along with using a size 30 Century Gothic font.

Now, let’s say instead of using common CSS fonts (e.g. Arial, Times New Roman), you wanted to get a little creative with your CSS styling. In this example, let’s say you wanted to pull a font from somewhere else-we’ll use a font from the Google Fonts API (here’s the link to the API, which contains a catalog of thousands of fonts-https://fonts.google.com/).

Here’s the homepage of the Google Fonts API:

If you scroll down further on the page, you can see thousands of freely-available fonts for your website’s use.

  • In case you’re wondering why you see the sentence This is the year 2022 several times on the homepage, it’s because in the box to the right of the font size slider (currently set to 40px), you can type in a word or phrase and see what that word/phrase looks like in hundreds of different fonts. This is the year 2022 happened to be my test phrase.

For this example, let’s change the font of the elements in the container class (the last two lines of text on this webpage) to Press Start 2P-which you can find on the Google Fonts API.

Here’s the Press Start 2P font on the Google Fonts API-I like the font’s retro gaming aesthetic:

Now, how do we get this font onto our CSS styling and in turn, onto the webpage? Take a look at the line in red in the form’s HTML code:

<!DOCTYPE html>
<html lang="es-US" dir="ltr">
  <head>
    <meta charset="utf-8">
    <link rel="stylesheet" href="Form.css">
    <link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Press+Start+2P">
    <title></title>
  </head>
  <body>
    <h1>Flight finder:</h1>
    <form action="Submitted.html" method="POST">
      <label for="datepicker1">Pick the date you want to depart for your vacation</label><br>
      <input type="date" id="datepicker1" name="datepicker1" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="datepicker2">Pick the date you want to return from your vacation</label><br>
      <input type="date" id="datepicker2" name="datepicker2" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="time1">What time would you like to depart? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time1" name="time1"><br>
      <br>
      <label for="time2">What time would you like to return? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time2" name="time2"><br>
      <br>
      <label for="layover">How many layovers do you want?</label><br>
      <input type="number" id="layover" name="layover" min="0" max="3"><br>
      <br>
      <input type="submit" value="Submit">
    </form>
    <div class="container">
     <p>Thank you for booking your next trip with XYZ Airlines!!</p>
     <p>Can't wait to see you on your travels!!</p>
   </div>
  </body>
</html>

Also take a look at the line in red in the form’s CSS code:

h1{
  color: green;
  font-family: "Comic Sans MS";
  font-size: 40px;
  text-align: center
}

.container{
  color: red;
  font-family: "Press Start 2P";
  font-size: 30px;
  text-align: center
}

See, I can declare Press Start 2P in the font-family property of the .container styling calls just fine. However, since Press Start 2P is not a standard HTML font, setting this font as the value of the font-family property alone won’t change the font.

  • Standard HTML fonts refer to fonts that you can find pre-installed onto a standard edition of Microsoft Word, PowerPoint, or Excel.

That’s where the red-highlighted line in the form’s HTML code comes in. If you’re not using a standard HTML font on your webpage, you’d need to create another <link> tag that links to the font’s URL on the Google Fonts API (or any fonts API you might use for that matter). The link’s rel would still be stylesheet, but the href would be the font’s URL on the API.

Let’s take a look and see what the webpage looks like with the Press Start 2P font:

Pretty neat, right? Recall that I kept the green, center-aligned Comic Sans font for the top header on the webpage, so that’s why the style looks the same.

Thanks for reading,

Michael

CSS Lesson 1: Introduction to CSS Styling

Advertisements

Hello everybody,

Michael here, and today I will be going over the basics of CSS to you guys.

What is CSS? First of all, CSS is a tool that stands for cascading style sheets-CSS and HTML always go hand-in-hand since CSS is the tool you’d use to give HTML webpages their style (as opposed to leaving them in bland black-and-white Times New Roman).

  • You can have HTML without CSS, but you can’t have CSS without HTML.

To start exploring CSS, let’s use the HTML form we used in the previous post (HTML Lesson 8: Block & Inline Content in HTML):

<!DOCTYPE html>
<html lang="es-US" dir="ltr">
  <head>
    <meta charset="utf-8">
    <title></title>
  </head>
  <body>
    <h1>Flight finder:</h1>
    <form action="Submitted.html" method="POST">
      <label for="datepicker1">Pick the date you want to depart for your vacation</label><br>
      <input type="date" id="datepicker1" name="datepicker1" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="datepicker2">Pick the date you want to return from your vacation</label><br>
      <input type="date" id="datepicker2" name="datepicker2" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="time1">What time would you like to depart? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time1" name="time1"><br>
      <br>
      <label for="time2">What time would you like to return? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time2" name="time2"><br>
      <br>
      <label for="layover">How many layovers do you want?</label><br>
      <input type="number" id="layover" name="layover" min="0" max="3"><br>
      <br>
      <input type="submit" value="Submit">
    </form>
    <div class="container">
     <p>Thank you for booking your next trip with XYZ Airlines!!</p>
     <p>Can't wait to see you on your travels!!</p>
   </div>
  </body>
</html>

As you can see here, we have a perfectly functional, albeit bland looking website. Let’s explore how we can add some CSS styling to this website.

First, we’d need to create a separate CSS file-ideally, keep this CSS file in the same directory as the HTML file that you wish to style (and, although not super necessary, use the same name for the CSS file that you have for the HTML file):

As you can see, I have created a CSS file for my HTML Form file-my CSS file is also named Form.

Now, let’s start adding some simple styling to the CSS file:

h1{
  color: green;
  text-align: center
}

OK, for those of you unfamiliar with CSS, you’re probably wondering what on earth you’re seeing here.

All CSS styling calls (like what you’re seeing in the example above) consist of two parts-a selector and a declaration block. The selector indicates the HTML element you want to apply a particular styling to-in this example, h1 is the selector, which indicates that I want to apply a certain styling call to any h1 element in my HTML file. The declaration block is where the CSS styling magic really happens as it contains one or more styling declarations (each styling declaration is separated by a semicolon as you can see from the example above). Each declaration is wrapped in a pair of curly brackets (much like a Python dictionary) and contains the name of a CSS property (color and text-align in this example) and a corresponding value (green and center, respectively) separated by a colon.

  • In case you weren’t sure what the above styling call meant, it’s telling HTML to style all elements with an H1 tag with a green color and center-align the text.

Now, what if you wanted to style another element on the webpage? Take a look at the code below to see how to add another styling call:

h1{
  color: green;
  text-align: center
}

.container{
  color: red;
  font-weight: bold
}

In this example-and in addition to the h1 styling call that I had previously used-I also added a .container styling call to apply certain stylings to all elements in the container class. To add another styling call to the CSS file, simply create a new styling call using the following syntax: selector { CSS property : CSS value ; }.

In the styling call, I’m telling HTML to make all text in the container class red and bold-faced.

  • You’ll only need the semi-colon if you’ve got more than one CSS property-value pair. Also, no need to add a semi-colon after the last CSS property-value pair in your styling call.

Why did I add a dot (.) in front of container for the styling? Well, the dot indicates that I want to style elements of a certain class, and since container is a class in the HTML form, .container indicates that I want to applying a certain set of stylings to all elements in the .container class.

In CSS, there are six CSS styling selectors that your should know. Here’s a table that explains each of these selectors and how they are applied in CSS styling:

SelectorExampleHow it’s used
elementh1Applies a certain set of stylings
to all H1 elements
.class.containerApplies a certain set of stylings
to all elements inside a container class
element.classdiv.containerApplies a certain set of stylings
only to elements inside a container class
AND a <div> tag
**Applies a certain set of stylings to everything on
an HTML page
#id#datepickerApplies a certain set of stylings to all elements with
the datepicker ID
element, elementh1, pApplies a certain set of stylings to all H1 AND <p>
elements

Now, the big question is how you would connect the CSS file to the HTML and in turn, apply the CSS styling to the HTML webpage. Take a look at this new HTML code-pay attention the line in red:

<!DOCTYPE html>
<html lang="es-US" dir="ltr">
  <head>
    <meta charset="utf-8">
    <link rel="stylesheet" href="Form.css">
    <title></title>
  </head>
  <body>
    <h1>Flight finder:</h1>
    <form action="Submitted.html" method="POST">
      <label for="datepicker1">Pick the date you want to depart for your vacation</label><br>
      <input type="date" id="datepicker1" name="datepicker1" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="datepicker2">Pick the date you want to return from your vacation</label><br>
      <input type="date" id="datepicker2" name="datepicker2" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="time1">What time would you like to depart? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time1" name="time1"><br>
      <br>
      <label for="time2">What time would you like to return? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time2" name="time2"><br>
      <br>
      <label for="layover">How many layovers do you want?</label><br>
      <input type="number" id="layover" name="layover" min="0" max="3"><br>
      <br>
      <input type="submit" value="Submit">
    </form>
    <div class="container">
     <p>Thank you for booking your next trip with XYZ Airlines!!</p>
     <p>Can't wait to see you on your travels!!</p>
   </div>
  </body>
</html>

The highlighted line contains a <link> tag with two parameters-rel and href. In this example, you’d set the rel parameter equal to stylesheet, as you are connecting a CSS file to your HTML webpage. You’d set the value of the href parameter equal to the name of the CSS file that contains the stylings you want to apply to the HTML webpage.

  • As you can see, all it takes is a single line of code to connect a CSS file to an HTML file. Pretty impressive, right?

Once we’ve connected the CSS file to the HTML file, let’s see how our stylized HTML webpage looks:

Alright, the webpage is looking better. There is definitely much more CSS styling we can apply to webpage-I’ll certainly dive into more CSS styling concepts in the next few lessons.

Thanks for reading,

Michael

HTML Lesson 8: Block & Inline Content in HTML

Advertisements

Hello everybody,

Michael here, and today I thought I’d do another series of web-development lessons, starting with an HTML lesson on the difference between block and inline content in HTML.

When creating a website in HTML, it’s important to know the difference between block and inline content in HTML when it comes to designing your webpage.

Block content refers to webpage content that always starts on a new line; the browsers will automatically add a margin before and after the content. Block content always stretches out as far left and as far right on the webpage as it can.

Inline content, on the other hand, doesn’t start on a new line and doesn’t stretch across the webpage-rather, inline content only takes up as much width as necessary.

Now that I’ve explained the basics of block and inline content, let me first show you some examples of block content:

<!DOCTYPE html>
<html lang="en" dir="ltr">
  <head>
    <meta charset="utf-8">
    <title></title>
  </head>
  <body>
    <h1>Flight finder:</h1>
    <form action="Submitted.html" method="POST">
      <label for="datepicker1">Pick the date you want to depart for your vacation</label><br>
      <input type="date" id="datepicker1" name="datepicker1" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="datepicker2">Pick the date you want to return from your vacation</label><br>
      <input type="date" id="datepicker2" name="datepicker2" min="2021-03-25" max="2022-03-25"><br>
      <br>
      <label for="time1">What time would you like to depart? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time1" name="time1"><br>
      <br>
      <label for="time2">What time would you like to return? (flights shown within 90 minutes of selected time)</label><br>
      <input type="time" id="time2" name="time2"><br>
      <br>
      <label for="layover">How many layovers do you want?</label><br>
      <input type="number" id="layover" name="layover" min="0" max="3"><br>
      <br>
      <input type="submit" value="Submit">
    </form>

    <div class="container">
      <p>Thank you for booking your next trip with XYZ Airlines!!</p>
      <p>Can't wait to see you on your travels!!</p>
    </div>
  </body>
</html>

Take this HTML code (that I pulled from a form I made in HTML Lesson 7: Forms pt.2 (More Fun With Forms)) that will show you this form:

Pay attention to the code I highlighted in orange. Notice the <div> tag in the highlighted code. <div> simply denotes a section in a webpage, but it also often used for styling webpages with CSS (don’t worry, I’ve got a whole series of CSS lessons planned).

Wonder why I set a container class in my <div> tag? Well-although I won’t be doing so in this lesson-the container class will allow me to apply a certain CSS styling (color, font, size, etc.) to every element in the container. Let’s say I wanted to make all the text red and change the font to Comic Sans. I could easily do so with CSS simply by calling this <div> tag and applying the appropriate styling (I’ll discuss how to work CSS styling in the future).

However, you may have also noticed that I have two other block elements hiding within the <div> tag-if you guessed the two <p> elements, you are correct. Yes, the <p>, or paragraph, tag also counts as a block element and as you may have guessed, the <p> tag allows users to denote paragraphs (or single non-header lines of text, which are still paragraphs in the context of HTML) on their webpage.

Since you have two block elements within a larger block element, how would you work the CSS styling? If you wanted to apply the same style to everything in the <div> tag, you would call the <div> tag in your CSS file and apply whatever styling you want to all of the elements in the <div> tag.

However, if you wanted to apply different styling to each paragraph element inside the <div> tag, you would need to call each <p> tag in your CSS file and apply the individual stylings you want to each <p> tag.

  • If you really wanted to, you could apply the same styling to each <p> tag, but that would be redundant because if you wanted to apply the same styling to each <p>, simply call the <div> tag in your CSS file and apply the styling to that.
  • <form> is also an block element, and so are the header tags (<h1> in this form).

Now, what would inline content look like on an HTML webpage. Take a look at the form code that I posted above. There are three inline elements scattered throughout the form-<label>, <input>, and <br>-which denote a label for a form element, an inpute element for a form, and a line break between each section of the form, respectively.

While I’m on the topic of inline elements, I wanted to discuss a special type of inline element-the <span> tag. Like the <div> tag, the <span> tag defines a section in your document, however, you’d only use the <span> tag with inline elements (recall that the <div> tag is used for block-level elements).

  • Think of the <span> tag as the inline version of the <div> tag (or the <div> tag as the block version of the <span> tag).

Although the <div> and <span> tags both denote sections of your document, the <span> tag allows you to run CSS styling on certain sections of your document. Take a look at this section of the form code:

<div class="container">
      <p>Thank you for booking your next trip with XYZ Airlines!!</p>
      <p>Can't wait to see you on your travels!!</p>
</div>

Now, let’s see what happens when we wrap a <span> tag inside the first <p> tag:

    <div class="container">
      <p><span>Thank you for booking your next trip with XYZ Airlines!!</span></p>
      <p>Can't wait to see you on your travels!!</p>
    </div>

OK, in this case, the <span> tag has no effect on the appearance of the <p> tag since, even though <span> tags technically require no parameters, having no parameters in the <span> tag won’t change the styling of your document at all. Let’s see what happens when we add a little CSS styling magic to the <span> tag:

<div class="container">
      <p><span style='font-weight:bold'>Thank you</span> for booking your next trip with XYZ Airlines!!</p>
      <p>Can't wait to see you on your travels!!</p>
</div>

To add some CSS styling in your <span> tag, pass in a style parameter inside the <span> tag and pass in your desired styling as a string value for the style parameter. In this example, since I wanted to make the Thank you part of the first <p> tag bold, I wrapped Thank you in a <span> tag and applied a font-weight:bold styling to Thank you.

Now, what if you wanted to apply more than one CSS styling to your <span> tag? Take a look at this code below:

<div class="container">
      <p><span style='font-weight:bold; color:green'>Thank you</span> for booking your next trip with XYZ Airlines!!</p>
      <p>Can't wait to see you on your travels!!</p>
</div>

In this example, I made the Thank you portion of the first <p> tag both bold AND green by applying this styling: font-weight:bold; color:green. Keep in mind that if you’re applying more than one type of CSS styling to your <span> tag, you’ll need to separate each styling element (font-weight and color in this example) with a semicolon.

Thanks for reading,

Michael

Python Lesson 31: Fun with Python

Advertisements

Hello everybody,

Michael here, and today, I thought I try something different with my Python lessons. See, in 2020, you may recall I posted a lesson on fun R modules aptly titled R Lesson 20: Fun with R. Now this time, I thought we’d have a little fun with different fun Python modules (though unlike in R, Python doesn’t have an aptly-named fun package).

  • Keep in mind that you’ll need to PIP install all of the packages we’re playing with.

Now, let’s get started! First off, we’ll explore the pyjokes package, which simply outputs random corny (or funny, depending on your tastes) coding one-liners. Take a look at this:

!pip install pyjokes

pyjokes.get_joke()

"Waiter: He's choking! Is anyone a doctor? Programmer: I'm a Vim user."
  • Yes, you can PIP install packages in your IDE-simply place an exclamantion point before the pip install ... command.

To acutally get one of these one-lines, use the pyjokes module’s .get_joke() method (it takes in no parameters). As you can see, we were able to retrieve a coding joke-"Waiter: He's choking! Is anyone a doctor? Programmer: I'm a Vim user."

  • This one is clever-if any of you have ever worked with Git/Github, odds are you’ve used the Vim text editor (and realized how much it sucks).

Here’s another pyjoke:

pyjokes.get_joke()

'What does pyjokes have in common with Adobe Flash? It gets updated all the time, but never gets any better.'

Alright, now that we’ve explored some coding one-liners, let’s move on to our next fun package-antigravity. There’s no need to pip install this package-rather, simply type import antigravity into your IDE and you will be redirected to the (rather cheesy) antigravity web-comic:

  • Apparently this webcomic has been running since 2006. Who knew?

Now, let’s move on to our next package-art. Although this package doesn’t have much practical use for coders, it’s entertaining to play around with. Take a look:

!pip install art

from art import *
tprint('Michael`s Analytics Blog')

In this example, I used the art module’s tprint() method, passed in a String to this method, and voila, I get some simplistic ASCII art consisting of the String I passed in (Michael's Analytics Blog).

  • I think it looks pretty neat, but don’t expect to see this as my blog logo anytime soon.

Now, what if we wanted to change the style of the ASCII art generated? Take a look at this example:

from art import *
tprint('Coding', font='block')

In this example, I am still generating ASCII art. However, I did add the font parameter to the tprint method and set the value of font to block, which will show each character in the String inside an ASCII-generated block. I personally would only use the block font for short words, as the block font display looks really messy if I tried using a phrase like Michael's Analytics Blog (see picture below for the messy output):

  • This is only PART of the messy output.

The next fun little package I want to explore is wikipedia, which serves as a handy-dandy Wikipedia web-scraper library (don’t worry, we’ll explore web scraping in future Python lessons). To install the wikipedia package, run the !pip install wikipedia command in your IDE (or run this command in your command prompt without the exclamation point-that works too).

Now that you’ve installed the package, let’s explore some of the cool things wikipedia can do:

First, let’s print out a summary of an article on Wikipedia:

import wikipedia
print(wikipedia.summary('SouthPark'))

South Park is an American animated sitcom created by Trey Parker and Matt Stone and developed by Brian Graden for Comedy Central. The series revolves around four boys—Stan Marsh, Kyle Broflovski, Eric Cartman, and Kenny McCormick—and their exploits in and around the titular Colorado town. South Park became infamous for its profanity and dark, surreal humor that satirizes a wide range of topics toward an adult audience.
Parker and Stone developed South Park from two animated short films both titled The Spirit of Christmas. The second short became one of the first Internet viral videos, leading to South Park's production. The pilot episode was produced using cutout animation; subsequent episodes have since used computer animation recalling the cutout technique. South Park features a large ensemble cast of recurring characters.
Since its debut on August 13, 1997, 312 episodes (including television films) of South Park have been broadcast. It debuted with great success, consistently earning the highest ratings of any basic cable program. Subsequent ratings have varied, but it remains one of Comedy Central's highest-rated programs. In August 2021, the series was renewed through 2027, and a series of films was announced for the streaming service Paramount+, the first two of which were released later that year.South Park has received numerous accolades, including five Primetime Emmy Awards, a Peabody Award, and numerous inclusions in various publications' lists of greatest television shows. A theatrical film, South Park: Bigger, Longer & Uncut, was released in June 1999 to commercial and critical success, garnering an Academy Award nomination. In 2013, TV Guide ranked South Park the tenth Greatest TV Cartoon of All Time.

In this example, (after importing wikipedia) I used wikipedia‘s .summary() method to retrieve a summary of Wikipedia’s article on South Park-I also used the print() method to print out the article’s summary.

  • You can run a .summary() on literally any topic under the sun, but if your topic has multiple words (as in South Park), pass in the .summary() method parameter as a single word (e.g. SouthPark). Here’s what happened when I tried passing in South Park as two separate words:
import wikipedia
print(wikipedia.summary('South Park'))

---------------------------------------------------------------------------
PageError                                 Traceback (most recent call last)
<ipython-input-5-2fa4221dc36b> in <module>
      1 import wikipedia
----> 2 print(wikipedia.summary('South Park'))

~\anaconda3\lib\site-packages\wikipedia\util.py in __call__(self, *args, **kwargs)
     26       ret = self._cache[key]
     27     else:
---> 28       ret = self._cache[key] = self.fn(*args, **kwargs)
     29 
     30     return ret

~\anaconda3\lib\site-packages\wikipedia\wikipedia.py in summary(title, sentences, chars, auto_suggest, redirect)
    229   # use auto_suggest and redirect to get the correct article
    230   # also, use page's error checking to raise DisambiguationError if necessary
--> 231   page_info = page(title, auto_suggest=auto_suggest, redirect=redirect)
    232   title = page_info.title
    233   pageid = page_info.pageid

~\anaconda3\lib\site-packages\wikipedia\wikipedia.py in page(title, pageid, auto_suggest, redirect, preload)
    274         # if there is no suggestion or search results, the page doesn't exist
    275         raise PageError(title)
--> 276     return WikipediaPage(title, redirect=redirect, preload=preload)
    277   elif pageid is not None:
    278     return WikipediaPage(pageid=pageid, preload=preload)

~\anaconda3\lib\site-packages\wikipedia\wikipedia.py in __init__(self, title, pageid, redirect, preload, original_title)
    297       raise ValueError("Either a title or a pageid must be specified")
    298 
--> 299     self.__load(redirect=redirect, preload=preload)
    300 
    301     if preload:

~\anaconda3\lib\site-packages\wikipedia\wikipedia.py in __load(self, redirect, preload)
    343     if 'missing' in page:
    344       if hasattr(self, 'title'):
--> 345         raise PageError(self.title)
    346       else:
    347         raise PageError(pageid=self.pageid)

PageError: Page id "south part" does not match any pages. Try another id!
  • As to why wikipedia thinks I was looking for “south part”-your guess is as good as mine readers.

Now, let’s say I wanted to web-scrape the results of a Wikipedia search. Here’s how to do so:

import wikipedia
wikipedia.search('MCU')

['Marvel Cinematic Universe',
 'List of Marvel Cinematic Universe films',
 'Marvel Cinematic Universe: Phase Four',
 'List of Marvel Cinematic Universe television series',
 'Characters of the Marvel Cinematic Universe',
 'MCU (disambiguation)',
 'Avengers (Marvel Cinematic Universe)',
 'What If...? (TV series)',
 'Bucky Barnes (Marvel Cinematic Universe)',
 'Peter Parker (Marvel Cinematic Universe)']

In this example, I used the .search() method from the wikipedia package to run a search on MCU (the Marvel Cinematic Universe). In my MCU search, the .search() method returned a list of Wikipedia articles that relate to my search-in fact, all but one of the results in the list relates to the Marvel Cinematic Universe.

Now, let’s see what happens when we run .search() on a term that can have multiple meanings:

import wikipedia
wikipedia.search('Archer')

['Archery',
 'Jeffrey Archer',
 'Archer (2009 TV series)',
 'Anne Archer',
 'List of Archer characters',
 'The Archers',
 'Jack Archer',
 'Lance Archer',
 'Archer (disambiguation)',
 'Tasmin Archer']

In this example, I ran a Wikipedia search for Archer, and the output list shows articles related to both people with the surname Archer and articles related to the cartoon Archer.

Pretty neat stuff, right? Let’s see how we can do some cool web-scraping on a Wikipedia page:

BM = wikipedia.page('Baker Mayfield')
print(BM.title)
print()
print(BM.url)

Baker Mayfield

https://en.wikipedia.org/wiki/Baker_Mayfield

To perform web-scraping on a Wikipedia page, run the .page() method of the wikipedia package and pass in a Wikipedia page you would like to web-scrape (I picked Baker Mayfield’s Wikipedia page-he’s the QB of the Cleveland Browns). I stored the result of the wikipedia.page() method in the variable BM.

I then ran two simple web-scraping methods on my BM variable-.title and .url (notice that neither method uses the pair of parentheses)-to retrieve two bits of information-the Wikipedia page’s title and URL.

Simple enough, right? Well, let’s see what other information we can retrieve from web-scraping on a Wikipedia page:

BM = wikipedia.page('Baker Mayfield')
print(BM.images)
print()
print(BM.content)

['https://upload.wikimedia.org/wikipedia/commons/e/ed/2017-0717-Big12MD-BakerMayfield.jpg', 'https://upload.wikimedia.org/wikipedia/commons/4/4e/3_stars.svg', 'https://upload.wikimedia.org/wikipedia/commons/1/1a/Baker_Mayfield_%2849206381928%29.jpg', 'https://upload.wikimedia.org/wikipedia/commons/f/fc/Baker_Mayfield_2020.jpg', 'https://upload.wikimedia.org/wikipedia/commons/f/f1/Baker_Mayfield_training_camp_2018_%282%29_%28cropped%29.jpg', 'https://upload.wikimedia.org/wikipedia/commons/3/3f/Baker_Mayfield_vs_Bengals_2019_%282%29.jpg']

Baker Reagan Mayfield (born April 14, 1995) is an American football quarterback for the Cleveland Browns of the National Football League (NFL). Following a stint with Texas Tech, Mayfield played college football at Oklahoma, where he won the Heisman Trophy as a senior. He was selected by the Browns first overall in the 2018 NFL Draft.
In his NFL debut, Mayfield led Cleveland to their first win in 19 games, ending a 635-day streak, and went on to set the rookie quarterback record for passing touchdowns at 27. Mayfield struggled during his sophomore year, but rebounded in 2020 when he led the Browns to their first playoff appearance since 2002 and victory since 1994. He is also the only quarterback to win a postseason game with the Browns since their 1999 reactivation as an expansion team.


== Early life and high school career ==
Mayfield was born on April 14, 1995, in Austin Texas, to James and Gina Mayfield as the second of two sons. James, a private equity consultant, encountered financial difficulties during his younger son's senior year in high school. These struggles forced the Mayfields to sell their family home and move from rental home to rental home.Mayfield grew up as a fan of Oklahoma, and he attended a number of their games during his childhood. His father played football for three years for the University of Houston, though James never lettered.Mayfield was the starting quarterback for the Lake Travis High School Cavaliers football team. He led Lake Travis to a 25–2 record in two seasons and won the 2011 4A State Championship. He finished his high school football career totaling 6,255 passing yards, 67 touchdowns, and eight interceptions.


== College career ==


=== Texas Tech ===
Shortly before the start of the 2013 season, Mayfield was named as the starting quarterback following a back injury of projected starter and former Lake Travis quarterback Michael Brewer. Mayfield is the first walk-on true freshman quarterback to start a FBS season opener at the quarterback position.In his first start against SMU, Mayfield passed for 413 yards and four touchdowns. His 43 completions of 60 attempts broke a school record held by Billy Joe Tolliver, and fell only four completions short of the NCAA Division I FBS single-game record for completions by a freshman, held by Luke McCown. For his performance, Mayfield was named Big 12 Conference Offensive Player of the Week – the first freshman Texas Tech quarterback to be named so since former Red Raider head coach Kliff Kingsbury in 1999. The game featured the last four former Lake Travis quarterbacks combined on both teams: Garrett Gilbert, Michael Brewer, Collin Lagasse, and Mayfield.Following the Red Raiders' second victory over Stephen F. Austin, Mayfield's 780 season yards and seven touchdowns already exceeded the 755 yards and six touchdowns accrued by Texas Tech's last true freshman quarterback, Aaron Keesee, in 10 games. After being affected by a knee injury and losing the starting job to fellow true freshman Davis Webb, Mayfield finished the season with 2,315 yards on 218-of-340 completions with 12 touchdowns and 9 interceptions.Mayfield was named one of 10 semifinalists for the Burlsworth Trophy in November; the award is given to the best player in Division I football who began his college career as a walk-on.Mayfield earned Big 12 Conference Freshman Offensive Player of the Year for the 2013 season. Mayfield announced that he would be leaving the program due to a "miscommunication" with the coaching staff.


=== Oklahoma ===
After playing for Texas Tech, Mayfield transferred to the University of Oklahoma in January 2014, but had not contacted the Sooners coaching staff. Mayfield further elaborated in an interview with ESPN that he sought to transfer due to scholarship issues and a perception that he had earned the starting position and that further competition was not "really fair." The alleged scholarship issues were denied by Texas Tech coach Kliff Kingsbury.In February 2014, Oklahoma head coach Bob Stoops confirmed that Mayfield would be walking on for the Oklahoma Sooners. Mayfield was not eligible to play until the 2015 season, and he lost a season of eligibility due to Big 12 Conference transfer rules following an unsuccessful appeal of his transfer restrictions.


==== 2015 season ====
On August 24, 2015, Mayfield was named the starting quarterback for the Sooners after winning an open quarterback competition against Trevor Knight. On September 6, 2015, Mayfield started against Akron. Mayfield totaled 388 passing yards with three passing touchdowns on 23 completions in the 41–3 win. In the second game of the 2015 season, Mayfield started at Tennessee at Neyland Stadium. The Sooners were ranked 19th at the time and the Volunteers were ranked 23rd. Mayfield started off very slow in the game, not even reaching midfield until the 13-minute mark of the fourth quarter. Oklahoma came back from a 17-point deficit to win the game by a score of 31–24 in double overtime. Mayfield threw for 187 yards and three touchdowns on 19 completions while throwing two interceptions early in the game. In the third game of the season, Mayfield started against Tulsa. He had a career day, throwing for 487 yards and four touchdowns, including 316 yards in the first half. Mayfield also ran for 85 yards and two touchdowns in the 52–38 win.Mayfield finished the year with 3,700 passing yards, 36 touchdowns, and seven interceptions, a résumé which propelled him to fourth place in voting for the Heisman Trophy. Mayfield helped lead Oklahoma to the 2015 Orange Bowl, which served as the semifinal for the 2015 College Football Playoff. However, Oklahoma lost to Clemson by a score of 37–17.


==== 2016 season ====
Mayfield started off the 2016 season with 323 passing yards and two touchdowns in a 33–23 loss to #15 Houston. In the rivalry game against Texas on October 8, he had 390 passing yards, three touchdowns, and two interceptions in the 45–40 victory. On October 22, in a 66–59 victory over Texas Tech, Mayfield had 545 passing yards and seven touchdowns in a historic matchup against future NFL quarterback Patrick Mahomes. Mahomes tallied 734 passing yards and five touchdowns to go along with Mayfield's numbers in a game that broke various single-game passing records. Over the final five games of the regular season, Mayfield totaled 1,321 passing yards, 15 passing touchdowns, and three interceptions, to go along with three rushing touchdowns. All five games were victories for the Sooners.In December 2016, it was announced that Mayfield and his top receiving target, Dede Westbrook, would be finalists for the 2016 Heisman Trophy. It was also announced that they would play in the 2017 Sugar Bowl. Mayfield ended up finishing third in the Heisman voting.In the 2017 Sugar Bowl, Mayfield helped lead the Sooners to a 35–19 victory over Auburn. He finished the game with 19 completions on 28 attempts for 296 passing yards and two touchdowns, earning him the MVP award.


==== 2017 season ====
On September 9, 2017, after a win against the Ohio State Buckeyes in Columbus, Mayfield planted the Sooners' flag in the middle of the painted "O" at Ohio Stadium, causing a major public backlash. Mayfield issued an apology shortly afterwards.On November 4, 2017, Mayfield threw for a school-high 598 yards against in-state rival Oklahoma State. Mayfield finished 24-for-36 with five passing touchdowns and one rushing touchdown, and Oklahoma won the game by a score of 62–52. Mayfield completed his career 3–0 as the starting Oklahoma quarterback in the Bedlam Series.

In November 2017, Mayfield was under fire again after an interaction during the game against Kansas. Mayfield was seen grabbing his crotch and mouthing "Fuck you!" at the coach of the opposing team. He also told their fans to "Go cheer on basketball." In response, Mayfield issued another public apology. Days after the 41–3 victory over Kansas, Sooners head coach Lincoln Riley announced that Mayfield would not start or be the captain during the upcoming game against West Virginia due to his actions against Kansas.On December 2, 2017, with the return of the Big 12 Championship Game after a six-year hiatus, Mayfield led Oklahoma to its third straight Big 12 championship, with Oklahoma beating the TCU Horned Frogs 41–17. Mayfield won MVP honors while Oklahoma clinched a second playoff berth in three years. A month later, the Sooners lost to the Georgia Bulldogs 54–48 in the 2018 Rose Bowl, which served as the national semifinal game.On December 9, 2017, Mayfield won the 2017 Heisman Trophy with a sweeping majority. He received 732 first-place votes and a total of 2,398 points. This amount translated to 86% of the possible points and the third highest percentage in Heisman history. In addition, Mayfield became the first and only walk-on player to ever win the Heisman Trophy.


=== "Baker Mayfield rule" ===
When Mayfield transferred from Texas Tech to Oklahoma after his freshman year, he filed an appeal to the NCAA to allow him to be eligible to play immediately at Oklahoma on the basis that he was a walk-on and not a scholarship player at Texas Tech; therefore, the transfer rules that apply to scholarship players should not be applicable to his situation. The NCAA denied his appeal as he did not meet the criteria. Big 12 Conference rules additionally stipulate that intra-conference transfers will lose one year of eligibility over and beyond the one-year sit-out imposed by the NCAA. Mayfield attempted to appeal his initial loss of eligibility to the Big 12 Conference faculty athletics representatives but was denied in September 2014.Officials from Oklahoma asked Texas Tech officials to authorize Mayfield's immediate eligibility, but Texas Tech officials objected and declined the request before granting a release in July 2014. Mayfield was thus forced to sit out the 2014 season, while also losing one year of eligibility as required by the rules.On June 1, 2016, the Big 12 faculty athletic representatives voted against a rule proposal that would have allowed walk-on players to transfer within the conference and not lose a year of eligibility. The next day, the rule proposal was amended to allow walk-on players, without a written scholarship offer from the school they are transferring from, to transfer within the conference without losing a season of eligibility. The faculty athletic representatives approved the amended proposal with a vote of 7–3. The rule change made Mayfield eligible to play for Oklahoma through the 2017 season. Texas Tech voted in favor of the rule.


=== College statistics ===
Source:


== Professional career ==

The Cleveland Browns selected Mayfield with the first overall pick in the 2018 NFL Draft. Mayfield signed a four-year rookie contract with the Browns on July 24, 2018, with the deal worth $32.68 million in guaranteed salary.


=== 2018 season ===

Mayfield played in his first NFL game in Week 3 against the New York Jets, replacing an injured Tyrod Taylor with the Browns down 14–0. Mayfield went 17 of 23, passing for 201 yards as the Browns came back and prevailed 21–17, ending their winless streak at 19 games. Mayfield became the first player since Fran Tarkenton in 1961 to come off the bench in his debut, throw for more than 200 yards, and lead his team to its first win of the season.Mayfield started for the first time in the Browns' next game, making him the 30th starting quarterback for the Browns since their return to the NFL in 1999, in a 42–45 overtime loss to the Oakland Raiders. In Week 5, Mayfield threw for 342 passing yards and one touchdown as he earned his first victory as a Browns' starter, in a 12–9 overtime win over the Baltimore Ravens. In Week 10, Mayfield led the Browns to a 28–16 victory over the Atlanta Falcons. throwing for 216 yards, three touchdowns, and a passer rating of 151.2, with no turnovers. The following week, Mayfield led the Browns to their first away win since 2015, against the Cincinnati Bengals. He completed 19 of 26 passes for 258 yards and four touchdowns. In Week 12, in a 29–13 loss to the Houston Texans, Mayfield passed for 397 yards, one touchdown, and three interceptions. Mayfield bounced back in the following game, a 26–20 victory over the Carolina Panthers, going 18 of 22 for 238 passing yards and one touchdown.In Week 16, Mayfield completed 27 of 37 passes for 284 yards and three touchdowns with no interceptions in a 26–18 win over the Cincinnati Bengals, earning him AFC Offensive Player of the Week. He also won the Pepsi NFL Rookie of the Week fan vote for the sixth time. On December 29, Mayfield was fined $10,026 for unsportsmanlike conduct during the game. As reported by The Plain Dealer, Mayfield "pretended to expose his private parts" to Browns offensive coordinator Freddie Kitchens after throwing a touchdown to tight end Darren Fells. Kitchens later defended the gesture as an inside joke between the two. Mayfield's agent Tom Mills said they would appeal the fine. On December 30, in the regular-season finale against the Ravens' league-best defense and fellow rookie quarterback Lamar Jackson, Mayfield threw for 376 yards and three touchdowns, but his three costly interceptions— one of which came at the hands of linebacker C. J. Mosley with 1:02 left in the fourth quarter while attempting to drive the team into range of a game-winning field goal attempt— ultimately contributed to a 26–24 loss.
Nonetheless, Mayfield helped lead the Browns to a 7-8-1 record and their best record since 2007. He finished the season with 3,725 passing yards and also surpassed Peyton Manning and Russell Wilson for most touchdowns thrown in a rookie season with 27.While Mayfield was considered by many to be the favorite for Offensive Rookie of the Year for 2018, the award was given to Giants running back Saquon Barkley. On the annual Top 100 Players list for 2019, Mayfield's peers named him the 50th best player in the league, one spot behind teammate Myles Garrett. He was named 2018 PFWA All-Rookie, the second Cleveland quarterback to receive this honor since Tim Couch in 1999.


=== 2019 season ===

In Week 1 against the Tennessee Titans, Mayfield threw for 285 yards and a touchdown.  However, he also threw three fourth-quarter interceptions, one of which was returned by Malcolm Butler for a touchdown. The Browns lost 43–13. After the blowout loss, Mayfield said "I just think everybody just needs to be more disciplined. I think everybody knows what the problem is. We'll see if it's just bad technique or just see what it is. Dumb penalties hurting ourself and then penalties on my part. Just dumb stuff." In Week 2 against the New York Jets, Mayfield finished with 325 passing yards, including a quick-attack pass to Beckham that went 89 yards for a touchdown as the Browns won 23–3. In Week 4 against the Baltimore Ravens, Mayfield threw for 342 yards, one touchdown, and one interception in the 40–25 win. Against the San Francisco 49ers, Mayfield struggled against a stout 49ers defense, completing just 8-of-22 passes for 100 yards with two interceptions as the Browns were routed 31–3.Mayfield recorded his first game of the season with two or more passing touchdowns in Week 10 against the Buffalo Bills, completing 26 of 38 passes for 238 yards and two touchdowns, including the game-winner to Rashard Higgins, as the Browns snapped a four-game losing streak with a 19–16 win. Four days later against the Pittsburgh Steelers and former Big 12 Conference rival Mason Rudolph, Mayfield recorded his first career win against Pittsburgh, accounting for three total touchdowns (2 passing, 1 rushing) as Cleveland won 21–7. In Week 12 against the Miami Dolphins, Mayfield threw for 327 yards, three touchdowns, and one interception in the 41–24 win. In Week 17 against the Cincinnati Bengals, Mayfield became the first Cleveland Browns QB to start all 16 games in a season since Tim Couch in 2001. In the game, Mayfield threw for 279 yards, three touchdowns, and three interceptions as the Browns lost 33–23. Mayfield finished the 2019 season with 3,827 passing yards, 22 touchdowns, and 21 interceptions as the Browns finished with a 6–10 record.


=== 2020 season ===

In Week 1 against the Baltimore Ravens, Mayfield threw for 189 passing yards, a touchdown and an interception in the 38–6 loss. In the following week against the Cincinnati Bengals, Mayfield finished with 218 passing yards, two touchdowns and an interception in the 35–30 win. In Week 6 against the Pittsburgh Steelers, Mayfield completed 10 of 18 passes for 119 yards, with one touchdown, two interceptions and took four sacks during the 38–7 loss. Mayfield was replaced by Case Keenum in the third quarter due to aggravation of a minor rib injury he suffered in the previous week's game. In Week 7 against the Cincinnati Bengals, Mayfield started off slow completing 0 of 5 passes with an interception, but later completed 22 of 23 passes for 297 yards and a career-high five touchdowns including one to Donovan Peoples-Jones with 11 seconds remaining in the fourth quarter to help secure a 37–34 Browns' win. Mayfield was named AFC Offensive Player of the Week for his performance in Week 7.Mayfield was placed on the reserve/COVID-19 list on November 8 after being in close contact with a person who tested positive for the virus, and was activated three days later. In Week 13 against the Tennessee Titans, Mayfield completed 25 of 33 passes for 334 yards and four touchdowns which were all in the first half in a 41–35 victory.  Mayfield tied Otto Graham for four first half touchdowns and the victory marked the Browns first winning record since 2007. Hence, Mayfield was named the FedEx Air player of the week for week 13. In Week 14 against the Ravens, Mayfield threw for 343 yards, 2 touchdowns, and 1 interception as well as rushing for 23 yards and a touchdown during the 47–42 loss. In Week 16 against the New York Jets, Mayfield lost a fumble on fourth down with 1:25 remaining in the game while attempting a quarterback sneak during the 23–16 loss. In Week 17, Mayfield and the Browns defeated the Pittsburgh Steelers 24–22 and earned their first post season playoff berth since 2002.  The Browns finished the regular season 11–5.In the Wild Card Round against the Pittsburgh Steelers, Mayfield went 21 of 34 for 263 yards and 3 touchdowns during the 48–37 win, leading the Browns to their first playoff victory since the 1994 season In the Divisional Round of the playoffs against the Kansas City Chiefs, Mayfield threw for 204 yards, 1 touchdown, and 1 interception during the 22–17 loss.Overall, Mayfield finished the 2020 season with 4,030 passing yards, 30 touchdowns, and 9 interceptions through 18 total games.


=== 2021 season ===

The Browns exercised Mayfield's fifth-year contract option for the 2022 season on April 23, 2021, worth $18.9 million guaranteed. On October 7, 2021, it was revealed that Mayfield was playing with a partially torn labrum which he suffered during the Browns Week 2 victory over the Houston Texans. Mayfield continued to play with the injury until reaggravating it in Week 6 against the Arizona Cardinals. Due to the injury, Mayfield was ruled out for the Browns' Week 7 game against the Denver Broncos, missing his first game since taking over as the Browns' starter in 2018. On November 14, 2021, Mayfield suffered a right knee contusion during their crushing Week 10 loss to the Patriots. While the injury was not severe, coach Kevin Stefanski decided not to put him in for the rest of the game due to Mayfield absorbing hits and the game being out of reach. After the Browns were eliminated from the postseason following a Week 17 loss to the Pittsburgh Steelers, the Browns announced Mayfield would undergo surgery on the torn labrum, ending Mayfield's season. He was placed on injured reserve on January 5, 2022. Mayfield threw for 3,010 yards, 17 touchdowns, and 13 interceptions in 14 games played.


== NFL career statistics ==


=== Regular season ===


=== Postseason ===


== Career accomplishments ==


=== NCAA ===


==== Accolades ====
Heisman Trophy (2017)
2x Heisman Trophy Finalist (2016, 2017)
Maxwell Award (2017)
Walter Camp Award (2017)
Davey O'Brien Award (2017)
Associated Press Player of the Year (2017)
2× Sporting News Player of the Year (2015, 2017)
2× Burlsworth Trophy (2015, 2016)
2× Big 12 Offensive Player of the Year (2015, 2017)
Big 12 Offensive Freshman of the Year (2013)
2× First-team All-American (2015, 2017)
3× First-team All-Big 12 (2015–2017)


==== Records and accomplishments ====
First former walk-on to win Heisman Trophy
NCAA passer rating leader (2017) [203.8]
2x NCAA passing efficiency rating leader (2016, 2017) [196.4, 198.9]
2x NCAA yards per attempt leader (2016, 2017) [11.1, 11.5]
2x NCAA adjusted passing yards per attempt leader (2016, 2017) [12.3, 12.9]
2x NCAA pass completion percentage leader (2016, 2017) [70.9, 70.5]
NCAA total yards per play leader (2017) [9.9]
NCAA TDs responsible for leader (2017) [49]Oklahoma Sooners football records

Most career total touchdowns  — 137 (119 passing, 18 rushing)
Highest career passing completion percentage  — 69.8 (tied)
Most passing yards in a game — 598
Most passing touchdowns in a game — 7


=== NFL ===


==== Accolades ====
7× Pepsi NFL Rookie of the Week (2018 Weeks 3, 7, 9, 12, 14, 16, 17)
2x AFC Offensive Player of the Week (2018 Week 16, 2020 Week 7)
PFT Rookie of the Year (2018)
PFWA Rookie of the Year (2018)
PFF Offensive Rookie of the Year (2018)
PFWA All-Rookie Team (2018)


==== Records and accomplishments ====
NFL Rookie QB QBR Leader (2018)
NFL Rookie QB Pass Completions Leader (2018)
NFL Rookie QB Pass Attempts Leader (2018)
NFL Rookie QB Pass Completion Percentage Leader (2018)
NFL Rookie QB Pass Attempts per Game Leader (2018)
NFL Rookie QB Pass Yards Leader (2018)
NFL Rookie QB Pass Yards per Pass Attempt Leader (2018)
NFL Rookie QB Pass Yards per Game Leader (2018)
NFL Rookie QB Pass Touchdowns Leader (2018)Browns franchise records

Most consecutive games with at least 2 passing touchdowns — 5
Most Passing Yards per Game in a season – 266.1
Highest QBR for a rookie — 55.7
Highest Passer Rating by a rookie — 93.7
Highest Completed Pass Percentage by a rookie — 63.8
Highest Net Yards per Pass Attempt by a rookie — 6.95
Highest Adjusted Net Yards per Pass Attempt by a rookie — 6.77
Lowest Percentage of Sacks per Pass Attempt by a rookie — 4.9
Most Passing Completions by a rookie — 310
Most Passing Yards by a rookie — 3,725
Most Passing Yards per Game by a rookie – 266.1
Most 4th quarter Comebacks by a rookie — 3
Most Game Winning Drives by a rookie — 4
Most Passing Yards in a Game by a rookie — 397
Most Touchdown Passes in a game by a rookie — 4
Most passing touchdowns by a rookie — 27
Most Passing Completions in a game by a rookie — 29 (Done twice, tied with Tim Couch)
High Passing Completion Percentage in a game by a rookie — 85.0 (17/20, Week 10)


== Personal life ==
In July 2019, Mayfield married Emily Wilkinson.


== References ==


== External links ==
Official website
Cleveland Browns profile
Oklahoma Soones profile
Baker Mayfield at Heisman.com

Career statistics and player information from NFL.com · Pro Football Reference

In this example, I retrieved the Wikipedia page’s images and content using the wikipedia package’s .images() and .content() methods, respectively. However, you’ll notice that the .images() method doesn’t display all the images on the Wikipedia page but rather a list of the URLs of the images on the Wikipedia page.

So, how can we access the page’s images? Take a look at this code:

print(BM.images[0])

https://upload.wikimedia.org/wikipedia/commons/e/ed/2017-0717-Big12MD-BakerMayfield.jpg

In this example, I’m accessing the first image in the images list and I get that image’s hyperlink, which takes me to the JPG of Baker Mayfield that you see above.

Pretty impressive stuff, right?

Last but not least, let’s explore Python’s freegames package, which allows you to play several free Python games (yes, R isn’t the only programming tool with free games). To access the freegames package, first install the package by running the line pip install freegames on your command prompt (or run this line of code on your IDE preceded by an exclamation point).

Let’s play around with some of the games provided in the freegames package:

!pip install freegames

!python -m freegames.connect

And here’s what the board looks like after a (hypothetical) game:

In this example, after I pip-installed the freegames package, I ran the command !python -m freegames.connect to run the freegames package’s Connect-4 game, which, as you can guess, runs a Pythonic Connect-4 game in a separate window.

However, when you run the game, you’ll notice that, even though you can click on the board and a “chip” will drop in a certain slot (depending on where you click) and the color of the chips dropped will alternate between red and yellow with each click, the game doesn’t end when either color gets 4 in a row-rather, you can keep clicking until you fill in the board if you wish. Why is that the case? Well, the website for the freegames Python package-http://www.grantjenks.com/docs/freegames/index.html-contains not only the list of all the available free games on the freegames package but also the code for each of these games. Take a look at the code for the package’s Connect-4 game:

  • You can find this code by scrolling down the page I just hyperlinked in this post and clicking on the “Connect” hyperlink.

When you scroll down the code for the freegames package’s Connect-4 game, you’ll notice that although it has the functionality to generate a Connect-4 board and drop “chips” of alternating colors onto the game board, there is no functionality to detect a winner or create a random computer player (which would make the game more fun). However, from the insights I gathered from the code, that seemed to be the developers’ intent, as they created this tool as a fun way to teach programming to inner-city youth in the early 2010s (this fact is mentioned on their website). The fact that most of these games have missing functionalities (like the fact that Connect-4 doesn’t end when a player gets 4 in a row) was intentional, as this would provide some fun programming challenges for students (or anybody wanting to learn programming).

Let’s run another game from the package-snake. To run the Snake game (yes, Snake like the classic 70s arcade game), run this command on your IDE !python -m freegames.snake.

Here’s what the Snake screen looks like after I’ve finished a game:

And here’s the output you see on the IDE after a game is finished:

Interestingly enough, this is one of the few games in the freegames package that keeps your score and stops running when the game ends (recall the Connect-4 game didn’t do this).

  • At least in Python’s freegames package, you start off with one point in Snake and get another point each time you “eat” the green square. As you can see, I managed to get 12 points before my game ended.

Also, remember how I showed you that you could see the game code for the Connect-4 game? You can do the same for the Snake game (and all other games on this package), but to see the code for the Snake game, click on the “Snake” link in the hyperlinked page I posted earlier (the link with grantjenks in the URL).

As you see from the snake code, the developers included some programming exercises for students (perhaps challenging them to see if they can implement the data logic to enhance game functionalities):

  • I might revisit the freegames package in a separate lesson, so stay tuned ;-).

Thanks for reading,

Michael