Cara menggunakan kelas yang diimplementasikan dalam exe dari dll

Saya sedang membangun mesin permainan sederhana dan permainan di dalamnya. Idenya adalah untuk mengimplementasikan sebagian besar fungsionalitas dan hierarki kelas dasar di mesin yang seharusnya berupa exe dan kemudian memiliki dll yang akan mengimplementasikan permainan tertentu dengan alat yang disediakan mesin. Mirip dengan mesin id seperti idTech4.

Mesin kemudian akan memuat dll, memperoleh instance game, memberikan petunjuk game ke fungsi dan struktur data apa pun yang dibutuhkan game, dan memanggil metode seperti game->update(); pada instance game. Sejauh ini bagus.

Saya ingin hal-hal seperti kelas dasar seperti Entity, Transform, Vector3 dll diimplementasikan di mesin. Lalu di dalam game yang saya inginkan misalnya mendapatkan karakter saya dari Entity.

class Character : public engine::Entity {...};

Hal-hal seperti ini dikompilasi dengan baik karena saya menyertakan header dari mesin tetapi tidak tertaut karena saya tidak menggunakan file obj atau file cpp dari mesin. Saya tahu mengapa ini tidak berhasil. Sejauh yang saya tahu, pilihan saya (yang masuk akal) adalah:

  1. Jadikan kelas-kelas ini hanya sebagai header - dengan cara ini ia akan selalu dikompilasi di mana saja.

Saya tidak menginginkan ini karena akan menambah waktu kompilasi, ukuran biner, dll.

  1. Masukkan fungsionalitas umum ke dalam lib atau dll.

Ini akan berhasil, tetapi file lib berarti saya memiliki kelas yang sama yang dikompilasi (ditautkan) baik di exe (mesin) dan dll (permainan) - ini tampaknya ceroboh. Dll akan berfungsi tetapi sepertinya banyak pekerjaan dengan semua ekspor dan impor yang perlu saya lakukan pada mesin dan game. Mungkin juga yang paling penting pendekatan lib dan dll memiliki masalah yang sama yaitu selama pengembangan saya mungkin akan sering berpindah-pindah kelas dari dan ke kelas tersebut karena hierarki kelas mungkin banyak berubah, dll.

Pertanyaan saya adalah, apakah ada cara lain untuk mengatasi hal ini? Bagi saya ini sepertinya fitur yang cukup berguna untuk memiliki hierarki kelas dalam exe yang dapat digunakan dari dll. Saya bahkan mencoba hal yang sangat konyol seperti membuat linker menggunakan file .obj yang dihasilkan selama kompilasi mesin, tetapi tidak berhasil kecuali saya menentukan semua file .obj satu per satu (Saya menggunakan Visual Studio 2017).

Saya tidak ingin melepaskan modularitas desain ini.

Edit: Karena dll bersifat khusus platform, mari kita pertimbangkan Windows (walaupun menurut saya platform lain akan serupa).


person Aldarrion    schedule 27.04.2017    source sumber
comment
Saya agak bingung mesinnya exe dan gamenya dll. Bukankah sebaliknya akan lebih masuk akal?   -  person 463035818_is_not_a_number    schedule 27.04.2017


Jawaban (2)


Sepertinya Anda ingin menggunakan pemuatan dinamis, tetapi menurut saya Anda mungkin melakukan hal yang salah. Exe biasanya memiliki kode permainan dan .dll memiliki logika dan kelas mesin permainan. Anda memuat .dll dalam kode .exe dan mendaftarkan berbagai hal ke mesin sehingga kode permainan Anda diperbarui dan dirender.

Saya berpikir sekarang saat saya mengetik ini apakah ada cara untuk membalikkannya, tetapi hal ini memerlukan perubahan paradigma dalam logika desain game Anda di mana game tersebut hanya menyediakan fungsi pembaruan dan render ke mesin game atau semacamnya. Hanya itu yang dapat Anda andalkan karena mesinnya harus cukup umum untuk menangani permainan.

Jika saya memikirkan sesuatu yang inovatif, saya akan mempostingnya di sini, namun sementara ini, berikut adalah beberapa info tentang pemuatan dinamis untuk membantu Anda memulai. https://en.wikipedia.org/wiki/Dynamic_loading

person MrJman006    schedule 27.04.2017
comment
Menurut saya, masuk akal jika memiliki mesin yang mengontrol game loop utama yang hanya memanggil game-›update(). Jika gamenya adalah exe, setiap orang yang ingin membuat game harus mengurus loop utama. Memiliki mesin sebagai dll sepertinya lebih seperti memiliki kerangka kerja. Saya mungkin harus mendalami kode IdTech4 dan melihat bagaimana tepatnya hal itu dilakukan di sana. Terima kasih :) - person Aldarrion; 28.04.2017
comment
Ya, selalu menyenangkan melihat bagaimana proyek yang sukses melakukan sesuatu untuk mendapatkan inspirasi. FYI ada situs pertukaran tumpukan pengembangan game di mana hal ini mungkin lebih tepat. Berikut adalah pertanyaan tentang memisahkan mesin dari game dari editor level yang mungkin menarik bagi Anda. gamedev.stackexchange.com/questions/26520/ - person MrJman006; 28.04.2017
comment
Anda benar dalam konsep bahwa mesin harus cukup umum untuk memanggil pembaruan pada hal-hal dalam game, tetapi Anda ingin pemrogram dapat menggunakan kode mesin Anda setidaknya untuk mendaftarkan objek. Untuk melakukan itu, Anda perlu memiliki cara agar mereka memuat kode tersebut untuk digunakan. Itu sebabnya biasanya dalam format .dll. Anda tidak dapat memuat dari .exe kecuali Anda menyiapkan memori bersama. - person MrJman006; 28.04.2017
comment
Pada akhirnya kita akan mendiskusikan bagaimana kode mesin Anda dikompilasi dan dimuat oleh beberapa kode lain yang memiliki logika permainan sebenarnya. Bagaimanapun Anda mencapai hal itu tidak relevan selama pemrogram independen dapat mendaftarkan objek permainan dengan mesin (dalam pengaturan normal, mesin dalam .dll) atau dapat mendaftarkan sinyal mesin permainan dengan kode logika permainan (tebakan terbaik saya pada desain untuk apa Anda ingin dicapai). - person MrJman006; 28.04.2017

Put the common functionality into a lib or a dll.

Ini akan berhasil, tetapi file lib berarti saya memiliki kelas yang sama yang dikompilasi (ditautkan) baik di exe dan dll

tidak, itu tidak akan terjadi. Kelas-kelas tersebut akan dikompilasi dan tersedia di perpustakaan bersama (.so di linux, .dll di windows, .dylib di mac), dan executable Anda akan memanggil metode khusus itu, dari perpustakaan bersama. itu tidak akan dikompilasi lagi di file executable Anda.

Lihatlah semua kerangka kerja atau pustaka di C++ yang diimplementasikan:

  • The public part is exposed on the headers
    • __dllexport(true) on the classes / functions.
  • The private part is hidden
  • Jangan khawatir tentang peningkatan waktu muat jika Anda menggunakan pendekatan perpustakaan bersama, ini dapat diabaikan.
person Tomaz Canabrava    schedule 27.04.2017
comment
Bagian yang Anda kutip berbicara tentang pendekatan lib (statis). Pendekatan dinamis memiliki kelemahan lain yang saya bicarakan. Terima kasih, saya mungkin akan mengubah keadaan, meskipun pendekatan IdTech tampaknya sangat bagus. - person Aldarrion; 28.04.2017