جدول المحتويات:

لعبة حروف العلة مع Arduino و YX5300 MP3 Module Catalex: 13 خطوة
لعبة حروف العلة مع Arduino و YX5300 MP3 Module Catalex: 13 خطوة

فيديو: لعبة حروف العلة مع Arduino و YX5300 MP3 Module Catalex: 13 خطوة

فيديو: لعبة حروف العلة مع Arduino و YX5300 MP3 Module Catalex: 13 خطوة
فيديو: طريقة تشغيل الملفات الصوتية والتحكم بها عن طريق المايكروبت 2024, شهر نوفمبر
Anonim
لعبة حروف العلة مع Arduino و YX5300 MP3 Module Catalex
لعبة حروف العلة مع Arduino و YX5300 MP3 Module Catalex

هل تستطيع قراءة هذا السؤال؟ هذا غريب! سألت هذا السؤال عن قصد. إذا كنت تستطيع قراءة هذا النص ، فذلك لأنك تعرف الأبجدية بأكملها ، وبالطبع ، تعلمت كل حروف العلة.

حروف العلة موجودة في كل الكلمات. من المستحيل الهروب من كل منهم. والآن دعني أسألك سؤالا. هل كان تعلم طفولتك ممتعًا واشتمل على موارد تكنولوجية؟

أنا متأكد من أن مصادر التعلم كانت قليلة وأنك استخدمت الطرق التقليدية لتعلم حروف العلة والحروف الأبجدية.

بعد كل شيء ، هل من الممكن استخدام بعض الموارد التكنولوجية لتعلم حروف العلة؟

في هذا المقال ، سوف أعلمك كيفية تعليم طلابك وأطفالك أحرف العلة من خلال لعبة.

سوف أعلمك كيفية إنشاء نظام بصوت ، حيث يسمع طفلك / تلميذك صوت الحرف ويجب عليه الضغط على زر للإشارة إلى الحرف الصحيح.

وبالتالي ، سيتعلمون أثناء اللعب وسيكونون دائمًا متحمسين للدراسة.

الآن ، سأريكم العملية خطوة بخطوة لإنشاء لعبتك الخاصة ، وتعليم حروف العلة للأطفال.

اللوازم

لوحة الدوائر المطبوعة JLCPCB

اردوينو اونو

مفتاح الضغط

10kR المقاوم

رأس ذكر 2 ، 54 مم 1 × 7

الخطوة 1: تطوير لعبة أحرف العلة باستخدام Arduino

تطوير لعبة أحرف العلة باستخدام Arduino
تطوير لعبة أحرف العلة باستخدام Arduino

قلب اللعبة هو لوحة الدوائر المطبوعة JLCPCB من حروف العلة. يمكنك الوصول إلى هذا الرابط وتنزيل ملفات المشروع. لديها 5 أزرار. ستستخدم كل زر لتمثيل حرف متحرك وتوصيله بـ Arduino.

تظهر لوحة الدوائر المطبوعة في الشكل 1.

الخطوة 2:

صورة
صورة

باستخدام مشروع PCB هذا ، يمكنك توصيله بـ Arduino وإنشاء لعبتك. بعد ذلك ، سأقدم لك مخططًا إلكترونيًا لتجميع أو بناء المشروع على لوح الحماية الخاص بك.

الخطوه 3:

من هذا التخطيطي ، قمنا بإعداد تخطيط اللوحة الإلكترونية. يظهر في الشكل 2 ويمكنك تنزيل الملفات وإنشاء مشروعك.

اختر 5 دبابيس من Arduino وقم بتوصيل وصلات العبور على اللوحة بـ Arduino. أو بخلاف ذلك ، يمكنك تجميع الرسم التخطيطي الإلكتروني التالي.

الخطوة 4: فكرة المشروع

فكرة المشروع
فكرة المشروع

سأعلمك كيفية تجميع نظام صوت MP3 باستخدام Arduino. سيكون هذا النظام مسؤولاً عن إعادة إنتاج الصوت الذي يتحدث بالحرف. سيتم رسم صوت كل حرف باستخدام قيمة من 1 إلى 5 ، حيث يمثل 1 A و 5 يمثل U.

وهكذا ، عندما يسمع الطفل الصوت ، يجب عليه أن ينظر إلى لوحة المفاتيح ، ويتعرف على هجاء الحرف المتحرك ، ويضغط على المفتاح الصحيح.

