Skip to content

Commit

Permalink
Merge pull request #3 from pge23-24/main
Browse files Browse the repository at this point in the history
Merge Vis with main
  • Loading branch information
Arthuino authored Jan 23, 2024
2 parents 608e04c + b6f8ae6 commit 51478a6
Show file tree
Hide file tree
Showing 104 changed files with 4,290 additions and 0 deletions.
13 changes: 13 additions & 0 deletions .github/workflows/test.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
name: run unittests
on: ["push"]
jobs:
test:
runs-on: "ubuntu-latest"
steps:
- uses: actions/checkout@v4
- uses: actions/setup-python@v4
with:
python-version: 3.11
- name: Install dependencies
run: pip install -r prototyping/setup/requirements.txt
- run: python -m unittest discover -v -s prototyping/test
71 changes: 71 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
# Prerequisites
*.d

# Compiled Object files
*.slo
*.lo
*.o
*.obj

# Precompiled Headers
*.gch
*.pch

# Compiled Dynamic libraries
*.so
*.dylib
*.dll

# Fortran module files
*.mod
*.smod

# Compiled Static libraries
*.lai
*.la
*.a
*.lib

# Executables
*.exe
*.out
*.app

# Virtual environment
.venv

# Models
*.ckpt
*.pth
*.pt

# Pycache
*.pyc

# Log folder
*log*

# COCO dataset
COCO_2017/
COCO2017/

# Surround dataset
*/DATA*

# ZIP fodlers
*.zip

# USE CASES
*USE_CASE*

# Vscode cache
*.vscode

# Irrevelant assets
localization
bird_view

# Mac folders
.DS_Store
*/.DS_Store
*DS_Store
51 changes: 51 additions & 0 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -8,3 +8,54 @@ repos:
language: python
files: \.(h\+\+|h|hh|hxx|hpp|cuh|c|cc|cpp|cu|c\+\+|cxx|tpp|txx)$
entry: cpplint

- repo: https://github.com/PyCQA/isort
rev: 5.12.0
hooks:
- id: isort
args:
- --filter-files

- repo: https://github.com/astral-sh/ruff-pre-commit
rev: v0.1.1
hooks:
- id: ruff
args:
- --fix
- --exit-non-zero-on-fix

- repo: https://github.com/cheshirekow/cmake-format-precommit
rev: v0.6.13
hooks:
- id: cmake-format

- repo: https://github.com/pre-commit/mirrors-clang-format
rev: v17.0.3
hooks:
- id: clang-format
args:
- --style=Google

- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.5.0
hooks:
- id: check-added-large-files
- id: check-ast
- id: check-executables-have-shebangs
- id: check-json
- id: check-merge-conflict
- id: check-symlinks
- id: check-toml
- id: check-yaml
- id: debug-statements
- id: destroyed-symlinks
- id: detect-private-key
- id: end-of-file-fixer
- id: fix-byte-order-marker
- id: mixed-line-ending
- id: trailing-whitespace

- repo: https://github.com/psf/black
rev: 23.10.0
hooks:
- id: black
18 changes: 18 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -74,3 +74,21 @@ Cpplint est executé automatiquement avant chaque commit. Si des erreurs sont d
- **Google Test** : framework de test unitaire pour c++
Les tests unitaires seront tous executé avant de merge une pull request sur le repo principal. Le taux de couverture de ces tests sera vérifié.
La compilation sera également vérifiée à ce moment là.

## Prototypage Python

###  INSTALLATION DE L'ENVIRONNEMENT VIRTUEL

Pour installer l'environnement virtuel nécessaire au projet, exécutez la commande suivante dans le dossier `prototyping` du dossier du projet :

```bash
bash ./setup/venv_install.sh
```

Afin de désinstaller la venv, la procédure est identique mais le script à lancer est `venv_uninstall.sh`, toujours dans le dossier `prototyping`.

```bash
bash ./setup/venv_uninstall.sh
```

Le but actuel de cette venv n'est pas de faire tourner le workspace ros, mais de pouvoir avoir un environnement commun aux prototypages.
8 changes: 8 additions & 0 deletions prototyping/setup/requirements.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
ultralytics
opencv-python
pillow
pywavefront
transformers
accelerate
numpy
natsort
31 changes: 31 additions & 0 deletions prototyping/setup/venv_install.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
#!/bin/bash

# Define the name of the virtual environment directory
VENV_DIR=".venv"

# Check if the virtual environment directory exists
if [ -d "$VENV_DIR" ]; then
echo "Virtual environment already exists"
else
# Create the virtual environment
python3 -m venv $VENV_DIR
echo "Virtual environment created"
fi

# Activate the virtual environment
source $VENV_DIR/bin/activate

# Upgrade pip
pip install --upgrade pip

# Check if requirements.txt exists
if [ -f "setup/requirements.txt" ]; then
# Install requirements
pip install -r setup/requirements.txt
echo "Requirements installed"
else
echo "requirements.txt not found"
fi

# Deactivate the virtual environment
deactivate
34 changes: 34 additions & 0 deletions prototyping/setup/venv_uninstall.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
#!/bin/bash


# Define the name of the virtual environment directory
VENV_DIR=".venv"

# Function to ask for confirmation
confirm_deletion() {
read -p "Are you sure you want to delete the virtual environment? (y/n): " -n 1 -r
echo # Move to a new line
if [[ $REPLY =~ ^[Yy]$ ]]; then
# Confirmation received, proceed with deletion
return 0
else
# Confirmation not received, do not delete
return 1
fi
}

