fbpixel
Reconhecimento de objectos com TensorFlow e OpenCV

Reconhecimento de objectos com TensorFlow e OpenCV

Neste tutorial, veremos como realizar o reconhecimento de objetos com o TensorFlow e o OpenCV usando uma rede neural pré-treinada usando o aprendizado profundo.

Vimos num tutorial anterior como reconhecer formas simples utilizando a visão por computador. Este método só funciona para certas formas simples predefinidas. Se quiser reconhecer uma maior variedade de objectos, a forma mais fácil é utilizar a inteligência artificial.

Hardware

  • Um computador com uma instalação Python3
  • Uma câmara

Princípio

A inteligência artificial é um domínio da informática em que o próprio programa aprende a realizar determinadas tarefas. O reconhecimento visual, em particular. Neste tutorial, vamos utilizar uma rede neural treinada para reconhecer formas específicas.

São necessários muitos dados para poder treinar corretamente uma rede neural. Foi demonstrado que a aprendizagem é mais rápida numa rede neuronal treinada para outra coisa. Por exemplo, uma rede neuronal treinada para reconhecer cães será treinada mais facilmente para reconhecer gatos.

Configurar o Python

Caso contrário, pode descarregar e instalar o Python 3

Pode então instalar as bibliotecas OpenCV, numpy e imutils necessárias.

python3 -m pip install opencv-python numpy imutils

Eis as versões que estou a utilizar neste tutorial

numpy== 1.22.0
tensorflow== 2.13.0
opencv== 4.6.0

Nota: Ao utilizar certos pacotes python, como o TensorFlow, podem ocorrer frequentemente problemas de compatibilidade. Se tiver dificuldades, não hesite em instalar versões específicas dos pacotes. Se tiver vários projectos em curso, recomendo vivamente que crie ambientes virtuais (venv).

Recuperar um modelo pré-treinado

Descarregar o modelo ModelNet-SSD do Model Zoo (por exemplo, MobileNet SSD v2 320×320)

descarregar o ficheiro mscoco_label_map.pbtxt, que contém os identificadores dos objectos reconhecidos pelo modelo.

N.B.: num tutorial anterior, utilizámos os resultados da estrutura Caffe para o modelo (ficheiros prototxt e caffemodel). Neste artigo, usamos o SavedModel do TensorFlow.

Crie uma pasta TensorFlowCV, que será seu espaço de trabalho. Nesta pasta, crie uma pasta pretrained_models na qual pode descompactar o modelo descarregado.

Também pode criar uma pasta de dados para colocar as suas imagens ou vídeos.

Coloque os ficheiros do modelo numa pasta e crie o ficheiro ObjectRecognition.py

Script Python para reconhecimento de objectos

Em primeiro lugar, criamos um fluxo de vídeo (vs) utilizando a biblioteca imutils, que irá obter as imagens da câmara.

vs = VideoStream(src=0, resolution=(1600, 1200)).start()

Inicializamos uma rede neural com os parâmetros de SSD-ModelNetV2 (net) utilizando a biblioteca TensorFlow.

model= tf.saved_model.load("./pretrained_models/ssd_mobilenet_v2_320x320_coco17_tpu-8/saved_model")

Uma função obtém os nomes das classes reconhecidas pelo modelo a partir do ficheiro pbtxt

#load class names
def read_label_map(label_map_path):

    item_id = None
    item_name = None
    items = {}
    
    with open(label_map_path, "r") as file:
        for line in file:
            line.replace(" ", "")
            if line == "item{":
                pass
            elif line == "}":
                pass
            elif "id" in line:
                item_id = int(line.split(":", 1)[1].strip())
            elif "display_name" in line: #elif "name" in line:
                item_name = line.split(":", 1)[1].replace("'", "").strip()

            if item_id is not None and item_name is not None:
                #items[item_name] = item_id
                items[item_id] = item_name
                item_id = None
                item_name = None

    return items

class_names=read_label_map("./pretrained_models/ssd_mobilenet_v2_320x320_coco17_tpu-8/mscoco_label_map.pbtxt")
class_colors = np.random.uniform(0, 255, size=(len(class_names), 3))

Em seguida, criaremos um ciclo que, em cada iteração, lerá a imagem da câmara e passá-la-á para a entrada da rede neural para deteção e reconhecimento de objectos.

	#Main loop
	while True:
		# Get video sttream. max width 800 pixels 
		#img = vs.read()
		img= cv2.imread('./data/two-boats.jpg') #from image file
		#ret, img=vc.read() #from video or ip cam
		img = imutils.resize(img, width=800)

		img = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)
		# get height and width of image
		h, w, _ = img.shape

		input_tensor = np.expand_dims(img, 0)

		# predict from model
		resp = model(input_tensor)