إذا فشلت ، سيومض النظام المصباح الأحمر 3 مرات. وإلا ، فسيقوم النظام بتنشيط الجرس لمدة 5 ثوانٍ وسيرسم حرفًا متحركًا جديدًا.

للقيام بذلك ، يجب عليك تجميع الدائرة التالية.

في هذه الدائرة ، ستقوم بتوصيل وحدة MP3 ولوحة الحروف المتحركة على Arduino. تم استخدام وحدة Bluetooth لتمثيل وحدة Catalex MP3.

سيكون Arduino مسؤولاً عن فرز الأرقام الخمسة ثم إرسال الأمر لتنشيط حرف العلة المرسوم

الخطوة الخامسة:

صورة
صورة

بعد ذلك سننتظر حتى يسمع الطفل ويضغط على زر كما هو مبين في الشكل أعلاه.

يمثل كل زر أعلاه حرف علة للأبجدية. بعد ذلك ، سأوضح لك كيف ستبني منطق البرمجة لهذا المشروع.

الخطوة السادسة: بناء منطق برمجة اللعبة

بناء منطق برمجة اللعبة
بناء منطق برمجة اللعبة

يعتمد نظام لعبة الحروف المتحركة على تشغيل وحدة YX5300. تحتوي هذه الوحدة على بعض الوظائف ، ومع ذلك ، سنركز على تقديم هيكل عمل اللعبة من خلال الوظائف الرئيسية لوحدة YX5300.

أدناه أقدم لكم كل منطق البرمجة للمشروع.

الخطوة السابعة:

فيما يلي سأشرح خطوة بخطوة لبناء منطق هذه اللعبة الممتعة للأطفال.

#يشمل

