Vă mulțumim pentru susținere

Adăugarea de funcționalități de scripting la aplicațiile .NET

Am un joc mic scris în C #. Utilizează o bază de date ca back-end. este un joc de cărți de tranzacționare și am vrut să pun în aplicare funcția cardurilor ca un script.

Ceea ce vreau sa spun este ca in esenta am o interfata, ICard , pe care o clasa de card implementeaza ( clasa publica Card056: ICard ) si care contine functia numita de joc.

Acum, pentru a face lucrul menținabil / moddabil, aș dori să am clasa pentru fiecare carte ca sursă în baza de date și să o compilesez în mod esențial la prima utilizare. Deci, când trebuie să adaug / schimba o carte, o voi adăuga la baza de date și va spune ca cererea mea să se reîmprospăteze, fără a fi nevoie de niciun fel de implementare a ansamblului (mai ales că am vorbi despre 1 ansamblu pe card, ceea ce înseamnă sute de ansambluri) .

Este posibil? Înregistrați o clasă dintr-un fișier sursă și apoi instanțiați-o, etc.

ICard Cards[current] = new MyGame.CardLibrary.Card056();
Cards[current].OnEnterPlay(ref currentGameState);

Limba este C #, dar bonus suplimentar dacă este posibil să scrieți scriptul în orice limbă .NET.

0
adăugat editat
@mattytommo Nu, nu au mai rămas nimic, au fost în stadii foarte precoce și în esență a fost doar de lucru ca am subliniat mai sus. În prezent, m-aș uita în Roslyn să facă compilația C #: blogs.msdn.com/b/csharpfaq/archive/2011/10/19/… - Alternativ, JavaScript folosind Jint - jint.codeplex.com
adăugat autor Michael Stum
Asta e amuzant, eu și un prieten m-am gândit să scriu un joc de cărți de tranzacționare în C # un timp în urmă, să nu presupunem că mai ai sursa pentru asta? Interesat de modul în care ați abordat acest lucru.
adăugat autor mattytommo
mulțumiri ah, dar căutam mai mult pentru implementarea jocului de cărți de tranzacționare în sine și a structurii pe care o utilizați, spre deosebire de motorul scripting. Multumesc oricum :)
adăugat autor mattytommo

9 răspunsuri

Da, m-am gândit la asta, dar în curând am dat seama că un alt domeniu specific limbajului (DSL) ar fi un pic prea mult.

În esență, ei trebuie să interacționeze cu jocul meu în moduri imprevizibile. De exemplu, o cartelă ar putea avea o regulă "Când aceste cărți intră în joc, toți adversarii tăi undead câștigă +3 atac împotriva dușmanilor zburători, cu excepția cazului în care dușmanul este binecuvântat". Deoarece jocurile de cărți de tranzacționare se bazează pe rând, GameState Manager va declanșa evenimentele OnStageX și va lăsa cardurile să modifice alte carduri sau GameState în orice mod de care are nevoie cardul.

Dacă încerc să creez un DSL, trebuie să pun în aplicare un set de caracteristici destul de mare și, eventual, să îl actualizez în mod constant, ceea ce schimbă munca de întreținere într-o altă parte, fără ao elimina.

De aceea, am vrut să rămân cu o limbă "reală" .NET în esență să fie capabilă să tragă evenimentul și să lase cardul să manipuleze jocul în orice fel (în limitele securității accesului la cod).

0
adăugat
(Nu este nevoie să semnalezi acest lucru, în timp ce acesta ar trebui să fie un update de comentarii / răspunsuri, dar este deținut înainte de aceste opțiuni)
adăugat autor Will

Oleg Shilo's C# Script solution (at The Code Project) really is a great introduction to providing script abilities in your application.

O abordare diferită ar fi considerarea unei limbi care este construită special pentru scripting, cum ar fi IronRuby , < IronPython sau Lua .

IronPython și IronRuby sunt disponibile astăzi.

Pentru un ghid pentru încorporarea programului IronPython citiți Cum să încorporați suportul de scripting IronPython în aplicația existentă în 10 pași simpli .

Lua is a scripting language commonly used in games. There is a Lua compiler for .NET, available from CodePlex -- http://www.codeplex.com/Nua

Această bază de date este o mare citire dacă doriți să aflați despre construirea unui compilator în .NET.

A different angle altogether is to try PowerShell. There are numerous examples of embedding PowerShell into an application -- here's a thorough project on the topic: Powershell Tunnel

0
adăugat
Apropo, am ales acest lucru ca răspunsul acceptat, pentru că am vrut să fiu la Python și IronPython oricum, așa că abordarea IronPython funcționează cel mai bine pentru me .
adăugat autor Michael Stum
LuaInterface este un interpret interpretar care funcționează și ca fantastic.
adăugat autor RCIX
Am implementat C # Script într-un sistem de flux de lucru în Nov 09. A jucat foarte bine pentru noi.
adăugat autor David Robbins

S-ar putea să puteți folosi IronRuby pentru asta.