Por fim, o código apresenta a caixa de deteção na imagem, a probabilidade de reconhecimento e a posição.

					# write classname for bounding box
					cls=int(cls) #convert tensor to index
					label = "{}: {:.2f}%".format(class_names[cls],score * 100)
					cv2.putText(img, label, (xmin, ymin-10), cv2.FONT_HERSHEY_SIMPLEX, 1, class_colors[cls], 1)
					
					#display position
					X= (xmax+xmin)/2
					Y= (ymax+ymin)/2
					poslbl= "X: ({},{})".format(X,Y)
					cv2.circle(img, (int(X)-15, int(Y)), 1, class_colors[cls], 2)	
					cv2.putText(img, poslbl, (int(X), int(Y)),
						cv2.FONT_HERSHEY_SIMPLEX, 0.5, class_colors[cls], 2)
					
					# draw on image
					cv2.rectangle(img, (xmin, ymin), (xmax, ymax), class_colors[cls], 4)

Código completo de reconhecimento de objectos com OpenCV e TensorFlow

#!/usr/bin/env python
# -*- coding: utf-8 -*-
#
#  ObjectRecognitionTFVideo.py
#  Description:
#		Use ModelNetV2-SSD model to detect objects on image or video
#
#  www.aranacorp.com

# import packages
import sys
from imutils.video import VideoStream
from imutils.video import FPS
import numpy as np
import argparse
import imutils
import time
import cv2
import tensorflow as tf


# load model from path
model= tf.saved_model.load("./pretrained_models/ssd_mobilenet_v2_320x320_coco17_tpu-8/saved_model")
print("model loaded")

#load class names
def read_label_map(label_map_path):

    item_id = None
    item_name = None
    items = {}
    
    with open(label_map_path, "r") as file:
        for line in file:
            line.replace(" ", "")
            if line == "item{":
                pass
            elif line == "}":
                pass
            elif "id" in line:
                item_id = int(line.split(":", 1)[1].strip())
            elif "display_name" in line: #elif "name" in line:
                item_name = line.split(":", 1)[1].replace("'", "").strip()

            if item_id is not None and item_name is not None:
                #items[item_name] = item_id
                items[item_id] = item_name
                item_id = None
                item_name = None

    return items

class_names=read_label_map("./pretrained_models/ssd_mobilenet_v2_320x320_coco17_tpu-8/mscoco_label_map.pbtxt")
class_colors = np.random.uniform(0, 255, size=(len(class_names), 3))


if __name__ == '__main__':

	# Camera initialisation
	print("Start Camera...")
	vs = VideoStream(src=0, resolution=(1600, 1200)).start() #from usb cam
	#vs = VideoStream(usePiCamera=True, resolution=(1600, 1200)).start() #from RPi cam
	#vc = cv2.VideoCapture('./data/Splash - 23011.mp4') #from video file

	time.sleep(2.0)
	fps = FPS().start()
	
	#Main loop
	while True:
		#get image
		img = vs.read() # Get video stream
		#img= cv2.imread('./data/two-boats.jpg') #from image file
		#ret, img=vc.read() #from video or ip cam

                #process image
		img = imutils.resize(img, width=800) #max width 800 pixels 
		img = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)
		# get height and width of image
		h, w, _ = img.shape

		input_tensor = np.expand_dims(img, 0)

		# predict from model
		resp = model(input_tensor)

		# iterate over boxes, class_index and score list
		for boxes, classes, scores in zip(resp['detection_boxes'].numpy(), resp['detection_classes'], resp['detection_scores'].numpy()):
			for box, cls, score in zip(boxes, classes, scores): # iterate over sub values in list
				if score > 0.61: # we are using only detection with confidence of over 0.6
					ymin = int(box[0] * h)
					xmin = int(box[1] * w)
					ymax = int(box[2] * h)
					xmax = int(box[3] * w)
									
					# write classname for bounding box
					cls=int(cls) #convert tensor to index
					label = "{}: {:.2f}%".format(class_names[cls],score * 100)
					cv2.putText(img, label, (xmin, ymin-10), cv2.FONT_HERSHEY_SIMPLEX, 1, class_colors[cls], 1)
					
					#display position
					X= (xmax+xmin)/2
					Y= (ymax+ymin)/2
					poslbl= "X: ({},{})".format(X,Y)
					cv2.circle(img, (int(X)-15, int(Y)), 1, class_colors[cls], 2)	
					cv2.putText(img, poslbl, (int(X), int(Y)),
						cv2.FONT_HERSHEY_SIMPLEX, 0.5, class_colors[cls], 2)
					
					# draw on image
					cv2.rectangle(img, (xmin, ymin), (xmax, ymax), class_colors[cls], 4)
				
				
		# Show video frame
		cv2.imshow("Frame", img)
		key = cv2.waitKey(1) & 0xFF

		# Exit script with letter q
		if key == ord("q"):
			break

		# FPS update 
		fps.update()

	# Stops fps and display info
	fps.stop()
	print("[INFO] elapsed time: {:.2f}".format(fps.elapsed()))
	print("[INFO] approx. FPS: {:.2f}".format(fps.fps()))

	cv2.destroyAllWindows()
	vs.stop()
	#vc.release()

