Smart Alarms are very common today yet the good ones expensive. What if you wanted to make a smart alarm clock on your own using as little hardware and cost as possible? You may ask isn’t the RPI costly, yes it is but, the only purpose of using an RPI is easy to net connectivity which can readily be replaced by a Node MCU or even an Arduino board. To make the coding simpler we make the smart alarm clock with raspberry pi. Smart Alarm is a combination of APIs, an RPI, and a small section of natural language processing. The time, date, and news are got using python libraries based on their APIs. The news is obtained from several websites and summarised using NLP. All actions and commands are performed by voice. The weather API directly dives the details.
Content
Text-to-Speech
Text-to-Speech is used to automate the clock and give all outputs in audio formats. It is also an easy but good piece of code to have while working on various projects. For our purpose, we will use a python library called ‘gTTS‘ to interface with the Google text to speech API and give results. Finally, use the ‘playsound‘ library to play the respective audio.
Start by installing the library:
pip3 install gTTS
pip3 install playsound
Then import these libraries:
from gtts import gTTS
import playsound
Create a new function that reads a text and returns an audio:
def text_to_speech(text):
language = 'en'
# conversion of text to audio object
myobj = gTTS(text=text, lang=language, slow=False)
myobj.save("welcome.mp3")
playsound.playsound('welcome.mp3', True)
Speech-to-Text
To enable voice commands speech to text will be used. Again Google’s speech to text API will come in play with other prerequisite Python libraries. The default API key is publicly available and there is no need to get a personal one. The conversion of speech to text is rather a complex machine learning model and we will not go into details about it.
Start by instaling the given libraries:
pip3 install pyaudio
pip3 install SpeechRecognition
Speech recognition should be installed first as the latter is its prerequisite. It also has a variety of other Speech-to-Text APIs such as Bing, IBM, etc. Each has a different efficiency and accuracy, so do try them. Import these libraries in a new python file to code this section:
import speech_recognition as sr
Create objects of the library speech recognition and microphone:
r = sr.Recognizer()
m = sr.Microphone()
Define a new function to listen to audio and convert to text:
start = True
while(start):
try:
with m as source:
r.adjust_for_ambient_noise(source)
print("start speaking")
audio = r.listen(source)
Mytext = r.recognize_google(audio)
Mytext = Mytext.lower()
print(Mytext)
if(Mytext[len(Mytext)-4:] == 'quit'):
start = False
except sr.RequestError as e:
print("Could not request results; {0}".format(e))
except sr.UnknownValueError:
print("unknown error occured")
- Line 7 listens for additional surrounding noise and removes them when hearing other sounds. This process happens once per code run.
- Line 10 listens for the sound. The advantage of using this library is that it starts listening when you speak and stops as you do.
- Line 12 converts the speech to text.
- Finally, if you speak quit the recording stops. The last 2 exception conditions are there because there are times when no voice is recorded or some error occurred during initialization.
Time-Date
Using certain python libraries we can find time and date of any place, at any moment. These parameters are basic to every clock and hence must be present. Install the library and start coding.
pip3 install datetime
Import the libraries:
from datetime import datetime
import time
Create a new function which returns the date and time:
def dt():
# datetime object containing current date and time
now = datetime.now()
# dd/mm/YY H:M:S
year = int(now.strftime("%Y"))
month = int(now.strftime("%m"))
day = int(now.strftime("%d"))
hour = int(now.strftime("%H"))
minute = int(now.strftime("%M"))
second = int(now.strftime("%S"))
date_time = (year, month, day, hour, minute, second, 1, 48, 0)
format = "%b %d %Y, %r"
datetime_str = time.mktime(date_time)
dateTime = time.strftime(format, time.gmtime(datetime_str))
return dateTime
- Line 3 contains the exact date and time of the present.
- Read each parameter individually from the variable and convert it to a speech understandable format.
Weather
Today the weather also has become essential for smart clocks. Purely core python libraries will be used to access an API of the ‘OpenWeatherMap‘ website. The API key with certain restrictions can be obtained by signing into the website. There is also a variety of APIs from the same website that can be used for similar reasons, do go through them.
Import the core libraries in a new python file:
import requests
import json
Get the API key from the website and store it in a variable:
api_key = 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx'
1. Set City
The weather varies from place to place. In this code, each city is treated as a different region, and therefore your home city must be set in the clock to get weather. Define a new function in the same file that must keep running till a valid city is given to the API.
def set_city(city):
base_url = "http://api.openweathermap.org/data/2.5/weather?"
complete_url = base_url + "appid=" + api_key + "&q=" + city
response = requests.get(complete_url)
x = response.json()
if x["cod"] != "404":
text_to_speech("your city is set")
valid = True
else:
text_to_speech("Invalid city name, give another one.")
valid = False
return valid
- The output of the API is in JSON format
2. API
Using the same API we also get the weather of the place. The humidity, temperature, pressure, and weather description can be obtained from the API. For now, also in general humidity and pressure values can be ignored, hence the other 2 will be displayed. Define a new function to take city name as input and give the above parameters as output:
def weather(city_name):
base_url = "http://api.openweathermap.org/data/2.5/weather?"
complete_url = base_url + "appid=" + api_key + "&q=" + city_name
response = requests.get(complete_url)
x = response.json()
if x["cod"] != "404":
y = x["main"]
current_temperature = y["temp"]
current_pressure = y["pressure"]
current_humidiy = y["humidity"]
z = x["weather"]
weather_description = z[0]["description"]
# print following values
print(" Temperature (in kelvin unit) = " + str(current_temperature) + "\n atmospheric pressure (in hPa unit) = " + str(current_pressure) +
"\n humidity (in percentage) = " + str(current_humidiy) + "\n description = " + str(weather_description))
else:
print(" City Not Found ")
return current_temperature, weather_description
- The above code is similar to the one before, the only difference being that the content of the JSON output is stored in variables like temperature, humidity, pressure, and description.
- The JSON output is also syntax specific therefore follow the above steps strictly.
News
Every morning you get up, still half asleep to scroll social media sites and news applications. Instead of going through so much trouble why not simply command your smart clock and it will scrape news from the internet with news containing the specified keywords.
1. Newspaper
Generally, web scrapping is a skill hard to master and also perform in a short time but with the help of the python library newspaper, news can easily be scrapped and converted to text, all it takes is 5 to 10 lines of code. Install the library in your system:
pip3 install newspaper
Import the above library and random in a new python file:
import newspaper
from newspaper import Article
import random
Define a new function which takes in the keywords and outputs 10 stories. Declare the websites from which to extract and download articles.
def news(keywords):
URL = []
key_URL = []
stories = []
websites = ['http://qz.com', 'http://www.cnn.com', 'https://www.ndtv.com/', 'https://www.nytimes.com/', 'https://www.nbcnews.com/', 'https://www.foxnews.com/', 'https://www.theguardian.com/international']
ch = random.choice(websites[:])
paper = newspaper.build(ch)
for article in paper.articles:
URL.append(article.url)
print(article.url)
print(len(URL))
- Line 9 chooses the websites randomly every time.
- The one disadvantage of this library which I found is that sometimes accessing the same URL more than a time or two will result in a sort of timeout and the number of articles returned will be 0.
2. Stories
In the same function write a few more lines of code to parse and download the full articles from the given URLS:
for link in URL:
if keywords in link:
continue
else:
key_URL.append(link)
print(len(key_URL))
key_URL =key_URL[:10]
for i in range(len(key_URL)):
article = Article(key_URL[i], language='en')
article.download()
article.parse()
stories.append(article.text)
return stories
- From the list of URLs find the ones containing the keyword, discard the rest.
- Line 8 chooses the first 10 articles from the list.
- Lines 9-13 get the article in a particular language, download it, parse into a readable format and append into a list.
Text summarization
We have the stories stored in a list ready to be spoken out, but does anyone have the patience to read the whole story? I definitely would not. So to overcome this problem, each story is summarized into a single paragraph. The length of each paragraph depends on the length of the story. The summarization is done with the help of natural language processing, a branch of AI that deals with understanding and learning from languages.
1. NLP
Natural Language processing has a wide range of applications starting from chatbots, text classification, speech conversion, sentiment analysis, etc. Unknowingly we use NLP a lot in our daily lives from Siri, Alexa to Grammarly, Google searches. In this tutorial, we will use it to summarize the articles. The python library that will be used for this is called the natural language toolkit. Install the library in your system :
pip3 install nltk
Import the library in a new file with other supporting libraries such as regular expressions:
import re
import nltk
import heapq
Heapq is a form of a queue which pops the smallest value every time. I recommend going through its documentation for more information. Now in that python file download the stop words from NLTK, and remove special characters from the text using regular expressions.
nltk.download('stopwords')
keywords = 'corona'
# This function calls news file to get stories. Asuume only 1 story is stored in article_text for the moment
article_text = news(keywords)
print(article_text)
# Remove multiple spaces and square brackets
article_text = re.sub(r'\[[0-9]*\]', ' ', article_text)
article_text = re.sub(r'\s+', ' ', article_text)
# Remove special characters
formatted_article_text = re.sub('[^a-zA-Z]', ' ', article_text )
formatted_article_text = re.sub(r'\s+', ' ', formatted_article_text)
2. Summary
Calculate the weight of each word using the number of occurrences in the text. Then normalize the values. Using the given weights of the words add ones with most occurrences to the summary.
sentence_scores = {}
for sent in sentence_list:
for word in nltk.word_tokenize(sent.lower()):
if word in word_frequencies.keys():
if len(sent.split(' ')) < 30:
if sent not in sentence_scores.keys():
sentence_scores[sent] = word_frequencies[word]
else:
sentence_scores[sent] += word_frequencies[word]
summary_sentences = heapq.nlargest(7, sentence_scores, key=sentence_scores.get)
summary = ' '.join(summary_sentences)
For the complete explanation and article, visit this link:https://stackabuse.com/text-summarization-with-nltk-in-python/
The Article:
Its Summary:
Raspberry Pi
Raspberry pi is a small computer. It mostly uses Rasbian as its operating system but, as of today, can support almost anything. From home automation to self-driving cars, it is used in most hardware projects. We will use it to connect our clock to the internet and run the codes sequentially starting with speech to text. Use an external monitor or OLED for display. The power to the RPi can be provided normally.
I will go through the basics of initializing RPI:
STEP-1 : Take a RPI model, preffered above model 3. Get a SD card with at least 16 gb space. Download Rasbian in it. Connect it to a monitor, keyword, and install the OS in it.
STEP-2 : Install all the above libraries. It may not be as easy s doing it in your system but there are many tutorials, go through them.
STEP-3 : Copy all the codes in the RPI, connect it to the internet and run the codes.
Output
The input, as well as the output, are voice-controlled. In ideal conditions, time and date can always be seen as coded. The clock continuously listens for voice commands and performs the tasks accordingly. It does not use natural language processing to understand the commands, as it may get tough with the integration. Each valid command is performed by a different function coded in a separate python file to avoid any confusion.
Any further developments to this project are welcomed, comment below. There might be certain issues you might face while running the code. For example, the speech recognition library may cause some unusual errors or even lags. The news scrapper might not give any output at times, maybe because of a timeout problem. Except for the minor issues, I believe this project if not as a whole but in parts can be very useful. If you are interested in more IoT happenings go through this site: https://iot4beginners.com/top-5-must-read-for-latest-updates-and-news-in-iot/
With this, we come to the end of the tutorial. I hope you learned something new about using APIs and interfacing with raspberry pi. If you come across any doubts or errors, comment below, and an answer will be there soon enough. The entire code and original working directory of the project can be found in this GitHub repository: https://github.com/Shaashwat05/Smart_clock