From a4925aab38346ea8a9e20864b7b8d0497da9f9b8 Mon Sep 17 00:00:00 2001 From: groogy Date: Sat, 20 Nov 2010 00:44:23 +0000 Subject: [PATCH] Finally finished making all the functions that I will eventually bind to the SFML::Image class. To tired right now, I'll continue tomorrow. git-svn-id: https://sfml.svn.sourceforge.net/svnroot/sfml/branches/sfml2@1682 4e206d99-4929-0410-ac5d-dfc041789085 --- .../ruby/sfml-graphics/graphics/Image.cpp | 248 +++++++++++++++++- bindings/ruby/sfml-graphics/graphics/Rect.cpp | 42 +++ bindings/ruby/sfml-graphics/graphics/Rect.hpp | 11 + bindings/ruby/sfml-window/window/Window.cpp | 2 + 4 files changed, 294 insertions(+), 9 deletions(-) diff --git a/bindings/ruby/sfml-graphics/graphics/Image.cpp b/bindings/ruby/sfml-graphics/graphics/Image.cpp index 1809b37c..45929c51 100644 --- a/bindings/ruby/sfml-graphics/graphics/Image.cpp +++ b/bindings/ruby/sfml-graphics/graphics/Image.cpp @@ -109,10 +109,10 @@ static VALUE Image_Create( int argc, VALUE *args, VALUE self ) { case 3: rubyColor = Color_ForceType( args[2] ); - color.r = Color_GetR( rubyColor ); - color.g = Color_GetG( rubyColor ); - color.b = Color_GetB( rubyColor ); - color.a = Color_GetA( rubyColor ); + color.r = FIX2INT( Color_GetR( rubyColor ) ); + color.g = FIX2INT( Color_GetG( rubyColor ) ); + color.b = FIX2INT( Color_GetB( rubyColor ) ); + color.a = FIX2INT( Color_GetA( rubyColor ) ); case 2: width = FIX2UINT( args[0] ); height = FIX2UINT( args[1] ); @@ -139,10 +139,10 @@ static VALUE Image_CreateMaskFromColor( int argc, VALUE *args, VALUE self ) alpha = FIX2UINT( alpha ); case 1: rubyColor = Color_ForceType( args[0] ); - color.r = Color_GetR( rubyColor ); - color.g = Color_GetG( rubyColor ); - color.b = Color_GetB( rubyColor ); - color.a = Color_GetA( rubyColor ); + color.r = FIX2INT( Color_GetR( rubyColor ) ); + color.g = FIX2INT( Color_GetG( rubyColor ) ); + color.b = FIX2INT( Color_GetB( rubyColor ) ); + color.a = FIX2INT( Color_GetA( rubyColor ) ); break; default: rb_raise( rb_eArgError, "Expected 1 or 2 arguments but was given %d", argc ); @@ -152,8 +152,238 @@ static VALUE Image_CreateMaskFromColor( int argc, VALUE *args, VALUE self ) return Qnil; } +static VALUE Image_Copy( int argc, VALUE *args, VALUE self ) +{ + Image *source; + unsigned int destX = 0; + unsigned int destY = 0; + sf::IntRect sourceRect = sf::IntRect(0, 0, 0, 0); + VALUE rubySourceRect = Qnil; + bool applyAlpha = false; + + switch( argc ) + { + case 5: + if( args[4] == Qtrue ) + { + applyAlpha = true; + } + else if( args[4] == Qfalse ) + { + applyAlpha = false; + } + else + { + VALIDATE_CLASS( args[4], rb_cTrueClass, "applyAlpha" ); + } + case 4: + rubySourceRect = Rect_ForceType( args[3] ); + sourceRect.Left = FIX2INT( Rect_GetLeft( rubySourceRect ) ); + sourceRect.Top = FIX2INT( Rect_GetTop( rubySourceRect ) ); + sourceRect.Width = FIX2INT( Rect_GetWidth( rubySourceRect ) ); + sourceRect.Height = FIX2INT( Rect_GetHeight( rubySourceRect ) ); + case 3: + VALIDATE_CLASS( args[0], globalImageClass, "source" ); + Data_Get_Struct( args[0], sf::Image, source ); + destX = FIX2UINT( args[1] ); + destX = FIX2UINT( args[2] ); + break; + default: + rb_raise( rb_eArgError, "Expected 3..5 arguments but was given %d", argc ); + } + + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + object->Copy( *source, dextX, dextY, sourceRect, applyAlpha ); + return Qnil; +} + +static VALUE Image_CopyScreen( int argc, VALUE *args, VALUE self ) +{ + sf::RenderWindow *source; + sf::IntRect sourceRect = sf::IntRect(0, 0, 0, 0); + VALUE rubySourceRect = Qnil; + + switch( argc ) + { + case 2: + rubySourceRect = Rect_ForceType( args[3] ); + sourceRect.Left = FIX2INT( Rect_GetLeft( rubySourceRect ) ); + sourceRect.Top = FIX2INT( Rect_GetTop( rubySourceRect ) ); + sourceRect.Width = FIX2INT( Rect_GetWidth( rubySourceRect ) ); + sourceRect.Height = FIX2INT( Rect_GetHeight( rubySourceRect ) ); + case 1: + VALIDATE_CLASS( args[0], globalImageClass, "source" ); + Data_Get_Struct( args[0], sf::RenderWindow, source ); + break; + default: + rb_raise( rb_eArgError, "Expected 1 or 2 arguments but was given %d", argc ); + } + + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + if( object->CopyScreen( *source, sourceRect ) == true ) + { + return Qtrue; + } + else + { + return Qfalse; + } +} + +static VALUE Image_SetPixel( VALUE self, VALUE aX, VALUE aY, VALUE aColor ) +{ + VALUE rbColor = Color_ForceType( aColor ); + sf::Color color; + color.r = FIX2INT( Color_GetR( rubyColor ) ); + color.g = FIX2INT( Color_GetG( rubyColor ) ); + color.b = FIX2INT( Color_GetB( rubyColor ) ); + color.a = FIX2INT( Color_GetA( rubyColor ) ); + + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + object->SetPixel( FIX2INT( aX ), FIX2INT( aY ), color ); + return Qnil; +} + +static VALUE Image_SetPixel( VALUE self, VALUE aX, VALUE aY ) +{ + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + const sf::Color color = object->SetPixel( FIX2INT( aX ), FIX2INT( aY ) ); + return rb_funcall( globalColorClass, rb_intern( "new" ), 4, + INT2FIX( color.r ), INT2FIX( color.g ), + INT2FIX( color.b ), INT2FIX( color.a ) ); +} + +static VALUE Image_GetPixelPtr( VALUE self ) +{ + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + + VALUE pixels = rb_ary_new2( dataSize ); + const sf::Uint8 *const pixelPointer = object->GetPixelPtr(); + + const unsigned int rawWidth = object->GetWidth(); + const unsigned int rawHeight = object->GetHeight(); + const unsigned long dataSize = rawWidth * rawHeight * 4; + for(unsigned long index = 0; index < dataSize; index++) + { + rb_ary_store( pixels, index, CHR2FIX( pixelPointer[index] ) ); + } + + return pixels; +} + +static VALUE Image_UpdatePixels( int argc, VALUE *args, VALUE self ) +{ + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + VALUE somePixels = Qnil; + VALUE aRectangle = Qnil; + IntRect rectangle = IntRect(0, 0, object->GetWidth(), object->GetHeight() ); + + switch( argc ) + { + case 2: + aRectangle = Rect_ForceType( args[1] ); + rectangle.Left = FIX2INT( Rect_GetLeft( aRectangle ) ); + rectangle.Top = FIX2INT( Rect_GetTop( aRectangle ) ); + rectangle.Width = FIX2INT( Rect_GetWidth( aRectangle ) ); + rectangle.Height = FIX2INT( Rect_GetHeight( aRectangle ) ); + case 1: + VALIDATE_CLASS( args[0], rb_cArray, "pixels" ); + somePixels = args[0]; + break; + default: + rb_raise( rb_eArgError, "Expected 1 or 2 arguments but was given %d", argc ); + } + const unsigned int rawWidth = FIX2UINT( rectangle.Width ); + const unsigned int rawHeight = FIX2UINT( rectangle.Height ); + const unsigned long dataSize = rawWidth * rawHeight * 4; + sf::Uint8 * const tempData = new sf::Uint8[dataSize]; + VALUE pixels = rb_funcall( somePixels, rb_intern("flatten"), 0 ); + for(unsigned long index = 0; index < dataSize; index++) + { + sf::Uint8 val = NUM2CHR( rb_ary_entry( pixels, index ) ); + tempData[index] = val; + } + bool result = object->UpdatePixels( tempData, rectangle ); + delete[] tempData; + + return Qnil; +} + +static VALUE Image_Bind( VALUE self ) +{ + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + object->Bind(); + return Qnil; +} + +static VALUE Image_SetSmooth( VALUE self, VALUE aSmoothFlag ) +{ + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + + if( aSmoothFlag == Qtrue ) + { + object->SetSmooth( true ): + } + else if( aSmoothFlag == Qfalse ) + { + object->SetSmooth( false ); + } + else + { + VALIDATE_CLASS( aSmoothFlag, rb_cTrueClass, "smoothFlag" ); + } + return Qnil; +} + +static VALUE Image_IsSmooth( VALUE self ) +{ + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + return ( object->IsSmooth() == true ? Qtrue : Qfalse ); +} + +static VALUE Image_GetWidth( VALUE self ) +{ + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + return INT2FIX( object->GetWidth() ); +} + +static VALUE Image_GetHeight( VALUE self ) +{ + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + return INT2FIX( object->GetHeight() ); +} + +static VALUE Image_GetTexCoords( VALUE self, VALUE aRectangle ) +{ + VALUE rubyRectangle = Rect_ForceType( aRectangle ); + sf::IntRect rectangle; + rectangle.Left = FIX2INT( Rect_GetLeft( aRectangle ) ); + rectangle.Top = FIX2INT( Rect_GetTop( aRectangle ) ); + rectangle.Width = FIX2INT( Rect_GetWidth( aRectangle ) ); + rectangle.Height = FIX2INT( Rect_GetHeight( aRectangle ) ); + + sf::Image *object = NULL; + Data_Get_Struct( self, sf::Image, object ); + + sf::FloatRect result = object->GetTexCords( rectangle ); + return rb_funcall( globalRectClass, rb_intern( "new" ), 4, + rb_float_new( result.Left ), rb_float_new( result.Top ), + rb_float_new( result.Width ), rb_float_new( result.Height ) ); +} + /* call-seq: - * Image.new() -> image + * Image.new() -> image * * The clock starts automatically after being constructed. */ diff --git a/bindings/ruby/sfml-graphics/graphics/Rect.cpp b/bindings/ruby/sfml-graphics/graphics/Rect.cpp index 56e763ba..1950e3f2 100644 --- a/bindings/ruby/sfml-graphics/graphics/Rect.cpp +++ b/bindings/ruby/sfml-graphics/graphics/Rect.cpp @@ -51,6 +51,48 @@ VALUE Rect_ForceType( VALUE someValue ) } } +VALUE Rect_GetLeft( VALUE self ) +{ + static ID id = rb_intern( "left" ); + return rb_funcall( self, id, 0 ); +} +VALUE Rect_GetTop( VALUE self ) +{ + static ID id = rb_intern( "top" ); + return rb_funcall( self, id, 0 ); +} +VALUE Rect_GetWidth( VALUE self ) +{ + static ID id = rb_intern( "width" ); + return rb_funcall( self, id, 0 ); +} +VALUE Rect_GetHeight( VALUE self ) +{ + static ID id = rb_intern( "height" ); + return rb_funcall( self, id, 0 ); +} + +VALUE Rect_SetLeft( VALUE self, VALUE aVal ) +{ + static ID id = rb_intern( "left=" ); + return rb_funcall( self, id, 1, aVal ); +} +VALUE Rect_SetTop( VALUE self, VALUE aVal ) +{ + static ID id = rb_intern( "top=" ); + return rb_funcall( self, id, 1, aVal ); +} +VALUE Rect_SetWidth( VALUE self, VALUE aVal ) +{ + static ID id = rb_intern( "width=" ); + return rb_funcall( self, id, 1, aVal ); +} +VALUE Rect_SetHeight( VALUE self, VALUE aVal ) +{ + static ID id = rb_intern( "height=" ); + return rb_funcall( self, id, 1, aVal ); +} + /* Internal function * Will copy the x and y from aSource to self. */ diff --git a/bindings/ruby/sfml-graphics/graphics/Rect.hpp b/bindings/ruby/sfml-graphics/graphics/Rect.hpp index c9b48d26..bf5b4b44 100644 --- a/bindings/ruby/sfml-graphics/graphics/Rect.hpp +++ b/bindings/ruby/sfml-graphics/graphics/Rect.hpp @@ -27,6 +27,17 @@ VALUE Rect_ForceType( VALUE someValue ); +VALUE Color_GetLeft( VALUE self ); +VALUE Color_GetTop( VALUE self ); +VALUE Color_GetWidth( VALUE self ); +VALUE Color_GetHeight( VALUE self ); + +VALUE Color_SetLeft( VALUE self, VALUE aVal ); +VALUE Color_SetTop( VALUE self, VALUE aVal ); +VALUE Color_SetWidth( VALUE self, VALUE aVal ); +VALUE Color_SetHeight( VALUE self, VALUE aVal ); + + void Init_Rect( void ); #endif // SFML_RUBYEXT_RECT_HEADER_ diff --git a/bindings/ruby/sfml-window/window/Window.cpp b/bindings/ruby/sfml-window/window/Window.cpp index e65ab4ff..fdc434b4 100644 --- a/bindings/ruby/sfml-window/window/Window.cpp +++ b/bindings/ruby/sfml-window/window/Window.cpp @@ -27,6 +27,8 @@ #include "main.hpp" VALUE globalWindowClass; + +/* External classes */ extern VALUE globalVideoModeClass; extern VALUE globalContextSettingsClass; extern VALUE globalEventClass;