Fontes de imagem para deteção de objectos

Pode utilizar este script com diferentes fontes de imagem. Para tal, é necessário adaptar ligeiramente o código anterior para modificar a variável “img” que contém a imagem a analisar.

  • A câmara Web do seu computador
vs = VideoStream(src=0, resolution=(1600, 1200)).start()
while True:
	frame = vs.read()

O fluxo de vídeo deve ser interrompido no final do guião com vs.stop()

vc = cv2.VideoCapture('rtsp://user:password@ipaddress:rtspPort')
while True:
	ret, frame=vc.read() #from ip cam

Certifique-se de que pára a captura de vídeo no final do guião com vc.release()

  • O Raspberry Pi Picam
vs = VideoStream(usePiCamera=True, resolution=(1600, 1200)).start()
while True:
	frame = vs.read()

Lembre-se de parar o fluxo no final do script com vs.stop()

  • Um ficheiro de vídeo
vc = cv2.VideoCapture('./img/Splash - 23011.mp4') #from video
while True:
	ret, frame=vc.read() #from video
  • Um ficheiro de imagem
frame= cv2.imread('./img/two-boats.jpg') 

Resultados

Para este exemplo, enviamos uma imagem de dois barcos como entrada para a rede neural, que são corretamente reconhecidos. Para obter resultados ligeiramente diferentes, pode modificar o parâmetro de confiança para evitar falsos positivos.

Pode testar este código com a sua webcam ou com fotografias, por exemplo, para ver o desempenho do modelo e do reconhecimento de objectos.

Quando o script estiver a funcionar, pode treinar o modelo para detetar outros objectos.

Pacotes e modelos

Neste tutorial, usamos o modelo pré-treinado SSD ModelNetV2. Vale a pena notar que existem outros modelos de classificação com desempenho e características diferentes.

  • vgg16
  • vgg19
  • resnet50
  • resnet101
  • resnet152
  • densenet121
  • densenet169
  • densenet201
  • inceptionresnetv2
  • inceptionv3
  • mobilenet
  • mobilenetv2
  • nasnetlarge
  • nasnetmobile
  • exceção

Não hesite em deixar-nos um comentário para partilhar os modelos que utiliza ou conhece e a sua opinião.

Fontes

Reconhecimento de texto com Python

Reconhecimento de texto com Python

Neste tutorial, vamos ver como reconhecer texto de uma imagem usando Python e Tesseract. O Tesseract é uma ferramenta para reconhecer caracteres, e portanto texto, contidos numa imagem (OCR, Optical Character Recognition).

Instalar o Tesseract

  • Em Linux

Para instalar o tesseract, introduza os seguintes comandos num terminal

sudo apt install tesseract-ocr
sudo apt install libtesseract-dev
  • Para Windows

pode descarregar e executar o instalador para o seu sistema operativo

Quando a instalação estiver concluída, adicione C:\Program Files\Tesseract-OCR à sua variável de ambiente Path.

Pode agora executar o tesseract e testar o resultado com o seguinte comando

tesseract <path_to_image> <path_to_result_file> -l <language>

ex:

tesseract test.png result -l fra

O Tesseract reconhecerá o texto contido na imagem test.png e escreverá o texto em bruto no ficheiro result.txt.

N.B.: O Tesseract pode ter dificuldades com a pontuação e o alinhamento do texto.

Reconhecimento de texto com o Pytesseract

Pode então instalar o pacote pytesseract

pip install pytesseract

A vantagem de utilizar Python, e OpenCV em particular, é que pode processar imagens e implementar a ferramenta em pacotes de software maiores. Segue-se uma lista de algumas das vantagens:

  • deteção de texto num vídeo
  • Processamento e filtragem de imagens para caracteres obstruídos, por exemplo
  • Detetar texto de um ficheiro PDF
  • Escrever os resultados num ficheiro Word ou Excel

