• ORBITER-FORUM will be temporarily closed at 2026-07-23 18:00 UTC while we complete some OF maintenance tasks. The amount of downtime is expected to take up to one hour, but probably less.

Question Ranger (and other ships) from Interstellar?

Ok. On the Ranger we have 8 mfds. Not sure if mfd facing the x direction will work as far as the buttons go?

But I have 4 mfd facing the z direction. 3 of them work great. The 4th one though the sys buttom (Power, menu, Select) work. But not the function.

So I have been told I can write to the log the mouse click point to see if it is hitting the mouse. I guess I can also see if the mouse is slicking the fn buttons. Not sure how though?

Basically on our mfd code rather than a area we used the mesh.
Code:
	// COPILOT Right
	DefineMfdButtons(
		TEX_NEWRANGER17VC_MFD_DYNAMIC_05,
		AID_COPILOT_MFD_RIGHT_BTNS_FN, GRP_NEWRANGER17VC_COPILOT_MFD_RIGHT_BTNS_FN, buttonFnRect[MFD_COPILOT_RIGHT],
		AID_COPILOT_MFD_RIGHT_BTNS_SYS, GRP_NEWRANGER17VC_COPILOT_MFD_RIGHT_BTNS_SYS
		);


}

void ClassicMfd::DefineMfdButtons(
	UINT const texId,
	UINT const fuctionAreaId, UINT const functionGroupId, RECT const functionRect,
	UINT const sysAreaId, UINT const sysGroupId
	)
{
	SURFHANDLE const texDyn = oapiGetTextureHandle(meshhg_VC, texId);
	oapiVCRegisterArea(fuctionAreaId, functionRect, PANEL_REDRAW_USER, PANEL_MOUSE_LBDOWN | PANEL_MOUSE_LBPRESSED | PANEL_MOUSE_ONREPLAY, PANEL_MAP_NONE, texDyn);
	DefineStaticClickArea(oapiMeshGroup(meshhg_VC, functionGroupId), fuctionAreaId, true);

	oapiVCRegisterArea(sysAreaId, PANEL_REDRAW_NEVER, PANEL_MOUSE_LBDOWN | PANEL_MOUSE_ONREPLAY);
	DefineStaticClickArea(oapiMeshGroup(meshhg_VC, sysGroupId), sysAreaId, true);
}

static int get_font_height(HDC const hDC)
{
	TEXTMETRIC tm;
	if (GetTextMetrics(hDC, &tm))
	{
		return abs(tm.tmAscent);
	}

	return 5; // Wild, crazy guessing
}

void ClassicMfd::RedrawMFDButtons(SURFHANDLE const surf, int const mfd)
{
	int const btnWidth = buttonFnDim->width;
	int const btnHeight = buttonFnDim->height;
	RECT const draw_area = _R(0, 0, buttonFnRect[mfd].right - buttonFnRect[mfd].left, buttonFnRect[mfd].bottom - buttonFnRect[mfd].top);

	HDC const hDC = oapiGetDC(surf);

	SelectObject(hDC, buttonBrush);
	SetBkMode(hDC, OPAQUE);
	Rectangle(hDC, draw_area.left, draw_area.top, draw_area.right, draw_area.bottom);

	HFONT pFont = (HFONT)SelectObject(hDC, labelFont);
	SetTextColor(hDC, labelColor);
	SetTextAlign(hDC, TA_CENTER);
	int const half_font_height = get_font_height(hDC) / 2;

	char const * label;
	int const label_x_offset = (btnWidth / 2);
	int const label_y_offset = (btnHeight / 2) - buttonFnDim->marginHeight - half_font_height;
	for (int i = 0; i < 12; i++) {
		int const x = i / 6;
		int const y = i % 6;
		if (label = oapiMFDButtonLabel(mfd, i)) {
			int const xwidth = (x * btnWidth);
			int const yheight = (y * btnHeight);

			SelectObject(hDC, buttonLabelBrush);
			SetBkMode(hDC, OPAQUE);
			Rectangle(hDC,
				draw_area.left + xwidth + buttonFnDim->marginWidth,
				draw_area.top + yheight + buttonFnDim->marginHeight,
				draw_area.left + xwidth + btnWidth - buttonFnDim->marginWidth,
				draw_area.top + yheight + btnHeight - buttonFnDim->marginHeight
				);
			SetBkMode(hDC, TRANSPARENT);
			TextOut(hDC, draw_area.left + xwidth + label_x_offset, draw_area.top + yheight + label_y_offset, label, strlen(label));
		}
		else break;
	}

	SelectObject(hDC, pFont);
	oapiReleaseDC(surf, hDC);
}