#define ARDUINO_RX 5 // يجب الاتصال بـ TX لوحدة Serial MP3 Player # تعريف ARDUINO_TX 6 // الاتصال بـ RX للوحدة SoftwareSerial mp3 (ARDUINO_RX ، ARDUINO_TX) ؛ ثابت int8_t Send_buf [8] = {0} ؛ // عازلة لإرسال الأوامر. // BETTER LOCALLY static uint8_t ansbuf [10] = {0} ؛ // عازلة للإجابات. // BETTER LOCALLY String mp3Answer؛ // إجابة من MP3. سلسلة sanswer (باطل) ؛ String sbyte2hex (uint8_t b) ؛ / ************ Command byte **************************** / #define CMD_NEXT_SONG 0X01 // العب التالي أغنية. #define CMD_PREV_SONG 0X02 // تشغيل الأغنية السابقة. #define CMD_PLAY_W_INDEX 0X03 #define CMD_VOLUME_UP 0X04 #define CMD_VOLUME_DOWN 0X05 #define CMD_SET_VOLUME 0X06 #define CMD_SNG_CYCL_PLAY 0X08 // Single Cycle Play. #define CMD_SEL_DEV 0X09 #define CMD_SLEEP_MODE 0X0A #define CMD_WAKE_UP 0X0B #define CMD_RESET 0X0C #define CMD_PLAY 0X0D #define CMD_PAUSE 0X0E #PLAYFINE #define CMD_FOLDER_CYCLE 0X17 #define CMD_SHUFFLE_PLAY 0x18 // #define CMD_SET_SNGL_CYCL 0X19 // Set single cycle. # تعريف CMD_SET_DAC 0X1A # تعريف DAC_ON 0X00 # تعريف DAC_OFF 0X01 # تعريف CMD_PLAY_W_VOL 0X22 # تعريف CMD_PLAYING_N 0x4C # تعريف CMD_QUERY_STATUS 0x42 # تعريف CMD_QUERY_VOLUME 0x43 # تعريف CMD_QUERY_FLDR_TRACKS 0x4e # تعريف CMD_QUERY_TOT_TRACKS 0x48 # تعريف CMD_QUERY_FLDR_COUNT 0x4f / ********* *** أوبيتونس **************************** / # تعريف DEV_TF 0X02 / ************** **************************************************** ***** / int numero؛ بايت إستادو بايت الجرس = 2 ؛ دبوس البايت = 0 ؛ بايت SortNumber = 0 ؛ زر منطقي = 0 ؛ إعداد باطل () {Serial.begin (9600) ؛ mp3.begin (9600) ، تأخير (500) ؛ لـ (pin = 8 ؛ pin 13) {pin = 8 ؛ } Serial.println ("Varrendo…") ، Serial.println (دبوس) ؛ // تأخير (1000) ؛ } while (button! = 1) ؛ Serial.println ("Saiu…") ؛ if (button == 1 && (pin-1)! = SortNumber) {sendCommand (0x03، 0، 6)؛ تأخير (3000) ؛ } if (button == 1 && (pin-1) == SortNumber) {sendCommand (0x03، 0، 7)؛ تأخير (3000) ؛ } // تحقق من الإجابة. إذا (mp3.available ()) {Serial.println (decodeMP3Answer ()) ؛ } تأخير (100)؛ //Serial.println("Tocando musica … ")؛ } / ************************************************** ******************************** / / * وظيفة sendMP3Command: ابحث عن أمر 'c' وأرسله إلى MP3 * / / * المعلمة: c. رمز لأمر MP3 ، "h" للمساعدة. * / / * Return: void * / void sendMP3Command (char c) {switch (c) {case '؟': case 'h': Serial.println ("HELP")؛ Serial.println ("p = تشغيل") ؛ Serial.println ("P = Pause") ؛ Serial.println ("> = التالي") ؛ Serial.println ("": Serial.println ("التالي") ؛ sendCommand (CMD_NEXT_SONG) ؛ sendCommand (CMD_PLAYING_N) ؛ // اطلب رقم الملف الذي يتم تشغيل الفاصل ؛ الحالة 'بطاقة الذاكرة المدرجة. "؛ فاصل ؛ الحالة 0x3D: decodedMP3Answer + = "-> عدد التشغيل المكتمل" + String (ansbuf [6]، DEC)؛ // sendCommand (CMD_NEXT_SONG)؛ // sendCommand (CMD_PLAYING_N)؛ // اطلب رقم الملف الذي يتم تشغيله فاصل ؛ الحالة 0x40: decodedMP3Answer + = "-> Error"؛ break؛ case 0x41: decodedMP3Answer + = "-> استرجاع البيانات بشكل صحيح."؛ break؛ case 0x42: decodedMP3Answer + = "-> Status play:" + String (ansbuf [6]، DEC) ؛ كسر ؛ الحالة 0x48: فك الشفرة MP3Answer + = "-> عدد الملفات:" + سلسلة (ansbuf [6] ، DEC) ؛ كسر ؛ الحالة 0x4C: فك شفرة MP3Answer + = "-> تشغيل:" + سلسلة (ansbuf [6] ، DEC)؛ break؛ case 0x4E: decodedMP3Answer + = "-> عدد ملفات المجلد:" + String (ansbuf [6]، DEC)؛ break؛ case 0x4F: decodedMP3Answer + = "-> Folder count:" + String (ansbuf [6]، DEC)؛ break؛} إرجاع مفكك MP3Answer؛} / *********************************** ************ ********************************* / / * الوظيفة: إرسال الأمر إلى MP3 * / / * المعلمة: بايت الأمر * / / * المعلمة: معلمة بايت dat1 للأمر * / / * المعلمة: معلمة بايت dat2 للأمر * / void sendCommand (أمر بايت) {sendCommand (الأمر ، 0 ، 0) ؛ } void sendCommand (أمر بايت ، بايت dat1 ، بايت dat2) {تأخير (20) ؛ Send_buf [0] = 0x7E ، // Send_buf [1] = 0xFF ؛ // Send_buf [2] = 0x06 ؛ // Len Send_buf [3] = أمر ؛ // Send_buf [4] = 0x01 ؛ // 0x00 NO ، 0x01 feedback Send_buf [5] = dat1 ؛ // datah Send_buf [6] = dat2 ؛ // البيانات Send_buf [7] = 0xEF ؛ // Serial.print ("إرسال:") ؛ لـ (uint8_t i = 0؛ i <8؛ i ++) {mp3.write (Send_buf ) ؛ Serial.print (sbyte2hex (Send_buf )) ؛ } Serial.println () ، } / ************************************************** ******************************** / / * الوظيفة: sbyte2hex. إرجاع بيانات بايت بتنسيق HEX. * / / * المعلمة: - uint8_t ب. بايت للتحويل إلى HEX. * / / * إرجاع: String * / String sbyte2hex (uint8_t b) {String shex؛ عرافة = "0X" ؛ إذا (ب <16) شيخ + = "0" ؛ عرافة + = سلسلة (ب ، ست عشري) ؛ شيخ + = "" ؛ عودة hex } / ************************************************** ******************************** / / * الوظيفة: shex2int. إرجاع int من سلسلة HEX. */ /*العوامل. char * s للتحويل إلى HEX. * / / * المعلمة: n. طول الحرف. * / / * إرجاع: int * / int shex2int (char * s، int n) {int r = 0؛ لـ (int i = 0؛ i = '0' && s = 'A' && s <= 'F') {r * = 16 ؛ r + = (s - 'A') + 10 ؛ }} عودة r؛ } / ************************************************** ******************************** / / * الوظيفة: sanswer. إرجاع إجابة سلسلة من وحدة mp3 UART. * / / * المعلمة: - uint8_t ب. فارغ. * / / * العودة: سلسلة. إذا كانت الإجابة جيدة الصياغة. * / سلسلة sanswer (باطل) {uint8_t i = 0 ؛ String mp3answer = ""؛ // احصل على 10 بايت فقط أثناء (mp3.available () && (i <10)) {uint8_t b = mp3.read ()؛ أنسبوف = ب ؛ أنا ++ ؛ mp3answer + = sbyte2hex (ب) ؛ } // إذا كان تنسيق الإجابة صحيحًا. if ((ansbuf [0] == 0x7E) && (ansbuf [9] == 0xEF)) {return mp3answer؛ } إرجاع "؟؟؟:" + mp3answer؛ }