# Check if the virtual environment directory exists
if [ -d "$VENV_DIR" ]; then
echo "Virtual environment directory detected."

# Ask for confirmation
if confirm_deletion; then
# Remove the virtual environment directory
rm -rf $VENV_DIR
echo "Virtual environment deleted."
else
echo "Deletion cancelled."
fi
else
echo "Virtual environment does not exist."
fi
Empty file added prototyping/src/__init__.py
Empty file.
130 changes: 130 additions & 0 deletions prototyping/src/bird_view.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,130 @@
import cv2
import numpy as np


def read_images(image_paths):
"""Read images from the given paths."""
return [cv2.imread(path) for path in image_paths]


def find_keypoints_and_descriptors(images):
"""Find keypoints and descriptors in all images."""
orb = cv2.ORB_create()
keypoints, descriptors = [], []
for image in images:
kp, desc = orb.detectAndCompute(image, None)
keypoints.append(kp)
descriptors.append(desc)
return keypoints, descriptors


def match_keypoints(descriptors):
"""Match keypoints between all image pairs."""
bf = cv2.BFMatcher(cv2.NORM_HAMMING, crossCheck=True)
matches = []
for i in range(len(descriptors) - 1):
matches.append(bf.match(descriptors[i], descriptors[i + 1]))
return matches


def stitch_images(images, keypoints, matches):
"""Stitch images together using the matches."""
# Start with the first image
result = images[0]
result_kp = keypoints[0]

for i in range(1, len(images)):
# Retrieve keypoints, descriptors, and matches
kp1, kp2 = result_kp, keypoints[i]
good_matches = matches[i - 1]

# Extract location of good matches
points1 = np.zeros((len(good_matches), 2), dtype=np.float32)
points2 = np.zeros((len(good_matches), 2), dtype=np.float32)

for j, match in enumerate(good_matches):
points1[j, :] = kp1[match.queryIdx].pt
points2[j, :] = kp2[match.trainIdx].pt

# Find homography
H, _ = cv2.findHomography(points1, points2, cv2.RANSAC)

# Warp image
height, width = images[0].shape[:2]
result = cv2.warpPerspective(result, H, (width, height))

# Stitch the image with the result
result = cv2.addWeighted(result, 0.5, images[i], 0.5, 0)

# Update keypoints for the next iteration
result_kp = kp2

return result


def transform_to_birds_eye_view(image, src_points, dest_size=(300, 300)):
"""Transform the stitched image to a bird's eye view.
Args:
- image: The input stitched image.
- src_points: Four source points in the image defining the area to transform.
- dest_size: Size of the output bird's eye view image.
Returns:
- Bird's eye view of the selected portion of the input image.
"""
# Destination points are the corners of a rectangle with the given size
dst_points = np.array([
[0, 0],
[dest_size[0] - 1, 0],
[dest_size[0] - 1, dest_size[1] - 1],
[0, dest_size[1] - 1]
], dtype=np.float32)

# Compute the perspective transform matrix and apply it
M = cv2.getPerspectiveTransform(src_points, dst_points)
birds_eye_view = cv2.warpPerspective(image, M, dest_size)

return birds_eye_view


def visualize_src_points(image, src_points):
for point in src_points:
int_point = (int(point[0]), int(point[1])) # Convert to integer
cv2.circle(image, int_point, 5, (0, 0, 255), -1) # Red circles
cv2.imshow("Source Points on Panorama", image)
cv2.waitKey(0)
cv2.destroyAllWindows()


def visualize_matches(img1, kp1, img2, kp2, matches):
"""Visualize matches between two images."""
match_img = cv2.drawMatches(
img1, kp1, img2, kp2, matches[:50], None, flags=cv2.DrawMatchesFlags_NOT_DRAW_SINGLE_POINTS
)
cv2.imshow('Matches', match_img)
cv2.waitKey(0)
cv2.destroyAllWindows()


# Example usage
image_paths = ['assets/bird_view/front.png', 'assets/bird_view/left.png',
'assets/bird_view/rear.png', 'assets/bird_view/right.png']
images = read_images(image_paths)
keypoints, descriptors = find_keypoints_and_descriptors(images)
matches = match_keypoints(descriptors)
panorama = stitch_images(images, keypoints, matches)


# Define source points (these should be adjusted based on your specific image)
src_points = np.float32([[100, 100], [400, 100], [400, 400], [100, 400]])

# Visualize src_points on the panorama
visualize_src_points(panorama.copy(), src_points)

# Generate the bird's eye view
birds_eye_view = transform_to_birds_eye_view(panorama, src_points)

cv2.imshow("Bird's Eye View", birds_eye_view)
cv2.waitKey(0)
cv2.destroyAllWindows()
Empty file.
Empty file.
23 changes: 23 additions & 0 deletions prototyping/src/communication/network/receiver.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import socket


class Receiver:
def __init__(self, host="127.0.0.1", port=65432):
self.host = host
self.port = port
self.last_received_data = None # New attribute to store the last received data

def start_server(self):
with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
s.bind((self.host, self.port))
s.listen()
print(f"Server started. Listening on {self.host}:{self.port}")
conn, addr = s.accept()
with conn:
print(f"Connected by {addr}")
while True:
data = conn.recv(1024)
if not data:
break
self.last_received_data = data.decode() # Store the received data
print(f"Received data: {self.last_received_data}")
Loading

0 comments on commit 51478a6

Please sign in to comment.