See site in english Voir le site en francais
Website skin:
home  download  forum  link  contact

Welcome, Guest. Please login or register.
Did you miss your activation email?

Login with username, password and session length

Author Topic: [tutorial] Comment ma DLL marche dans Orbiter ?  (Read 4243 times)

0 Members and 1 Guest are viewing this topic.

Offline DanSteph

  • Administrator
  • Legend
  • *****
  • Posts: 15002
  • Karma: 178
  • Hein, quoi !?
    • FsPassengers
26 June 2007, 02:47:35

Cliquez le lien ci-dessous pour retourner au sommaire des "tutorials pour créer une DLL Orbiter"
http://orbiter.dansteph.com/forum/index.php?topic=6335.msg95352#msg95352



Comment ma DLL marche dans Orbiter ?

Votre dll est declarée dans les fichier config de votre vaisseau très simplement:

fichier Orbiter/Config/Vessel/ShuttlePB.cfg:
; === Configuration file for vessel class ShuttlePB ===
ClassName = ShuttlePB
Module = ShuttlePB


Module=ShuttlePB donc Orbiter va charger ShuttlePB.dll quand il rencontre ca dans un scenario:

PB01:ShuttlePB

Ensuite votre DLL obei à certaines regles définie par Orbiter, certaines fonctions type de votre DLL serons appellée par Orbiter au bon moment. Vous gardez la souplesse du C++ et pouvez definir vos propre fonctions en plus.


Les fonctions callbacks

Les premieres fonctions sont des "callback" et commencent toutes par "clbk" elle sont appellée par orbiter à des moments très précis. La seul qui est obligatoire c'est clbkSetClassCap pour l'initialisation de votre vessel, après c'est a vous de voir si votre vaisseau en necessite d'autres. Il en existe une petite trentaines dans orbiter.

Quelques Exemple pour bien comprendre le principe des callback:

clbkSetClassCap appellée quand un vaisseau doit etre initialisé dans Orbiter, ici vous definissez les
caracteristiques de votre vaisseau, taille, poid, inertie, moteurs, carburant, point de contact au sol, mesh à utiliser et
bien d'autre choses, vous pouvez aussi y initialisé vos propre trucs, variables etc etc.

clbkDockEvent appellée quand votre vaisseau ce dock ou s'undock d'un autre, ici vous allez traiter les
fonctionnalité de docking, son à jouer, animations, endommagement du sas et mort de l'équipage si il était ouvert etc etc.

clbkConsumeBufferedKey appellée quand l'utilisateur tape une touche de son clavier, la touche est passée en
parametre et vous permet de l'intercepter pour ajouter des fonctionnalités, exemple si "V" doit ouvrir le cockpit par
exemple.

clbkPostStep celle la est appellée à chaque image, c'est ici que vous definirez tout ce qui ce passe de
dynamique dans votre vessel, comme l'animation du train,un pilote auto qui controle les moteurs, gestion des systeme électrique, refueling, bref , tout ce qui "bouge" et varie en fonction du temps ce fait ici. (vous pouvez meme incrementer l'age de votre equipage en fonction de la date si vous voulez ;) )

clbkLoadStateEx et clbkSaveState la première est appellée quand Orbiter charge un scenario et la
deuxieme quand il le sauve (on quitte orbiter) important pour sauver vos valeurs, si le gars avait ouvert le cockpit
vous aimeriez bien que quand il relance le scenario le cockpit soit toujours ouvert, ca ce fait ici.