أولاً ، نحدد جميع متغيرات البرنامج وعناوين تسجيل الوصول لوحدة YX5300.

#يشمل

#define ARDUINO_RX 5 // يجب أن يتصل بـ TX لوحدة Serial MP3 Player #define ARDUINO_TX 6 // الاتصال بـ RX للوحدة SoftwareSerial mp3 (ARDUINO_RX ، ARDUINO_TX) ؛ ثابت int8_t Send_buf [8] = {0} ؛ // عازلة لإرسال الأوامر. // BETTER LOCALLY static uint8_t ansbuf [10] = {0} ؛ // عازلة للإجابات. // BETTER LOCALLY String mp3Answer؛ // إجابة من MP3. سلسلة sanswer (باطل) ؛ String sbyte2hex (uint8_t b) ؛ / ************ Command byte **************************** / #define CMD_NEXT_SONG 0X01 // العب التالي أغنية. #define CMD_PREV_SONG 0X02 // تشغيل الأغنية السابقة. #define CMD_PLAY_W_INDEX 0X03 #define CMD_VOLUME_UP 0X04 #define CMD_VOLUME_DOWN 0X05 #define CMD_SET_VOLUME 0X06 #define CMD_SNG_CYCL_PLAY 0X08 // Single Cycle Play. #define CMD_SEL_DEV 0X09 #define CMD_SLEEP_MODE 0X0A #define CMD_WAKE_UP 0X0B #define CMD_RESET 0X0C #define CMD_PLAY 0X0D #define CMD_PAUSE 0X0E #PLAYFINE #define CMD_FOLDER_CYCLE 0X17 #define CMD_SHUFFLE_PLAY 0x18 // #define CMD_SET_SNGL_CYCL 0X19 // Set single cycle. # تعريف CMD_SET_DAC 0X1A # تعريف DAC_ON 0X00 # تعريف DAC_OFF 0X01 # تعريف CMD_PLAY_W_VOL 0X22 # تعريف CMD_PLAYING_N 0x4C # تعريف CMD_QUERY_STATUS 0x42 # تعريف CMD_QUERY_VOLUME 0x43 # تعريف CMD_QUERY_FLDR_TRACKS 0x4e # تعريف CMD_QUERY_TOT_TRACKS 0x48 # تعريف CMD_QUERY_FLDR_COUNT 0x4f / ********* *** أوبيتونس **************************** / # تعريف DEV_TF 0X02 / ************** **************************************************** ***** / int numero؛ بايت إستادو بايت الجرس = 2 ؛ دبوس البايت = 0 ؛ بايت SortNumber = 0 ؛ زر منطقي = 0 ؛

الخطوة الثامنة:

