[PYTHON] Logiciel mis à jour pour Rubik Cube Robot 4. Reconnaissance de statut

Quel est cet article?

Je développe actuellement un robot qui résout un cube rubic 2x2x2. Ceci est une collection d'articles de commentaires sur le programme du robot. soltvvo3.jpg J'ai écrit une fois une collection d'articles représentés par l'article ici, mais depuis cette fois, le logiciel a été considérablement mis à jour, je vais donc introduire un nouveau programme. pense.

Le code applicable est disponible ici [https://github.com/Nyanyan/soltvvo/tree/master/Soltvvo3.2).

Articles Liés

"Faisons un robot qui résout le Rubik Cube!"

  1. Présentation
  2. Algorithme
  3. Logiciel
  4. Matériel

Logiciel mis à jour pour Rubik Cube Robot

  1. Fonction de base
  2. Pré-calcul
  3. Recherche de solutions
  4. Reconnaissance de l'État (cet article)
  5. Fonctionnement de la machine (Python)
  6. Fonctionnement de la machine (Arduino)
  7. Traitement principal

Cette fois, nous allons introduire detector.py '' comme édition de reconnaissance d'état.

Importer les modules à utiliser

Importez le module que vous souhaitez utiliser.

import cv2
from time import sleep

from basic_functions import *
from controller import move_actuator

Ici, contrôleur '' est le programme qui sera expliqué la prochaine fois, mais la fonction move_actuator '' dans cette fonction est une fonction qui envoie des commandes pour déplacer l'actionneur (ici, le moteur) comme son nom l'indique.

Créez 6 côtés d'informations sur 4 côtés du puzzle

Avec le Rubik Cube 2x2x2, vous pouvez deviner la couleur de toute la surface simplement en regardant les couleurs sur les quatre côtés. Pour tirer parti de cette propriété, nous avons besoin d'une fonction qui déduit la couleur non remplie à partir des informations de couleur remplies. Je vais vous présenter la fonction.

Je vous prie de m'excuser d'abord. Cette fonction a été créée à l'origine avec un élan à l'ère de la saisie manuelle des couleurs (il y a quelques mois), et je ne sais pas vraiment ce que je fais maintenant! Et maintenant, cela n'a pas besoin d'être une fonction aussi polyvalente, car vous pouvez deviner les couleurs des deux côtés restants en regardant les couleurs de quatre côtés particuliers. En d'autres termes, les fonctions présentées ici sont des ** fonctions un peu redondantes et je ne suis pas sûr de ce qu'elles font, mais elles fonctionnent **. Pardon. Faites attention à vous, "ajoutez au moins un commentaire".

En passant, j'écris cet article pour moi-même dans le futur. Pour ne pas être incapable de lire ce code à l'avenir, j'ai écrit un commentaire maintenant et laissé un article de commentaire.

'''Remplissez l'endroit où la couleur est fixée là où elle n'est pas remplie'''
''' Fill boxes if the color can be decided '''
def fill(colors):
    for i in range(6):
        for j in range(8):
            if (1 < i < 4 or 1 < j < 4) and colors[i][j] == '':
                done = False
                for k in range(8):
                    if [i, j] in parts_place[k]:
                        for strt in range(3):
                            if parts_place[k][strt] == [i, j]:
                                idx = [colors[parts_place[k][l % 3][0]][parts_place[k][l % 3][1]] for l in range(strt + 1, strt + 3)]
                                for strt2 in range(3):
                                    idx1 = strt2
                                    idx2 = (strt2 + 1) % 3
                                    idx3 = (strt2 + 2) % 3
                                    for l in range(8):
                                        if parts_color[l][idx1] == idx[0] and parts_color[l][idx2] == idx[1]:
                                            colors[i][j] = parts_color[l][idx3]
                                            done = True
                                            break
                                    if done:
                                        break
                                break
                    if done:
                        break
    return colors

Je vais vous expliquer en devinant.

L'instruction `` for```, qui transforme les deux premiers `ʻi, j```, regarde simplement le tableau de couleurs suivant, une à la fois.

colors = [
    ['', '', 'w', 'o', '', '', '', ''],
    ['', '', 'w', 'g', '', '', '', ''],
    ['b', 'o', 'g', 'y', 'r', 'w', 'b', 'r'],
    ['o', 'o', 'g', 'g', 'w', 'r', 'b', 'b'],
    ['', '', 'y', 'r', '', '', '', ''],
    ['', '', 'y', 'y', '', '', '', '']
    ]

w, y, g, b, o, r '' '' représentent respectivement le blanc, le jaune, le vert, le bleu, l'orange et le rouge. Il convient de noter que la manière de tenir cet arrangement est un gaspillage car elle hérite de la tradition des programmes réalisés dans le passé dans une mauvaise direction. Je veux y remédier un jour.

```If (1 <i <4 ou 1 <j <4) et couleurs [i] [j] == '': `` `où les informations de couleur sont initialement incluses ou non Je vais le diviser.

for k in range(8):Transformez toutes les pièces candidates possibles, si[i, j] in parts_place[k]:Si les deux couleurs correspondent à, pour strt dans la plage(3):Vérifiez les trois directions des pièces avec.



 Je pense que le traitement se fait de cette façon.

# Reconnaissance d'état à l'aide d'une caméra
 Utilisez l'appareil photo pour reconnaître l'état du puzzle. Cette fois, nous utilisons une bibliothèque appelée OpenCV pour reconnaître les couleurs.

```python
'''Obtenez l'état du puzzle'''
''' Get colors of stickers '''
def detector():
    colors = [['' for _ in range(8)] for _ in range(6)]
    #Prenez le puzzle
    for i in range(2):
        move_actuator(i, 0, 1000)
    for i in range(2):
        move_actuator(i, 1, 2000)
    sleep(0.3)
    rpm = 200
    capture = cv2.VideoCapture(0)
    #Chaque couleur(HSV)Gamme de
    #color: g, b, r, o, y, w
    color_low = [[40, 50, 50],   [90, 50, 70],    [160, 50, 50],   [170, 50, 50],    [20, 50, 30],   [0, 0, 50]]
    color_hgh = [[90, 255, 255], [140, 255, 200], [170, 255, 255], [10, 255, 255], [40, 255, 255], [179, 50, 255]]
    #Position de chaque pièce sur le tableau des couleurs
    surfacenum = [[[4, 2], [4, 3], [5, 2], [5, 3]], [[2, 2], [2, 3], [3, 2], [3, 3]], [[0, 2], [0, 3], [1, 2], [1, 3]], [[3, 7], [3, 6], [2, 7], [2, 6]]]
    #Autres constantes
    d = 10
    size_x = 130
    size_y = 100
    center = [size_x // 2, size_y // 2]
    dx = [-1, -1, 1, 1]
    dy = [-1, 1, -1, 1]
    #Chargez les quatre côtés du puzzle
    for idx in range(4):
        #Comme il y a des moments où la lecture ne se passe pas bien, laissez le mannequin lire 5 fois
        for _ in range(5):
            ret, frame = capture.read()
        tmp_colors = [['' for _ in range(8)] for _ in range(6)]
        loopflag = [1 for _ in range(4)]
        #Tandis que jusqu'à ce que toutes les couleurs des quatre autocollants d'un côté soient chargées
        while sum(loopflag):
            ret, show_frame = capture.read()
            show_frame = cv2.resize(show_frame, (size_x, size_y))
            hsv = cv2.cvtColor(show_frame,cv2.COLOR_BGR2HSV)
            #Examinez les quatre autocollants dans l'ordre
            for i in range(4):
                y = center[0] + dy[i] * d
                x = center[1] + dx[i] * d
                val = hsv[x, y]
                #Découvrez laquelle des 6 couleurs
                for j in range(6):
                    flag = True
                    for k in range(3):
                        if not ((color_low[j][k] < color_hgh[j][k] and color_low[j][k] <= val[k] <= color_hgh[j][k]) or (color_low[j][k] > color_hgh[j][k] and (color_low[j][k] <= val[k] or val[k] <= color_hgh[j][k]))):
                            flag = False
                    if flag:
                        tmp_colors[surfacenum[idx][i][0]][surfacenum[idx][i][1]] = j2color[j]
                        loopflag[i] = 0
                        break
        #Stocker les valeurs dans un tableau de couleurs
        for i in range(4):
            colors[surfacenum[idx][i][0]][surfacenum[idx][i][1]] = tmp_colors[surfacenum[idx][i][0]][surfacenum[idx][i][1]]
        #Tournez le moteur pour voir le côté suivant
        move_actuator(0, 0, -90, rpm)
        move_actuator(1, 0, 90, rpm)
        sleep(0.2)
    capture.release()
    colors = fill(colors)
    return colors

Le problème ici est que la gamme de couleurs est décisive. Cela peut entraîner une mauvaise reconnaissance des couleurs en raison de perturbations. En fait, cela n'a pas bien fonctionné sur le site de Maker Faire Tokyo 2020 en raison de l'environnement lumineux (j'ai fait une légère correction de la valeur et j'ai survécu).

Résumé

Cette fois, j'ai introduit la partie qui reconnaît l'état avec la caméra et restaure la surface qu'on ne voit pas. La prochaine fois, je déplacerai le robot.

Recommended Posts

Logiciel mis à jour pour Rubik Cube Robot 4. Reconnaissance de statut
Logiciel mis à jour pour Rubik Cube Robot 7. Opérations clés
Logiciel mis à jour pour Rubik Cube Robot 2. Pré-calcul
Logiciel mis à jour pour Rubik Cube Robot 3. Recherche de solutions
Logiciel mis à jour pour Rubik Cube Robot 1. Fonctions de base
Logiciel mis à jour pour Rubik Cube Robot 6. Fonctionnement de la machine (Arduino)
Logiciel mis à jour pour Rubik Cube Robot 5. Machine Operation (Python)
Faisons un robot qui résout le Rubik Cube! 3 Logiciel
Faisons un robot qui résout le Rubik Cube! 2 Algorithme
Faisons un robot qui résout le Rubik Cube! 1. Vue d'ensemble