void ClassicMfd::DefineStaticClickArea(MESHGROUP const * const gr, int const id, bool const rect, const VECTOR3& revert, const VECTOR3& maxShift)
{
	float minX, maxX, minY, maxY, minZ, maxZ, x, y, z;
	minX = minY = minZ = 1000.0f;
	maxX = maxY = maxZ = -1000.0f;
	for (DWORD i = 0; i < gr->nVtx; i++) {
		x = gr->Vtx[i].x;
		y = gr->Vtx[i].y;
		z = gr->Vtx[i].z;
		if (x < minX) minX = x;
		if (y < minY) minY = y;
		if (z < minZ) minZ = z;
		if (x > maxX) maxX = x + (float)maxShift.x;
		if (y > maxY) maxY = y + (float)maxShift.y;
		if (z > maxZ) maxZ = z + (float)maxShift.z;
	}
	if (rect) {
		VECTOR3 p1 = _V(revert.x > 0 ? maxX : minX, revert.y > 0 ? minY : maxY, revert.z > 0 ? minZ : maxZ);
		VECTOR3 p2 = _V(revert.x > 0 ? minX : maxX, revert.y > 0 ? minY : maxY, revert.z > 0 ? minZ : maxZ);
		VECTOR3 p3 = _V(revert.x > 0 ? maxX : minX, revert.y > 0 ? maxY : minY, revert.z > 0 ? maxZ : minZ);
		VECTOR3 p4 = _V(revert.x > 0 ? minX : maxX, revert.y > 0 ? maxY : minY, revert.z > 0 ? maxZ : minZ);
		oapiVCSetAreaClickmode_Quadrilateral(id, p1, p2, p3, p4);
	}
	else {
		double distX = Distance(minX, maxX);
		double distY = Distance(minY, maxY);
		double distZ = Distance(minZ, maxZ);
		VECTOR3 center = _V(minX + distX / 2.0f, minY + distY / 2.0f, minZ + distZ / 2.0f);
		double rad = max(distX, max(distY, distZ)) / 2.0;
		oapiVCSetAreaClickmode_Spherical(id, center, rad);
	}
}

Since it is based off the mesh I tied switching the mesh group number. I could get the functions to work with the "wrong" mesh group but not the correct one.
 
Last edited:
So how can I see where the mouse click is?

Basically rather than measured vectors we are using the mesh group.
Code:
DefineMfdButtons(
		TEX_NEWRANGER21VC_MFD_DYNAMIC_8,
		AID_COPILOT_MFD_RIGHT_BTNS_FN, GRP_NEWRANGER21VC_COPILOT_MFD_RIGHT_BTNS_FN, buttonFnRect[MFD_COPILOT_RIGHT],
		AID_COPILOT_MFD_RIGHT_BTNS_SYS, GRP_NEWRANGER21VC_COPILOT_MFD_RIGHT_BTNS_SYS
		);

So the FN buttons are in
Code:
#define GRP_NEWRANGER21VC_COPILOT_MFD_RIGHT_BTNS_FN	 	63

Code:
void ClassicMfd::DefineMfdButtons(
	UINT const texId,
	UINT const fuctionAreaId, UINT const functionGroupId, RECT const functionRect,
	UINT const sysAreaId, UINT const sysGroupId
	)
{
	SURFHANDLE const texDyn = oapiGetTextureHandle(meshhg_VC, texId);
	oapiVCRegisterArea(fuctionAreaId, functionRect, PANEL_REDRAW_USER, PANEL_MOUSE_LBDOWN | PANEL_MOUSE_LBPRESSED | PANEL_MOUSE_ONREPLAY, PANEL_MAP_NONE, texDyn);
	DefineStaticClickArea(oapiMeshGroup(meshhg_VC, functionGroupId), fuctionAreaId, true);

	oapiVCRegisterArea(sysAreaId, PANEL_REDRAW_NEVER, PANEL_MOUSE_LBDOWN | PANEL_MOUSE_ONREPLAY);
	DefineStaticClickArea(oapiMeshGroup(meshhg_VC, sysGroupId), sysAreaId, true);
}

So based on the mesh group if clicked it works the mfd. But all work but the copilot right fn.

---------- Post added 09-17-16 at 07:10 AM ---------- Previous post was 09-16-16 at 05:19 PM ----------

No clue.

I do get a warning in compiling;
c:\orbiter100830\orbitersdk\samples\testranger\RANGER.h(103): warning C4227: anachronism used : qualifiers on reference are ignored

Code:
	bool VCMouseEvent(int const id, int const event, VECTOR3& const p);
 
I do get a warning in compiling;
c:\orbiter100830\orbitersdk\samples\testranger\RANGER.h(103): warning C4227: anachronism used : qualifiers on reference are ignored

Code:
    bool VCMouseEvent(int const id, int const event, VECTOR3& const p);