No script seguinte, carregamos a imagem com o OpenCV e desenhamos rectângulos à volta do texto detectado. Os dados de posição são obtidos utilizando a função image_to_data. O texto em bruto pode ser obtido utilizando a função image_to_string

from PIL import Image
import pytesseract
from pytesseract import Output
import cv2
 
source = 'test.png'
img = cv2.imread(source)
text=pytesseract.image_to_string(img)
print(text)

d = pytesseract.image_to_data(img, output_type=Output.DICT)
 
NbBox = len(d['level'])
print ("Number of boxes: {}".format(NbBox))

for i in range(NbBox):
	(x, y, w, h) = (d['left'][i], d['top'][i], d['width'][i], d['height'][i])
	# display rectangle
	cv2.rectangle(img, (x, y), (x + w, y + h), (0, 255, 0), 2)
 
cv2.imshow('img', img)
cv2.waitKey(0)
cv2.destroyAllWindows()

O guião também funciona com fotografias de documentos

Bonus: Reconhecimento de texto com Python à partir d’un fichier PDF

Instalando a biblioteca pdf2image

pip install pdf2image

O pdf2image requer que o poppler esteja instalado

Bastante simples no Linux

sudo apt-get install poppler-utils

Para Windows

  • Descarregar o ficheiro zip
  • Extraia os ficheiros para onde desejar (C:
  • Adicione a pasta bin à variável de ambiente Path (C:\Users\ADMIN\Documents\poppler\Library\bin)
  • teste com o comando pdftoppm -h

Script para recuperar texto de um PDF

from pdf2image import convert_from_path, convert_from_bytes
from PIL import Image
import pytesseract
from pytesseract import Output

images = convert_from_path('invoice.pdf')

# get text
print("Number of pages: {}".format(len(images)))
for i,img in enumerate(images):
    print ("Page N°{}\n".format(i+1))
    print(pytesseract.image_to_string(img))

Script para apresentar rectângulos num PDF

from pdf2image import convert_from_path, convert_from_bytes
from PIL import Image
import pytesseract
from pytesseract import Output
import cv2
import numpy

images = convert_from_path('invoice.pdf')
for i,source in enumerate(images):
	print ("Page N°{}\n".format(i+1))
	
	#convert PIL to opencv
	pil_image = source.convert('RGB') 
	open_cv_image = numpy.array(pil_image) 
	# Convert RGB to BGR 
	img = open_cv_image[:, :, ::-1].copy() 
	#img = cv2.imread(source)

	d = pytesseract.image_to_data(img, output_type=Output.DICT)
	 
	NbBox = len(d['level'])
	print ("Number of boxes: {}".format(NbBox))

	for j in range(NbBox):
		(x, y, w, h) = (d['left'][j], d['top'][j], d['width'][j], d['height'][j])
		# display rectangle
		cv2.rectangle(img, (x, y), (x + w, y + h), (0, 255, 0), 2)
	 
	cv2.imshow('img', img)
	cv2.waitKey(0)
	cv2.destroyAllWindows()

Aplicações

  • Ler documentos digitalizados
  • Reconhecimento de texto em tempo real a partir de vídeo

Fontes

Criar o seu banco de imagens com Python

Criar o seu banco de imagens com Python

, ,

Para treinar uma rede neural na deteção e reconhecimento de objectos, é necessário um banco de imagens para trabalhar. Veremos como descarregar um grande número de imagens do Google utilizando Python. Para treinar uma rede neural, é necessária uma grande quantidade de dados. Quanto mais dados, melhor será o treino. No nosso caso, queremos treinar uma rede neural para reconhecer um determinado objeto. Para isso, criamos um script Python que descarrega os ficheiros da Internet e os coloca numa pasta.

Configurar o Python3

Descarregar as bibliotecas Selenium e OpenCV (opcional)

python3 -m pip install selenium
python3 -m pip install opencv-python

descarregar ficheiro geckodriver

N.B.: Apenas utilizamos a biblioteca OpenCV para verificar se o OpenCV pode abrir e utilizar as imagens, de modo a não sobrecarregar desnecessariamente a pasta.

Script Python para descarregar imagens

Este script lança uma pesquisa no Google Image e guarda as imagens encontradas na pasta especificada para o banco de imagens.

Nota: Não se esqueça de especificar o caminho para o ficheiro GECKOPATH do geckodriver, o caminho para a pasta de destino e as palavras-chave para a pesquisa no Google.

import sys
import os
import time 

#Imports Packages
from selenium import webdriver
from selenium.webdriver.common.keys import Keys
from selenium.common.exceptions import TimeoutException,WebDriverException
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By

import cv2

########################################################################
GECKOPATH = "PATH-TO-GECKODRIVER"
parent_dir = "PATH-TO-FOLDER"
search='coffee mug'
########################################################################

# path 
folderName=search.replace(" ","_")
directory = os.path.join(parent_dir, folderName,'img') 
   
# Create the directory 
try: 
	if not os.path.exists(directory):
		os.makedirs(directory) #os.mkdir(directory)
except OSError as error: 
	print("ERROR : {}".format(error)) 


sys.path.append(GECKOPATH)  
#Opens up web driver and goes to Google Images
browser = webdriver.Firefox()#Firefox(firefox_binary=binary)

#load google image
browser.get('https://www.google.ca/imghp?hl=en')

delay = 10 # seconds
try:
	btnId="L2AGLb"
	myElem = WebDriverWait(browser, delay).until(EC.presence_of_element_located((By.ID , btnId))) #id info-address-place-wrapper 
	elm=browser.find_element_by_id(btnId)
	elm.click()
	print("Popup is passed!")
except TimeoutException as e:
	print("Loading took too much time!")



# get and fill search bar
box = browser.find_element_by_xpath('//*[@id="sbtc"]/div/div[2]/input')
box.send_keys(search)
box.send_keys(Keys.ENTER)


#Will keep scrolling down the webpage until it cannot scroll no more
last_height = browser.execute_script('return document.body.scrollHeight')
while True:
	browser.execute_script('window.scrollTo(0,document.body.scrollHeight)')
	time.sleep(5)
	new_height = browser.execute_script('return document.body.scrollHeight')
	try:
		browser.find_element_by_xpath('//*[@id="islmp"]/div/div/div/div/div[5]/input').click()
		time.sleep(5)
	except:
		print("button not found")
		pass
		
	if new_height == last_height:
		break
	last_height = new_height
	
imgList=[]
for i in range(1, 1000):
	try:
		browser.find_element_by_xpath('//*[@id="islrg"]/div[1]/div['+str(i)+']/a[1]/div[1]/img').screenshot(directory+'\{}.png'.format(i))
		imgList.add(directory+'\{}.png'.format(i))
		
	except:
		pass
browser.quit()
 
#Test images with OpenCV
for img in imgList:
	try:   
		cv2.imread(img)
	except Exception as e:
		os.remove(img)
		print("remove {}".format(img))

BÓNUS: Gerir um pop-up

No código, adicionei um comando para gerir o pop-up que aparece quando a página Web é aberta. Este comando espera que o botão com o identificador correto seja carregado antes de o premir.

delay = 10 # seconds
try:
	btnId="L2AGLb"
	myElem = WebDriverWait(browser, delay).until(EC.presence_of_element_located((By.ID , btnId))) #id info-address-place-wrapper 
	elm=browser.find_element_by_id(btnId)
	elm.click()
	print("Popup is passed!")
except TimeoutException as e:
	print("Loading took too much time!")

Resultados

O script percorre os resultados do Google e tira screenshots de cada imagem para as colocar na nossa base de dados e formar um banco de imagens.

Tem agora um banco de imagens que pode utilizar para reconhecimento visual, por exemplo, ou para processamento de imagens.

Aplicações

  • Desenvolver algoritmos de processamento de imagem
  • Treino de redes neuronais para deteção e reconhecimento de objectos

Fontes

Sintetizador de voz eSpeak para Raspberry Pi

Sintetizador de voz eSpeak para Raspberry Pi

Pode fazer com que o seu Raspberry Pi fale utilizando um sintetizador de voz como o eSpeak para o transformar num assistente inteligente. Este tutorial ajudá-lo-á a fazer o seu robô ou aplicação falar.

Hardware

  • Raspberry Pi 3 avec Raspberry Pi OS
  • Ligação à Internet e acesso remoto

Verificar os periféricos áudio

Vamos começar por verificar os periféricos de áudio disponíveis

aplay -l

Selecionar o dispositivo de áudio

Por defeito, o som é emitido através da porta jack ou HDMI. Se quiseres ligar auscultadores, tens de selecionar a saída correspondente na GUI do Raspberry Pi ou com o sudo raspi-config.

Verificar o áudio

Vamos começar por verificar se o áudio está a funcionar corretamente e se os periféricos de áudio são tidos em conta.

aplay /usr/share/sounds/alsa/*

Instalar o sintetizador de voz espseak

sudo apt-get install espeak

Para testar a instalação do espeak, basta introduzir o seguinte comando:

espeak "Hello World"

Também pode instalar o pacote python e utilizá-lo diretamente num script.

sudo apt-get install python3-espea
from espeak import espeak
espeak.synth("hello world")

Para obter a lista de vozes disponíveis, introduza o comando

espeak --voices

Usando o eSpeak em um script Python com Subprocess

Pode executar comandos shell a partir de um script Python utilizando a biblioteca de subprocessos.

from time import sleep
import subprocess

def say(something, voice='fr+f1'):
	print("espeak -v {} {}".format(voice,something))
	subprocess.call(['espeak', '-v%s' % (voice), something])
    
text=[u"bonjour",u"aurevoir",u"a bientot", u"sa va", u"merci"]
textf=u"bienvenu admine, comment allez-vous aujourd'hui?"

for t in text:
	say(t)
	sleep(0.5)

say(textf)

Instalar o pyttsx3

Para usar o sintetizador de voz com Python, vamos usar o pacote pyttsx3.

Para instalar o pacote Python pyttsx3, introduza o seguinte comando:

pip3 install pyttsx3

Escolha a voz que pretende

for i,voice in enumerate(voices):
	print("----------------{}".format(i))
	print(voice.id)
	engine.setProperty('voice', voice.id)  # changes the voice
	print(voice.age)
	print(voice.gender)
	print(voice.languages)

Código txt2speech

#!/usr/bin/python3.4
# -*-coding:Utf-8 -*

from time import sleep
import pyttsx3 as pyttsx
engine = pyttsx.init()
voices = engine.getProperty('voices')

print(voices)

engine.setProperty('voice', voices[0].id)  # changes the voice
	
#engine.setProperty('voice', voices[14].id)  # changes the voice
voiceNum=0
#Fr=[0 1 6 7 8 14] #6 = AC
"""
for voice in voices:
	print(voiceNum)
	voiceNum=voiceNum+1
	print(voice.id)
	engine.setProperty('voice', voice.id)  # changes the voice
	print(voice.age)
	print(voice.gender)
	print(voice.languages)
	print(voice.name)
"""

text=[u"bonjour",u"aurevoir",u"a bientot", u"sa va", u"merci"]
textf=u"bienvenu admine, comment allez-vous aujourd'hui?"

#rate = engine.getProperty('rate')
engine.setProperty('rate', 120)

#volume = engine.getProperty('volume')
#engine.setProperty('volume', volume)

for t in text:
	engine.say(t)
	sleep(0.5)

engine.say(textf)


engine.runAndWait()

Devias ouvir o teu Rapsberry Pi a falar!

Adicionar outras vozes

Pode criar e adicionar uma voz personalizada inspirando-se nas vozes existentes e lendo a documentação com atenção. Isto permitir-lhe-á concentrar-se em determinadas frases e pronúncias. Depois, quando dominar as definições, acabará por ter uma voz à sua medida.

Melhorar os resultados com os votos MBROLA

Pode utilizar outro sintetizador de voz um pouco mais potente do que o eSpeak e instalar novas vozes com o MBROLA. No nosso caso, estamos a instalar uma voz feminina francesa. Pode encontrar a voz que lhe convém na lista de vozes disponíveis.

Verificar se o mbrola existe. O seguinte comando dá-lhe as vozes disponíveis

apt-cache search mbrola
mkdir espeak
cd espeak
wget https://raspberry-pi.fr/download/espeak/mbrola3.0.1h_armhf.deb -O mbrola.deb
sudo dpkg -i mbrola.deb
rm mbrola.deb

Uma vez instalado o mbrola, pode instalar novas vozes

sudo apt-get install mbrola-fr4
espeak -v mb-fr4 "bonjour admin, comment allez-vous?"

N.B.: Pour installer le paquet mbrola, j’ai dû mettre à jour l’OS vers la version 11 (bullseye). Vous pouvez vérifier la version de l’os avec la commande cat /etc/os-release

Obviamente, as vozes mbrola não podem ser usadas com pyttsx3. Por isso, usamos o subprocesso

from time import sleep
import subprocess

def say(something, voice='mb-fr4'):
	print("espeak -v {} {}".format(voice,something))
	subprocess.call(['espeak', '-v%s' % (voice), something])
    
text=[u"bonjour",u"aurevoir",u"a bientot", u"sa va", u"merci"]
textf=u"bienvenu admine, comment allez-vous aujourd'hui?"

for t in text:
	say(t)
	sleep(0.5)

say(textf)

Saída de áudio HMDI

Se pretender utilizar a saída de áudio HDMI e não houver som, poderá ser necessário modificar o ficheiro config.txt

sudo nano /boot/config.txt

Descomente a linha hdmi_drive=2

Fontes

Reconhecimento de objectos com Python

Reconhecimento de objectos com Python

Neste tutorial, veremos como realizar o reconhecimento de objetos com Python usando uma rede neural pré-treinada usando aprendizado profundo.

Vimos num tutorial anterior como reconhecer formas simples utilizando a visão por computador. Este método só funciona para certas formas simples predefinidas. Se quiser reconhecer uma maior variedade de objectos, a forma mais fácil é utilizar a inteligência artificial.

Hardware

  •  Um computador com uma instalação Python3
  • Uma câmara

Princípio

A inteligência artificial é um domínio da informática em que o próprio programa aprende a realizar determinadas tarefas. O reconhecimento visual, em particular. Neste tutorial, vamos utilizar uma rede neural treinada para reconhecer formas específicas.

São necessários muitos dados para poder treinar corretamente uma rede neural. Foi demonstrado que a aprendizagem é mais rápida numa rede neuronal treinada para outra coisa. Por exemplo, uma rede neuronal treinada para reconhecer cães será treinada mais facilmente para reconhecer gatos.

Configurar o Python

Caso contrário, pode descarregar e instalar o Python 3

Pode então instalar as bibliotecas OpenCV, numpy e imutils necessárias.

pip3 install opencv-python numpy imutils

ou

python3 -m pip install opencv-python numpy imutils

Coloque os ficheiros do modelo numa pasta e crie o ficheiro ObjectRecognition.py

Script Python para reconhecimento de objectos

Em primeiro lugar, criamos um fluxo de vídeo (vs) utilizando a biblioteca imutils, que irá obter as imagens da câmara.

vs = VideoStream(src=0, resolution=(1600, 1200)).start()

Inicializamos uma rede neural com os parâmetros da ModelNet-SSD (net) utilizando a biblioteca OpenCV.

net = cv2.dnn.readNetFromCaffe(args["prototxt"], args["model"])

Em seguida, criaremos um ciclo que, em cada iteração, lerá a imagem da câmara e passá-la-á para a entrada da rede neural para deteção e reconhecimento de objectos.

while True:
	# Get video stream. max width 800 pixels 
	frame = vs.read()
	blob = cv2.dnn.blobFromImage(cv2.resize(frame, (300, 300)), 0.007843, (300, 300), 127.5)

	# Feed input to neural network 
	net.setInput(blob)
	detections = net.forward()

Por fim, o código apresenta a caixa de deteção e a probabilidade de reconhecimento na imagem.

label = "{}: {:.2f}%".format(CLASSES[idx],confidence * 100)
cv2.rectangle(frame, (startX, startY), (endX, endY),COLORS[idx], 2)
y = startY - 15 if startY - 15 > 15 else startY + 15
cv2.putText(frame, label, (startX, y),cv2.FONT_HERSHEY_SIMPLEX, 0.5, COLORS[idx], 2)
#!/usr/bin/env python
# -*- coding: utf-8 -*-
#
#  ObjectRecognition.py
#  Description:
#		Use ModelNet-SSD model to detect objects
#
#  www.aranacorp.com

# import packages
import sys
from imutils.video import VideoStream
from imutils.video import FPS
import numpy as np
import argparse
import imutils
import time
import cv2

# Arguments construction
if len(sys.argv)==1:
	args={
	"prototxt":"MobileNetSSD_deploy.prototxt.txt",
	"model":"MobileNetSSD_deploy.caffemodel",
	"confidence":0.2,
	}
else:
	#lancement à partir du terminal
	#python3 ObjectRecognition.py --prototxt MobileNetSSD_deploy.prototxt.txt --model MobileNetSSD_deploy.caffemodel
	ap = argparse.ArgumentParser()
	ap.add_argument("-p", "--prototxt", required=True,
		help="path to Caffe 'deploy' prototxt file")
	ap.add_argument("-m", "--model", required=True,
		help="path to Caffe pre-trained model")
	ap.add_argument("-c", "--confidence", type=float, default=0.2,
		help="minimum probability to filter weak detections")
	args = vars(ap.parse_args())



# ModelNet SSD Object list init
CLASSES = ["arriere-plan", "avion", "velo", "oiseau", "bateau",
	"bouteille", "autobus", "voiture", "chat", "chaise", "vache", "table",
	"chien", "cheval", "moto", "personne", "plante en pot", "mouton",
	"sofa", "train", "moniteur"]
COLORS = np.random.uniform(0, 255, size=(len(CLASSES), 3))

# Load model file
print("Load Neural Network...")
net = cv2.dnn.readNetFromCaffe(args["prototxt"], args["model"])

if __name__ == '__main__':

	# Camera initialisation
	print("Start Camera...")
	vs = VideoStream(src=0, resolution=(1600, 1200)).start()
	#vs = VideoStream(usePiCamera=True, resolution=(1600, 1200)).start()
	#vc = cv2.VideoCapture('./img/Splash - 23011.mp4') #from video

	time.sleep(2.0)
	fps = FPS().start()
	
	#Main loop
	while True:
		# Get video sttream. max width 800 pixels 
		frame = vs.read()
		#frame= cv2.imread('./img/two-boats.jpg') #from image file
		#ret, frame=vc.read() #from video or ip cam
		frame = imutils.resize(frame, width=800)

		# Create blob from image
		(h, w) = frame.shape[:2]
		blob = cv2.dnn.blobFromImage(cv2.resize(frame, (300, 300)), 0.007843, (300, 300), 127.5)

		# Feed input to neural network 
		net.setInput(blob)
		detections = net.forward()

		# Detection loop
		for i in np.arange(0, detections.shape[2]):
			# Compute Object detection probability
			confidence = detections[0, 0, i, 2]
			
			# Suppress low probability
			if confidence &gt; args["confidence"]:
				# Get index and position of detected object
				idx = int(detections[0, 0, i, 1])
				box = detections[0, 0, i, 3:7] * np.array([w, h, w, h])
				(startX, startY, endX, endY) = box.astype("int")

				# Create box and label
				label = "{}: {:.2f}%".format(CLASSES[idx],
					confidence * 100)
				cv2.rectangle(frame, (startX, startY), (endX, endY),
					COLORS[idx], 2)
				y = startY - 15 if startY - 15 &gt; 15 else startY + 15
				cv2.putText(frame, label, (startX, y),
					cv2.FONT_HERSHEY_SIMPLEX, 0.5, COLORS[idx], 2)
					
				# enregistrement de l'image détectée 
				cv2.imwrite("detection.png", frame)
				
				
		# Show video frame
		cv2.imshow("Frame", frame)
		key = cv2.waitKey(1) &amp; 0xFF

		# Exit script with letter q
		if key == ord("q"):
			break

		# FPS update 
		fps.update()

	# Stops fps and display info
	fps.stop()
	print("[INFO] elapsed time: {:.2f}".format(fps.elapsed()))
	print("[INFO] approx. FPS: {:.2f}".format(fps.fps()))

	cv2.destroyAllWindows()
	vs.stop()
	vc.release()

Fontes de imagem para deteção de objectos

Pode utilizar este script com diferentes fontes de imagem. Para tal, é necessário adaptar ligeiramente o código anterior para modificar a variável “frame” que contém a imagem a analisar.

  • A câmara Web do seu computador
vs = VideoStream(src=0, resolution=(1600, 1200)).start()
while True:
	frame = vs.read()
vc = cv2.VideoCapture('rtsp://user:password@ipaddress:rtspPort')
while True:
	ret, frame=vc.read() #from ip cam
  • O Raspberry Pi Picam
vs = VideoStream(usePiCamera=True, resolution=(1600, 1200)).start()
while True:
	frame = vs.read()
  •  Um ficheiro de vídeo
vc = cv2.VideoCapture('./img/Splash - 23011.mp4') #from video
while True:
	ret, frame=vc.read() #from video
  •  Um ficheiro de imagem
frame= cv2.imread('./img/two-boats.jpg') 

Resultados

Para este exemplo, enviamos uma imagem de dois barcos como entrada para a rede neural, que são corretamente reconhecidos. Para obter resultados ligeiramente diferentes, pode modificar o parâmetro de confiança para evitar falsos positivos.

Pode testar este código com a sua webcam ou com fotografias, por exemplo, para ver o desempenho do modelo e do reconhecimento de objectos.

Pacotes e modelos

Neste tutorial, utilizámos o modelo ModelNet-SSD pré-treinado. Vale a pena notar que existem outros modelos de reconhecimento, como o Coco, e outras bibliotecas de reconhecimento visual, como a ImageIA.

Não hesite em deixar-nos um comentário para partilhar as ferramentas que utiliza ou de que tem conhecimento.

Fontes