
Paul Henty
Members-
Posts
1,724 -
Joined
-
Days Won
76
Content Type
Profiles
Forums
Events
Gallery
Downloads
Everything posted by Paul Henty
-
Reading doubles (Payload stations) problem
Paul Henty replied to lordofwings's topic in FSUIPC Support Pete Dowson Modules
Incase you don't already know, I have a .NET dll available for interfacing with FSUIPC. It has a number of advantages over the original SDK, for example it has support for doubles and it's object-oriented rather than procedural. Details and download in the sticky near the top of this forum. Paul -
Hi, I'm Paul, author of the .NET dll. I've never tested it against FSUIPC4/FSX because I don't own it but FSUIPC4 should be no different to 3 as far as the DLL is concerned. To check if there is a problem in the DLL or not, can you please try running one of my example apps provided (C# or VB.NET). They handle FS not being ready or being closed unexpectedly. See if they eventually connect if loaded before FSX, or if you shut down FSX and restart it while using the test app. If they work then the DLL is OK. Look at the source of the example apps and see if it different to what your code does. If the example apps show the same problems as your code or you need more help then let me know. Thanks, Paul
-
FSUIPC Client DLL for .NET - Version 2.0
Paul Henty replied to Paul Henty's topic in FSUIPC Client DLL for .NET
Hi Graham, You need to be checking each boundry of the runway as opposed to just checking if it's in the four corners like you're doing at the moment. The main thing you need to find out is the latitudes of the edges of the runway at the plane's current longitude and vice verse. I've attached a graphic to show the maths for one boundry (NW/SW). (the lon/lat units have been simplified to make things clearer) We know the plane is at Lon 23.5E. But at what longitude is the edge of the runway at the current aircraft Latitude (24N)? To find out we use some basic trigonometry with right angled triangles... 1. We know the positions of the NW corner and SW corner. From this we can get the lengths of two sides of the triangle. (Blue numbers) 2. The ratio between these side is 10:5 = 2:1. 3. What we want to know is: How far across is the edge of the runway at 24N. ('X' on the diagram). 24N is only 6 south of from the NW latitude . This forms a smaller triangle inside the larger one. (In red) 4. The ratio of the sides of this smaller triangle will be the same at the larger one (2:1). 5. To if the long edge is 6 the short one will be 6/2 which is 3. 6. Add that distance to the NW longitude (20E) and you get the absolute longitude of where the runway starts. In this case 23E. 7. Since the aircraft is at 23.5E it's east of the west boundry and so we could be on the runway. You just do similar calculations for the other 4 boundries. If they all pass, you're on the runway. So here's a routine that will check if a point is within a quadrangle. This even works if the sides arn't parralel. It's important that you enter the corordinates of the four corners correctly or it won't work. They are labeled NW, NE, SW and SE. Just make sure your map is pointing north and it should be fairly easy to work out which is which. C# private bool AreaContainsPoint(double AreaNELat, double AreaNELon, double AreaSELat, double AreaSELon, double AreaSWLat, double AreaSWLon, double AreaNWLat, double AreaNWLon, double PointLat, double PointLon) { bool InArea = false; // Check if point is EAST of the NW/SW boundry if (PointLon > AreaNWLon + ((AreaSWLon - AreaNWLon) / (AreaNWLat - AreaSWLat) * (AreaNWLat - PointLat ))) { // Check if point is WEST of the NE/SE boundry if (PointLon < AreaNELon + ((AreaSELon - AreaNELon) / (AreaNELat - AreaSELat) * (AreaNELat- PointLat))) { // Check if point is NORTH of the SW/SE boundry if (PointLat > AreaSWLat + ((AreaSELat - AreaSWLat) / (AreaSELon - AreaSWLon) * (PointLon - AreaSWLon))) { // Check if point is South of the NW/NE boundry InArea = (PointLat < AreaNWLat + ((AreaNELat - AreaNWLat) / (AreaNELon - AreaNWLon) * (PointLon - AreaNWLon))); } } } return InArea; } VB.NET Private Function AreaContainsPoint(ByVal AreaNELat As Double, ByVal AreaNELon As Double, ByVal AreaSELat As Double, ByVal AreaSELon As Double, ByVal AreaSWLat As Double, ByVal AreaSWLon As Double, ByVal AreaNWLat As Double, ByVal AreaNWLon As Double, ByVal PointLat As Double, ByVal PointLon As Double) As Boolean Dim InArea As Boolean = False ' Check if point is EAST of the NW/SW boundry If (PointLon > AreaNWLon + ((AreaSWLon - AreaNWLon) / (AreaNWLat - AreaSWLat) * (AreaNWLat - PointLat))) Then ' Check if point is WEST of the NE/SE boundry If (PointLon < AreaNELon + ((AreaSELon - AreaNELon) / (AreaNELat - AreaSELat) * (AreaNELat - PointLat))) Then ' Check if point is NORTH of the SW/SE boundry If (PointLat > AreaSWLat + ((AreaSELat - AreaSWLat) / (AreaSELon - AreaSWLon) * (PointLon - AreaSWLon))) Then ' Check if point is South of the NW/NE boundry InArea = (PointLat < AreaNWLat + ((AreaNELat - AreaNWLat) / (AreaNELon - AreaNWLon) * (PointLon - AreaNWLon))) End If End If End If AreaContainsPoint = InArea End Function It's also worth noting that this assumes the earth is flat. That's probably not a problem with checking a small area like a runway. The larger the area you check, the more inaccurate it becomes because of the roundness of the earth. The maths to do it property taking into account the round earth is fairly complicated. Hope this works. I've started to put Lon/Lat support in the .NET client DLL. I'll put this in there as well. Can't say when I'll get time to finish it off though. Let me know how it goes... Paul -
FSUIPC Client DLL for .NET - Version 2.0
Paul Henty replied to Paul Henty's topic in FSUIPC Client DLL for .NET
Say you have: 40* 24' 36.1" 1. take the minutes and divide by 60 to convert to degrees: 24/60 = 0.4 2. take the seconds and divide by 3600 to convert to degrees: 36.1/3600 = 0.0100278 3. Add them both to the number of degrees: 40 + 0.4 + 0.0100278 = 40.4100278 so in short it's: Degrees + (Minutes / 60) + (Seconds / 3600) If the lon or lat degrees are -tve (e.g. -40* 24' 36.1") Then it's: Degrees - (Minutes / 60) - (Seconds / 3600) -40 - 0.4 - 0.0100278 = -40.4100278 I'm going to look at adding a Lon/Lat class or type into the DLL. It'll let you convert between the FS Integer format, the degrees decimal format, the degrees,minutes,seconds format and let you extract the degrees or minutes or seconds portion of the value. I'll try and get it done over Easter but I can't promise. Paul -
FSUIPC Client DLL for .NET - Version 2.0
Paul Henty replied to Paul Henty's topic in FSUIPC Client DLL for .NET
Hi Graham, 1. Take off the degrees part so you're left with only the value after the point 2. Multiply the result by 60 to convert to minutes. In .NET you can use the Math.Truncate method to get the integer portion and then subtract it leaving only the bit after the point. Here's how the whole thing looks: (This assumes a double called Lon has already been created and is holding the location in decimal degrees. What you end up with is another double which holds the number of Minutes represented by the deciimal portion of Lon). C# double lonMinutes = Math.Abs(lon - Math.Truncate(lon)) * 60d; VB.NET Dim lonMinutes As Double = Math.Abs(lon - Math.Truncate(lon)) * 60D BTW the 'Abs' method makes sure the answer is +tve. Otherwise for -tve degrees you'll end up with a -tve seconds value which probably isn't what you want. If you do, just delete "Math.Abs" - Leave the brackets in though! The same thing will work for Lat. LonMinutes now holds the number of minutes before the decimal point with the seconds represented as the part after the decimal point. That's as far as the FS display goes. You can however do the same operation on lonMinutes to get the number of seconds if you need to. I assume you need to do this for display purposes. If you are just trying to test the position of the aircraft in code I think it would be much easier just to use the raw decimal degrees that you get from FSUIPC. That way you only have to test one number and don't have to go through the conversion. If you need any more info let me know. Paul -
FSUIPC Client DLL for .NET - Version 2.0
Paul Henty replied to Paul Henty's topic in FSUIPC Client DLL for .NET
Hi Devon, I'm assuming that your app executes the Process() in a try, catch block. If FS is closed the Process() method should throw an FSUIPCException which you have to catch and then do whatever you need to. If you are doing this (as Luis above seems to be) but there's still an unhandled exception appearing from somewhere then there seems to be a problem. Can you let me know the exact exception wording (message) and its classtype. Can you also do me a quick favour? If you use C# or VB.NET can you load up one of my sample programs and see what happens when you unload FS while it's are running? It should handle it gracefully - ie, there should be a message box telling you the connection has been lost and the [connect] button should light. If you can give my any code snippits that would help too. My email address is in the documentation if you'd prefer email. Paul -
FSUIPC Client DLL for .NET - Version 2.0
Paul Henty replied to Paul Henty's topic in FSUIPC Client DLL for .NET
Hi Devon, Not a stupid question - it's simple when you know how, but if you don't know then it's not so easy! The offset for COM2 is specified as 2 bytes in the programmer’s documentation so we declare it as a 16 bit integer (ie, System.Int16, or Short in VB, or short in C#): VB: Dim com2bcd As Offset(Of Short) = New FSUIPC.Offset(Of Short)(&H3118) C#: Offset<short> com2bcd = new Offset<short>(0x3118); After processing, the value of this offset will be a number with the frequency encoded in BCD format. Each group of 4 bits out of the 16 specifies a digit in the frequency. To get this into a string representing the frequency we need to convert each group of 4 bits into a digit representing the value stored in those 4 bits. This is the same as converting a binary number into Hexadecimal format. Fortunately the .NET framework can do this for us. We use one of the overloads of the ToString method. We pass in "X" to request the number to be formatted in Hex: VB: Dim com2String As String = com2bcd.Value.ToString("X") C#: string com2String = com2bcd.Value.ToString("X"); What we now have is a four digit string where the first two are before the decimal point and the last two are after. For example if the frequency is 119.45 what we will have now is "1945". All we need to do now is put the missing 1 on the front and insert the decimal point thus: VB: com2String = "1" & com2String.Substring(0, 2) & "." & com2String.Substring(2, 2) c#: com2String = "1" + com2String.Substring(0, 2) + "." + com2String.Substring(2, 2); If you want to set a com frequency you'll need to reverse the process. The following shows using the static Parse method on the System.Int16 class to set the value of the com2bcd offset we declared. Note that you need to parse the 'interesting' four digits so you'll need to get the new frequency into that format first. VB: Dim newCom2Frequency As String = "1945" ' Set to 119.45 com2bcd.Value = Short.Parse(newCom2Frequency, Globalization.NumberStyles.AllowHexSpecifier) C#: string newCom2Frequency = "1945"; // Set to 119.45 com2bcd.Value = short.Parse(newCom2Frequency, System.Globalization.NumberStyles.AllowHexSpecifier); Hope this helps. If you need any more info just ask... Paul -
FSUIPC Client DLL for .NET - Version 2.0
Paul Henty replied to Paul Henty's topic in FSUIPC Client DLL for .NET
Hi Luis, The code you have posted looks OK to me. You've setup a Try/Catch block, so when the Process() executes and FS isn't arouond anymore the DLL should throw an error. You're catching this so there shouldn't be an unhandled exeption thrown to the debugger. You're right about the Close(), Open() at the start of your timer loop - you don't want to do that. It shouldn't be necassary. I can't really tell from your post what's going on - could you let me know: 1. Which line(s) the exception is being thrown on 2. The exact message and type of the exception(s) 3. Do you have any other methods in your application that also call Process()? Regards, Paul -
FSUIPC Client DLL for .NET - Version 2.0
Paul Henty replied to Paul Henty's topic in FSUIPC Client DLL for .NET
Hi Luis, The Lon and Lat offsets are 64 bit Integers which are called Long in C# and VB. (The underlying class is System.Int64 if you are using a different language). So the declaration of the offsets would be: C# private Offset<long> latFS = new Offset<long>(0x0560); private Offset<long> lonFS = new Offset<long>(0x0568); VB.NET Private latFS As Offset(Of Long) = New FSUIPC.Offset(Of Long)(&H560) Private lonFS As Offset(Of Long) = New FSUIPC.Offset(Of Long)(&H568) I've called them LonFS and LatFS because they return Lon and Lat in FS internal units. After calling Process() you can transform the FS Units into degrees with the following lines (as described in the FSUIPC Documentation) and you end up with a Double floating point type that holds the Lon/Lat as degress. C# // Convert Lat and Lon from FS Units into degrees (as a double), double lat = (double)latFS.Value * 90d / (10001750d * 65536d * 65536d); double lon = (double)lonFS.Value * 360d / (65536d * 65536d * 65536d * 65536d); . VB.NET ' Convert Lat and Lon from FS Units into degrees (as a double). Dim lat As Double = latFS.Value * 90D / (10001750D * 65536D * 65536D) Dim lon As Double = lonFS.Value * 360D / (65536D * 65536D * 65536D * 65536D) Paul -
VB2005 Express is Visual Basic.NET. It's a different language to VB6 but the syntax is similar. I recommend you have a look at my DLL that lets .NET languages talk to FSUIPC. It's in a sticky near the top of this forum. (Subject is: FSUIPC Client DLL for .NET - Release Version 1.1). You may find it easier to use than the current VB.NET SDK. It has an example application (and documentation) in VB.NET to show you how to use it. If you need any more help than the documentation provides feel free to email me. Paul
-
The new dll (1.1) is now on the sticky post near the top of the forum. Paul
-
There's two issues here - one is a bug in the DLL which I will fix tomorrow: When you do a write it continues to write on every process after that. I think this was intruduced in the last update. The other issue is that you're adding the two offsets into the default group by not specifying a group name. I'm guessing you have another loop somewhere that's also calling Process(). When you do that it'll write the message and delay offset again. You can fix your code (even with the broken DLL) by adding these offsets to a seperate group. Another thing you need to do is disconnet the group before these offsets go out of scope at the end of the function. As it stands at the moment you can only run this function once. The second time it will throw an error because you're trying to re-register the offsets Below is a new version which will fix it. The user guide describes the group and scope concepts in more detail. If you need any more explaination let me know. (BTW, I can't see any need for the WriteText bits. Just do FSWriteMessage.Value = Message) Public Function ShowFSMessage(ByVal Message As String, ByVal Delay As Integer) Dim FSWriteMessage As Offset(Of String) = New FSUIPC.Offset(Of String)("Message",&H3380, 127) Dim DelayMessage As Offset(Of Integer) = New FSUIPC.Offset(Of Integer)("Message",&H32FA) Dim WriteText As String WriteText = Message WriteText = WriteText FSWriteMessage.Value = WriteText DelayMessage.Value = Delay FSUIPC.FSUIPCConnection.Process("Message") FSUIPC.FSUIPCConnection.DisconnectGroup("Message") Return 0 End Function Hope this helps. Look out for the update tomorrow. Paul
-
FSUIPC_Write in Visual Basic
Paul Henty replied to chrieger's topic in FSUIPC Support Pete Dowson Modules
VB has always supported 16-bit integers - they are called 'Integer'. 32-bit integers are called 'Long' in VB. 64-bit integers are not supported. VB6 does not support unsigned 16-bit or 32-bit integers. The 8-bit integer (Byte) is treated as unsigned. VB.NET 2003 added 64-Bit integers and changed the integer naming to the more usual: 16-Bit = Short 32-Bit = Integer 64-Bit = Long VB.NET 2005 finally added support for unsigned Integers: UShort, UInteger and ULong. Paul -
FSUIPC_Write in Visual Basic
Paul Henty replied to chrieger's topic in FSUIPC Support Pete Dowson Modules
It's correct. It's about -20 degrees from north, which is another way of saying 340 which is what you were looking for. To translate your -20 into 340 just add 360. When you're working with headings this happen alot, sometimes you get negative headings, sometimes over they go over 360. As JD says, you just need to write a function to normalise them. He posted one eariler in this thread, about 12 messages up. It's called norm360. You need to call that everytime you do maths on a heading and you want it in conventional 0-360 notation. Paul -
FSUIPC_Write in Visual Basic
Paul Henty replied to chrieger's topic in FSUIPC Support Pete Dowson Modules
Is the difference not due to magnetic variation? 0x0580 is a True heading, while the whisky compass, the gyro compass and the Autopilot heading at 0x07CC are all Magnetic headings. The current Magnetic Variation is at offset 0x02A0. If it's 20 degrees then your 0.312 is probably correct. Paul -
Version 2.0 is now out of date. Please get the latest version that is pinned at the top of this subforum. Thanks. Paul
-
Hi Joao, Your code looks like it will work (except you need to change the res = r(i) to res = r(1) ) However, it's a bit more compilcated than it need be - you don't need to use an array of doubles: This should be all you need to do, but I don't have VB6 on my machine anymore so I can't test it: ------------------------------------------------------------------------ Private Function Read_Value(v As Long, n As Long) As Double Dim dwResult As Long Dim res As Double If FSUIPC_Read(v, n, VarPtr(res), dwResult) Then If FSUIPC_Process(dwResult) Then Read_Value = res Else ' Can't process End If Else ' Can't read End If End Function ------------------------------------------------------------------------ Give that a try. If it doesn't work I'm sure a proper VB6 programmer will stop by and help you out. :-) Paul
-
You need to say what programmng languge you are using to get specific help for how to handle them in that specific language. However, in general you need to cast the 8-byte value directly to a 64 bit floating point type, (it's not an an 8byte Integer). The name of this type varies from language to language, as does the method of casting. In many languages the type you need is called a 'Double. Paul
-
:-) I did volunteer back in February but I didn't do it because a guy called Pelle was already doing one. I'll have another look at it though. Paul
-
Out of interest - Is this a wrapper around the VB.Net code that's in the SDK at the moment, or have you written the whole thing from scratch? Thanks, Paul
-
Hi Pete, As scruffy said, nothing. You can call any Win32 DLL if that's the platform you're running on. In fact the .net FSUIPC SDK code does just that. It calls User32.dll and Kernel.dll just like your C example. This is a useful thing to be able to do the moment as we're still running on Win32 OS. For example, the FSUIPC client uses windows messages which do not exist in .net. It's essential that we can call Win32 dlls for legacy reasons like this. If one was to imaging a version of FSUIPC written in .net, you'd use the Remoting Services to exchange data between different processes instead of IPC. Interestingly, the remoting services also work between different machines on a network. So if FSUIPC was written in .net there'd be no need for a seperate WideFS program as any FSUIPC client program could access the FSUIPC server on the same machine or a networked one. They wouldn't care. There would also be no need to write any networking code either - that's all handled by the framework. Standard memory allocations arn't required because you don't manage your own memory - the framework does it for you and cleans up after you. Explicit memory allocations are a Win32 concept. You can't normally use pointer arythmatic in .net because you could get into a mess like corrupting the stack or you might try to read or write memory that you isn't yours. Having said that - if you're using C++.net or C# these do have full pointer functions available, but if you use them you have to declare your code as 'unsafe'. It's only really useful for porting existing code. There's no reason to use such techniques in .net. Ponter arythmetic is simply not required to write a .net program. The token stuff is not nessasary. I suspect it's only there because the author was from a win32 background and didn't know enough about .net at the time. There are much tidier ways it could have been done without pointers or the token system. The managing is not done by interpreting the code, or running it inside a 'proper' Win32 process and looking over it's shoulder. It's done by inserting calls to the various framework libraries at compilaton time. Paul
-
Hi Pete, .Net code is not 'interpreted' like BASIC or a scripting language. Any program written in a .net language gets compiled to native machine code before they are run. They're as 'fully compiled' as any C or C++ program. The only thing that isn't 'native' about them is that they can't be run directly by the operating system (as of WindowsXP) as they're not programmed against the Win32 API. They have to sit on top of a framework that does talk to the OS and Win32. This will all change in Vista as the Win32 API is being replaced with the WinFX API which is written in .net. So .net will become the native code (both in terms of being compiled to machine code and also being run directly by the OS). Paul
-
Hi, Your code looks fine. I've copied and pasted it from your post and I get a proper value back in the Bank variable. Must be something wrong somewhere else. Have you got a registered copy of FSUIPC? I remember a similar post not so long ago where the problem was an unregistered version. Paul