Remove the const at VECTOR3& or invert the order to "const VECTOR3 &"
 
Thanks. I have this:
Code:
	bool VCMouseEvent(int const id, int const event, VECTOR3&  p);

but still the issue with the mfd. It is like it is not in the right area.

---------- Post added 09-18-16 at 05:07 AM ---------- Previous post was 09-17-16 at 08:46 AM ----------

I started running the debugger.

When I click on the sys i get this:
Code:
		aid	8	const int
		event	1	const int
-		p	{data=0x00aefe34 {0.033084739530499618, 0.35614239193941444, 0.00000000000000000} x=0.033084739530499618 ...}	const VECTOR3 &

But if those are coordinates. It doesn't match the mesh.
I get nothing for processing

case AID_COPILOT_NEW_MFD_RIGHT_BTNS_FN:

Code:
bool ClassicMfd::HandleMouseEvent(int const aid, int const event, VECTOR3 const &p)
{
	switch (aid) {
	case AID_PILOT_MFD_LEFT_BTNS_FN:
		return ProcessMfdFnButton(MFD_PILOT_LEFT, event, p);
	case AID_PILOT_MFD_LEFT_BTNS_SYS:
		return ProcessMfdSysButton(MFD_PILOT_LEFT, event, p);

	case AID_PILOT_MFD_RIGHT_BTNS_FN:
		return ProcessMfdFnButton(MFD_PILOT_RIGHT, event, p);
	case AID_PILOT_MFD_RIGHT_BTNS_SYS:
		return ProcessMfdSysButton(MFD_PILOT_RIGHT, event, p);

	case AID_COPILOT_MFD_LEFT_BTNS_FN:
		return ProcessMfdFnButton(MFD_COPILOT_LEFT, event, p);
	case AID_COPILOT_MFD_LEFT_BTNS_SYS:
		return ProcessMfdSysButton(MFD_COPILOT_LEFT, event, p);

	case AID_COPILOT_NEW_MFD_RIGHT_BTNS_FN:
		return ProcessMfdFnButton(MFD_COPILOT_RIGHT, event, p);
	case AID_COPILOT_MFD_RIGHT_BTNS_SYS:
		return ProcessMfdSysButton(MFD_COPILOT_RIGHT, event, p);

	}

	return false;
}
Code:
#define AID_PILOT_MFD_LEFT_BTNS_FN 1
#define AID_PILOT_MFD_LEFT_BTNS_SYS 2
#define AID_PILOT_MFD_RIGHT_BTNS_FN 3
#define AID_PILOT_MFD_RIGHT_BTNS_SYS 4
#define AID_COPILOT_MFD_LEFT_BTNS_FN 5
#define AID_COPILOT_MFD_LEFT_BTNS_SYS 6
#define AID_COPILOT_NEW_MFD_RIGHT_BTNS_FN 7
#define AID_COPILOT_MFD_RIGHT_BTNS_SYS 8
 
The coordinates are relative to your clickable area definition. If you use a quad, its the relative coordinates inside a rectangle, if you use a spherical definition, its the radius relative to the reference position.
 
Thanks.
I guess I need to figure out why the mouse click doesn't trigger the
AID_COPILOT_NEW_MFD_RIGHT_BTNS_FN

success:::
 
Last edited:
Well, a new issue here. Gattispilot and Co. have modeled the ships of Interstellar; the Endurance, the Ranger, and the Lander. We're having an issue with the Lander. The Lander is designed to reenter Earth-like planets inverted (cargo pallets are attached to undersurface of the Lander so inverted reentry protects the cargo). As it stands now, using BaseSync MFD and Glideslope 2 MFD to guide reentry, the Lander's Lift/Drag performance is erratic. We need suggestions on coding the aerodynamic properties of the ship.
 