تُستخدم عناوين التسجيل هذه لتكوين عملية الوحدة. على سبيل المثال ، راجع عنوان التسجيل هذا أدناه.

#define CMD_PLAY_W_INDEX 0X03

يتم تعريف العنوان 0x03 بالاسم CMD_PLAY_W_INDEX. يتم استخدامه لتشغيل أغنية من رقمها ، أي أنك تقوم بإدخال رقم الصوت وسيتم تشغيله.

بهذه القيم سنستخدمها ونقوم بتهيئة عمل مشروعنا.

بعد تحديد العناوين المختلفة التي سيتم استخدامها ، سندخل وظيفة الإعداد وتكوين المسامير والاتصال التسلسلي لمشروعنا.

الخطوة 9: وظيفة Void Setup ()

بعد ذلك ، راجع وظيفة إعداد الفراغ. لقد أجريت جميع إعدادات دبابيس الأزرار ، والاتصال التسلسلي لوحدة MP3 ، وتهيئة وحدة البطاقة في MP3.

الإعداد باطل()

{Serial.begin (9600) ، mp3.begin (9600) ، تأخير (500) ؛ لـ (pin = 8 ؛ pin <13 ؛ pin ++) {pinMode (pin ، INPUT) ؛ } sendCommand (CMD_SEL_DEV، 0، DEV_TF) ؛ تأخير (500) ؛ }

لقد بدأت الاتصال التسلسلي لطباعة البيانات على المسلسل للكمبيوتر ثم بدأنا الاتصال التسلسلي من خلال كائن mp3.

Serial.begin (9600) ؛

mp3.begin (9600) ، تأخير (500) ؛

يتم التحكم في وحدة mp3 من خلال الأوامر التي يتلقاها مسلسل Arduino. في هذه العملية ، استخدمنا مكتبة SoftwareSerial وقمنا بمحاكاة المسلسل على دبابيس Arduino الرقمية.

وبالتالي ، ستتمكن من استخدام Arduino للتحكم في وحدة MP3 من خلال الأوامر المرسلة إليها.

بالإضافة إلى ذلك ، قمنا بتهيئة المسامير الرقمية وتهيئة وحدة بطاقة MP3

لـ (pin = 8 ؛ pin <13 ؛ pin ++) {pinMode (pin ، INPUT) ؛ } sendCommand (CMD_SEL_DEV، 0، DEV_TF) ؛ تأخير (500) ؛

بعد إجراء التكوين ، يجب أن نذهب إلى المنطق الرئيسي في وظيفة الحلقة الفارغة.

الخطوة 10: حلقة الفراغ للوظيفة الرئيسية ()

الكود بسيط للغاية ويتم تقديم الهيكل المنطقي بأكمله أدناه. فيما يلي سأشرح لك المنطق الكامل للوظيفة الرئيسية.

حلقة فارغة()

