Obsah:
2025 Autor: John Day | [email protected]. Naposledy změněno: 2025-01-23 14:38
V tomto pokynu vám ukážu, jak jsem napsal automatický generátor 3D planetária pomocí Pythonu a Electronu
Video výše ukazuje jedno z náhodných planetárií, které program vygeneroval.
** Poznámka: Tento program není nijak dokonalý a na některých místech ani příliš pythonický. Diskriminátor neurální sítě je přesný pouze ~ 89%, takže některé podivné obrázky se dostanou do planetária **
Specifika
Planetárium vyhledává v NASA API snímky související s vesmírem a využívá konvoluční neuronovou síť k určení, zda je snímek vhodný ke zpracování. Program poté pomocí OpenCV odstraní pozadí z obrázku a nakonec jsou obrázky spojeny dohromady v jeden velký ekvirektangulární obrázek. Tento obrázek se poté uloží a aplikace Electron Node.js obrázek otevře a pomocí balíčku PhotoSphere.js si obrázek prohlédne ve formátu 3D ve stylu planetária.
Závislosti
Krajta:
- Keras
- Polštář
- cv2
- Numpy
- Žádosti
- urllib
- Náhodný
- čas
- io
Elektron:
Fotosféra
Krok 1: Nastavení prostředí
Instalace Electronu a Pythonu
Nejprve se ujistěte, že máte nainstalované node.js a npm (pokud ne, můžete si je stáhnout zde)
Dále musíte nainstalovat Electron. Otevřete příkazový řádek a zadejte následující příkaz:
npm nainstalovat elektron -g
Dále potřebujete python, který lze stáhnout zde
Nastavení virtuálního prostředí
Otevřete příkazový řádek a poté zadejte následující příkazy k nastavení virtuálního prostředí:
pip install virtualenv
virtuální prostor
cd prostor
skripty / aktivovat
Instalace závislostí Pythonu
Spuštěním těchto příkazů na příkazovém řádku nainstalujete závislosti pythonu:
pip install keras
pip install polštář
pip install numpy
požadavky na instalaci pipu
pip install opencv-pythonPokud chcete síť trénovat sami, nezapomeňte nastavit pro GPRS akceleraci GPU
Krok 2: Dotaz na API pro vyhledávání NASA
Přehled
NASA má spoustu opravdu užitečných API, která můžete použít se svými projekty. Pro tento projekt použijeme vyhledávací API, které nám umožňuje prohledávat snímky související s vesmírem v databázi obrázků NASA.
Kód
Nejprve musíme definovat funkci pythonu, aby přijala argument, který bude fungovat jako hledaný výraz:
def get_image_search (fráze):
složit
Dále zkonvertujeme hledaný výraz do formátu URL a poté použijeme knihovnu požadavků k dotazování na API:
def get_image_search (fráze):
params = {"q": urllib.parse.quote (arg), "media_type": "image"} results = requests.get ("https://images-api.nasa.gov/search", params = params)
Nakonec dekódujeme řetězec kolekce+JSON, který nám API vrátilo, a extrahujeme seznam odkazů na obrázky související s hledaným výrazem:
def get_image_search (fráze):
params = {"q": urllib.parse.quote (arg), "media_type": "image"} results = requests.get ("https://images-api.nasa.gov/search", params = params) data = [result ['href'] pro výsledek ve results.json () ["collection"] ["items"]
Tam jedeme! Nyní máme úryvek kódu, který lze dotazovat na API pro vyhledávání obrázků NASA a vrátit seznam odkazů na obrázky související s naším hledaným výrazem.
Krok 3: Konvoluční neuronová síť
Přehled
Úkolem neuronové sítě je klasifikovat, zda obraz je něčím ve vesmíru, nebo zda není. K tomu použijeme konvoluční neuronovou síť nebo CNN k provedení řady maticových operací s obrazem a určení, jak velký je prostor-y. Nebudu to všechno vysvětlovat, protože je za tím spousta teorie, ale pokud se chcete dozvědět něco o neurálních sítích, navrhuji „Machine Learning Mastery“
Kód
Nejprve musíme importovat naše závislosti:
import os
#Opravit problém během vlaku při nástupu na GPU os.environ ['CUDA_VISIBLE_DEVICES'] = '' importovat tensorflow jako tf if tf.test.gpu_device_name (): print ('GPU found') else: print ("No GPU found") z keras.preprocessing.image import ImageDataGenerator z keras.preprocessing import image from keras.models import Sequential from keras.layers import Conv2D, MaxPooling2D from keras.layers import Activation, Dropout, Flatten, Dense from keras import backend as K from PIL import Image import numpy jako np
Dále musíme definovat náš model:
img_width, img_height = 1000, 500
train_data_dir = 'v_data/train' validation_data_dir = 'v_data/test' nb_train_samples = 203 nb_validation_samples = 203 epochs = 10 batch_size = 8 if K.image_data_format () == 'channels_first': input_shape = (img_width, img_height, 3) model = Sequential () model.add (Conv2D (32, (2, 2), input_shape = input_shape)) model.add (Activation ('relu')) model.add (MaxPooling2D (pool_size) = (2, 2))) model.add (Conv2D (32, (2, 2))) model.add (Aktivace ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) model.add (Conv2D (64, (2, 2))) model.add (Activation ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) model.add (Flatten ()) model. add (Dense (64)) model.add (Activation ('relu')) model.add (Dropout (0.5)) model.add (Dense (1)) model.add (Activation ('sigmoid')) model.compile (loss = 'binary_crossentropy', optimizer = 'rmsprop', metrics = ['přesnost'])
Vycvičil jsem pro vás model, ale pokud byste chtěli trénovat model sami, na vlastní datové sadě, pak jsem připojil tréninkový kód. V opačném případě si můžete stáhnout soubor HDF5 natrénovaného modelu. Kvůli omezením souboru Instructables jsem jej musel přejmenovat pomocí přípony „.txt“. Chcete -li jej použít, přejmenujte soubor na příponu „.h5“a načtěte jej pomocí tohoto kódu:
model.load_weights ("model_saved.h5")
Abychom pomocí sítě mohli předpovědět, jak velký je obrázek, definujeme tuto funkci:
def předpovědět (image_path):
img = image.load_img (cesta_obrazu, cílová_ velikost = (1000, 500)) img = np.expand_dims (img, axis = 0) result = model.predict_classes (img) návratový výsledek [0] [0]
Krok 4: Zpracování obrázku
Přehled
Pro zpracování obrazu používám knihovnu OpenCV (cv2). Nejprve rozostříme okraje obrázku a poté odstraníme pozadí vytvořením masky a změnou hodnot alfa tmavších barev.
Kód
Toto je část funkce, která rozmazává okraje:
def processImage (img):
RADIUS = 20 # Otevřít obrázek im = Image.open ("pilbuffer.png") # Vložit obrázek na bílém pozadí diam = 2 * RADIUS zpět = Image.new ('RGB', (im.size [0] + diam, im.size [1] + diam), (0, 0, 0)) back.paste (im, (RADIUS, RADIUS)) # Create mask blur mask mask = Image.new ('L', (im.size [0] + diam, im.size [1] + diam), 255) blck = Image.new ('L', (im.size [0] - diam, im.size [1] - diam), 0) maska. paste (blck, (diam, diam)) # Rozostření obrázku a vložení rozmazaného okraje podle masky blur = back.filter (ImageFilter. GaussianBlur (RADIUS / 2)) back.paste (blur, mask = mask) back.save (" transition-p.webp
Dále nastavíme tmavší barvy na průhledné a dočasně uložíme obrázek:
#Vytvořit masku a filtr nahradit černé alfa
image = cv2.imread ("transition.png") hMin = 0 sMin = 0 vMin = 20 hMax = 180 sMax = 255 vMax = 255 nižší = np.array ([hMin, sMin, vMin]) horní = np.array ([hMax, sMax, vMax]) hsv = cv2.cvtColor (obrázek, cv2. COLOR_BGR2HSV) maska = cv2.inRange (hsv, dolní, horní) výstup = cv2.bitwise_and (obrázek, obrázek, maska = maska) *_, alfa = cv2.split (výstup) dst = cv2.merge ((výstup, alfa)) výstup = dst s otevřeným ("buffer.png", "w+") jako soubor: předejte cv2.imwrite ("buffer.png", výstup)
Krok 5: Spojení obrazů dohromady do ekvirektangulární projekce
Přehled
Tato funkce pořídí více obrázků a spojí je do formátu, který lze interpretovat pomocí balíčku PhotoSphere.js pomocí knihovny PIL (polštář)
Kód
Nejprve musíme vytvořit obrázek, který může fungovat jako hostitel pro ostatní obrázky:
new = Image.new ("RGBA", (8000, 4000), color = (0, 0, 0))
Dále musíme iterovat prostřednictvím řady obrázků (u všech bylo změněno rozlišení na 1000 x 500) a umístit je do obrázku:
h = 0
w = 0 i = 0 pro img v img_arr: new.paste (img, (w, h), img) w += 1000 if w == 8000: h += 500 w = 0 i += 1
Nyní to zabalíme do funkce, která jako argument vezme řadu obrázků a vrátí nový obrázek:
def stitch_beta (img_arr):
new = Image.new ("RGBA", (8000, 4000), color = (0, 0, 0)) h = 0 w = 0 i = 0 pro img in img_arr: new.paste (img, (w, h), img) w += 1000 pokud w == 8000: h += 500 w = 0 i += 1 vrátit nový
Krok 6: Úplný skript Pythonu
Toto je úplný skript neuronové sítě python, který je uložen jako net.py a importován do hlavního skriptu:
# import knihoven
import os #Fix for issue during train stepn oN GPU os.environ ['CUDA_VISIBLE_DEVICES'] = '' import tensorflow as tf if tf.test.gpu_device_name (): print ('GPU found') else: print ("No GPU found ") from keras.preprocessing.image import ImageDataGenerator from keras.preprocessing import image from keras.models import Sequential from keras.layers import Conv2D, MaxPooling2D from keras.layers import Activation, Dropout, Flatten, Dense from keras import backend as K from PIL import Image import numpy as np img_width, img_height = 1000, 500 train_data_dir = 'v_data/train' validation_data_dir = 'v_data/test' nb_train_samples = 203 nb_validation_samples = 203 epochs = 10 batch_size == if_image_: input_shape = (3, img_width, img_height) else: input_shape = (img_width, img_height, 3) model = Sequential () model.add (Conv2D (32, (2, 2), input_shape = input_shape)) model.add (Aktivace ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) model.add (Conv2D (32, (2, 2))) model. add (Activation ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) model.add (Conv2D (64, (2, 2))) model.add (Activation ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) model.add (Flatten ()) model.add (Dense (64)) model.add (Activation ('relu')) model.add (Dropout (0,5)) model.add (Hustý (1)) model.add (Aktivace ('sigmoid')) model.compile (ztráta = 'binary_crossentropy', optimizer = 'rmsprop', metrics = ['přesnost']) model.load_weights ("model_saved.h5") def předpovědět (image_path): img = image.load_img (image_path, target_size = (1000, 500)) img = np.expand_dims (img, axis = 0) result = model.predict_classes (img) return result [0] [0]
Toto je hlavní soubor pythonu, api.py:
import požadavků, sys, random, urllib.parse, cv2
z PIL import Image, ImageFilter z io import BytesIO import numpy jako np import net def get_image_search (num, fráze): count = 0 img_arr = pro arg ve frázi: print (arg) print (f "Aktuální počet obrázků: {count } ") i = 0 params = {" q ": urllib.parse.quote (arg)," media_type ":" image "} results = requests.get (" https://images-api.nasa.gov/search ", params = params) data = [result ['href'] pro výsledek in results.json () [" collection "] [" items "] print (len (data)) if num> len (data): num = len (data) při počítání
Krok 7: Aplikace Electron
Přehled
Vytvoříme jednoduchou elektronovou aplikaci, která pouze umístí a načte prvek PhotoSphere. Soubory main.js a package.json jsou přímo z webu Electron a HTML je mírně upravenou verzí HTML, která je k dispozici na webu PhotoSphere. Zahrnul jsem soubory, ale přejmenoval vše na.txt, protože Instructables tyto typy souborů nepovoluje. Chcete -li soubory použít, přejmenujte je s příslušnou příponou.
Kód
main.js
const {aplikace, BrowserWindow} = vyžadovat ('elektron')
funkce createWindow () {const win = new BrowserWindow ({šířka: 800, výška: 600, webPreferences: {nodeIntegration: true}}) win.loadFile ('index.html')} app.whenReady (). then (createWindow) app.on ('window-all-closed', () => {if (process.platform! == 'darwin') {app.quit ()}}) app.on ('activate', () => {if (BrowserWindow.getAllWindows (). length === 0) {createWindow ()}})
balíček.json
{
"name": "space", "version": "0.1.0", "main": "main.js", "scripts": {"start": "elektron." }}
index.html
Krok 8: Provedení
Vytvoření ekvirektangulárního obrázku
Chcete -li vytvořit bitovou kopii, spusťte na příkazovém řádku skript api.py s aktivovaným virtuálním prostředím:
api.py
Po dokončení spouštění skriptů spusťte elektronovou aplikaci pomocí:
npm startVoila! Vaše planetárium je aktivní! Děkuji za přečtení:)
Doporučuje:
Elektrické autíčko poháněné RC: 10 kroků (s obrázky)
Elektrické autíčko poháněné RC: Autor: Peter Tran 10ELT1 Tento tutoriál podrobně popisuje teorii, design, výrobu a proces testování elektrického autíčka na dálkové ovládání (RC) využívající IC čipy HT12E/D. Návody podrobně popisují tři fáze návrhu vozu: Infračervený kabel s tethered
Solární poháněné srdce Blinky LED přívěsek šperky: 11 kroků (s obrázky)
Solární poháněné srdce Blinky LED přívěskové šperky: Tento návod je určen pro srdce napájené solární energií s pulzující červenou LED. Měří asi 2 " o 1,25 " včetně záložky USB. Má jeden otvor v horní části desky, takže je zavěšení snadné. Noste jej jako náhrdelník, náušnice, poutko na špendlík
Zalévání chytrých rostlin poháněné solárním panelem: 7 kroků
Zalévání chytrých rostlin poháněné solárním panelem: Toto je aktualizovaná verze mého prvního projektu SmartPlantWatering (https://www.instructables.com/id/Smart-Plant-Water … Hlavní rozdíly oproti předchozí verzi: 1. Připojuje se na ThingSpeaks.com a používá tento web k publikování zachycených dat (teplota
Bezdrátové duhové světlo poháněné Tesla Coil: 6 kroků
Bezdrátové duhové světlo poháněné Tesla cívkou: Zde je projekt, který využívá energii vysokofrekvenční energie generované malou bipolární Tesla cívkou k napájení kruhu vícebarevných studených katodových lamp. Stejně jako u všech vysokonapěťových zařízení postupujte při provozu opatrně a s dobrým úsudkem
Automatické pneumatické dělo. Přenosné a poháněné Arduino .: 13 kroků
Automatické pneumatické dělo. Portable and Arduino Powered .: Ahoj všichni! Toto je návod na sestavení přenosného pneumatického děla. Cílem bylo vytvořit dělo, které může střílet různé věci. Stanovil jsem si několik hlavních cílů. Jaké by tedy mělo být moje dělo: Automatické. Aby nedošlo ke stlačení vzduchu ručně pomocí