Pour une liste et une explication de tout les callback voir la doc PDF API_Reference.pdf (section 12.1 VESSEL2)
Vous trouvez aussi la liste dans le fichier header de la SDK "VesselApi.h" (j'aime bien regarder dedans pour la liste C++ "brut" et switcher avec la doc pour plus de détails)

Pour un usage pratique faite une recherche dans les exemples de la SDK ca peut aider.


Les autres fonctions de la SDK

Elle ce comptent par dizaine et elle vous permettent d'interagir avec votre vaisseaux. Vous avez besoin de savoir a quel altitude vous ête ? appelez "GetAltitude()" la valeur retournée sera votre altitude. Puissance des moteurs, niveau de carburant, position de la caméra, valeurs orbitale, nombre de vessel dans le scenario, liste des vessel, nom de la planete ou vous orbitez, carburant, poids, mesh et pleins d'autres fonctions sont disponible.

Pour une liste et une explication de toute les fonctions voir la doc PDF API_Reference.pdf Vous trouvez aussi la liste de toutes les fonctions dans les fichier header de la SDK "OrbiterAPi.h" et VesselApi.h"

Of course regarder les exemples pour utilisation pratique c'est pas mal.


Et quand j'ai plusieurs vaisseaux ca ce passe comment ?

Bonne question, vous aviez une variable "train_attero" qui garde l'etat du train, il est à zéro (rentré) et maintenant si vous avez un deuxieme vessel avec le train ouvert il vont ce battre pour avoir cette variable ?

Non ! et ceci grace à "la programation orienté objet (OO) avec heritance subaugmentée du yogourt bulgare"  :badsmile:

En bref on s'en fout un peu du nom. Il suffit de savoir que toutes vos fonctions, variables ressources sont contenue dans une classe C++. Une classe c'est en gros une "boite" ou vous fourrez tous vos truc spécific à un objet (un vessel) et que personne d'autre ne peut toucher à pars l'objet en question. (a moins de le specifiez explicitement C++ est d'une souplesse incroyable)

Vous ne definissez qu'une classe pour votre vessel, Orbiter lui va creer autant d'instance de cette classe en mémoire
(copie de votre boite) que le scenario aura de vessels, donc votre variable "train_attero" sera deux fois
en mémoire à des endroit différents chacune dans une copie de la boite et évoluera independament des autres instances.

Comme le C++ est hyper souple rien ne vous oblige à declarer vos variable dans cette classe , du coup elle deviendraient globale (commune a tout vos vessel) et effectivement la il y aurais combat entre vos vessels et arrachage de cheveux en perspective. C'est une erreur de débutant.

Je ne vais pas rentrer dans les détails mais une classe ce défini dans un fichier "header" de déclaration
exemple pour le shuttlePB:

Code: [Select]
int UneFonctionGlobale();  //NON dans la plupart des cas
int UneVariableGlobale;     //NON dans la plupart des cas

class ShuttlePB: public VESSEL2 {
   public:
   int MaVariableAMoi;
   int MaFonctionAMoi();
}

Votre classe (boite) s'appelle "ShuttlePB", tout le monde peut acceder a "UneVariableGlobale" mais seulement les fonctions membre de votre classe *et de la même instance* (copie) peuvent acceder a "MaVariableAMoi"

Dans votre source *.cpp votre fonction MaFonctionAMoi() à cette gueule la:
Code: [Select]
int SHuttlePB::MaFonctionAMoi(void)
{
  MaVariableAMoi=1;   //JUSTE
}
"ShuttlePB::" indique quelle est "membre" de la classe "ShuttlePB". Comme les callback sont déclaré aussi dans votre  classe Orbiter appelera autant de fois les callback qu'il y a de vaisseaux. (2 fois clbkSetClassCap si deux vessel etc etc)

IMPORTANT: les variables de classes ne sont pas initialisée automatiquement au démarrage elle ont un etat "indéfini" donc si vous ne faite rien "train_attero" peut très bien avoir la valeur -187624876.67543, il est IMPORTANT de les initialiser dans clbkSetClassCap()

REGLE: Une declaration de variable dans la classe = une initialisation dans clbkSetClassCap

Code: [Select]
class ShuttlePB: public VESSEL2 {
   public:
   double train_attero;
}

int SHuttlePB::clbkSetClassCap()
{
  train_attero=1;   //Train sorti par defaut
}

C'est d'autant plus vicieux qu'en mode debug, les variables sont mise a zéro, tout marche bien, vous avez passé 6 mois sur votre addon, vous passez en release et la avec un train d'atterissage à -1873435.87345 ca va rien donner de génial.



Message modifié ( 26-06-2007 12:53 )

« Last Edit: 26 June 2007, 03:43:44 by DanSteph »

Offline DanSteph

  • Administrator
  • Legend
  • *****
  • Posts: 15002
  • Karma: 178
  • Hein, quoi !?
    • FsPassengers
Reply #1 - 26 June 2007, 03:43:44

Cliquez le lien ci-dessous pour retourner au sommaire des "tutorials pour créer une DLL Orbiter"
http://orbiter.dansteph.com/forum/index.php?topic=6335.msg95352#msg95352




Message modifié ( 26-06-2007 13:01 )

« Last Edit: 26 June 2007, 03:43:44 by DanSteph »