תוכן עניינים:
2025 מְחַבֵּר: John Day | [email protected]. שונה לאחרונה: 2025-01-23 14:46
במדריך זה, אראה לך כיצד כתבתי מחולל פלנטריום תלת מימדי אוטומטי, באמצעות פייתון ואלקטרון
הסרטון למעלה מציג את אחד הפלנטריומים האקראיים שהתוכנית יצרה.
** הערה: התוכנית הזו בשום אופן לא מושלמת ובמקומות מסוימים לא מאוד פיתונית. מפלה הרשת העצבית מדויקת רק ~ 89%, כך שתמונות מוזרות יכנסו לפלנטריום **
פרטים
הפלנטריום מבקש API של NASA לתמונות הקשורות לחלל, ומשתמש ברשת עצבית מתפתלת כדי לקבוע אם התמונה מתאימה לעיבוד. לאחר מכן התוכנית משתמשת ב- OpenCV כדי להסיר את הרקע מהתמונה, ולבסוף התמונות נתפרות יחד לתמונה אחת גדולה -מלבנית. תמונה זו נשמרת ואז יישום Electron Node.js פותח את התמונה ומשתמש בחבילת PhotoSphere.js כדי להציג את התמונה בפורמט תלת מימדי בסגנון פלנטריום.
תלות
פִּיתוֹן:
- קראס
- כרית
- cv2
- מגושם
- בקשות
- urllib
- אַקרַאִי
- זְמַן
- io
אֶלֶקטרוֹן:
PhotoSphere
שלב 1: הגדרת הסביבה שלך
התקנת אלקטרון ופייתון
ראשית, ודא שהתקנת node.js ו- npm (אם לא, תוכל להוריד כאן)
לאחר מכן, עליך להתקין את אלקטרון. פתח שורת פקודה והזן את הפקודה הבאה:
npm התקן אלקטרון -g
לאחר מכן, אתה צריך פייתון, אותו ניתן להוריד כאן
הקמת סביבה וירטואלית
פתח שורת פקודה ולאחר מכן הזן את הפקודות הבאות כדי להגדיר את הסביבה הווירטואלית שלך:
pip להתקין virtualenv
שטח virtualenv
שטח תקליטורים
סקריפטים / הפעל
התקנת תלות ב- Python
הפעל פקודות אלה בשורת הפקודה כדי להתקין את התלות שלך בפייתון:
pip להתקין keras
פיפ להתקין כרית
pip להתקין numpy
בקשות להתקנת pip
pip התקן opencv-pythonאם אתה רוצה לאמן את הרשת בעצמך, הקפד להגדיר האצת GPU עבור Keras
שלב 2: שאילתת ה- API של חיפוש NASA
סקירה כללית
ל- NASA יש הרבה ממשקי API ממש שימושיים שתוכלו להשתמש בהם עם הפרויקטים שלכם. עבור פרויקט זה נשתמש בממשק API לחיפוש, המאפשר לנו לחפש במאגר התמונות של נאס א תמונות הקשורות לחלל.
הקוד
ראשית, עלינו להגדיר פונקציית פייתון כדי לקבל טיעון שישמש כמונח החיפוש:
def get_image_search (ביטוי):
לַעֲבוֹר
לאחר מכן, נמיר את מונח החיפוש לתבנית כתובת אתר, ולאחר מכן נשתמש בספריית הבקשות לשאילתת ה- API:
def get_image_search (ביטוי):
params = {"q": urllib.parse.quote (arg), "media_type": "image"} results = requests.get ("https://images-api.nasa.gov/search", params = params)
לבסוף, נפענח את האוסף+מחרוזת JSON שה- API החזיר לנו, ונחלץ רשימת קישורים לתמונות הקשורות למונח החיפוש:
def get_image_search (ביטוי):
params = {"q": urllib.parse.quote (arg), "media_type": "image"} results = requests.get ("https://images-api.nasa.gov/search", params = params) data = [result ['href'] לתוצאה ב- results.json () ["collection"] ["items"]
הנה! כעת יש לנו קטע קוד שיכול לבדוק את ממשק API של חיפוש תמונות של NASA, ולהחזיר רשימה של קישורים לתמונות הקשורות למונח החיפוש שלנו.
שלב 3: הרשת העצבית המתפתחת
סקירה כללית
תפקידה של הרשת העצבית הוא לסווג אם דימוי הוא של משהו בחלל, או לא. לשם כך נשתמש ברשת עצבית מתפתלת, או CNN, לביצוע שורה של פעולות מטריצה בתמונה, ונקבע עד כמה היא רווח- y. אני לא אסביר את כל זה, כי יש הרבה תיאוריה מאחורי זה, אבל אם אתה רוצה ללמוד על רשתות עצביות, אני מציע "לימוד מכונה שליטה"
הקוד
ראשית, עלינו לייבא את התלות שלנו:
ייבוא מערכת הפעלה
#תיקון לבעיה במהלך שלב רכבת ב- GPU os.environ ['CUDA_VISIBLE_DEVICES'] = '' ייבא tensorflow כ- tf אם tf.test.gpu_device_name (): הדפס ('GPU נמצא') אחר: הדפס ("לא נמצא GPU") מאת keras.preprocessing.image import ImageDataGenerator מאת keras.preprosing image image from keras.models יבוא רצף מ- keras.layers ייבוא Conv2D, MaxPooling2D מ- keras.layers ייבוא הפעלה, נשירה, שיטוח, צפוף מאחזור יבוא של keras כמו K מ- PIL יבוא תמונה ייבא numpy כמו 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 תקופות = 10 batch_size = 8 אם K.image_data_format () == 'channel_first': input_shape = (3, img_ = (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 (הפעלה ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) דגם.add (Conv2D (64, (2, 2))) model.add (Activation ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) model.add (Flatten ()) דגם. הוסף (Dense (64)) model.add (Activation ('relu')) model.add (Dropout (0.5)) model.add (Dense (1)) model.add (Activation ('sigmoid')) model.compile (loss = 'binary_crossentropy', אופטימיזר = 'rmsprop', מדדים = ['דיוק'])
הכשרתי את המודל עבורך, אבל אם תרצה לאמן את המודל בעצמך, על בסיס הנתונים שלך, אז צירפתי את קוד האימון. אחרת, תוכל להוריד את קובץ ה- HDF5 של הדגם המאומן. בשל מגבלות הקבצים של Instructables, נאלצתי לשנות את שמו בתוסף ".txt". כדי להשתמש בו, שנה את שם הקובץ לסיומת ".h5" וטען אותו עם קוד זה:
model.load_weights ("model_saved.h5")
כדי להשתמש ברשת לחיזוי עד כמה התמונה היא רווח y, נגדיר פונקציה זו:
def predict (image_path):
img = image.load_img (image_path, target_size = (1000, 500)) img = np.expand_dims (img, axis = 0) result = model.predict_classes (img) תוצאת החזרה [0] [0]
שלב 4: עיבוד התמונה
סקירה כללית
לעיבוד תמונות, אני משתמש בספריית OpenCV (cv2). ראשית, נטשטש את קצוות התמונה ולאחר מכן נסיר את הרקע על ידי יצירת מסכה ושינוי ערכי האלפא של הצבעים הכהים יותר.
הקוד
זהו החלק של הפונקציה שמטשטש את הקצוות:
def processImage (img):
RADIUS = 20 # פתח תמונה im = Image.open ("pilbuffer.png") # הדבק תמונה על רקע לבן diam = 2 * RADIUS back = Image.new ('RGB', (im.size [0] + diam, im.size [1] + diam), (0, 0, 0)) back.paste (im, (RADIUS, RADIUS)) # צור מסכת טשטוש לטשטוש = 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) מסכה. הדבק (blck, (diam, diam)) # טשטוש תמונה והדבק קצה מטושטש לפי טשטוש מסכה = back.filter (ImageFilter. GaussianBlur (RADIUS / 2)) back.paste (טשטוש, מסכה = מסכה) back.save (" transition-p.webp
לאחר מכן, נגדיר את הצבעים הכהים לשקופים, ונשמור את התמונה באופן זמני:
#צור מסכה וסנן החלף שחור באלפא
image = cv2.imread ("transition.png") hMin = 0 sMin = 0 vMin = 20 hMax = 180 sMax = 255 vMax = 255 lower = np.array ([hMin, sMin, vMin]) upper = np.array ([hMax, sMax, vMax]) hsv = cv2.cvtColor (image, cv2. COLOR_BGR2HSV) mask = cv2.inRange (hsv, תחתון, עליון) פלט = cv2.bitwise_and (תמונה, תמונה, מסכה = מסכה) *_, אלפא = cv2.split (פלט) dst = cv2.merge ((פלט, אלפא)) פלט = dst עם פתוח ("buffer.png", "w+") כקובץ: העבר cv2.imwrite ("buffer.png", פלט)
שלב 5: תפירת תמונות יחדיו להקרנה מלבנית
סקירה כללית
פונקציה זו לוקחת מספר תמונות ותופרת אותן בפורמט שניתן לפרש אותו על ידי חבילת PhotoSphere.js, באמצעות ספריית ה- PIL (כרית)
הקוד
ראשית, עלינו ליצור תמונה שיכולה לשמש כמארח של התמונות האחרות:
new = Image.new ("RGBA", (8000, 4000), color = (0, 0, 0))
לאחר מכן, עלינו לחזור על מערך התמונות (שכולן שונו לגודל 1000x500) ולהציב אותן בתמונה:
h = 0
w = 0 i = 0 עבור img ב- img_arr: new.paste (img, (w, h), img) w += 1000 אם w == 8000: h += 500 w = 0 i += 1
עכשיו אנחנו רק עוטפים את זה בפונקציה שלוקחת מערך של תמונות כטיעון שלה ומחזירה את התמונה החדשה:
def stitch_beta (img_arr):
new = Image.new ("RGBA", (8000, 4000), color = (0, 0, 0)) h = 0 w = 0 i = 0 עבור img ב- img_arr: new.paste (img, (w, h), img) w += 1000 אם w == 8000: h += 500 w = 0 i += החזר אחד חדש
שלב 6: סקריפט Python המלא
זהו סקריפט הרשת העצבית המלאה של פייתון, השמורה כ- net.py, ומיובאת לתסריט הראשי:
# ייבוא ספריות
יבוא OS #תיקון להנפקה במהלך שלב רכבת ב- GPU os.environ ['CUDA_VISIBLE_DEVICES'] = '' ייבא tensorflow כ- tf אם tf.test.gpu_device_name (): הדפס ('GPU נמצא') אחר: הדפס ("לא נמצא GPU ") מאת keras.preprocessing.image ייבוא ImageDataGenerator מ keras.preprosing תמונת יבוא מ keras.models יבוא רצף מ- keras.layers ייבוא Conv2D, MaxPooling2D מ- keras.layers ייבוא הפעלה, נשירה, שטחים, צפוף מאחורי יבוא keras כמו K מ- 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 = 8 if K.imat_data ': 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 (הפעלה ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) model.add (Conv2D (32, (2, 2))) דגם. הוסף (הפעלה ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) model.add (Conv2D (64, (2, 2))) model.add (הפעלה ('relu')) model.add (MaxPooling2D (pool_size = (2, 2))) model.add (Flatten ()) model.add (Dense (64)) model.add (Activation ('relu')) model.add (נשירה (0.5)) model.add (Dense (1)) model.add (Activation ('sigmoid')) model.compile (loss = 'binary_crossentropy', optimizer = 'rmsprop', metrics = ['דיוק']) model.load_weights ("model_saved.h5") def predict (image_path): img = image.load_img (image_path, target_size = (1000, 500)) img = np.expand_dims (img, axis = 0) result = model.predict_classes (img) תוצאה חזרה [0] [0]
זהו קובץ הפיתון הראשי, api.py:
בקשות ייבוא, sys, random, urllib.parse, cv2
מ- PIL image image, ImageFilter מ- io import BytesIO import numpy as np import net def get_image_search (num, phrase): count = 0 img_arr = עבור arg בביטוי: print (arg) print (f "ספירת תמונות נוכחית: {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'] לתוצאה ב- results.json () [" collection "] [" items "] print (len (data)) if num> len (data): num = len (נתונים) בזמן הספירה
שלב 7: אפליקציית האלקטרונים
סקירה כללית
ניצור אפליקציית אלקטרונים פשוטה שממקמת ומטעינה רק את אלמנט ה- PhotoSphere. הקבצים main.js ו- package.json מגיעים ישירות מאתר Electron, ו- HTML הוא גרסה מעט שונה של ה- HTML המסופק באתר PhotoSphere. צירפתי את הקבצים, אך שמתי את כולם ל.txt, מכיוון ש- Instructables אינו מתיר סוגי קבצים אלה. כדי להשתמש בקבצים, שנה את שמו בתוסף המתאים.
הקוד
main.js
const {app, BrowserWindow} = require ('electron')
function createWindow () {const win = new BrowserWindow ({width: 800, height: 600, webPreferences: {nodeIntegration: true}}) win.loadFile ('index.html')} app.whenReady (). לאחר מכן (createWindow) app.on ('window-all-closed', () => {if (process.platform! == 'darwin') {app.quit ()}}) app.on ('activ', () => {if (BrowserWindow.getAllWindows (). length === 0) {createWindow ()}})
package.json
{
"name": "space", "version": "0.1.0", "main": "main.js", "scripts": {"start": "electron". }}
index.html
שלב 8: ביצוע
יצירת התמונה המשווה -מלבנית
כדי ליצור את התמונה, הפעל את הסקריפט api.py בשורת הפקודה, כשהסביבה הווירטואלית שלה מופעלת:
api.py
לאחר סיום ביצוע התסריטים, הפעל את אפליקציית האלקטרונים באמצעות:
npm התחלהוואלה! הפלנטריום שלך פעיל! תודה שקראתם:)
מוּמלָץ:
בנה מכשיר צג אנרגיה באמצעות אלקטרון חלקיקים: 5 שלבים (עם תמונות)
בנה מכשיר לפקח אנרגיה באמצעות אלקטרון חלקיקי: ברוב העסקים אנו רואים באנרגיה הוצאה עסקית. החשבון מופיע בדואר או במיילים שלנו ואנו משלמים אותו לפני תאריך הביטול. עם הופעתם של IoT ומכשירים חכמים, אנרגיה מתחילה לתפוס מקום חדש בעסק
רובוט מצחיק והקטן ביותר (רשת רשת): 7 שלבים
רובוט מצחיק והקטן ביותר (meshmesh): זהו פרויקט מצחיק
פלנטריום/Orrery מופעל באמצעות Bluetooth: 13 שלבים (עם תמונות)
פלנטריום/Orrery מופעל באמצעות Bluetooth: זהו מדריך שנוצר להגשמת דרישת הפרויקט של מסלול Makecourse באוניברסיטת דרום פלורידה (www.makecourse.com). זהו הפלנטריום/אוררי 3 כוכבי הלכת שלי. זה התחיל כפרויקט של סמסטר בלבד עבור Makecour
האם זו יד? (מצלמת פטל + רשת עצבית) חלק 1/2: 16 שלבים (עם תמונות)
האם זו יד? (מצלמה פטל + רשת עצבית) חלק 1/2: לפני כמה ימים פצעתי את כף היד הימנית שלי בחדר הכושר. אחר כך בכל פעם שהשתמשתי בעכבר המחשב שלי, זה גרם לכאבים רבים בגלל זווית תלולה של פרק כף היד. אז זה היכה בי &"; האם זה לא יהיה נהדר אם נוכל להמיר כל משטח ל trackp
רובוט רשת עצבית Arduino: 21 שלבים (עם תמונות)
רובוט רשת עצבית של Arduino: ההוראה מבוססת על סדרה בת 3 חלקים שהכנתי לערוץ YouTube Make שמראה לך בדיוק כיצד לבנות אב טיפוס, לעצב, להרכיב ולתכנת, רובוט רשת עצבי משלך. לאחר צפייה בסדרה המלאה, אתה אמור לקבל בטה