TurnedOff. ولا يعمل دونه إلا ثلاثة: الفيديو الاختباري، وإجابة
اللاعب عن سؤال الموافقة، ومعرّف Steam الذي يُحفظ للجلسة القادمة. وإعداد البناء مشروح في صفحة
حزمة Unity.
ما الذي سمح به اللاعب
يسأل البناء لاعبه عمّا يجوز لاختبار اللعب أن يجمعه قبل أن يجمع أي شيء، وإجابته تقرّر ما تفعله بقية هذه الصفحة:
وتجيب
ProtokitePlaytest.IsFeatureEnabled عن الأمرين معًا: الميزة التي يشغّلها اختبار اللعب ويستثنيها
اللاعب تُقرأ مطفأة في كل مكان. والتقاط الاستثناءات يتبع بيانات اللعب هناك، أما الاستثناءات نفسها
فمن شأن حزمة Flock، تبلّغ عنها بإعدادها الخاص مهما أجاب اللاعب.
نموذج الملاحظات لا تشمله تلك الإجابة. فهو لا يُرسل إلا حين يملؤه اللاعب ويضغط Send، وذلك من فعله في
كل حال — والنموذج الذي لم يستطع تشغيلٌ سابق إرساله يُرسل لاحقًا، مهما أجاب اللاعب بعد ذلك.
تسجيل الفيديو
تُسجَّل شاشة اللعبة منذ لحظة تحميل اختبار اللعب وسماح اللاعب بذلك، قبل أن يسجّل أحد دخوله: تسجيل واحد لكل تشغيل، يُكتب أثناء التسجيل في ملف WebM يشغّله المتصفّح دون تثبيت أي شيء. ويُستثنى الوقت الذي تقضيه اللعبة في الخلفية. الإعدادات في Protokite → Playtest → Settings، تحت Video recording (64-bit Windows):
يُنسخ الإطار ويُحجَّم ويُحوَّل على بطاقة الرسوميات ويُقرأ دون انتظارها؛ ويعمل الترميز والكتابة كلٌّ في خيط
خاص به، والإطار الذي لا يلحق يُسقَط بدل أن يوقف اللعبة. وحين ينتهي التسجيل تذكر نافذة Console ما يحويه، وكم
إطارًا أُسقط، ولماذا.
متى يُرفع التسجيل
يُرفع التسجيل إلى جلسته بعد أن يكتمل ملفه وتبدأ الجلسة، أيّهما جاء ثانيًا. ويكتمل الملف حين:- يبلغ Max Recording Minutes أو Max Recording Size Mb؛
- يضغط اللاعب Upload your recording في نموذج الملاحظات، أو تستدعي لعبتك
ProtokitePlaytest.StopRecordingAndSendIt()؛ - توقفه لعبتك نهائيًا بـ
ProtokitePlaytest.StopVideoRecording().
الإغلاق لا يرفع. لا يمكن إرسال تسجيل كامل بينما تُغلق اللعبة، فالتسجيل الجاري عند الإغلاق يُكمَل
ويُحفظ، ويرسله التشغيل التالي. ويرسل التشغيل اللاحق كل تسجيل حفظه تشغيل سابق — رفع فاشل، أو إغلاق، أو
انهيار — الأقدم أولًا، حتى مع إطفاء Playtesting Enabled، فلا يضيّع بناء النشر ما سجّله بناء اختبار لعب.
أما التسجيل الذي لم تبدأ له أي جلسة فيُحذف، إذ لا يمكن إرساله أبدًا.
ProtokitePlaytest.CanSendTheRecording صحيحة. فهي خاطئة حين
لم تبدأ جلسة للتسجيل، والزر المضغوط حينها يوقف التسجيل ولا يرسل شيئًا:
المساحة على قرص اللاعب
Recordings Disk Budget Mb أقصى ما يجوز أن تشغله كل التسجيلات المحفوظة على الجهاز معًا. قبل أن يبدأ تسجيل، تُحذف التسجيلات التي تركتها تشغيلات سابقة حتى يتّسع له المكان: مقاطع الفيديو الاختبارية أولًا، ثم التسجيلات المنتظرة للرفع، الأقدم أولًا. والتسجيل الجاري رفعه، أو الذي تمسكه نسخة من اللعبة ما زالت تعمل، لا يُحذف أبدًا. ولا يفسح التسجيل مكانًا إلا لما يسجّله حدّ طوله بمعدّل بتاته، مع ربع زائد (نحو 845 ميغابايت بالقيم الافتراضية)، فلا يحذف تسجيلٌ قصير تسجيلًا يتّسع بجانبه. وإن بقي أقل من ميغابايت واحد، لا يسجّل ذلك التشغيل فيديو، ويذكر تحذيرٌ الإعدادَ الذي يجب رفعه. والتسجيل الذي قطعه انهيار أو انقطاع كهرباء أو إنهاء قسري للعبة يُكمله التشغيل التالي بكل إطار كامل فيه، ثم يُرفع إلى جلسته كغيره؛ أما الذي لم تبدأ جلسته قط فيُحذف.التحليلات الثقيلة
يرسل اختبار اللعب هذه عبر تحليلات حزمة Flock، ضمن فئةplaytest، وتُقرأ في Dashboards → Game Metrics:
-
performance_windowلكل عشر ثوانٍ من اللعب: الوسيط والمئين 95 والمئين 99 لزمن الإطار، وhitches(الإطارات التي استغرقت Hitch Frame Time Ms، أي 60 افتراضيًا، أو أكثر)، والذاكرة المستعملة وذروتها، وmapأي المشهد النشط. وزمن الإطار هو الوقت الفعلي بين إطار والذي يليه، فالحركة البطيئة أو اللعبة الموقوفة تُقاس بالإطارات التي رآها اللاعب. -
level_loadedلكل مشهد تحمّله اللعبة مكان الذي قبله، مع المشهد السابق وload_seconds، أي المدة التي أوقف فيها التحميلُ اللعبة. - أحداثك الخاصة، على الخط الزمني نفسه وفي الفئة نفسها:
RecordPlaytestEvent بـtrue حين يوضع الحدث في الطابور، ويمكن استدعاؤها من أي خيط، ولا ترسل إلا ما دامت
التحليلات الثقيلة تعمل، وهي تبدأ بعد تحميل اختبار اللعب؛ والحدث المسجّل قبل ذلك في التشغيل يجيب بـfalse ولا
يُحفظ. ويُرفض الاسمان اللذان يرسلهما اختبار اللعب بنفسه.
تحتاج التحليلات الثقيلة إلى Analytics Enabled في حزمة Flock: فإن كان مطفأً لا يُقاس شيء، وتذكر نافذة
Console ذلك مرة واحدة. والأحداث أحداث Flock كغيرها، فهي تنتظر لاعبًا مسجّل الدخول وتتبع موافقة التحليلات
الخاصة بحزمة Flock. راجع التحليلات والأحداث لترى كيف تتلاءم الفئة ولوحات
المعلومات.
الاستثناءات
تبقى الاستثناءات من شأن حزمة Flock. فهي تلتقط استثناءات اللعبة من كل خيط، والمهام الفاشلة التي لم ينتظرها أحد، عبر Analytics Capture Exceptions في Flock → Settings → Advanced Settings (مفعّل افتراضيًا)، وتبلّغ عنها في Diagnostics → Errors. ومفتاح الاستثناءات في اختبار اللعب لا يشغّل ذلك ولا يطفئه أبدًا. والاستثناء نفسه إذا رُمي مرة بعد مرة يصل إلى لوحة المعلومات تقريرًا واحدًا، ثم تقريرَ تكرار واحدًا يعدّ البقية حين تُغلق نافذة التكرار (Analytics Exception Repeat Window، أي 60 ثانية). أما أسطرDebug.LogError
فليست استثناءات ولا يُبلَّغ عنها.
نموذج الملاحظات
حين ينشر اختبار اللعب نموذج ملاحظات في Protokite، يفتحه اللاعب فوق اللعبة بـF9 ويملؤه. وهو مبني ممّا نشرته — كل سؤال وتسمية ونص مساعد وخيار — فتعديل النموذج في Protokite لا يحتاج إلى بناء جديد.
نموذج منشور، مرسوم من اختبار اللعب: كل سؤال، والزر الذي يرسل التسجيل.
- يفحص Send الإجابات كما يفحصها Protokite، ويعرض كل مشكلة بجانب سؤالها قبل إرسال أي شيء: سؤال مطلوب تُرك فارغًا، أو تقييم خارج النطاق، أو خيار لا يعرضه السؤال.
- النموذج المرسَل يُحفظ على الجهاز أولًا ويُرسل من هناك، فلا يضيّعه إغلاق اللعبة ولا انقطاع الشبكة: ما لم يستطع الذهاب الآن يُرسل حين تعود الشبكة، أو بعد دقيقتين، أو في تشغيل لاحق. والإرسال مجددًا في الجلسة نفسها يستبدل الإجابات السابقة.
- إغلاقه دون إرسال يحفظ ما كُتب لبقية التشغيل.
- يظهر Upload your recording ما دام هذا التشغيل يسجّل الشاشة وقد بدأت جلسته: يوقف التسجيل ويرسله الآن. وفتح النموذج لا يوقف التسجيل من تلقاء نفسه أبدًا.
نموذج خاص بك
تعطيProtokitePlaytest.FeedbackForm واجهتك الأسئلة: لكل حقل Id وType وLabel وHelpText وOptions،
وهل هو Required. أجب عنها وافحصها وأرسلها عبر الفحص والحفظ نفسيهما اللذين يمرّ بهما النموذج المدمج:
Type الخاص بالحقل بثوابت ProtokitePlaytestFormFieldTypes بدل كتابته، وعامل النوع الذي لا تعرفه على
أنه نص، فهكذا يقرؤه الخادم.
الاستدعاءات المتاحة للعبتك
كلها علىProtokitePlaytest، في مساحة الأسماء Protokite.Playtest. استدعها من الخيط الرئيسي؛ وتعمل
RecordPlaytestEvent من أي خيط آخر أيضًا.
ومثال الحزمة،
Samples/PlaytestSample/ProtokitePlaytestSample.cs، يضع كل هذه على شاشة واحدة: أضفه إلى
GameObject واضغط Play.
التجربة في المحرّر
في النصف السفلي من نافذة الإعداد، Protokite → Playtest → Setup Checks And Test Video، كل ما يلزم للاختبار. وفي Play Mode تبدو هكذا:
نافذة الإعداد في Play Mode: الفحوص، وإجابة هذا الجهاز، والفيديو الاختباري، والاختبار الذاتي المباشر.
- Forget This Machine’s Answer يجعل Play التالي يطرح سؤال الموافقة مجددًا.
- Open Feedback Form يفتح النموذج كما يفتحه مفتاحه.
- Record Test Video يسجّل نافذة Game للثواني التي تضبطها، بإعدادات الفيديو ودون حاجة إلى اختبار لعب:
فلا بأس أن يكون اختبار اللعب مطفأً وألا يكون أحد مسجّل الدخول. يُحفظ الفيديو الاختباري في
ProtokitePlaytest/Recordings/TestVideos/داخل مجلد البيانات الدائمة للعبة، ولا يُرفع أبدًا، وتعرض النافذة أين ذهب. ويُرفض ما دام تسجيل اختبار اللعب نفسه جاريًا، ويفسح له الطريق. وككل فيديو، لا يُسجَّل إلا على Windows بنواة 64 بت. - Run Live Self-Test يفحص اختبار اللعب كله مقابل Protokite الحقيقي لديك (أدناه).
فحص بناء اختبار لعب
يفحص الاختبار الذاتي المباشر كل ما يفعله بناء اختبار اللعب مقابل Protokite الحقيقي لديك دفعة واحدة، ويسجّل سطرًا لكل خطوة وعدًّا في النهاية. شغّله في Play Mode بـRun Live Self-Test، أو من الشيفرة في المحرّر أو في بناء تطوير (بناء النشر يرفضه):- سجّل دخول لاعب أولًا، وأجب عن سؤال الموافقة. فهو لا يسجّل دخول أحد؛ والخطوات التي تحتاج إلى جلسة أو إجابة تُتخطّى مع ذكر السبب.
- شغّله في Play أو تشغيل خاص به. فهو يوقف تسجيل هذا التشغيل ليرفعه، ويرسل نموذجًا مملوءًا يستبدل ما أرسله اللاعب في هذا التشغيل، ويرمي استثناءين عمدًا — فإن كان Error Pause مفعّلًا في Console يتوقّف Play عندهما حتى تستأنفه.
- يترك أثرًا في لوحات معلوماتك: نموذجًا مملوءًا واحدًا في الجلسة، وحدث
playtest_self_testواحدًا، واستثناءً واحدًا مرميًّا مرتين ليُحتسب تكراره، وتسجيل التشغيل. وكلٌّ منها يحمل معرّف التشغيل (report.RunId)، لتجدها في Flock وProtokite. - تُتخطّى الخطوة مع ذكر السبب حين لا يشغّل اختبار اللعب ميزتها، وحين لا يكون في البناء مرمّز فيديو (كل منصّة
سوى Windows بنواة 64 بت)، وفي اختبار اللعب المغلق ما لم تسمِّ واحدًا: مرّر معرّف Game Version لاختبار لعب مغلق
إلى
RunAsync، أو اكتبه في Closed Playtest Version ID في النافذة.
ما يبقى على جهاز اللاعب
تحتProtokitePlaytest/ في مجلد البيانات الدائمة للعبة (Application.persistentDataPath):
المنصّات
كل ما في هذه الصفحة يعمل حيثما تعمل حزمة Flock، عدا الفيديو. يُسجَّل الفيديو على Windows بنواة 64 بت فقط، في المحرّر وفي المشغّلات، مع Mono وIL2CPP على السواء. ويعمل على Direct3D 11 و12 وVulkan وOpenGL، في Built-in Render Pipeline وURP، وبالألوان Linear وGamma، ويحتاج إلى بطاقة رسوميات تشغّل compute shaders. «لا فيديو على هذه المنصّة» يعني ذلك بالضبط ولا شيء أكثر: البناء لأي منصّة أخرى — macOS أو Linux أو الهواتف أو WebGL أو Windows بنواة 32 بت أو ARM64 — يترك مرمّز الفيديو خارجه، ويذكر مرة واحدة في Console أنه لا يسجّل فيديو، ويشغّل كل شيء آخر: الجلسة، وسؤال الموافقة، والتحليلات الثقيلة، والاستثناءات، ونموذج الملاحظات. وتنبّهك نافذة الإعداد مسبقًا: «Players built for … record no video». واللعبة التي لا ترسم شيئًا (بناء خادم، أو لعبة بدأت بـ-nographics أو -batchmode) لا تسجّل شيئًا كذلك، ولا تستطيع عرض سؤال الموافقة: أجب عنه من الشيفرة
بـSetPlaytestConsent، أو أطفئ السؤال.
على WebGL تُنسخ ملفات اختبار اللعب — إجابة الموافقة، ومعرّف الجهاز، ونماذج الملاحظات المنتظرة للإرسال — إلى
تخزين المتصفّح بعد كل تغيير، فتكون موجودة في زيارة اللاعب التالية حيثما يحفظ المتصفّح بيانات الموقع. والنافذة
الخاصة تنساها حين تُغلق.