Altfel aș sugera că aveți un director unde plasați ansambluri precompilate. Apoi, ați putea avea o referință în DB la ansamblu și clasă și utilizați reflexia pentru a încărca ansamblurile corespunzătoare la timpul de execuție.

Dacă într-adevăr doriți să compilați la run-time ați putea folosi CodeDOM, atunci ați putea folosi reflexia pentru a încărca ansamblul dinamic. articol MSDN care ar putea ajuta .

0
adăugat

Principala aplicație pe care divizia mea o vinde face ceva foarte asemănător cu oferirea de personalizări ale clienților (ceea ce înseamnă că nu pot posta nicio sursă). Avem o aplicație C # care încarcă scripturi dinamice VB.NET (deși orice limbă .NET poate fi ușor suportată - VB a fost aleasă deoarece echipa de personalizare a venit dintr-un fundal ASP).

Folosind CodeDom-ul .NET, compilam script-urile din baza de date, folosind VD CodeDomProvider (deranjant la default .NET 2, daca doriti sa suportati 3.5 caracteristici care trebuie sa treaca un dicționar cu "CompilerVersion" "v3.5" constructorului său). Utilizați metoda CodeDomProvider.CompileAssemblyFromSource pentru ao compila (puteți trece setările pentru al forța să se compileze numai în memorie.

Acest lucru ar duce la stocarea a sute de ansambluri în memorie, dar puteți pune împreună toate codurile clasei dinamice într-o singură ansamblu și puteți recompila întregul lot în orice schimbare. Acest lucru are avantajul că ați putea adăuga un semnalizator pentru a compila pe disc cu un PDB atunci când testați, permițându-vă să depanați codul dinamic.

0
adăugat

Următoarea versiune .NET (5.0?) A avut o mulțime de discuții despre deschiderea "compilatorului ca serviciu", ceea ce ar face posibil ca evaluarea directă a scenariilor să fie posibilă.

0
adăugat
Da. Deși Roslyn este încă la orizont, Mono.CSharp (disponibil pe NuGet) folosește toate funcțiile.
adăugat autor Eric Falsken
Adăugarea unei actualizări pentru a menține opțiunile relevante: Platforma .NET Compiler Platform ("Roslyn") este disponibilă. Deci, o alternativă viabilă la toate celelalte. github.com/dotnet/roslyn .
adăugat autor Riv
Cred că asta se referă la Roslyn? en.wikipedia.org/wiki/Microsoft_Roslyn
adăugat autor Stephen Kennedy

Dacă nu doriți să utilizați DLR, puteți utiliza Boo (care are un interpret) sau ați putea lua în considerare proiectul Script.NET (S #) pe CodePlex . Cu soluția Boo puteți alege între scripturile compilate sau folosind interpretul, iar Boo face o limbă de scripturi frumoasă, are o sintaxă flexibilă și o limbă extensibilă prin intermediul arhitecturii deschise a compilatorului. Script.NET arata, de asemenea, frumos, si ai putea extinde cu usurinta acest limbaj, precum si un proiect open source si foloseste un foarte prietenos Generator de compilatoare ( Irony.net ).

0
adăugat

Puteți utiliza oricare dintre limbile DLR, care oferă o modalitate de a găzdui într-adevăr cu ușurință propria platformă de scripting. Cu toate acestea, nu trebuie să utilizați o limbă de scripting pentru acest lucru. Puteți utiliza C # și îl puteți compila cu furnizorul de cod C #. Atâta timp cât îl încărcați în propriul AppDomain, îl puteți încărca și descărca în conținutul inimii.

0
adăugat

Aș sugera să utilizați LuaInterface , deoarece a implementat pe deplin Lua în cazul în care se pare că Nua nu este completă și probabil nu implementează câteva funcții foarte utile (corutine etc.).

Dacă doriți să utilizați unele dintre modulele Lua pre-ambalate în exterior, vă sugeram să folosiți ceva de-a lungul liniilor de 1.5.x, spre deosebire de seria 2.x care construiește un cod gestionat complet și nu poate expune C API-ul necesar.

0
adăugat

I'm using LuaInterface1.3 + Lua 5.0 for a NET 1.1 application.

Problema cu Boo este că de fiecare dată când parsezi / compilați / evaluezi codul în zbor, creează un set de clase boo, astfel încât să primești scurgeri de memorie.

Lua în cealaltă parte, nu face asta, deci este foarte stabil și funcționează minunat (pot trece obiecte de la C # la Lua și înapoi).

Până acum nu am pus-o încă în PROD, dar pare foarte promițătoare.

I did have memory leaks issues in PROD using LuaInterface + Lua 5.0, therefore I used Lua 5.2 and linked directly into C# with DllImport. The memory leaks were inside the LuaInterface library.

Lua 5.2: from http://luabinaries.sourceforge.net and http://sourceforge.net/projects/luabinaries/files/5.2/Windows%20Libraries/Dynamic/lua-5.2_Win32_dll7_lib.zip/download

Odată ce am făcut asta, toate pierderile de memorie au dispărut, iar aplicația a fost foarte stabilă.

0
adăugat