با سلام خدمت دوستان عزیز چندی پیش در پی مسائلی که برام پیش اومد نیاز شد توی یک برنامه که هسته سی پلاس پلاس داره و کاملا با سی پلاس پلاس هست از کیو ام ال استفاده کنم ولی جالب بود دو روشی که قبلا میشناختم برای این کار جوابگوی نیازم نبود اما اجازه بدید اول روش های قبلی رو با مثال توضیح بدم برای دوستانی که اون رو روش رو بلد نیستند :

 

روش اول :

  1. ایجاد یک کلاس که از QObject به ارث ببرد.
  2. تعریف سیگنال و اسلات های مورد نیاز
  3. تعریف متغیر با ماکروی Q_PROPERTY و ایجاد سیگنال تغییر و اسلات های تنظیم و گرفتن (set & get )
  4. ایجاد یک شی از این کلاس
  5. ارسال اشاره گر به این شی با تایع setContextProperty از rootContext که از engine گرفته می‌شود.

اگر از موارد بالا چیزی رو متوجه نشدید نگران نباشید چون الان با یک مثال کامل براتون روشن میکنم قضیه چی هست به مثال زیر در گیتهاب توجه کنید اول فایل main.cpp و بعد فایل main.qml

تمامی 5 موردی که در بالا گفتم در فایل main.cpp انجام میشود (اگر نخواهید انجین را به جایی پاس دهید )

لینک پروژه در Github

مشکل اصلی این روش این است که ابجکت ارسال شده به کیو ام ال در تمامی فایل های کیو ام ال در دسترس هست و این باعث پیچیدگی و کثیفی و رعایت نکردن سطح دسترسی خواهد شد که با توجه به داینامیک بودن کد های کیو ام ال اصلا روش قابل قبولی در برنامه تجاری و واقعی نیست پس استفاده از این روش به صورت کامل رد می‌شود و بهتر است برای در نظر گرفتن مسائل امنیتی از این روش استفاده نکنیم.

 

روش دوم:

در این روش تا مرجله 3 دقیقا با روش بالا یکسان است اما تفاوت در این است که بعد از ساختن کلاس نیازی به ساختن شی از آن کلاس نداریم و خود کلاس را در کیو ام ال ریجستر میکنیم و نمونه ساختن از کلاس و مدیریت حافظه و طول عمر به دست کی ام ال سپرده می‌شود. مثال این روش نیز درون گیتهاب قابل مشاهده است که در فایل main.cpp کلاس را در کیو ام ال ریجستر می‌کنیم و در main.qml از آن نمونه ایجاد میکنیم و از آن استفاده می‌کنیم

 

لینک پروژه در Github

این روش نسبت به روش قبل تمیز تر به نظر میرسد چون هرکجا که نیاز داشته باشیم از کلاس نمونه میسازیم و از آن استفاده می‌کنیم البته این روش هم حساسیت های خود را دارد ولی گذشته از آنها مشکل اصلی این روش این است که وقتی شی در کیو ام ال ساخته می‌شود ما در سی پلاس پلاس به آن دسترسی نداریم تا با آن توسط اصل برنامه خود در سی پلاس پلاس تعامل داشته باشیم و این روش بیشتر به درد برنامه هایی با ساختار درختی میخورد که هر کاری که نیاز به انجام شدن در سی پلاس پلاس دارد تماما درون یک کلاس یا چند کلاس وابسته به هم انجام شود و نیاز به جابجایی شی بین توابع کلاس های مختلف از اطح بالا نباشد وگرنه در این روش برای یو ای های زیاد مشکل به وجود میاید و قابل استفاده نیست چون ارتباط ما را به هسته سی پلاس پلاس برناه که معمولا به صورت مجزا کار میکند قطع می‌کند.

 

روش سوم:

احساس نیاز به روش سوم وقتی در من ایجاد شد که نیاز داشتم بین توابع مختلف از کلاس های مختلف که در سی پلاس پلاس بودند شی یا داده سنگین جابجا کنم و روش اول که به دلایل امنیتی قابل استفاده در برنامه تجاری نبود و روش دوم هم برنامه را سمت کیو ام ال برده و سعی می‌کند به صورت شاخه ای و درختی با سی پلاس پلاس مرتبط شود و این روش قابل استفاده در برنامه هایی که هسته پردازشی و سنگین سمت سی پلاس پلاس داشتند نبود چون نیاز به ارسال داده سنین بین کلاس های مختلف وجود داشت و در صورتی که میخواستیم به صورت شاخه ای از این روش استفاده کنیم باید یک کلاس در سی پلاس پلاس رابط کل سیگنال ها و اسلات های کیو ام ال و سی پلاس پلاس میشد که این باعث سنگینی شدید این کلاس و به هم خوردن معماری و کثیفی و مشکلات زیاد در تست می‌شد.

بنابر این با تحقیق و مطالعه به روش سوم رسیدم که میتواند قطعه گمشده این پازل باشد در این روش هسته اصلی در سی پلاس پلاس وجود دارد و بنابر این خوبی روش اول را داراست ولی بجای این که شی به کیو ام ال فرستاده شود میتوان روت ابجکت اصلی را به کلاس مورد نظر فرستاد و با در نظر گرفتن یک ابجکت نیم یکتا برای کلاس مورد نظر در کیو ام ال میتوان آن کلاس را پیدا کرده و در همان کلاس سی پلاس پلاس سیگنال ها و اسلات های مورد نظر را متصل کرد و حتی میتوان کلاس کیو ام ال را به سی پلاس پلاس فرستاد و تغییرات مورد نیاز را بر روی آن اعمال کرد و حتی میتوان با ترکیب روش دوم از این مورد استفاده کرد یعنی در مورادی که لازم است یک کلاس برای استفاده در کیو ام ال آماده کرد و بعد آن را در کیو ام ال ریجستر کرد و از ان استفاده کرد و با این روش ان کلاس را توسط یک سیگنال در قالب QObject* گرفت و به کلاس مورد نظر cast کرد و به این ترتیب یک معماری تمیز برای برنامه سمت سی پلاس پلاس شکل داد مثال زیر فقط استفاده از این روش را به صورت ساده نشان میدهد به امید خدا در آینده نزدیک یک برنامه کامل با استفاده از این معماری آماده میکنم تا رهنمونی برای دوستان باشد :

لینک پروژه در Github

صلواتی برای شهدای مدافع حرم و تعجیل در ظهور آقا امام زمان بفرستید.

در راه حق استوار باشید.