0 Members and 1 Guest are viewing this topic.
// transformation des valeurs en pourcentagePOxygen=(GetPropellantMass(&oxygentank)*100)/2000; //2000 représente la masse maximum en ressources du réservoir.PFood=(GetPropellantMass(&foodtank)*100)/2000;PFuel=(GetPropellantMass(&maintank)*100)/2000;sprintf(SendRessourcesHudMessage(),"O2 Level = %i food level = %i fuel level = %i",POxygen,PFood,PFuel);
// propellant resourcesmaintank = CreatePropellantResource (PB_FUELMASS);foodtank = CreatePropellantResource (PB_FOODMASS);oxygentank = CreatePropellantResource (PB_OXYGENMASS);
POxygen=0;PFood=0;PFuel=0;
double POxygen;double PFood;double PFuel;
Jim Lovell a écrit:Je vais peut-être dire une bêtise, mais tu mais des %i dans ton sprintf, or tu initialises des double...Je n'ai jamais été bon dans toutes ces histoires de casting mais est-ce que ça pourrait être une piste ?
sprintf(SendRessourcesHudMessage(),"O2 Level = %d food level = %d fuel level = %d",POxygen,PFood,PFuel);
sprintf(SendRessourcesHudMessage(),"O2 Level = %f food level = %f fuel level = %f",POxygen,PFood,PFuel);
sprintf(SendRessourcesHudMessage(),"O2 Level = %.0f food level = %.0f fuel level = %.0f",POxygen,PFood,PFuel);
double dPOxygen; // 'd'= doublefloat fPOxygen; // 'f'= floatint iPoxygen; // 'i'= integerchar cPoxygen[25]; // 'c'= char
// pas de bol, le premier est bool le deuxième est char et encore celle-là n'est pas vicieuse // car tu aurais une erreur compilateur. Alors que d'autres...if(ValeurCheveux==ValeurArrache) // tu l'aurais vu tout de suite avecif(bValeurCheveux==cValeurArrache)
fPOxygen=(GetPropellantMass(&oxygentank)*100)/2000;fPFood=(GetPropellantMass(&foodtank)*100)/2000;fPFuel=(GetPropellantMass(&maintank)*100)/2000;sprintf(SendRessourcesHudMessage(),"O2 Level %.2f food level %.2f fuel level %.2f",fPOxygen,fPFood,fPFuel);
float fPOxygen;float fPFood;float fPFuel;
dPOxygen=(GetPropellantMass(&oxygentank)*100)/2000;dPFood=(GetPropellantMass(&foodtank)*100)/2000;dPFuel=(GetPropellantMass(&maintank)*100)/2000;sprintf(SendRessourcesHudMessage(),"O2 Level %.2f food level %.2f fuel level %.2f",dPOxygen,dPFood,dPFuel);
double dPOxygen;double dPFood;double dPFuel;
1>------ Début de la génération : Projet : supplymodule, Configuration : Debug Win32 ------1> supplymodule.cpp1>C:\Program Files\MSBuild\Microsoft.Cpp\v4.0\Microsoft.CppBuild.targets(990,5): warning MSB8012: TargetPath(H:\programmes\orbiter\Orbitersdk\samples\Supplymodule\Debug\supplymodule.dll) ne correspond pas à la valeur de la propriété OutputFile (H:\programmes\orbiter\Modules\supplymodule.dll) de Linker. Cela peut entraîner une génération incorrecte de votre projet. Pour corriger ce problème, vérifiez que les valeurs des propriétés $(OutDir), $(TargetName) et $(TargetExt) correspondent à la valeur spécifiée dans %(Link.OutputFile).1> Création de la bibliothèque Debug\supplymodule.lib et de l'objet Debug\supplymodule.exp1>LINK : warning LNK4098: conflit entre la bibliothèque par défaut 'LIBCMT' et les autres bibliothèques ; utilisez /NODEFAULTLIB:library1> SDbase.vcxproj -> H:\programmes\orbiter\Orbitersdk\samples\Supplymodule\Debug\supplymodule.dll========== Génération : 1 a réussi, 0 a échoué, 0 mis à jour, 0 a été ignoré ==========
// ==============================================================// ORBITER MODULE: HST// Part of the ORBITER SDK// Copyright (C) 2001-2007 Martin Schweiger// All rights reserved//// HST.cpp// HST basic specs and animations//// HST mesh and textures by David Sundstrom// ==============================================================#define ORBITER_MODULE#include "supplymodule.h"#include <stdio.h>#include "UmmuSDK.h"// ==============================================================// HST class implementation// ==============================================================// --------------------------------------------------------------// Constructor// --------------------------------------------------------------supplymodule::supplymodule (OBJHANDLE hObj, int fmodel): VESSEL2 (hObj, fmodel){ ant_proc = 0.0; ant_status = DOOR_CLOSED; hatch_proc = 0.0; hatch_status = DOOR_CLOSED; array_proc = 1.0; array_status = DOOR_OPEN; arrayrot_proc = 1.0; arrayrot_status = DOOR_OPEN; DefineAnimations ();}// --------------------------------------------------------------// Define animation sequences for moving parts// --------------------------------------------------------------void supplymodule::DefineAnimations (void){ // 1. Hi-gain antenna //static UINT HiGainAnt1Grp[5] = {48,49,50,51,52}; //static MGROUP_ROTATE HiGainAnt1 (0, HiGainAnt1Grp, 5, _V(-2.75,0,-5), _V(0, 1,0), (float)(-PI*0.5)); //static UINT HiGainAnt2Grp[2] = {0,2}; //static MGROUP_ROTATE HiGainAnt2 (0, HiGainAnt2Grp, 2, _V(0.002740,-2.013091,0.238118), _V(1,0,0), (float)(PI*0.51)); //anim_ant = CreateAnimation (0.0196); //AddAnimationComponent (anim_ant, 0, 1, &HiGainAnt1); //AddAnimationComponent (anim_ant, 0, 1, &HiGainAnt2); // 2. Main telescope hatch //static UINT HatchGrp[5] = {48,49,50,51,52}; //static MGROUP_ROTATE Hatch (0, HatchGrp, 5, _V(-2.75,0,-5), _V(0, 1,0), (float)(-PI)); //anim_hatch = CreateAnimation (5); //AddAnimationComponent (anim_hatch, 0, 1, &Hatch); // 3. Solar arrays - folding anim_array = CreateAnimation (4); static UINT ArrayLFoldGrp[3] = {5,71,72}; static UINT ArrayRFoldGrp[3] = {7,75,76}; static UINT ArrayTFoldGrp[3] = {8,77,78}; static UINT ArrayBFoldGrp[3] = {6,73,74}; static MGROUP_ROTATE ArrayLFold1 (0, ArrayLFoldGrp, 3, _V(-2.915,0, 2.315), _V(0, 1,0), (float)(-PI*0.5)); AddAnimationComponent (anim_array, 0, 1, &ArrayLFold1); static MGROUP_ROTATE ArrayRFold2 (0, ArrayRFoldGrp, 3, _V( 2.915,0, 2.315), _V(0, 1,0), (float)(PI*0.5)); AddAnimationComponent (anim_array, 0, 1, &ArrayRFold2); //static MGROUP_SCALE ArrayTFoldGrp1 (0, ArrayLFoldGrp, 4, _V(0,0.053583,1.429349), _V(1,1,4)); //AddAnimationComponent (anim_array, 0.6, 1, &ArrayLFold3); static MGROUP_ROTATE ArrayTFold1 (0, ArrayTFoldGrp, 3, _V(0, 2.915,2.315), _V( 1,0,0), (float)(-PI*0.5)); AddAnimationComponent (anim_array, 0, 1, &ArrayTFold1); static MGROUP_ROTATE ArrayBFold1 (0, ArrayBFoldGrp, 3, _V(0,-2.915,2.315), _V( 1,0,0), (float)(PI*0.5)); AddAnimationComponent (anim_array, 0, 1, &ArrayBFold1); //static MGROUP_SCALE ArrayRFold3 (0, ArrayRFoldGrp, 4, _V(0,0.053583,1.429349), _V(1,1,4)); //AddAnimationComponent (anim_array, 0.6, 1, &ArrayRFold3); // 3. Solar arrays rotation - folding anim_arrayrot = CreateAnimation (5); static UINT ArrayrotLFoldGrp[5] = {68,73,74,75,76}; static UINT ArrayrotRFoldGrp[5] = {67,69,70,71,72}; static MGROUP_ROTATE ArrayrotLFold1 (0, ArrayrotLFoldGrp, 5, _V(-2.65,0,-2.85), _V(0, 1,0), (float)(PI*0.5)); AddAnimationComponent (anim_arrayrot, 0, 1, &ArrayrotLFold1); static MGROUP_ROTATE ArrayrotRFold1 (0, ArrayrotRFoldGrp, 5, _V( 2.65,0,-2.85), _V(0, 1,0), (float)(-PI*0.5)); AddAnimationComponent (anim_arrayrot, 0, 1, &ArrayrotRFold1); //static MGROUP_SCALE ArrayLFold3 (0, ArrayLFoldGrp, 4, _V(0,0.053583,1.429349), _V(1,1,4)); //AddAnimationComponent (anim_array, 0.6, 1, &ArrayLFold3); //static MGROUP_ROTATE ArrayRFold1 (0, ArrayRFoldGrp, 5, _V( 1.9, 0.053583,1.429349), _V(0, 1,0), (float)(PI*0.5)); //AddAnimationComponent (anim_array, 0, 0.4, &ArrayRFold1); //static MGROUP_ROTATE ArrayRFold2 (0, ArrayRFoldGrp, 5, _V(0,0.053583,1.429349), _V(-1,0,0), (float)(PI*0.5)); //AddAnimationComponent (anim_array, 0.4, 0.6, &ArrayRFold2); //static MGROUP_SCALE ArrayRFold3 (0, ArrayRFoldGrp, 4, _V(0,0.053583,1.429349), _V(1,1,4)); //AddAnimationComponent (anim_array, 0.6, 1, &ArrayRFold3);}//void supplymodule::ActivateAntenna (DoorStatus action)//{// ant_status = action;//}//void SDSFT::RevertAntenna (void)//{// ActivateAntenna ((ant_status == DOOR_CLOSED || ant_status == DOOR_CLOSING) ?// DOOR_OPENING : DOOR_CLOSING);//}//void supplymodule::ActivateHatch (DoorStatus action)//{// hatch_status = action;//}//void supplymodule::RevertHatch (void)//{// ActivateHatch ((hatch_status == DOOR_CLOSED || hatch_status == DOOR_CLOSING) ?// DOOR_OPENING : DOOR_CLOSING);//}void supplymodule::ActivateArray (DoorStatus action){ array_status = action;}void supplymodule::RevertArray (void){ ActivateArray ((array_status == DOOR_CLOSED || array_status == DOOR_CLOSING) ? DOOR_OPENING : DOOR_CLOSING);}void supplymodule::ActivateArrayrot (DoorStatus action){ arrayrot_status = action;}void supplymodule::RevertArrayrot (void){ ActivateArrayrot ((arrayrot_status == DOOR_CLOSED || arrayrot_status == DOOR_CLOSING) ? DOOR_OPENING : DOOR_CLOSING);}// ==============================================================// Overloaded callback functions// ==============================================================// --------------------------------------------------------------// Set vessel class parameters// --------------------------------------------------------------void supplymodule::clbkSetClassCaps (FILEHANDLE cfg){ // my variables TRessources=0; dPOxygen=0; dPFood=0; dPFuel=0; iUpdatetankstatus=0; THRUSTER_HANDLE th_main[8], th_rcs[24], th_group[4]; //THRUSTER_HANDLE th_main[2], th_hover, th_rcs[14], th_group[4]; SetSize (PB_SIZE); SetEmptyMass (PB_EMPTYMASS); SetPMI (PB_PMI); SetCrossSections (PB_CS); SetRotDrag (PB_RD); // docking port definitions //SetDockParams (PB_DOCK_POS, PB_DOCK_DIR, PB_DOCK_ROT); //SetDockParams (PB_DOCK2_POS, PB_DOCK2_DIR, PB_DOCK2_ROT); Dock0 = CreateDock(_V(0,0,4.7),_V(0,0,1),_V(0,1,0)); Dock1 = CreateDock(_V(0,0,-4.7),_V(0,0,-1),_V(0,1,0)); Dock2 = CreateDock(_V(2.7,0,0),_V(1,0,0),_V(0,1,0)); Dock3 = CreateDock(_V(-2.7,0,0),_V(-1,0,0),_V(0,1,0)); // propellant resources //PROPELLANT_HANDLE hpr = CreatePropellantResource (PB_FUELMASS); maintank = CreatePropellantResource (PB_FUELMASS); foodtank = CreatePropellantResource (PB_FOODMASS); oxygentank = CreatePropellantResource (PB_OXYGENMASS); // main engine th_main[0] = CreateThruster (_V(0, 2.5,-3.4), _V(0,0,1), PB_MAXMAINTH, maintank, PB_ISP); th_main[1] = CreateThruster (_V(0,-2.5,-3.4), _V(0,0,1), PB_MAXMAINTH, maintank, PB_ISP); th_main[2] = CreateThruster (_V( 2.5,0,-3.4), _V(0,0,1), PB_MAXMAINTH, maintank, PB_ISP); th_main[3] = CreateThruster (_V(-2.5,0,-3.4), _V(0,0,1), PB_MAXMAINTH, maintank, PB_ISP); th_main[4] = CreateThruster (_V( 1.8, 1.8,-3.4), _V(0,0,1), PB_MAXMAINTH, maintank, PB_ISP); th_main[5] = CreateThruster (_V(-1.8,-1.8,-3.4), _V(0,0,1), PB_MAXMAINTH, maintank, PB_ISP); th_main[6] = CreateThruster (_V(-1.8, 1.8,-3.4), _V(0,0,1), PB_MAXMAINTH, maintank, PB_ISP); th_main[7] = CreateThruster (_V( 1.8,-1.8,-3.4), _V(0,0,1), PB_MAXMAINTH, maintank, PB_ISP); th_group[0] = th_main[0]; CreateThrusterGroup (th_main, 8, THGROUP_MAIN); AddExhaust (th_main[0], 0.4, 0.2, _V(0, 2.5,-3.45), _V(0,0,-1)); AddExhaust (th_main[1], 0.4, 0.2, _V(0,-2.5,-3.45), _V(0,0,-1)); AddExhaust (th_main[2], 0.4, 0.2, _V( 2.5,0,-3.45), _V(0,0,-1)); AddExhaust (th_main[3], 0.4, 0.2, _V(-2.5,0,-3.45), _V(0,0,-1)); AddExhaust (th_main[0], 0.4, 0.2, _V( 1.8, 1.8,-3.45), _V(0,0,-1)); AddExhaust (th_main[0], 0.4, 0.2, _V(-1.8,-1.8,-3.45), _V(0,0,-1)); AddExhaust (th_main[0], 0.4, 0.2, _V(-1.8, 1.8,-3.45), _V(0,0,-1)); AddExhaust (th_main[0], 0.4, 0.2, _V( 1.8,-1.8,-3.45), _V(0,0,-1)); PARTICLESTREAMSPEC contrail_main = { 0, 5.0, 16, 200, 0.15, 1.0, 5, 3.0, PARTICLESTREAMSPEC::DIFFUSE, PARTICLESTREAMSPEC::LVL_PSQRT, 0, 2, PARTICLESTREAMSPEC::ATM_PLOG, 1e-4, 1 }; PARTICLESTREAMSPEC exhaust_main = { 0, 2.0, 20, 200, 0.05, 0.1, 8, 1.0, PARTICLESTREAMSPEC::EMISSIVE, PARTICLESTREAMSPEC::LVL_SQRT, 0, 1, PARTICLESTREAMSPEC::ATM_PLOG, 1e-5, 0.1 }; AddExhaustStream (th_main, _V(0,0.3,-10), &contrail_main); AddExhaustStream (th_main, _V(0,0.3,-5.8), &exhaust_main); // hover engine //th_hover = CreateThruster (_V(0,-1.5,0), _V(0,1,0), PB_MAXHOVERTH, hpr, PB_ISP); //CreateThrusterGroup (&th_hover, 1, THGROUP_HOVER); //AddExhaust (th_hover, 8, 1, _V(0,-1.5,1), _V(0,-1,0)); //AddExhaust (th_hover, 8, 1, _V(0,-1.5,-1), _V(0,-1,0)); //PARTICLESTREAMSPEC contrail_hover = { // 0, 5.0, 8, 200, 0.15, 1.0, 5, 3.0, PARTICLESTREAMSPEC::DIFFUSE, // PARTICLESTREAMSPEC::LVL_PSQRT, 0, 2, // PARTICLESTREAMSPEC::ATM_PLOG, 1e-4, 1 //}; //PARTICLESTREAMSPEC exhaust_hover = { // 0, 2.0, 10, 200, 0.05, 0.05, 8, 1.0, PARTICLESTREAMSPEC::EMISSIVE, // PARTICLESTREAMSPEC::LVL_SQRT, 0, 1, // PARTICLESTREAMSPEC::ATM_PLOG, 1e-5, 0.1 //}; //AddExhaustStream (th_hover, _V(0,-3, 1), &contrail_hover); //AddExhaustStream (th_hover, _V(0,-3,-1), &contrail_hover); //AddExhaustStream (th_hover, _V(0,-2, 1), &exhaust_hover); //AddExhaustStream (th_hover, _V(0,-2,-1), &exhaust_hover); // RCS engines th_rcs[ 0] = CreateThruster (_V(-2.5, 0.2,-3.4), _V(0,-1,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[ 1] = CreateThruster (_V(-2.5, 0.2, 3.4), _V(0,-1,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[ 2] = CreateThruster (_V( 2.5, 0.2,-3.4), _V(0,-1,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[ 3] = CreateThruster (_V( 2.5, 0.2, 3.4), _V(0,-1,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[ 4] = CreateThruster (_V(-2.5,-0.2,-3.4), _V(0, 1,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[ 5] = CreateThruster (_V(-2.5,-0.2, 3.4), _V(0, 1,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[ 6] = CreateThruster (_V( 2.5,-0.2,-3.4), _V(0, 1,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[ 7] = CreateThruster (_V( 2.5,-0.2, 3.4), _V(0, 1,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[ 8] = CreateThruster (_V(0, 2.5, 3.4), _V(0,0,-1), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[ 9] = CreateThruster (_V(0,-2.5, 3.4), _V(0,0,-1), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[10] = CreateThruster (_V(-0.2, 2.5, 3.4), _V( 1,0,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[11] = CreateThruster (_V( 0.2, 2.5, 3.4), _V(-1,0,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[12] = CreateThruster (_V(-0.2,-2.5,-3.4), _V( 1,0,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[13] = CreateThruster (_V( 0.2,-2.5,-3.4), _V(-1,0,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[14] = CreateThruster (_V(-2.5,0,-3.4), _V(0,0, 1), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[15] = CreateThruster (_V(-2.5,0, 3.4), _V(0,0,-1), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[16] = CreateThruster (_V( 2.5,0, 3.4), _V(0,0,-1), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[17] = CreateThruster (_V( 2.5,0,-3.4), _V(0,0, 1), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[18] = CreateThruster (_V(0,-2.5,-3.4), _V(0,0, 1), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[19] = CreateThruster (_V(0, 2.5,-3.4), _V(0,0, 1), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[20] = CreateThruster (_V(-0.2, 2.5,-3.4), _V( 1,0,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[21] = CreateThruster (_V(-0.2,-2.5, 3.4), _V( 1,0,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[22] = CreateThruster (_V( 0.2, 2.5,-3.4), _V(-1,0,0), PB_MAXRCSTH, maintank, PB_ISP); th_rcs[23] = CreateThruster (_V( 0.2,-2.5, 3.4), _V(-1,0,0), PB_MAXRCSTH, maintank, PB_ISP); AddExhaust (th_rcs[ 0], 0.4, 0.2, _V(-2.5, 0.2,-3.15), _V(0,-1,0)); AddExhaust (th_rcs[ 1], 0.4, 0.2, _V(-2.5, 0.2, 3.15), _V(0,-1,0)); AddExhaust (th_rcs[ 2], 0.4, 0.2, _V( 2.5, 0.2,-3.15), _V(0,-1,0)); AddExhaust (th_rcs[ 3], 0.4, 0.2, _V( 2.5, 0.2, 3.15), _V(0,-1,0)); AddExhaust (th_rcs[ 4], 0.4, 0.2, _V(-2.5,-0.2,-3.15), _V(0, 1,0)); AddExhaust (th_rcs[ 5], 0.4, 0.2, _V(-2.5,-0.2, 3.15), _V(0, 1,0)); AddExhaust (th_rcs[ 6], 0.4, 0.2, _V( 2.5,-0.2,-3.15), _V(0, 1,0)); AddExhaust (th_rcs[ 7], 0.4, 0.2, _V( 2.5,-0.2, 3.15), _V(0, 1,0)); AddExhaust (th_rcs[ 8], 0.4, 0.2, _V(0, 2.5, 3.5), _V(0,0,-1)); AddExhaust (th_rcs[ 9], 0.4, 0.2, _V(0,-2.5, 3.5), _V(0,0,-1)); AddExhaust (th_rcs[10], 0.4, 0.2, _V(-0.2, 2.5, 3.15), _V(-1,0,0)); AddExhaust (th_rcs[11], 0.4, 0.2, _V( 0.2, 2.5, 3.15), _V( 1,0,0)); AddExhaust (th_rcs[12], 0.4, 0.2, _V(-0.2,-2.5,-3.15), _V(-1,0,0)); AddExhaust (th_rcs[13], 0.4, 0.2, _V( 0.2,-2.5,-3.15), _V( 1,0,0)); AddExhaust (th_rcs[14], 0.4, 0.2, _V(-2.5,0,-3.5), _V(0,0, 1)); AddExhaust (th_rcs[15], 0.4, 0.2, _V(-2.5,0, 3.5), _V(0,0,-1)); AddExhaust (th_rcs[16], 0.4, 0.2, _V( 2.5,0, 3.5), _V(0,0,-1)); AddExhaust (th_rcs[17], 0.4, 0.2, _V( 2.5,0,-3.5), _V(0,0, 1)); AddExhaust (th_rcs[18], 0.4, 0.2, _V(0,-2.5,-3.5), _V(0,0, 1)); AddExhaust (th_rcs[19], 0.4, 0.2, _V(0, 2.5,-3.5), _V(0,0, 1)); AddExhaust (th_rcs[20], 0.4, 0.2, _V(-0.2, 2.5,-3.15), _V(-1,0,0)); AddExhaust (th_rcs[21], 0.4, 0.2, _V(-0.2,-2.5, 3.15), _V(-1,0,0)); AddExhaust (th_rcs[22], 0.4, 0.2, _V( 0.2, 2.5,-3.15), _V( 1,0,0)); AddExhaust (th_rcs[23], 0.4, 0.2, _V( 0.2,-2.5, 3.15), _V( 1,0,0)); th_group[0] = th_rcs[0]; th_group[1] = th_rcs[2]; th_group[2] = th_rcs[5]; th_group[3] = th_rcs[7]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_PITCHUP); th_group[0] = th_rcs[1]; th_group[1] = th_rcs[3]; th_group[2] = th_rcs[4]; th_group[3] = th_rcs[6]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_PITCHDOWN); th_group[0] = th_rcs[0]; th_group[1] = th_rcs[1]; th_group[2] = th_rcs[6]; th_group[3] = th_rcs[7]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_BANKLEFT); th_group[0] = th_rcs[2]; th_group[1] = th_rcs[3]; th_group[2] = th_rcs[4]; th_group[3] = th_rcs[5]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_BANKRIGHT); th_group[0] = th_rcs[4]; th_group[1] = th_rcs[5]; th_group[2] = th_rcs[6]; th_group[3] = th_rcs[7]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_UP); th_group[0] = th_rcs[0]; th_group[1] = th_rcs[1]; th_group[2] = th_rcs[2]; th_group[3] = th_rcs[3]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_DOWN); th_group[0] = th_rcs[11]; th_group[1] = th_rcs[12]; th_group[2] = th_rcs[23]; th_group[3] = th_rcs[20]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_YAWLEFT); th_group[0] = th_rcs[10]; th_group[1] = th_rcs[13]; th_group[2] = th_rcs[21]; th_group[3] = th_rcs[22]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_YAWRIGHT); th_group[0] = th_rcs[11]; th_group[1] = th_rcs[13]; th_group[2] = th_rcs[22]; th_group[3] = th_rcs[23]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_LEFT); th_group[0] = th_rcs[10]; th_group[1] = th_rcs[12]; th_group[2] = th_rcs[20]; th_group[3] = th_rcs[21]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_RIGHT); th_group[0] = th_rcs[14]; th_group[1] = th_rcs[17]; th_group[2] = th_rcs[18]; th_group[3] = th_rcs[19]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_FORWARD); th_group[0] = th_rcs[8]; th_group[1] = th_rcs[9]; th_group[2] = th_rcs[15]; th_group[3] = th_rcs[16]; CreateThrusterGroup (th_group, 4, THGROUP_ATT_BACK); // camera parameters //SetCameraOffset (_V(0,2.4,3.9)); SetCameraOffset (_V(0,0,-1.6)); // associate a mesh for the visual //AddMesh ("SD_SFT"); SetMeshVisibilityMode (AddMesh (exmesh_tpl = oapiLoadMeshGlobal ("SD_Supplymodule")), MESHVIS_EXTERNAL); SetMeshVisibilityMode (AddMesh (vcmesh_tpl = oapiLoadMeshGlobal ("SD_SFT_VC")), MESHVIS_VC); //hOrbiterVCMesh = oapiLoadMeshGlobal ("SD_SFT_VC"); //-------------------------------------------------------------- // InitUmmu // initialisation of Ummu must be done first ! return of 1 mean OK // return of -999 mean Ummu addon is not installed in user's Orbiter, return of -1 // mean misc error. If error simply all function will fail silently // and there will be no MMu. It's a good idea to warn the user. // (see function "WarnUserUMMUNotInstalled" below) Crew.InitUmmu(GetHandle()); //-------------------------------------------------------------- //-------------------------------------------------------------- // GetUserUMmuVersion // this check wich version of UMmu addon the user have in his orbiter directory. // this may be usefull for future version with more function so you can check // if user installation support the new functions. Return -1 on error (not installed, version cannot be read) // or version number in float value (ie: 2.0="2.0" version etc etc) float UMmuVersion=Crew.GetUserUMmuVersion(); //-------------------------------------------------------------- // DefineAirLockShape // We set the airlock shape and state, this virtual box will be the one // into were a Ummu asking to reenter will be taken in account // first parameter is airlock door state (OPEN=TRUE) and other are X,X1,Y,Y1 and Z,Z1 // min and max coordinate for this virtual box (vessel local coordinate) // Pay attention to reenter when landed (if suitable) and make the box large enough so // it's not a pain for the user to find airlock's entry. (See PDF doc) Crew.DefineAirLockShape(TRUE,-1,1,-1,1,-6,-5); // Airlock open, 2 meter large 2 meter high 0.75 meter long (vessel local coordinate) //-------------------------------------------------------------- // SetMembersPositionOrientationOnEVA // We define here were the Ummu will appear when they make an EVA // first parameter is position second is orientation, take care not to make // them appear to high on ground (will fall and die) or to low (Orbiter "light speed" bug) Crew.SetMembersPosRotOnEVA(_V(0,0,-5.5),_V(0,0,0)); // 3 meters in front of ship (z) facing direction of ship (vessel local coordinate) //--------------------------------------------------------------- // finally set the maximum seat available in this ship, default is // 8 but it can go from 1 to 100 // BAD IDEA: using this to "close" your ship, use "SetAirlockDoorState" instead. Crew.SetMaxSeatAvailableInShip(5); //-------------------------------------------------------------- // AddCrewMember // We'll add four default members for when the ship is spawned by Orbiter's scenario editor. // parameters are name, age, cardiac pulse,weight (in kilogramm) and Function (Misc ID) // max four characters wich define the spacesuit used. (see UmmuMiscID in UMuSDK.h header) // Return 1 on success -1 on error (probably vessel full, name>25 char // age, pulse or weight out of realistic range or MiscID>4 char) //Crew.AddCrewMember("Peter Falcon",41,65,74,"Capt"); //(for name and id a-z A-Z 0-9 characters only) //Crew.AddCrewMember("Fanny Gorgeous",27,67,55,"Eng"); //(for name and id a-z A-Z 0-9 characters only) SelectedUmmuMember =0; // our current selected member // The HUD display method variables, see PDF doc cUmmuHudDisplay[0] =0; // Initialisation of UMmu hud char variable dHudMessageDelay =0; // Initialisation of UMmu delay variable strcpy(SendHudMessage(),"Welcome aboard ! E=EVA 1,2=select UMmu 3,4=select active dock A=(Q for azerty) Open/Close airlock S=info M (? for azerty)=add crew"); // The Add mmu without scenery editor variable see PDF doc cAddUMmuToVessel[0]=0; iActiveDockNumber=0; SetUMMUAirlockPos(); //UCGO 2.0 Initialisation, cargo slot pos, rot declaration hUcgo.Init(GetHandle()); hUcgo.DeclareCargoSlot(0,_V( 1.8, 1.8, 1.5),_V(0,0,-45)); // slot 0 hUcgo.DeclareCargoSlot(1,_V( 1.8, 1.8,0),_V(0,0,-45)); // slot 1 hUcgo.DeclareCargoSlot(2,_V( 1.8, 1.8,-1.5),_V(0,0,-45)); // slot 2 hUcgo.DeclareCargoSlot(3,_V(-1.8, 1.8, 1.5),_V(0,0,45)); // slot 3 hUcgo.DeclareCargoSlot(4,_V(-1.8, 1.8,0),_V(0,0,45)); // slot 4 hUcgo.DeclareCargoSlot(5,_V(-1.8, 1.8,-1.5),_V(0,0,45)); // slot 5 // UCGO 2.0 Parameters settings hUcgo.SetReleaseSpeedInSpace(0.001); // release speed of cargo in space in m/s hUcgo.SetMaxCargoMassAcceptable(8000.0); // max cargo mass in kg that your vessel can carry hUcgo.SetGrappleDistance(50); // grapple distance radius in meter from center of ship hUcgo.SetGlobalGroundReleasePos(_V(0,0,4));// global release position on ground // UCGO Variables initialisation cCargoHudDisplay[0]=0; // Cargo hud display char variable dCargHudMessageDelay=0; // Cargo hud display delay iSelectedCargo=-1; // for the selection of cargos (-1 mean "default" see header) // welcome message with keys for users strcpy(SendCargHudMessage(),"Cargo key: C/SHF+C = grapple/release, 9/SHF+9 = add cargo from disk, 8=infos on cargos"); strcpy(SendSandersHudMessage(),"Welcome in the Sanders aerospace supply module for space station Y to consume a fuel cargo, U to consume a Oxygen cargo, I to consume a Food cargo"); // ********************* beacon lights ********************** static VECTOR3 beacon1pos = {{2.6,0,3}}; static VECTOR3 beacon1col = {{1,1,0.4}}; { beacon1.shape = (BEACONSHAPE_STAR); beacon1.pos = &beacon1pos; beacon1.col = &beacon1col; beacon1.size = (0.2); beacon1.falloff = (1); beacon1.period = (0); beacon1.duration = (0.5); beacon1.tofs = (2); beacon1.active = false; AddBeacon (&beacon1); } static VECTOR3 beacon2pos = {{-2.6,0,3}}; static VECTOR3 beacon2col = {{1,1,0.4}}; { beacon2.shape = (BEACONSHAPE_STAR); beacon2.pos = &beacon2pos; beacon2.col = &beacon2col; beacon2.size = (0.2); beacon2.falloff = (1); beacon2.period = (0); beacon2.duration = (0.5); beacon2.tofs = (2); beacon2.active = false; AddBeacon (&beacon2); } static VECTOR3 beacon3pos = {{2.8,0,-3}}; static VECTOR3 beacon3col = {{1,1,0.4}}; { beacon3.shape = (BEACONSHAPE_STAR); beacon3.pos = &beacon3pos; beacon3.col = &beacon3col; beacon3.size = (0.2); beacon3.falloff = (1); beacon3.period = (0); beacon3.duration = (0.5); beacon3.tofs = (2); beacon3.active = false; AddBeacon (&beacon3); } static VECTOR3 beacon4pos = {{-2.8,0,-3}}; static VECTOR3 beacon4col = {{1,1,0.4}}; { beacon4.shape = (BEACONSHAPE_STAR); beacon4.pos = &beacon4pos; beacon4.col = &beacon4col; beacon4.size = (0.2); beacon4.falloff = (1); beacon4.period = (0); beacon4.duration = (0.5); beacon4.tofs = (2); beacon4.active = false; AddBeacon (&beacon4); } static VECTOR3 beacon5pos = {{0,-2.6,3}}; static VECTOR3 beacon5col = {{1,1,0.4}}; { beacon5.shape = (BEACONSHAPE_STAR); beacon5.pos = &beacon5pos; beacon5.col = &beacon5col; beacon5.size = (0.2); beacon5.falloff = (1); beacon5.period = (0); beacon5.duration = (0.5); beacon5.tofs = (2); beacon5.active = false; AddBeacon (&beacon5); } static VECTOR3 beacon6pos = {{0,2.6,3}}; static VECTOR3 beacon6col = {{1,1,0.4}}; { beacon6.shape = (BEACONSHAPE_STAR); beacon6.pos = &beacon6pos; beacon6.col = &beacon6col; beacon6.size = (0.2); beacon6.falloff = (1); beacon6.period = (0); beacon6.duration = (0.5); beacon6.tofs = (2); beacon6.active = false; AddBeacon (&beacon6); } static VECTOR3 beacon7pos = {{0,2.6,-3}}; static VECTOR3 beacon7col = {{1,1,0.4}}; { beacon7.shape = (BEACONSHAPE_STAR); beacon7.pos = &beacon7pos; beacon7.col = &beacon7col; beacon7.size = (0.2); beacon7.falloff = (1); beacon7.period = (0); beacon7.duration = (0.5); beacon7.tofs = (2); beacon7.active = false; AddBeacon (&beacon7); } static VECTOR3 beacon8pos = {{0,-2.6,-3}}; static VECTOR3 beacon8col = {{1,1,0.4}}; { beacon8.shape = (BEACONSHAPE_STAR); beacon8.pos = &beacon8pos; beacon8.col = &beacon8col; beacon8.size = (0.2); beacon8.falloff = (1); beacon8.period = (0); beacon8.duration = (0.5); beacon8.tofs = (2); beacon8.active = false; AddBeacon (&beacon8); }}// --------------------------------------------------------------// Read status from scenario file// --------------------------------------------------------------void supplymodule::clbkLoadStateEx (FILEHANDLE scn, void *vs){ char *line; while (oapiReadScenario_nextline (scn, line)) { if(Crew.LoadAllMembersFromOrbiterScenario(line)==TRUE) continue; if(hUcgo.LoadCargoFromScenario(line)==TRUE) // UCGO load cargo continue; //if (!_strnicmp (line, "ANT", 3)) { //sscanf (line+3, "%d%lf", &ant_status, &ant_proc); if (!_strnicmp (line, "FOLD", 4)) { sscanf (line+5, "%d%lf", &array_status, &array_proc); //} else if (!_strnicmp (line, "HATCH", 5)) { // sscanf (line+5, "%d%lf", &hatch_status, &hatch_proc); } else if (!_strnicmp (line, "ARROT", 5)) { sscanf (line+5, "%d%lf", &arrayrot_status, &arrayrot_proc); } else { ParseScenarioLineEx (line, vs); } } //SetAnimation (anim_ant, ant_proc); //SetAnimation (anim_hatch, hatch_proc); SetAnimation (anim_array, array_proc); SetAnimation (anim_arrayrot, arrayrot_proc);}// --------------------------------------------------------------// Save status to scenario file// --------------------------------------------------------------void supplymodule::clbkSaveState (FILEHANDLE scn){ char cbuf[256]; SaveDefaultState (scn); sprintf (cbuf, "%d %0.4f", ant_status, ant_proc); oapiWriteScenario_string (scn, "ANT", cbuf); sprintf (cbuf, "%d %0.4f", hatch_status, hatch_proc); oapiWriteScenario_string (scn, "HATCH", cbuf); sprintf (cbuf, "%d %0.4f", array_status, array_proc); oapiWriteScenario_string (scn, "FOLD", cbuf); sprintf (cbuf, "%d %0.4f", arrayrot_status, arrayrot_proc); oapiWriteScenario_string (scn, "ARROT", cbuf); // ORBITER, default vessel parameters SaveDefaultState (scn); // UMmu, this will save all our members of crew in scenario // as airlock state depend of your ship (you may have a real animated airlock) // it's your responsabilites to save and reload UMmu's airlock state. Crew.SaveAllMembersInOrbiterScenarios(scn); // Save UCGO 2.0 cargo in scenario hUcgo.SaveCargoToScenario(scn); //if (beacon1.active) { // sprintf (cbuf, "%d %d %d", beacon1.active); // oapiWriteScenario_string (scn, "LIGHTS", cbuf); // }}// --------------------------------------------------------------// Frame update// --------------------------------------------------------------void supplymodule::clbkPostStep (double simt, double simdt, double mjd){ // Animate hi-gain antenna //if (ant_status >= DOOR_CLOSING) { // double da = simdt * ANTENNA_OPERATING_SPEED; // if (ant_status == DOOR_CLOSING) { // if (ant_proc > 0.0) ant_proc = max (0.0, ant_proc-da); // else ant_status = DOOR_CLOSED; // } else { // if (ant_proc < 1.0) ant_proc = min (1.0, ant_proc+da); // else ant_status = DOOR_OPEN; // } // SetAnimation (anim_ant, ant_proc); //} // Animate main telescope hatch //if (hatch_status >= DOOR_CLOSING) { // double da = simdt * HATCH_OPERATING_SPEED; // if (hatch_status == DOOR_CLOSING) { // if (hatch_proc > 0.0) hatch_proc = max (0.0, hatch_proc-da); // else hatch_status = DOOR_CLOSED; // } else { // if (hatch_proc < 1.0) hatch_proc = min (1.0, hatch_proc+da); // else hatch_status = DOOR_OPEN; // } // SetAnimation (anim_hatch, hatch_proc); //} // Animate solar arrays if (array_status >= DOOR_CLOSING) { double da = simdt * ARRAY_OPERATING_SPEED; if (array_status == DOOR_CLOSING) { if (array_proc > 0.0) array_proc = max (0.0, array_proc-da); else array_status = DOOR_CLOSED; } else { if (array_proc < 1.0) array_proc = min (1.0, array_proc+da); else array_status = DOOR_OPEN; } SetAnimation (anim_array, array_proc); } //Animate solar arrays rotation if (arrayrot_status >= DOOR_CLOSING) { double da = simdt * ARRAYROT_OPERATING_SPEED; if (arrayrot_status == DOOR_CLOSING) { if (arrayrot_proc > 0.0) arrayrot_proc = max (0.0, arrayrot_proc-da); else arrayrot_status = DOOR_CLOSED; } else { if (arrayrot_proc < 1.0) arrayrot_proc = min (1.0, arrayrot_proc+da); else arrayrot_status = DOOR_OPEN; } SetAnimation (anim_arrayrot, arrayrot_proc); } //--------------------------------------------------------------------------- // ProcessUniversalMMu // Here the routine that detect if someone entered the ship (eva or transfer) // No need to manage anything here all is automatic, crew is added to your ship, ship's weight is updated, // and UMmu vessel is automatically deleted from Orbiter. You may just look the return // code to see if someone entered and display wathewer message on panel or other. // notice it's FPS friendly, function process only 4 time per second not each frame // and return immediately if airlock closed or no Ummu is detected in vincinity. int ReturnCode=Crew.ProcessUniversalMMu(); switch(ReturnCode) { case UMMU_TRANSFERED_TO_OUR_SHIP: sprintf(SendHudMessage(),"%s \"%s\" aged %i was transfered to our ship", Crew.GetCrewMiscIdByName(Crew.GetLastEnteredCrewName()),Crew.GetLastEnteredCrewName() ,Crew.GetCrewAgeByName(Crew.GetLastEnteredCrewName())); break; case UMMU_RETURNED_TO_OUR_SHIP: sprintf(SendHudMessage(),"%s \"%s\" aged %i entered into our ship", Crew.GetCrewMiscIdByName(Crew.GetLastEnteredCrewName()), Crew.GetLastEnteredCrewName(),Crew.GetCrewAgeByName(Crew.GetLastEnteredCrewName())); break; } //---------------------------------------------------------------------------- // SetCrewMemberPulseBySlotNumber // Now we will kill all our crew aboard if we crash on ground. First we test // if we have ground contact, then we check vertical speed and if it's more than // -3 m/s we kill all people aboard. Of course in your code you'll do that only // one time using a bool flag if(!bCrewAlreadyKilled) for example. Here we do it each // time step for code ease of read. //if(GroundContact()==TRUE) //{ // we check vertical speed //int I; //VECTOR3 vHorizonAirspeedVector={0}; //GetHorizonAirspeedVector (vHorizonAirspeedVector); //double VertSpeed =vHorizonAirspeedVector.y; //if(VertSpeed<-3) //{ // we touched ground with more than -3 m/s, sorry dude, time to kill you all :( //for(I=0;I<Crew.GetCrewTotalNumber();I++) //{ //Crew.SetCrewMemberPulseBySlotNumber(I,0); // set cardiac pulse to zero //} //strcpy(SendHudMessage(),"Oooh no ! Crash - All crew aboard killed"); //} // TIPS: the vertical speed is often reset to zero when there is ground contact // this may bug somewhat the death of your crew. // to have an accurate VertSpeed at touchdown I recommand to record it at very END // of timestep and use this "old" value. The next frame you'll have the vertspeed value // of *last frame* just before the crash (GroundContact). This ensure an accurate // verticalspeed value. (keep this value in your vessel class and don't forget to // initialize it at zero in setclasscap) //} //--------------------------------------------------------------------------- // WarnUserUMMUNotInstalled - IMPORTANT helper // Put here this function and users will be automatically warned if they don't have // UMMU installed or if it's outdated. Warning text duration is 20 seconds and text is: // [AddonName] require "Universal MMU" ver 2.0 or higher. Download at www.orbiter.dansteph.com (message countdown in seconds) // an additonal "your version of UMMU is outdated" is displayed the last 5 seconds if they have version lower than 2.0 Crew.WarnUserUMMUNotInstalled("supplymodule"); // At the very end of clbkPostStep or clbkPreStep hUcgo.WarnUserUCGONotInstalled("supplymodule"); // THIS IS FOR ADDING CREW SEE PDF doc "Allow user to add crew to your ship // without scenery editor" AddUMmuToVessel(); //double CrewN = Crew.GetCrewTotalNumber(); //double O2consumption = CrewN; //double O2lvl = GetPropellantMass(oxygentank); //double foodlvl = GetPropellantMass(foodtank); // Crew O2 consumption //if (GetPropellantMass(oxygentank) > 0) { //O2lvl = O2lvl-(O2consumption*(simdt*0.001)); //} //// Crew food consumption //if (GetPropellantMass(foodtank) > 0) { //foodlvl = foodlvl-(O2consumption*(simdt*0.001)); //} Data.dDynPressure =GetDynPressure(); // Pression dynamique if(iDetecteChangementSeconde!=(int)simt) { // le principe: simt donnée par la fonction contient le temp actuel de simulation en seconde // je le stock dans dDetecteChangementSeconde et je la compare a chaque image avec le temp // actuel, si pas egal une seconde c'est ecoulée j'incrémente de 1 dTempDeSimulationTotal. // comme dTempDeSimulationTotal est sauvée/rechargée du scenario elle affichera le temps // total de vol *avec ce scenario* (on pourrait faire un temp total de vol avec votre addon // en sauvant dans un fichier externe mais on va pas exagerer dans ce template.) TRessources++; iDetecteChangementSeconde=(int)simt; } double CrewN = Crew.GetCrewTotalNumber(); double O2consumption = CrewN; double O2lvl = GetPropellantMass(oxygentank); double O2lv2; double foodlvl = GetPropellantMass(foodtank); double foodlv2; int TRessources=(0); if (GetPropellantMass(oxygentank) > 0) { O2lv2 = O2lvl-(O2consumption*0.000008); SetPropellantMass (oxygentank,O2lv2); TRessources=0; } if (GetPropellantMass(foodtank) > 0) { foodlv2 = foodlvl-(O2consumption*0.00001); SetPropellantMass (foodtank,foodlv2); TRessources=0; } if (GetPropellantMass(oxygentank) < 0.000008) // can be o2 or temperature problem etc etc { int C=0; // sorry dude, time to kill you all :( for(C=0;C<Crew.GetCrewTotalNumber();C++) { Crew.SetCrewMemberPulseBySlotNumber(C,0); // set cardiac pulse to zero sprintf(SendHudMessage(),"Oxygen tank are empty, GAME OVER"); } } if (GetPropellantMass(foodtank) < 0.00001) // can be o2 or temperature problem etc etc { int C=0; // sorry dude, time to kill you all :( for(C=0;C<Crew.GetCrewTotalNumber();C++) { Crew.SetCrewMemberPulseBySlotNumber(C,0); // set cardiac pulse to zero sprintf(SendHudMessage(),"Food reserve are empty, GAME OVER"); } } if (Data.dDynPressure > 7000) // can be o2 or temperature problem etc etc { int C=0; // sorry dude, time to kill you all :( for(C=0;C<Crew.GetCrewTotalNumber();C++) { Crew.SetCrewMemberPulseBySlotNumber(C,0); // set cardiac pulse to zero sprintf(SendHudMessage(),"you tried a reentry with a space station and this is a failure : we can deduce that all crew are death"); } } dPOxygen=(GetPropellantMass(&oxygentank)*100)/2000; dPFood=(GetPropellantMass(&foodtank)*100)/2000; dPFuel=(GetPropellantMass(&maintank)*100)/2000; sprintf(SendRessourcesHudMessage(),"O2 Level = %.2f food level = %.2f fuel level = %.2f",dPOxygen,dPFood,dPFuel);}// --------------------------------------------------------------// Keyboard interface handler (buffered key events)// --------------------------------------------------------------int supplymodule::clbkConsumeBufferedKey (DWORD key, bool down, char *kstate){ if (!down) return 0; // only process keydown events //if (KEYMOD_CONTROL (kstate)) { else { switch (key) { //case OAPI_KEY_G: // deploy/retract antenna // RevertAntenna(); // return 1; //case OAPI_KEY_O: // open/close hatch // RevertHatch(); // return 1; //case OAPI_KEY_K: // open/fold solar arrays // RevertArray(); // return 1; case OAPI_KEY_O: // open/fold solar arrays rotation RevertArrayrot(); return 1; } //} //return 0; //--------------------------------------------------------------------------- // Ummu Key "E" perform the EVA of the selected member // // ADD REALISM: It's your responsabilities also to set ship's control accordingly to crew aboard. // If you want to disable control if no one is aboard have a look at "SetADCtrlMode()" // and "SetAttitudeMode()" functions of Orbiter. To disable thrusters set their fuel // ressource to NULL. if(key==OAPI_KEY_E&&!KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)) { // PERFORM THE EVA, first we get is name with "GetCrewNameBySlotNumber" then we perform EVA with "EvaCrewMember" int Returned=Crew.EvaCrewMember(Crew.GetCrewNameBySlotNumber(SelectedUmmuMember)); //we provide feedback to user (You can display a message on panel or wathewer) //here below all the return code possible: switch(Returned) { case TRANSFER_TO_DOCKED_SHIP_OK: sprintf(SendHudMessage(),"Transfer to docked ship Ok - %s transfered", Crew.GetLastEvaedCrewName());SelectedUmmuMember=0; break; case EVA_OK: sprintf(SendHudMessage(),"EVA OK - %s left the ship", Crew.GetLastEvaedCrewName());SelectedUmmuMember=0; break; case ERROR_NO_ONE_ON_BOARD: strcpy(SendHudMessage(),"Error, no one on board, unable to EVA"); break; case ERROR_AIRLOCK_CLOSED: strcpy(SendHudMessage(),"Error, airlock is closed, unable to EVA"); break; case ERROR_DOCKED_SHIP_HAVE_AIRLOCK_CLOSED: strcpy(SendHudMessage(),"Error, docked ship's airlock is closed, unable to transfer"); break; case ERROR_DOCKED_SHIP_IS_FULL: strcpy(SendHudMessage(),"Error, docked ship is already full transfer failed"); break; case ERROR_CREW_MEMBER_NOT_FOUND: strcpy(SendHudMessage(),"Error, no crew by this name in ship"); break; case ERROR_DOCKEDSHIP_DONOT_USE_UMMU: strcpy(SendHudMessage(),"Error, docked ship do not use UMmu 2.0, ask author to add it"); break; case ERROR_MISC_ERROR_EVAFAILED: strcpy(SendHudMessage(),"Misc error with UMMU install it again"); break; } return TRUE; } //--------------------------------------------------------------------------- // Ummu Key "1" Select next member This is just internal to the demo // you may do your own selection system by panel button, name etc etc //if(key==OAPI_KEY_1&&!KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)) //{ if(key==OAPI_KEY_1) { // we test there is someone aboard if(Crew.GetCrewTotalNumber()==0) { strcpy(SendHudMessage(),"Sorry no one aboard unable to select"); return 1; } //we test that we select existing member if(SelectedUmmuMember<Crew.GetCrewTotalNumber()-1) SelectedUmmuMember++; char * Name=Crew.GetCrewNameBySlotNumber(SelectedUmmuMember); sprintf(SendHudMessage(),"Slot %i %s \"%s\" aged %i Selected for EVA or Transfer, please press \"E\" to EVA", SelectedUmmuMember,Crew.GetCrewMiscIdBySlotNumber(SelectedUmmuMember), Name,Crew.GetCrewAgeBySlotNumber(SelectedUmmuMember)); return 1; } //--------------------------------------------------------------------------- // Ummu Key "2" Select previous member This is just internal to the demo //you may do your own selection system by panel button //if(key==OAPI_KEY_2&&!KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)) //{ if(key==OAPI_KEY_2) { // we test there is someone aboard if(Crew.GetCrewTotalNumber()==0) { strcpy(SendHudMessage(),"Sorry no one aboard unable to select"); return 1; } if(SelectedUmmuMember>0) SelectedUmmuMember--; char * Name=Crew.GetCrewNameBySlotNumber(SelectedUmmuMember); sprintf(SendHudMessage(),"Slot %i %s \"%s\" aged %i Selected for EVA or Transfer" ", please press \"E\" to EVA",SelectedUmmuMember, Crew.GetCrewMiscIdBySlotNumber(SelectedUmmuMember),Name, Crew.GetCrewAgeBySlotNumber(SelectedUmmuMember)); return 1; } //--------------------------------------------------------------------------- //Ummu Key "A" Switch the virtual UMMU airlock door on/off //if(key==OAPI_KEY_A&&!KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)) //{ if(key==OAPI_KEY_A) { //switch state Crew.SetAirlockDoorState(!Crew.GetAirlockDoorState()); //display state if(Crew.GetAirlockDoorState()==TRUE) strcpy(SendHudMessage(),"Airlock is now open"); else strcpy(SendHudMessage(),"Airlock is now closed"); return 1; } //--------------------------------------------------------------------------- //Get some infos Name of ship and total soul aboard if(key==OAPI_KEY_S) { sprintf(SendHudMessage(),"%i souls aboard ship %s, %i seats available", Crew.GetCrewTotalNumber(),GetName(),4-Crew.GetCrewTotalNumber()); return 1; } //--------------------------------------------------------------------------- //ADD some Fun, Eject the guy, No check of all return code here to keep listing small and clear. //Notice eject function doesn't check airlock state at all. //GOOD IDEA: Get the Object's handle after ejection with function "GetObjHandleOfLastEVACrew" //and add to it one very small tank, thruster and smoke, then fire thruster (see pilot ejection of DGIV) //BAD IDEA: Not testing the handle returned by "GetObjHandleOfLastEVACrew" before using may //cause a CTD if by any bad luck the pointer is invalid (handle==NULL) if(key==OAPI_KEY_ESCAPE&&!KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)) { if(Crew.EjectCrewMember(Crew.GetCrewNameBySlotNumber(SelectedUmmuMember))==EVA_OK) sprintf(SendHudMessage(),"%s EJECTED",Crew.GetLastEvaedCrewName()); SelectedUmmuMember=0; return 1; } //--------------------------------------------------------------------------- //Use a different Mesh (type "C" then EVA someone) //better idea is to use the new UMMU Id definition //look readme.txt in folder "config/UMMUIdConfig" if(key==OAPI_KEY_Z) { Crew.SetAlternateMeshToUseForEVASpacesuit("mmu"); // the stock mmu of orbiter located in "meshes/mmu.msh" strcpy(SendHudMessage(),"Mesh changed"); return 1; } //THIS IS FOR ADDING CREW SEE PDF doc "Allow user to add crew to your ship //without scenery editor" //if(key==OAPI_KEY_M&&!KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)) //{ if(key==OAPI_KEY_M) { AddUMmuToVessel(TRUE); } // change active dock if(key==OAPI_KEY_3) { if(iActiveDockNumber>0) iActiveDockNumber--; sprintf(SendHudMessage(),"Active dock number changed to: %i",iActiveDockNumber); SetUMMUAirlockPos(); return 1; } //--------------------------------------------------------------------------- // change active dock if(key==OAPI_KEY_4) { if(iActiveDockNumber<4) iActiveDockNumber++; sprintf(SendHudMessage(),"Active dock number changed to: %i",iActiveDockNumber); SetUMMUAirlockPos(); return 1; } // 9 key "select" one cargo on disk (cycle) //if(key==OAPI_KEY_9&&!KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)) //{ // sprintf(SendCargHudMessage(),"%s - selected",hUcgo.ScnEditor_SelectNextCargoAvailableOnDisk()); // return 1; //} // SHIFT+9 key "add last cargo selected by key 9" // If iSelectedCargo=-1 (default) add to the first free slot found //if(key==OAPI_KEY_9&&KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)) //{ // if(hUcgo.ScnEditor_AddLastSelectedCargoToSlot(iSelectedCargo)==TRUE) //{ // strcpy(SendCargHudMessage(),"Cargo added to ship"); //} // else //{ // if(iSelectedCargo<0) //{ // strcpy(SendCargHudMessage(),"Cargo not added (ship full or weight excess ?)"); //} // else //{ // strcpy(SendCargHudMessage(),"Cargo not added (slot full ship full or weight excess ?)"); //} //} // return 1;//} // "C" grapple cargo. If iSelectedCargo=-1 (default) add to the first free slot found if(key==OAPI_KEY_C&&!KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)) { int ReturnedCode=hUcgo.GrappleOneCargo(iSelectedCargo); // for return code list see function "GrappleOneCargo" in the header switch(ReturnedCode) { case 1: strcpy(SendCargHudMessage(),"Cargo grappled"); break; case 0: strcpy(SendCargHudMessage(),"No cargo in range"); break; case -1: strcpy(SendCargHudMessage(),"cargo exceed maximum mass"); break; case -2: strcpy(SendCargHudMessage(),"bad config, mesh not found or slot not declared"); break; case -3: strcpy(SendCargHudMessage(),"Can't grapple cargo, slot not empty"); break; case -4: strcpy(SendCargHudMessage(),"Can't grapple cargo,doors closed "); break; case -5: strcpy(SendCargHudMessage(),"Can't grapple cargo,Ship full"); break; default: strcpy(SendCargHudMessage(),"Misc error Unable to grapple cargo"); } return 1;} // SHIFT+C release cargo. If iSelectedCargo=-1 (default) release the first free slot foundif(key==OAPI_KEY_C&&KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)){if(hUcgo.ReleaseOneCargo(iSelectedCargo)!=FALSE){strcpy(SendCargHudMessage(),"Cargo released");}else{strcpy(SendCargHudMessage(),"Cargo not released (empty slot, no cargo aboard?)");}return 1;}// "8" show some info on cargoif(key==OAPI_KEY_8&&!KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate)){sprintf(SendCargHudMessage(),"%i cargos aboard. ""Total cargos weight: %.0fkg",hUcgo.GetNbrCargoLoaded(),hUcgo.GetCargoTotalMass());return 1;}//if(key==OAPI_KEY_7&&KEYMOD_SHIFT(kstate)&&!KEYMOD_CONTROL (kstate))////{//SetFuelMass (4000);//return 1;//} switch (key) case OAPI_KEY_0: {if (beacon1.active == true){beacon1.active = false;beacon2.active = false;beacon3.active = false;beacon4.active = false;beacon5.active = false;beacon6.active = false;beacon7.active = false;beacon8.active = false;}else{beacon1.active = true;//beacon[i].active = true;beacon2.active = true;beacon3.active = true;beacon4.active = true;beacon5.active = true;beacon6.active = true;beacon7.active = true;beacon8.active = true;}return true;}if(key==OAPI_KEY_Y) //refill fuel tank{ double dNeededFuel=PB_FUELMASS-GetPropellantMass (maintank); if(dNeededFuel<20) { strcpy(SendCargHudMessage(),"Fuel tanks almost full"); return 1; } double dEatenFuel=hUcgo.EatCloserFuelCargo(dNeededFuel); if(dEatenFuel<0) { strcpy(SendCargHudMessage(),"no fuel cargo found aboard or in vincinity"); return 1; } // refill SetPropellantMass (maintank,GetPropellantMass (maintank)+dEatenFuel); sprintf(SendCargHudMessage(),"%.2fkg of fuel added to tank",dEatenFuel); return 1;}if(key==OAPI_KEY_U) //refill O2 tank{ double dNeededoxygen=PB_OXYGENMASS-GetPropellantMass (oxygentank); if(dNeededoxygen<20) { strcpy(SendCargHudMessage(),"Oxygen tanks almost full"); return 1; } double dEatenOxygen=hUcgo.EatCloserOxygenCargo(dNeededoxygen); if(dEatenOxygen<0) { strcpy(SendCargHudMessage(),"no oxygen cargo found aboard or in vincinity"); return 1; } // refill SetPropellantMass (oxygentank,GetPropellantMass (oxygentank)+dNeededoxygen); sprintf(SendCargHudMessage(),"%.2fkg of oxygen added to tank",dNeededoxygen); return 1;}if(key==OAPI_KEY_I) //refill food tank{ double dNeededfood=PB_FOODMASS-GetPropellantMass (foodtank); if(dNeededfood<20) { strcpy(SendCargHudMessage(),"Oxygen tanks almost full"); return 1; } double dEatenfood=hUcgo.EatCloserCargoByType("food",dNeededfood); if(dEatenfood<0) { strcpy(SendCargHudMessage(),"no food cargo found aboard or in vincinity"); return 1; } // refill SetPropellantMass (foodtank,GetPropellantMass (foodtank)+dNeededfood); sprintf(SendCargHudMessage(),"%.2fkg of food added to tank",dNeededfood); return 1;}return 0; }}bool supplymodule::clbkLoadVC (int id){ id = 0; SetCameraDefaultDirection (_V(0,0,1)); oapiVCSetNeighbours (-1, 1, -1, 2); //InitPanel(-1);// VC is -1 return true;}// --------------------------------------------------------------// Respond to generic messages// --------------------------------------------------------------int supplymodule::clbkGeneric (int msgid, int prm, void *context){ switch (msgid) { case VMSG_LUAINTERPRETER: return Lua_InitInterpreter (context); case VMSG_LUAINSTANCE: return Lua_InitInstance (context); } return 0;}// --------------------------------------------------------------// Orbiter's HUD callback// used to display UMMU's message see PDF doc:// "Example of feedback method by HUD Display"// --------------------------------------------------------------void supplymodule::clbkDrawHUD (int mode, const HUDPAINTSPEC *hps, HDC hDC){ // draw the default HUD VESSEL2::clbkDrawHUD (mode, hps, hDC); // UMmu display messages if(dHudMessageDelay>0) { TextOut (hDC,5,hps->H/60*15,cUmmuHudDisplay,strlen(cUmmuHudDisplay)); dHudMessageDelay-=oapiGetSimStep(); if(dHudMessageDelay<0) dHudMessageDelay=0; } // UCGO display messages if(dCargHudMessageDelay>0) { TextOut (hDC,5,hps->H/60*13,cCargoHudDisplay,strlen(cCargoHudDisplay)); dCargHudMessageDelay-=oapiGetSimStep(); if(dCargHudMessageDelay<0) dCargHudMessageDelay=0; } // Sanders display messages if(dSandersHudMessageDelay>0) { TextOut (hDC,5,hps->H/60*11,cSandersHudDisplay,strlen(cSandersHudDisplay)); dSandersHudMessageDelay-=oapiGetSimStep(); if(dSandersHudMessageDelay<0) dSandersHudMessageDelay=0; } // Ressources display messages if(dRessourcesHudMessageDelay>0) { TextOut (hDC,5,hps->H/60*17,cRessourcesHudDisplay,strlen(cRessourcesHudDisplay)); dRessourcesHudMessageDelay-=oapiGetSimStep(); if(dRessourcesHudMessageDelay<0) dRessourcesHudMessageDelay=0; }}//------------------------------------------------------------------------------------------------------------------// UTILITY FONCTION - UTILITY FONCTION - UTILITY FONCTION - UTILITY FONCTION - UTILITY FONCTION//// This below is not mandatory for UMmu to run, anyway such functions can help you to implement UMmu// in your addon. A recommended read at least.////------------------------------------------------------------------------------------------------------------------///////////////////////////////////////////////////////////////////////////////////////////// USING HUD INTERFACE FOR FEEDBACK DISPLAY//// This method is explained in the PDF tutorial, now if you want to use another method// comment the "UMMU" display lines in clbkHudDraw above and use the char variable // "cUmmuHudDisplay" wich will contain all the messages of UMMU to display it on VC or panel. // No other change required in code.///////////////////////////////////////////////////////////////////////////////////////////char *supplymodule::SendHudMessage(){ dHudMessageDelay=15; return cUmmuHudDisplay;}////////////////////////////////////////////////////////// SendCargHudMessage////////////////////////////////////////////////////////char *supplymodule::SendCargHudMessage(void){ dCargHudMessageDelay=15; // 15 seconds display delay for msg return cCargoHudDisplay;}char *supplymodule::SendSandersHudMessage(void){ dSandersHudMessageDelay=15; // 15 seconds display delay for msg return cSandersHudDisplay;}char *supplymodule::SendRessourcesHudMessage(void){ dRessourcesHudMessageDelay=1; // 15 seconds display delay for msg return cRessourcesHudDisplay;}//-------------------------------------------------------------------------// THIS IS FOR ADDING CREW SEE PDF doc "Allow user to add crew to your ship // without scenery editor"bool UMmuCrewAddCallback(void *id, char *str, void *data){ if(strlen(str)<2||strlen(str)>38) return false; char *cPtr=(char*)data; if(*cPtr==2){*cPtr=3;strcpy(cPtr+2,str);} else if(*cPtr==4){*cPtr=5;strcpy(cPtr+42,str);} else if(*cPtr==6){*cPtr=7;strcpy(cPtr+82,str);}return true;}void supplymodule::AddUMmuToVessel(BOOL bStartAdding){ if(bStartAdding==FALSE&&cAddUMmuToVessel[0]==0) return; if(bStartAdding==TRUE){ int salut=sizeof(cAddUMmuToVessel); memset(cAddUMmuToVessel,0,sizeof(cAddUMmuToVessel)); cAddUMmuToVessel[0]=1; } else if(cAddUMmuToVessel[0]==1){ cAddUMmuToVessel[0]=2; oapiOpenInputBox ("Enter new crew's name (or escape)",UMmuCrewAddCallback,0,30,(void*)cAddUMmuToVessel); } else if(cAddUMmuToVessel[0]==3){ cAddUMmuToVessel[0]=4; oapiOpenInputBox ("Enter crew's age",UMmuCrewAddCallback,0,30,(void*)cAddUMmuToVessel); } else if(cAddUMmuToVessel[0]==5){ cAddUMmuToVessel[0]=6; oapiOpenInputBox ("Enter function (Capt,Sec,Vip,Sci,Doc,Tech,Crew,Pax)",UMmuCrewAddCallback,0,30,(void*)cAddUMmuToVessel); } else if(cAddUMmuToVessel[0]==7){ cAddUMmuToVessel[0]=0; int Age=max(5,min(100,atoi(&cAddUMmuToVessel[42]))); if(Crew.AddCrewMember(&cAddUMmuToVessel[2],Age,70,70,&cAddUMmuToVessel[82])==TRUE){ sprintf(SendHudMessage(),"Crew \"%s\" aged %i added to vessel",&cAddUMmuToVessel[2],Age); } else{ strcpy(SendHudMessage(),"ERROR: Crew not added (vessel full?)"); } }}// --------------------------------------------------------------// clbkVisualCreated// --------------------------------------------------------------void supplymodule::clbkVisualCreated (VISHANDLE vis, int refcount){hUcgo.SetUcgoVisual(vis); // must be called in clbkVisualCreated.}//double supplymodule::foodOxygenConsuption()//{// int TRessources=(0);// double CrewN = Crew.GetCrewTotalNumber();//// if (GetPropellantMass(oxygentank) > 0) {// if (TRessources=1) {// oxygentank = oxygentank-(0.008*CrewN);// }// }//}// END of "Allow user to add crew to your ship without scenery editor"//--///////////////////////////////////////////////////////////////////////////////////////////// SetUMMUAirlockPos - example with two dock///////////////////////////////////////////////////////////////////////////////////////////void supplymodule::SetUMMUAirlockPos(void){ int AirlockStatus=Crew.GetAirlockDoorState(); Crew.SetActiveDockForTransfer(iActiveDockNumber); switch(iActiveDockNumber) { case 0: Crew.DefineAirLockShape(AirlockStatus,-1,1,-1,1,-6,-5); Crew.SetMembersPosRotOnEVA(_V(0,0,-5.5),_V(0,0,0)); //definissez ici la position de la camera pour ce dock break; case 1: Crew.DefineAirLockShape(AirlockStatus,-1,1,-1,1,-6,-5); Crew.SetMembersPosRotOnEVA(_V(0,0,-5.5),_V(0,0,0)); //definissez ici la position de la camera pour ce dock break; case 2: Crew.DefineAirLockShape(AirlockStatus,-1,1,-1,1,-6,-5); Crew.SetMembersPosRotOnEVA(_V(0,0,-5.5),_V(0,0,0)); //definissez ici la position de la camera pour ce dock break; case 3: Crew.DefineAirLockShape(AirlockStatus,-1,1,-1,1,-6,-5); Crew.SetMembersPosRotOnEVA(_V(0,0,-5.5),_V(0,0,0)); //definissez ici la position de la camera pour ce dock break; }}// ==============================================================// API callback interface// ==============================================================// --------------------------------------------------------------// Vessel initialisation// --------------------------------------------------------------DLLCLBK VESSEL *ovcInit (OBJHANDLE hvessel, int flightmodel){ return new supplymodule (hvessel, flightmodel);}// --------------------------------------------------------------// Vessel cleanup// --------------------------------------------------------------DLLCLBK void ovcExit (VESSEL *vessel){ if (vessel) delete (supplymodule*)vessel;}
sprintf(SendRessourcesHudMessage(),"O2 Level = %.2f food level = %.2f fuel level = %.2f",(float)dPOxygen,(float)dPFood,(float)dPFuel);
dPOxygen=(GetPropellantMass(oxygentank)*100)/2000;dPFood=(GetPropellantMass(foodtank)*100)/2000;dPFuel=(GetPropellantMass(maintank)*100)/2000;sprintf(SendRessourcesHudMessage(),"O2 Level %.2f food level %.2f fuel level %.2f",dPOxygen,dPFood,dPFuel);
dPOxygen=(GetPropellantMass(oxygentank)*100.0)/2000.0;dPFood=(GetPropellantMass(foodtank)*100.0)/2000.0;dPFuel=(GetPropellantMass(maintank)*100.0)/2000.0;sprintf(SendRessourcesHudMessage(),"O2 Level %.2f food level %.2f fuel level %.2f",dPOxygen,dPFood,dPFuel);