This is what we have. It is based off Shuttle-A
Code:
void Lander_MomentCoeff(double aoa, double M, double Re, double *cl, double *cm, double *cd)
{
	int i;
	const int nabsc = 7;
	static const double AOA[nabsc] = { -180 * RAD, -90 * RAD, -30 * RAD, 0 * RAD, 60 * RAD, 90 * RAD, 180 * RAD };
	static const double CL[nabsc] = { 0, 0, -0.004, 0, 0.008, 0, 0 };
	static const double CM[nabsc] = { 0, 0, 0.0014, 0, -0.0012, 0, 0 };

	for (i = 0; i < nabsc - 1 && AOA[i + 1] < aoa; i++);
	double f = (aoa - AOA[i]) / (AOA[i + 1] - AOA[i]);
	*cl = CL[i] + (CL[i + 1] - CL[i]) * f;  // aoa-dependent lift coefficient
	*cm = CM[i] + (CM[i + 1] - CM[i]) * f;  // aoa-dependent moment coefficient
	double saoa = sin(aoa);
	double pd = 0.045 + 0.4*saoa*saoa;  // profile drag
	*cd = pd + oapiGetInducedDrag(*cl, 0.1, 0.7) + oapiGetWaveDrag(M, 0.75, 1.0, 1.1, 0.04);
	// profile drag + (lift-)induced drag + transonic/supersonic wave (compressibility) drag
}
Code:
void LANDER6::clbkSetClassCaps(FILEHANDLE cfg)
{
	SetSize(11);
	SetEmptyMass(11000.0);
	SetCW(0.3, 0.3, 0.6, 0.9);
	SetWingAspect(1.7);
	SetWingEffectiveness(2.5);
	SetCrossSections(_V(71.59, 206.57, 50.58));
	SetRotDrag(_V(3.5, 3.5, 3.5));
	if (GetFlightModel() >= 1) {
		SetPitchMomentScale(1e-4);
		SetBankMomentScale(1e-4);
	}
	SetPMI(_V(32.49, 38.14, 23.67));
	SetTrimScale(0.08);
	SetCameraOffset(_V(0, 3, 10.1));
	SetTouchdownPoints(_V(0, -.003, 5.7), _V(-3.448, -.003, -5.0), _V(3.448, -.003, -5.0));;
 
So we have thought to make it like an inverted Delta Glider.

I can add the DG specs. But how to I make it inverted.
 
So we have thought to make it like an inverted Delta Glider.

I can add the DG specs. But how to I make it inverted.

Why inverted? Also why aerodynamic at all, it looks like a brick.
 
Even a brick has predictable lift/drag characteristics at hypersonic speeds. The problem we're having is that our current model of the Lander has erratic lift/drag performance. The ship is designed to renter inverted. As you vary pitch, the lift/drag response doesn't allow you fly a reentry profile. We need to create an aerodynamic model for the Lander that will allow you to fly reentry.
 
Hi gattispilot
Firstly i do apologise. Shortly after i started this thread a close family member was diagnosed with a serious illness, and alas subsequently passed away. A difficult time for all, which has kept me away from many things, including Orbiter.
However I have to say you have done absolutely fantastic work and i applaud you and all the contributors in helping to make the ships from Interstellar an Orbiter reality!!
Very Well Done!!!
I'm more than happy to aid in testing, if needed in a sparkly new install of Orbiter 2016!.
Hope you're well too.
 
Thanks. And sorry. We are still trying to get some coding issues fixed. But we do have the Endurance, Ranger and Lander. All seem to function in 2016 except for the Ummu part.
 
Thanks. And sorry. We are still trying to get some coding issues fixed. But we do have the Endurance, Ranger and Lander. All seem to function in 2016 except for the Ummu part.
Question. will this addon be reverse compatible with the 2010 version of Orbiter?
 
Not sure what you mean. But I think yes. You might have a 2010 and 2016 dll. The think that is holding us up and some code and Lander dynamics. And for 2016 Ummu
 
Ok some thoughts on the aerodynamics of the Lander:
Check the API guide section 1.9, 1.9.1, 1.9.4, & 1.9.5. Here’s my impression:

Drag is a force acting on the vessel in the direction of the freestream airflow. It is composed
from several components:
1. The skin friction drag caused by the boundary layer surrounding the airfoil.
2. The pressure drag caused by separation of flow from the surface.
3. The wave drag at supersonic velocities.
4. Induced drag, caused by airflow around the wingtip (finite wing) from the lower to the
upper surface.
The combination of components 1-3 is defined as profile drag or parasite drag.

Lift is an upward force (perpendicular to the airflow) caused by the shape of the airfoil and its
orientation to the airflow.

Drag D and lift L of an airfoil are expressed by the drag and lift coefficients cD and cL, with
cD = D/qS , cL = L/qS
where q = 1/2 rV2 is the freestream dynamic pressure, and S is the wing area. Generally, cD
and cL, will be functions of the angle of attack, the Mach number, and the Reynolds number.
We now split cD in the components of profile and induced drag.
 
Yes, very basic aerodynamics.

Airfoil_lift_and_drag.jpg


Now, you just need to plan, how the lift and drag arrows look like and how the resulting total force should be.

Also, you should plan, how the torque (aerodynamic moment) should be on your spacecraft, in the sense of "how does it rotate relative to the wind?"

Essentially, you just need to define some reference data points and then interpolate the full circle around them.
 
So:
Lander%20schematic%20E%5B1%5D.jpg

Lander%20schematic%20F'%5B1%5D.jpg

Lander%20schematic%20F%5B3%5D.jpg


Where A equals the length of the Lander, B it’s width, and C it’s height.
 
So the wing shape we can get from the area. But not sure about the rest
 
Back
Top