{دبوس = 8 ؛ randomSeed (analogRead (A0)) ؛ numero = عشوائي (8 ، 12) ؛ SortNumber = numero ؛ numero = numero - 7 ؛ Serial.println (numero) ؛ sendCommand (0x03 ، 0 ، numero) ؛ تأخير (1000) ؛ فعل {button = digitalRead (دبوس) ؛ Serial.println (زر) ؛ دبوس ++ ؛ إذا (دبوس> 13) {دبوس = 8 ؛ } Serial.println ("Varrendo…") ، Serial.println (دبوس) ؛ // تأخير (1000) ؛ } while (button! = 1) ؛ Serial.println ("Saiu…") ؛ if (button == 1 && (pin-1)! = SortNumber) {sendCommand (0x03، 0، 6)؛ تأخير (3000) ؛ } if (button == 1 && (pin-1) == SortNumber) {sendCommand (0x03، 0، 7)؛ تأخير (3000) ؛ } // تحقق من الإجابة. إذا (mp3.available ()) {Serial.println (decodeMP3Answer ()) ؛ } تأخير (100)؛ //Serial.println("Tocando musica … ")؛ }

في كل بداية لدورة وظيفة الحلقة ، سنولد قيمة جديدة بين 8 و 12 لتوليد صوت حرف علة. تشير القيمة من 8 إلى 12 إلى الدبوس الرقمي لحرف العلة.

يظهر رمز إنشاء القيمة العشوائية أدناه.

دبوس = 8 ؛

randomSeed (analogRead (A0)) ؛ numero = عشوائي (8 ، 12) ؛ SortNumber = numero ؛

بالإضافة إلى ذلك ، نطرح 7 من المبلغ المسحوب بين 8 و 12. هذا سيسمح لنا بالإشارة إلى مواضع 1 إلى 5 من الأغاني المسجلة على بطاقة الذاكرة.

numero = numero - 7 ؛

بعد ذلك ، قمت بإعادة إنتاج صوت حرف العلة المرسوم على السطر أدناه.

sendCommand (0x03 ، 0 ، numero) ؛

تأخير (1000) ؛

الآن حان الوقت المهم: اللحظة التي سنقرأ فيها الزر الذي ضغط عليه الطفل. يتم تقديم جزء الكود أدناه.

فعل

{زر = digitalRead (دبوس) ؛ Serial.println (زر) ؛ دبوس ++ ؛ إذا (دبوس> 13) {دبوس = 8 ؛ } Serial.println ("Varrendo…") ، Serial.println (دبوس) ؛ // تأخير (1000) ؛ } while (button! = 1) ؛

سيتم تنفيذ هذه الحلقة حتى يضغط المستخدم على الأزرار. تسمح لك الحلقة بفحص 5 دبابيس رقمية وفي اللحظة التي يضغط فيها الطفل على أحد الأزرار ، سيخرج من الحلقة ويتحقق مما إذا كان الطفل قد استجاب بشكل صحيح.

سوف تفعل التحقق باستخدام الرمز أدناه.

إذا (زر == 1 && (دبوس 1)! = رقم الترتيب)

{sendCommand (0x03، 0، 6) ؛ تأخير (3000) ؛ } if (button == 1 && (pin-1) == SortNumber) {sendCommand (0x03، 0، 7)؛ تأخير (3000) ؛ }

سيتم تنفيذ الشرط الأول عندما يرتكب المستخدم خطأ بسبب الضغط على زر وكانت القيمة المشغلة للدبوس مختلفة عن الدبوس المسحوب (SortNumber).

في هذه المرحلة ، يجب عليك تنفيذ الأمر أدناه.

sendCommand (0x03 ، 0 ، 6) ؛

تأخير (3000) ؛

يستخدم هذا الأمر لتشغيل نغمة الاستجابة الخاطئة. أخيرًا ، لدينا الشرط الثاني الذي سيتم استخدامه للتحقق مما إذا كان الطفل على حق.

إذا (زر == 1 && (دبوس 1) == رقم الترتيب)

{sendCommand (0x03، 0، 7) ؛ تأخير (3000) ؛ }

الخطوة 11:

صورة
صورة

إذا تم الضغط على زر وكان الدبوس الرقمي الذي تم الضغط عليه هو نفسه الدبوس المرسوم ، فسيقوم النظام بإصدار صوت إجابة صحيح.

كما أوضحت لك ، هذا الرمز بسيط للغاية وسيساعد أي طفل على تطوير معرفته بأحرف العلة من خلال لعبة باستخدام Arduino.

في الشكل أعلاه ، يقوم صندوق الصوت بتنفيذ الأغنية المخزنة في بطاقة SD الخاصة بوحدة MP3 YX5300.

الخطوة 12: الخاتمة

يحتاج التعليم في الفصل الدراسي إلى التغيير باستمرار ويمكن أن يكون Arduino حليفًا رائعًا في إنشاء مهام ممتعة.

من خلال هذا المشروع ، كان من الممكن تطوير نشاط بسيط يمكن أن يطور مهارات الأطفال من خلال معرفة الصوت والتهجئة لكل حرف متحرك.

على عكس طرق التدريس التقليدية ، سيتعلم الأطفال من خلال متعة الفصل الدراسي من خلال الألعاب والإلكترونيات.

الخطوة 13: شكر وتقدير

تم تطوير هذا المشروع بفضل دعم وتشجيع شركة JLCPCB. شجعوا التعليم ودعونا لتطوير لعبة حروف العلة لتعليم الأطفال في الفصل.

إذا كنت ترغب في شراء اللوحات الإلكترونية لـ Game of Vowels ، فيمكنك الوصول إلى هذا الرابط وشراء 10 وحدات مقابل 2 دولار في JLCPCB.

موصى به: