BlitzExtensions - Really Extending Blitz
Blitz3D Forums/Blitz3D Userlibs/BlitzExtensions - Really Extending Blitz
| ||
BlitzExtensions BlitzExtensions is a collection of User Libraries for the Blitz language, allowing you to do many additional things previously locked away from you. License: Lesser GPL v3 Links: Project Source Library: BlitzPointer BlitzPointer allows you to get the pointers of a Blitz function and use these to your advantage. Ever wanted to call a DLL function that requires a callback but didn't know C++? BlitzPointer can help you there, as Blitz functions are __stdcall-able! License: Lesser GPL v3 Links: Binary Releases | Library Source Library: BlitzSteam BlitzSteam brings the Steamworks API to the Blitz language or any other language unable to call __cdecl functions. Integrate your game with Steam by using the Workshop, HTMLSurface or Steam Networking - everything the Steamworks API offers is at your disposal. In order to use or compile this library you need to be a registered Steamworks developer. Steamworks restrictions will still apply. License: Lesser GPL v3 Links: Binary Releases | Library Source Library: BlitzUtility BlitzUtility gives you access to many extra 'Utility' functionality: ObjectList, TypeList, SQLite3, LongLong, Double, DisplayEnumerator, Indexers, WindowMessageHandler. For exact descriptions of what each does, check out README.md in the library source. License: Lesser GPL v3 Links: Binary Releases | Library Source |
| ||
Excellent work there :) |
| ||
Yes, smart stuff. |
| ||
@Ploppy: May I ask you something? I've figured out some things in Blitz (Variables, Functions, Types) but I can't wrap my head around strings. It just doesn't make sense to me, as Blitz functions recieve a pointer to a structure with a pointer to a cstring inside, or that's what I think it does. Is this actually what happens? |
| ||
In c++, strings in Blitz3d are handled by the BBStr class, I think it is the same in B+. Here is the class declaration in all it's beauty for example..struct BBStr : public std::string{ BBStr *next,*prev; BBStr(); BBStr( const char *s ); BBStr( const char *s,int n ); BBStr( const BBStr &s ); BBStr( const std::string &s ); BBStr &operator=( const char *s ); BBStr &operator=( const BBStr &s ); BBStr &operator=( const std::string &s ); ~BBStr(); void *operator new( size_t size ); void operator delete( void *q ); void *operator new( size_t size,const char *file,int line ){ return operator new( size ); } void operator delete( void *q,const char *file,int line ){ operator delete( q ); } }; As you can see, the class is a derivative of the std::string class, the actual string itself can be retrieved with the class's c_str() function, and the string length by the length() function. The internal workings of blitz process strings by passing pointers between functions. However, for userlibs, the char * method is used to pass strings, conversion happens between 'char *' and 'BBStr *' before and after calling a userlib function if needed. |
| ||
That means I have to temporarily create a BBStr object to pass the string to a blitz function, allowing even strings to be passed. Alright, thanks for clearing that up. Edit 1: Or retrieve the one that contains the original. Edit 2: On second thought, it might be better to just disable string return and passing until I found a proper way to handle it. Edit 3: I'm surprised my solution even worked like it did. Edit 4: I have no idea how to pass strings to a blitz function. It either crashes or ends up being empty (which is better than a crash though). |
| ||
You'll need a bit of c++ code to convert it, something like#include <string> using namespace std; string * ConvertToBBStr(char * input) { string * output=new string(input); return output; } This code for example will convert a char * string to a std::string type. To convert it back to char * try something like #include <windows.h> #include <string> using namespace std; char * ConvertToChar(string * input) { char * output= new char[input->length()]; memcpy (output,input->c_str(),input->length()); return output; } |
| ||
@Ploppy: If only that worked, that was one of the first things I tried. Sibly's BBStr is simply too different to be cast to a std::string: | 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F --------+------------------------------------------------ 00000000| 65 00 00 00 ?? ?? ?? ?? 0B 00 00 00 1F 00 00 00 00000010| <varying> Offset 0 is always the same 0x65 (0x00000065), after that there's a int32_t/intptr_t to a c-style string and then we have the weird 0x0B and 0x1F. This can't be directly casted to a std::string. If I substract 8 from the returned pointer, I can cast it to a std::string Edit: Here's a better view of the memory around the returned pointer: 0x004BB5F0 is the returned pointer. Edit: Upon further investigation, it seems that using BlitzPointer near the end of the program causes the repeat. Probably because I was using __cdecl instead of __stdcall by accident. Edit 2: I'll just take out those functions until further notice. |
| ||
I uploaded version 1.1 of the DLL just now, changelog 1.1 - 15/05/2015 - [New] Added and updated Examples - [New] Added functions for Direct Memory Access (DMA) - [Fix] Fixed memory leak when returning strings by removing the functions for now. (It was a bug anyway, should never have worked.) - [Fix] Hopefully fixed the backwards instruction jump caused by using BlitzPointer by using __stdcall. If I figure out how to properly do strings, I'll probably add additional functions to pass them as pointers with manual cleanup. |
| ||
Hi! I don't know much about coding so I post this just in case is useful This is how I've got the content of a string field based on other posts, I understood that is read only data ;Create the object Type testType Field FirstField% Field SecondField$ End Type testInstance.testType = New testType testInstance\FirstField = 10 testInstance\SecondField = "FieldContent" ;Get the Type Pointer: instancePTR = Int(testInstance) ;Get First Field Pointer: (just as an example) firstFieldPTR = ( instancePTR + 20 ) ;Get Second Field Pointer: secondFieldPTR = ( instancePTR + 20 ) + 4 ;Get Pointer from second Field Pointer: stringPTR = MemoryPeekInt(secondFieldPTR) ;Get length of string: stringLength = MemoryPeekInt( stringPTR + 8 ) ;Get location of the characters: CharsPTR = MemoryPeekInt(stringPTR + 4) ;Get each character: For n = 0 To ( stringLength - 1 ) theString$ = theString$ + Chr( MemoryPeekByte( CharsPTR + n ) ) Next Print theString I hope this help |
| ||
So, some news. The pointers retrieved by BlitzPointer should be directly callable as __stdcall functions, requiring no intermediate functions. No guarantee that it works though, haven't been able to test it due to an odd bug (Blitz3D won't load DLLs from the /userlibs/ folder anymore). Edit: __stdcall Test successful: |
| ||
BlitzPointer just received a much needed update and is now at version 1.4.0, featuring Variable-pointers and a few fixes. Changelog: * Upgraded to Visual Studio 2015 * Fixed broken .Decls file (missing parameter). * Implemented Variable-pointers (BP_GetVariablePointerInt, BP_GetVariablePointerFloat, BP_GetVariablePointerType) * Fixed BP_GetReturnAddress returning the wrong address. * Fixed BP_GetFunctionPointer being unstable by using a more intelligent design. * Reduced overall usage of raw asm instruction to just reading the BasePointer. * Added Example 8 - Variable-pointers. Binaries & Source Code: Here Screenshot: |
| ||
@Xaymar I just stumbled on your BlitzSteam Library. Some time ago, I wrote a game in B3B and sold a handful of copies, winning a bet in the process. 2014, I uploaded it on Steam Greenlight, just to get some experience with the Steam system. 2 days ago, I received an eMail from Valve, saying the game has been greenlit. Now I want to add some achievements to the game. My knowledge of C is literally ZERO, but I understand I can implement achievements in a B3D project with your library? That would be really awesome... Thanks in advance, PSY P.S. I tried to contact you by your website, but it seems to be down/emtpy... |
| ||
@PSY Indeed, almost all Steam Interfaces are available to you. Achievements, Statistics, Leaderboards, Networking, etc. I've included some examples for the APIs I understand, the rest is almost pure native C wrapper. You can reach me via michael.fabian.dirks@..., I'm currently moving servers. |
| ||
@Xaymar Awesome, thanks alot. I really appreciate that!! |