OSX, fixed tabulation

git-svn-id: https://sfml.svn.sourceforge.net/svnroot/sfml/branches/sfml2@1772 4e206d99-4929-0410-ac5d-dfc041789085
This commit is contained in:
mantognini 2011-01-20 21:52:27 +00:00
parent f9c4740894
commit 0a7b98dd0b
18 changed files with 1330 additions and 1332 deletions

View File

@ -37,149 +37,149 @@ namespace priv
{
////////////////////////////////////////////////////////////
RenderImageImplPBuffer::RenderImageImplPBuffer() :
myPBuffer(NULL),
myContext(NULL),
myWidth (0),
myHeight (0)
myPBuffer(NULL),
myContext(NULL),
myWidth (0),
myHeight (0)
{
/* Nothing else */
/* Nothing else */
}
////////////////////////////////////////////////////////////
RenderImageImplPBuffer::~RenderImageImplPBuffer()
{
if (myPBuffer && aglDestroyPBuffer(myPBuffer) == GL_FALSE) {
sf::Err()
<< "An error occurs while destroying the PBuffer in "
<< __PRETTY_FUNCTION__
<< ". The error code is "
<< aglGetError()
<< std::endl;
}
if (myContext && aglDestroyContext(myContext) == GL_FALSE) {
sf::Err()
<< "An error occurs while destroying the context in "
<< __PRETTY_FUNCTION__
<< ". The error code is "
<< aglGetError()
<< std::endl;
}
if (myPBuffer && aglDestroyPBuffer(myPBuffer) == GL_FALSE) {
sf::Err()
<< "An error occurs while destroying the PBuffer in "
<< __PRETTY_FUNCTION__
<< ". The error code is "
<< aglGetError()
<< std::endl;
}
if (myContext && aglDestroyContext(myContext) == GL_FALSE) {
sf::Err()
<< "An error occurs while destroying the context in "
<< __PRETTY_FUNCTION__
<< ". The error code is "
<< aglGetError()
<< std::endl;
}
// This is to make sure that another valid context is made
// active after we destroy the P-Buffer's one
Context::SetReferenceActive();
// This is to make sure that another valid context is made
// active after we destroy the P-Buffer's one
Context::SetReferenceActive();
}
////////////////////////////////////////////////////////////
bool RenderImageImplPBuffer::IsSupported()
{
const GLubyte* strExt = glGetString(GL_EXTENSIONS);
GLboolean isSupported = gluCheckExtension((const GLubyte*)"GL_APPLE_pixel_buffer", strExt);
return isSupported;
const GLubyte* strExt = glGetString(GL_EXTENSIONS);
GLboolean isSupported = gluCheckExtension((const GLubyte*)"GL_APPLE_pixel_buffer", strExt);
return isSupported;
}
////////////////////////////////////////////////////////////
bool RenderImageImplPBuffer::Create(unsigned int width, unsigned int height, unsigned int, bool depthBuffer)
{
// Store the dimensions
myWidth = width;
myHeight = height;
// Store the dimensions
myWidth = width;
myHeight = height;
// Create the pixel format.
GLint attribs[] = {
AGL_RGBA,
AGL_RED_SIZE, 8,
AGL_GREEN_SIZE, 8,
AGL_BLUE_SIZE, 8,
AGL_ALPHA_SIZE, 8,
AGL_DEPTH_SIZE, (depthBuffer ? 24 : 0),
0
};
AGLPixelFormat pf = aglChoosePixelFormat(NULL, 0, attribs);
if (!pf) {
sf::Err()
<< "Couldn't create the pixel format for the PBuffer."
<< std::endl;
return false;
}
// Create the context.
myContext = aglCreateContext(pf, NULL);
if (!myContext) {
sf::Err()
<< "Couldn't create the context for the PBuffer. (Error : "
<< aglGetError()
<< ")"
<< std::endl;
return false;
}
// Create the PBuffer.
GLboolean status = aglCreatePBuffer(myWidth, myHeight, GL_TEXTURE_RECTANGLE_EXT, GL_RGBA, 0, &myPBuffer);
if (status == GL_FALSE) {
sf::Err()
<< "Couldn't create the PBuffer. (Error : "
<< aglGetError()
<< ")"
<< std::endl;
return false;
}
// Set up the PBuffer with the context.
GLint screen = aglGetVirtualScreen(myContext);
if (screen == -1) {
sf::Err()
<< "Couldn't get the virtual screen of the context used with the PBuffer. (Error : "
<< aglGetError()
<< ")"
<< std::endl;
return false;
}
status = aglSetPBuffer(myContext, myPBuffer, 0, 0, screen);
if (status == GL_FALSE) {
sf::Err()
<< "Couldn't set up the PBuffer with the context. (Error : "
<< aglGetError()
<< ")"
<< std::endl;
return false;
}
return true;
// Create the pixel format.
GLint attribs[] = {
AGL_RGBA,
AGL_RED_SIZE, 8,
AGL_GREEN_SIZE, 8,
AGL_BLUE_SIZE, 8,
AGL_ALPHA_SIZE, 8,
AGL_DEPTH_SIZE, (depthBuffer ? 24 : 0),
0
};
AGLPixelFormat pf = aglChoosePixelFormat(NULL, 0, attribs);
if (!pf) {
sf::Err()
<< "Couldn't create the pixel format for the PBuffer."
<< std::endl;
return false;
}
// Create the context.
myContext = aglCreateContext(pf, NULL);
if (!myContext) {
sf::Err()
<< "Couldn't create the context for the PBuffer. (Error : "
<< aglGetError()
<< ")"
<< std::endl;
return false;
}
// Create the PBuffer.
GLboolean status = aglCreatePBuffer(myWidth, myHeight, GL_TEXTURE_RECTANGLE_EXT, GL_RGBA, 0, &myPBuffer);
if (status == GL_FALSE) {
sf::Err()
<< "Couldn't create the PBuffer. (Error : "
<< aglGetError()
<< ")"
<< std::endl;
return false;
}
// Set up the PBuffer with the context.
GLint screen = aglGetVirtualScreen(myContext);
if (screen == -1) {
sf::Err()
<< "Couldn't get the virtual screen of the context used with the PBuffer. (Error : "
<< aglGetError()
<< ")"
<< std::endl;
return false;
}
status = aglSetPBuffer(myContext, myPBuffer, 0, 0, screen);
if (status == GL_FALSE) {
sf::Err()
<< "Couldn't set up the PBuffer with the context. (Error : "
<< aglGetError()
<< ")"
<< std::endl;
return false;
}
return true;
}
////////////////////////////////////////////////////////////
bool RenderImageImplPBuffer::Activate(bool active)
{
if (active) {
if (!myContext || !myPBuffer) { // Not created yet.
return false;
}
if (aglGetCurrentContext() == myContext) {
return true;
} else {
return aglSetCurrentContext(myContext);
}
} else {
// To deactivate the P-Buffer's context, we actually activate
// another one so that we make sure that there is always an
// active context for subsequent graphics operations
return Context::SetReferenceActive();
}
if (active) {
if (!myContext || !myPBuffer) { // Not created yet.
return false;
}
if (aglGetCurrentContext() == myContext) {
return true;
} else {
return aglSetCurrentContext(myContext);
}
} else {
// To deactivate the P-Buffer's context, we actually activate
// another one so that we make sure that there is always an
// active context for subsequent graphics operations
return Context::SetReferenceActive();
}
}

View File

@ -101,7 +101,7 @@ private :
////////////////////////////////////////////////////////////
// Member data
////////////////////////////////////////////////////////////
AGLPbuffer myPBuffer; ///< P-Buffer
AGLPbuffer myPBuffer; ///< P-Buffer
AGLContext myContext; ///< Associated OpenGL context
unsigned int myWidth; ///< Width of the P-Buffer
unsigned int myHeight; ///< Height of the P-Buffer

View File

@ -129,7 +129,6 @@ bool RenderImageImplFBO::Activate(bool active)
////////////////////////////////////////////////////////////
void RenderImageImplFBO::UpdateTexture(unsigned int)
{
// Nothing to do: the FBO draws directly to the target image
glFlush();
}

View File

@ -37,35 +37,35 @@ namespace priv
////////////////////////////////////////////////////////////
void Joystick::Initialize(unsigned int Index)
{
// Reset the joystick state
// Initialize the Index-th available joystick
// Reset the joystick state
// Initialize the Index-th available joystick
}
////////////////////////////////////////////////////////////
JoystickState Joystick::UpdateState()
{
// Fill a JoystickState instance with the current joystick state
JoystickState s;
return s;
// Fill a JoystickState instance with the current joystick state
JoystickState s;
return s;
}
////////////////////////////////////////////////////////////
bool Joystick::HasAxis(Joy::Axis Axis) const
{
return false;
return false;
}
////////////////////////////////////////////////////////////
unsigned int Joystick::GetButtonsCount() const
{
// Return number of supported buttons
return 0;
// Return number of supported buttons
return 0;
}
} // namespace priv
} // namespace sf

View File

@ -31,7 +31,7 @@
////////////////////////////////////////////////////////////
#if USE_OS_X_VERSION_10_6
#include <IOKit/hid/IOHIDDevice.h>
#include <IOKit/hid/IOHIDDevice.h>
#endif
namespace sf
@ -44,51 +44,51 @@ namespace priv
////////////////////////////////////////////////////////////
class Joystick
{
public :
////////////////////////////////////////////////////////////
/// \brief Initialize the instance and bind it to a physical joystick
///
/// \param index Index of the physical joystick to bind to
///
////////////////////////////////////////////////////////////
void Initialize(unsigned int index);
////////////////////////////////////////////////////////////
/// \brief Update the current joystick and return its new state
///
/// \return Current state of the joystick
///
////////////////////////////////////////////////////////////
JoystickState UpdateState();
////////////////////////////////////////////////////////////
/// \brief Check if the joystick supports the given axis
///
/// \param axis Axis to check
///
/// \return True of the axis is supported, false otherwise
///
////////////////////////////////////////////////////////////
bool HasAxis(Joy::Axis Axis) const;
////////////////////////////////////////////////////////////
/// \brief Get the number of buttons supported by the joystick
///
/// \return Number of buttons
///
////////////////////////////////////////////////////////////
unsigned int GetButtonsCount() const;
private :
////////////////////////////////////////////////////////////
// Member data
////////////////////////////////////////////////////////////
public :
////////////////////////////////////////////////////////////
/// \brief Initialize the instance and bind it to a physical joystick
///
/// \param index Index of the physical joystick to bind to
///
////////////////////////////////////////////////////////////
void Initialize(unsigned int index);
////////////////////////////////////////////////////////////
/// \brief Update the current joystick and return its new state
///
/// \return Current state of the joystick
///
////////////////////////////////////////////////////////////
JoystickState UpdateState();
////////////////////////////////////////////////////////////
/// \brief Check if the joystick supports the given axis
///
/// \param axis Axis to check
///
/// \return True of the axis is supported, false otherwise
///
////////////////////////////////////////////////////////////
bool HasAxis(Joy::Axis Axis) const;
////////////////////////////////////////////////////////////
/// \brief Get the number of buttons supported by the joystick
///
/// \return Number of buttons
///
////////////////////////////////////////////////////////////
unsigned int GetButtonsCount() const;
private :
////////////////////////////////////////////////////////////
// Member data
////////////////////////////////////////////////////////////
};
} // namespace priv
} // namespace sf

View File

@ -37,25 +37,25 @@
////////////////////////////////////////////////////////////
+(void)processEventWithBlockingMode:(BOOL)block
{
[NSApplication sharedApplication]; // Make sure NSApp exists
NSEvent* event = nil;
if (block) { // At least one event is read.
event = [NSApp nextEventMatchingMask:NSAnyEventMask
untilDate:[NSDate distantFuture]
inMode:NSDefaultRunLoopMode
dequeue:YES]; // Remove the event from the dequeue
[NSApp sendEvent:event];
}
// If there are some other event read them.
while (event = [NSApp nextEventMatchingMask:NSAnyEventMask
untilDate:[NSDate distantPast]
inMode:NSDefaultRunLoopMode
dequeue:YES]) // Remove the event from the dequeue
{
[NSApp sendEvent:event];
}
[NSApplication sharedApplication]; // Make sure NSApp exists
NSEvent* event = nil;
if (block) { // At least one event is read.
event = [NSApp nextEventMatchingMask:NSAnyEventMask
untilDate:[NSDate distantFuture]
inMode:NSDefaultRunLoopMode
dequeue:YES]; // Remove the event from the dequeue
[NSApp sendEvent:event];
}
// If there are some other event read them.
while (event = [NSApp nextEventMatchingMask:NSAnyEventMask
untilDate:[NSDate distantPast]
inMode:NSDefaultRunLoopMode
dequeue:YES]) // Remove the event from the dequeue
{
[NSApp sendEvent:event];
}
}

View File

@ -61,84 +61,84 @@ namespace priv
class SFContext : public GlContext
{
public:
////////////////////////////////////////////////////////////
/// \brief Create a new context, not associated to a window
///
/// \param shared Context to share the new one with (can be NULL)
///
////////////////////////////////////////////////////////////
SFContext(SFContext* shared);
////////////////////////////////////////////////////////////
/// \brief Create a new context attached to a window
///
/// \param shared Context to share the new one with (can be NULL)
/// \param owner Pointer to the owner window
/// \param bitsPerPixel Pixel depth (in bits per pixel)
/// \param settings Creation parameters
///
////////////////////////////////////////////////////////////
SFContext(SFContext* shared, const WindowImpl* owner,
////////////////////////////////////////////////////////////
/// \brief Create a new context, not associated to a window
///
/// \param shared Context to share the new one with (can be NULL)
///
////////////////////////////////////////////////////////////
SFContext(SFContext* shared);
////////////////////////////////////////////////////////////
/// \brief Create a new context attached to a window
///
/// \param shared Context to share the new one with (can be NULL)
/// \param owner Pointer to the owner window
/// \param bitsPerPixel Pixel depth (in bits per pixel)
/// \param settings Creation parameters
///
////////////////////////////////////////////////////////////
SFContext(SFContext* shared, const WindowImpl* owner,
unsigned int bitsPerPixel, const ContextSettings& settings);
////////////////////////////////////////////////////////////
/// \brief Destructor
///
////////////////////////////////////////////////////////////
~SFContext();
////////////////////////////////////////////////////////////
/// \brief Display what has been rendered to the context so far
///
////////////////////////////////////////////////////////////
virtual void Display();
////////////////////////////////////////////////////////////
/// \brief Enable or disable vertical synchronization
///
/// Activating vertical synchronization will limit the number
/// of frames displayed to the refresh rate of the monitor.
/// This can avoid some visual artifacts, and limit the framerate
/// to a good value (but not constant across different computers).
///
/// \param enabled : True to enable v-sync, false to deactivate
///
////////////////////////////////////////////////////////////
virtual void EnableVerticalSync(bool enabled);
////////////////////////////////////////////////////////////
/// \brief Destructor
///
////////////////////////////////////////////////////////////
~SFContext();
////////////////////////////////////////////////////////////
/// \brief Display what has been rendered to the context so far
///
////////////////////////////////////////////////////////////
virtual void Display();
////////////////////////////////////////////////////////////
/// \brief Enable or disable vertical synchronization
///
/// Activating vertical synchronization will limit the number
/// of frames displayed to the refresh rate of the monitor.
/// This can avoid some visual artifacts, and limit the framerate
/// to a good value (but not constant across different computers).
///
/// \param enabled : True to enable v-sync, false to deactivate
///
////////////////////////////////////////////////////////////
virtual void EnableVerticalSync(bool enabled);
protected:
////////////////////////////////////////////////////////////
/// \brief Activate the context as the current target
/// for rendering
///
/// \return True on success, false if any error happened
///
////////////////////////////////////////////////////////////
virtual bool MakeCurrent();
////////////////////////////////////////////////////////////
/// \brief Activate the context as the current target
/// for rendering
///
/// \return True on success, false if any error happened
///
////////////////////////////////////////////////////////////
virtual bool MakeCurrent();
private:
////////////////////////////////////////////////////////////
/// \brief Create the context
/// \note Must only be called from Ctor.
///
/// \param shared Context to share the new one with (can be NULL)
/// \param settings Creation parameters
/// \param bitsPerPixel bpp
///
////////////////////////////////////////////////////////////
void CreateContext(SFContext* shared,
////////////////////////////////////////////////////////////
/// \brief Create the context
/// \note Must only be called from Ctor.
///
/// \param shared Context to share the new one with (can be NULL)
/// \param settings Creation parameters
/// \param bitsPerPixel bpp
///
////////////////////////////////////////////////////////////
void CreateContext(SFContext* shared,
const ContextSettings& settings,
unsigned int bitsPerPixel);
////////////////////////////////////////////////////////////
// Member data
////////////////////////////////////////////////////////////
NSOpenGLContextRef myContext; ///< OpenGL context
NSAutoreleasePoolRef myPool; ///< Memory manager for this class.
////////////////////////////////////////////////////////////
// Member data
////////////////////////////////////////////////////////////
NSOpenGLContextRef myContext; ///< OpenGL context
NSAutoreleasePoolRef myPool; ///< Memory manager for this class.
};
} // namespace priv
} // namespace sf
#endif // SFML_SFCONTEXT_HPP

View File

@ -35,14 +35,14 @@
* DISCUSSION :
* ============
*
* [1] (2010_07)
* should AA-related NSOpenGLPixelFormatAttribute not be in the array
* if AA is not enable (settings.AntialiasingLevel == 0) ?
* => will not be present in attributs array if 0.
* [1] (2010_07)
* should AA-related NSOpenGLPixelFormatAttribute not be in the array
* if AA is not enable (settings.AntialiasingLevel == 0) ?
* => will not be present in attributs array if 0.
*
* [2] (2010_07)
* how many buffer should be used for AA ?
* => «1» was choosen.
* [2] (2010_07)
* how many buffer should be used for AA ?
* => «1» was choosen.
*/
namespace sf
@ -53,132 +53,132 @@ namespace priv
////////////////////////////////////////////////////////////
SFContext::SFContext(SFContext* shared)
{
myPool = [[NSAutoreleasePool alloc] init];
// Create the context
CreateContext(shared, ContextSettings(0, 0, 0), 0);
myPool = [[NSAutoreleasePool alloc] init];
// Create the context
CreateContext(shared, ContextSettings(0, 0, 0), 0);
}
////////////////////////////////////////////////////////////
SFContext::SFContext(SFContext* shared, const WindowImpl* owner,
unsigned int bitsPerPixel, const ContextSettings& settings)
{
myPool = [[NSAutoreleasePool alloc] init];
// Create the context.
CreateContext(shared, settings, bitsPerPixel);
// Apply context.
WindowImplCocoa const * ownerCocoa = static_cast<WindowImplCocoa const *>(owner);
ownerCocoa->ApplyContext(myContext);
myPool = [[NSAutoreleasePool alloc] init];
// Create the context.
CreateContext(shared, settings, bitsPerPixel);
// Apply context.
WindowImplCocoa const * ownerCocoa = static_cast<WindowImplCocoa const *>(owner);
ownerCocoa->ApplyContext(myContext);
}
////////////////////////////////////////////////////////////
SFContext::~SFContext()
{
[myContext release];
[myPool drain]; // [1]
[myContext release];
[myPool drain]; // [A]
/*
[1] : Produce sometimes "*** attempt to pop an unknown autorelease pool"
[A] : Produce sometimes "*** attempt to pop an unknown autorelease pool"
*/
}
////////////////////////////////////////////////////////////
bool SFContext::MakeCurrent()
{
[myContext makeCurrentContext];
return myContext == [NSOpenGLContext currentContext]; // Should be true.
[myContext makeCurrentContext];
return myContext == [NSOpenGLContext currentContext]; // Should be true.
}
////////////////////////////////////////////////////////////
void SFContext::Display()
{
[myContext flushBuffer];
[myContext flushBuffer];
}
////////////////////////////////////////////////////////////
void SFContext::EnableVerticalSync(bool enabled)
{
// Make compiler happy
// Make compiler happy
#ifdef USE_OS_X_VERSION_10_4
long int swapInterval = enabled ? 1 : 0;
long int swapInterval = enabled ? 1 : 0;
#else /* USE_OS_X_VERSION_10_6 */
GLint swapInterval = enabled ? 1 : 0;
GLint swapInterval = enabled ? 1 : 0;
#endif
[myContext setValues:&swapInterval forParameter:NSOpenGLCPSwapInterval];
[myContext setValues:&swapInterval forParameter:NSOpenGLCPSwapInterval];
}
////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////
void SFContext::CreateContext(SFContext* shared,
const ContextSettings& settings,
unsigned int bitsPerPixel)
{
// Choose the attributs of OGL context.
std::vector<NSOpenGLPixelFormatAttribute> attrs;
attrs.reserve(20); // max attributs (estimation).
// These casts are safe. C++ is much more stric than Obj-C.
attrs.push_back(NSOpenGLPFAClosestPolicy);
attrs.push_back(NSOpenGLPFADoubleBuffer);
if (bitsPerPixel > 24) {
attrs.push_back(NSOpenGLPFAAlphaSize);
attrs.push_back((NSOpenGLPixelFormatAttribute)8);
}
attrs.push_back(NSOpenGLPFADepthSize);
attrs.push_back((NSOpenGLPixelFormatAttribute)settings.DepthBits);
attrs.push_back(NSOpenGLPFAStencilSize);
attrs.push_back((NSOpenGLPixelFormatAttribute)settings.StencilBits);
if (settings.AntialiasingLevel > 0) { // [1]
attrs.push_back(NSOpenGLPFAMultisample);
attrs.push_back(NSOpenGLPFASampleBuffers);
attrs.push_back((NSOpenGLPixelFormatAttribute)1); // [2]
attrs.push_back(NSOpenGLPFASamples);
attrs.push_back((NSOpenGLPixelFormatAttribute)settings.AntialiasingLevel);
}
attrs.push_back((NSOpenGLPixelFormatAttribute)0); // end of array
// Create the pixel pormat.
NSOpenGLPixelFormat* pixFmt = [[NSOpenGLPixelFormat alloc] initWithAttributes:&attrs[0]];
if(pixFmt == nil) {
sf::Err() << "Error. Unable to find a suitable pixel format." << std::endl;
return;
}
// Use the shared context if one is given.
NSOpenGLContext* sharedContext = shared != NULL ? shared->myContext : nil;
// Create the context.
myContext = [[NSOpenGLContext alloc] initWithFormat:pixFmt
// Choose the attributs of OGL context.
std::vector<NSOpenGLPixelFormatAttribute> attrs;
attrs.reserve(20); // max attributs (estimation).
// These casts are safe. C++ is much more stric than Obj-C.
attrs.push_back(NSOpenGLPFAClosestPolicy);
attrs.push_back(NSOpenGLPFADoubleBuffer);
if (bitsPerPixel > 24) {
attrs.push_back(NSOpenGLPFAAlphaSize);
attrs.push_back((NSOpenGLPixelFormatAttribute)8);
}
attrs.push_back(NSOpenGLPFADepthSize);
attrs.push_back((NSOpenGLPixelFormatAttribute)settings.DepthBits);
attrs.push_back(NSOpenGLPFAStencilSize);
attrs.push_back((NSOpenGLPixelFormatAttribute)settings.StencilBits);
if (settings.AntialiasingLevel > 0) { // [1]
attrs.push_back(NSOpenGLPFAMultisample);
attrs.push_back(NSOpenGLPFASampleBuffers);
attrs.push_back((NSOpenGLPixelFormatAttribute)1); // [2]
attrs.push_back(NSOpenGLPFASamples);
attrs.push_back((NSOpenGLPixelFormatAttribute)settings.AntialiasingLevel);
}
attrs.push_back((NSOpenGLPixelFormatAttribute)0); // end of array
// Create the pixel pormat.
NSOpenGLPixelFormat* pixFmt = [[NSOpenGLPixelFormat alloc] initWithAttributes:&attrs[0]];
if(pixFmt == nil) {
sf::Err() << "Error. Unable to find a suitable pixel format." << std::endl;
return;
}
// Use the shared context if one is given.
NSOpenGLContext* sharedContext = shared != NULL ? shared->myContext : nil;
// Create the context.
myContext = [[NSOpenGLContext alloc] initWithFormat:pixFmt
shareContext:sharedContext];
// Free up.
[pixFmt release];
// Free up.
[pixFmt release];
#warning update settings with ogl version not yet implemented
// Save the creation settings
mySettings = settings;
// Save the creation settings
mySettings = settings;
}
} // namespace priv
} // namespace sf

View File

@ -29,9 +29,9 @@
#import <AppKit/AppKit.h>
namespace sf {
namespace priv {
class WindowImplCocoa;
}
namespace priv {
class WindowImplCocoa;
}
}
////////////////////////////////////////////////////////////
@ -40,10 +40,10 @@ namespace sf {
/// Handle event and send them back to the requester.
////////////////////////////////////////////////////////////
@interface SFOpenGLView : NSOpenGLView {
sf::priv::WindowImplCocoa* myRequester;
BOOL myUseKeyRepeat;
NSTrackingRectTag myTrackingTag;
BOOL myMouseIsIn;
sf::priv::WindowImplCocoa* myRequester;
BOOL myUseKeyRepeat;
NSTrackingRectTag myTrackingTag;
BOOL myMouseIsIn;
}

View File

@ -38,83 +38,83 @@
////////////////////////////////////////////////////////
-(id)initWithFrame:(NSRect)frameRect
{
if (self = [super initWithFrame:frameRect]) {
[self setRequesterTo:0];
[self enableKeyRepeat];
// Register for mouse-move event
myMouseIsIn = [self isMouseInside];
myTrackingTag = [self addTrackingRect:[self frame]
owner:self
userData:nil
assumeInside:myMouseIsIn];
// Register for resize event
NSNotificationCenter* center = [NSNotificationCenter defaultCenter];
[center addObserver:self
selector:@selector(frameDidChange:)
name:NSViewFrameDidChangeNotification
object:nil];
}
if (self = [super initWithFrame:frameRect]) {
[self setRequesterTo:0];
[self enableKeyRepeat];
// Register for mouse-move event
myMouseIsIn = [self isMouseInside];
myTrackingTag = [self addTrackingRect:[self frame]
owner:self
userData:nil
assumeInside:myMouseIsIn];
// Register for resize event
NSNotificationCenter* center = [NSNotificationCenter defaultCenter];
[center addObserver:self
selector:@selector(frameDidChange:)
name:NSViewFrameDidChangeNotification
object:nil];
}
return self;
return self;
}
////////////////////////////////////////////////////////
-(void)setRequesterTo:(sf::priv::WindowImplCocoa*)requester
{
myRequester = requester;
myRequester = requester;
}
////////////////////////////////////////////////////////
-(void)enableKeyRepeat
{
myUseKeyRepeat = YES;
myUseKeyRepeat = YES;
}
////////////////////////////////////////////////////////
-(void)disableKeyRepeat
{
myUseKeyRepeat = NO;
myUseKeyRepeat = NO;
}
////////////////////////////////////////////////////////
-(void)frameDidChange:(NSNotification*)notification
{
// Adapt tracking area for mouse mouse event.
[self removeTrackingRect:myTrackingTag];
myTrackingTag = [self addTrackingRect:[self frame]
owner:self
userData:nil
assumeInside:myMouseIsIn];
// Update the OGL view to fit the new size.
[self update];
// Send an event
if (myRequester == 0) return;
// The new size
NSSize newSize = [self frame].size;
myRequester->WindowResized(newSize.width, newSize.height);
// Adapt tracking area for mouse mouse event.
[self removeTrackingRect:myTrackingTag];
myTrackingTag = [self addTrackingRect:[self frame]
owner:self
userData:nil
assumeInside:myMouseIsIn];
// Update the OGL view to fit the new size.
[self update];
// Send an event
if (myRequester == 0) return;
// The new size
NSSize newSize = [self frame].size;
myRequester->WindowResized(newSize.width, newSize.height);
}
////////////////////////////////////////////////////////
-(BOOL)isMouseInside
{
NSPoint relativeToWindow = [[self window] mouseLocationOutsideOfEventStream];
NSPoint relativeToView = [self convertPoint:relativeToWindow fromView:nil];
if (NSPointInRect(relativeToView, [self frame])) {
return YES;
}
return NO;
NSPoint relativeToWindow = [[self window] mouseLocationOutsideOfEventStream];
NSPoint relativeToView = [self convertPoint:relativeToWindow fromView:nil];
if (NSPointInRect(relativeToView, [self frame])) {
return YES;
}
return NO;
}
@ -125,27 +125,27 @@
////////////////////////////////////////////////////////
-(void)dealloc
{
// Unregister
[[NSNotificationCenter defaultCenter] removeObserver:self];
[self removeTrackingRect:myTrackingTag];
[super dealloc];
// Unregister
[[NSNotificationCenter defaultCenter] removeObserver:self];
[self removeTrackingRect:myTrackingTag];
[super dealloc];
}
////////////////////////////////////////////////////////
-(BOOL)acceptsFirstResponder
{
// Accepts key event.
return YES;
// Accepts key event.
return YES;
}
////////////////////////////////////////////////////////
-(BOOL)canBecomeKeyView
{
// Accepts key event.
return YES;
// Accepts key event.
return YES;
}
@ -156,194 +156,194 @@
////////////////////////////////////////////////////////
-(void)mouseDown:(NSEvent*)theEvent
{
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseDownAt(sf::Mouse::Left, loc.x, h - loc.y);
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseDownAt(sf::Mouse::Left, loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)mouseUp:(NSEvent*)theEvent
{
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseUpAt(sf::Mouse::Left, loc.x, h - loc.y);
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseUpAt(sf::Mouse::Left, loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)mouseMoved:(NSEvent*)theEvent
{
if (myRequester == 0) return;
// If the event is not useful.
if (!myMouseIsIn) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseMovedAt(loc.x, h - loc.y);
if (myRequester == 0) return;
// If the event is not useful.
if (!myMouseIsIn) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseMovedAt(loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)scrollWheel:(NSEvent*)theEvent
{
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseWheelScrolledAt([theEvent deltaY], loc.x, h - loc.y);
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseWheelScrolledAt([theEvent deltaY], loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)mouseEntered:(NSEvent*)theEvent
{
myMouseIsIn = YES;
if (myRequester == 0) return;
myRequester->MouseMovedIn();
myMouseIsIn = YES;
if (myRequester == 0) return;
myRequester->MouseMovedIn();
}
////////////////////////////////////////////////////////
-(void)mouseExited:(NSEvent*)theEvent
{
myMouseIsIn = NO;
if (myRequester == 0) return;
myRequester->MouseMovedOut();
myMouseIsIn = NO;
if (myRequester == 0) return;
myRequester->MouseMovedOut();
}
////////////////////////////////////////////////////////
-(void)rightMouseDown:(NSEvent*)theEvent
{
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseDownAt(sf::Mouse::Right, loc.x, h - loc.y);
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseDownAt(sf::Mouse::Right, loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)rightMouseUp:(NSEvent*)theEvent
{
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseUpAt(sf::Mouse::Right, loc.x, h - loc.y);
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseUpAt(sf::Mouse::Right, loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)otherMouseDown:(NSEvent*)theEvent
{
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
sf::Mouse::Button button;
switch ([theEvent buttonNumber]) {
case 2:
button = sf::Mouse::Middle;
break;
case 3:
button = sf::Mouse::XButton1;
break;
case 4:
button = sf::Mouse::XButton2;
break;
default:
break;
}
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseDownAt(button, loc.x, h - loc.y);
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
sf::Mouse::Button button;
switch ([theEvent buttonNumber]) {
case 2:
button = sf::Mouse::Middle;
break;
case 3:
button = sf::Mouse::XButton1;
break;
case 4:
button = sf::Mouse::XButton2;
break;
default:
break;
}
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseDownAt(button, loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)otherMouseUp:(NSEvent*)theEvent
{
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
sf::Mouse::Button button;
switch ([theEvent buttonNumber]) {
case 2:
button = sf::Mouse::Middle;
break;
case 3:
button = sf::Mouse::XButton1;
break;
case 4:
button = sf::Mouse::XButton2;
break;
default:
break;
}
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseUpAt(button, loc.x, h - loc.y);
if (myRequester == 0) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
sf::Mouse::Button button;
switch ([theEvent buttonNumber]) {
case 2:
button = sf::Mouse::Middle;
break;
case 3:
button = sf::Mouse::XButton1;
break;
case 4:
button = sf::Mouse::XButton2;
break;
default:
break;
}
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseUpAt(button, loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)rightMouseDragged:(NSEvent*)theEvent
{
if (myRequester == 0) return;
// If the event is not useful.
if (!myMouseIsIn) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseMovedAt(loc.x, h - loc.y);
if (myRequester == 0) return;
// If the event is not useful.
if (!myMouseIsIn) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseMovedAt(loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)mouseDragged:(NSEvent*)theEvent
{
if (myRequester == 0) return;
// If the event is not useful.
if (!myMouseIsIn) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseMovedAt(loc.x, h - loc.y);
if (myRequester == 0) return;
// If the event is not useful.
if (!myMouseIsIn) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseMovedAt(loc.x, h - loc.y);
}
////////////////////////////////////////////////////////
-(void)otherMouseDragged:(NSEvent*)theEvent
{
if (myRequester == 0) return;
// If the event is not useful.
if (!myMouseIsIn) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseMovedAt(loc.x, h - loc.y);
if (myRequester == 0) return;
// If the event is not useful.
if (!myMouseIsIn) return;
NSPoint loc = [self convertPoint:[theEvent locationInWindow] fromView:nil];
// Don't forget to change to SFML coord system.
float h = [self frame].size.height;
myRequester->MouseMovedAt(loc.x, h - loc.y);
}
@ -354,22 +354,22 @@
////////////////////////////////////////////////////////
-(void)keyDown:(NSEvent*)theEvent
{
if (myRequester == 0) return;
if (myUseKeyRepeat || ![theEvent isARepeat])
myRequester->KeyDown([theEvent keyCode], [theEvent modifierFlags]);
if ((myUseKeyRepeat || ![theEvent isARepeat]) && [[theEvent characters] length] > 0)
myRequester->TextEntred([[theEvent characters] characterAtIndex:0]);
if (myRequester == 0) return;
if (myUseKeyRepeat || ![theEvent isARepeat])
myRequester->KeyDown([theEvent keyCode], [theEvent modifierFlags]);
if ((myUseKeyRepeat || ![theEvent isARepeat]) && [[theEvent characters] length] > 0)
myRequester->TextEntred([[theEvent characters] characterAtIndex:0]);
}
////////////////////////////////////////////////////////
-(void)keyUp:(NSEvent*)theEvent
{
if (myRequester == 0) return;
myRequester->KeyUp([theEvent keyCode], [theEvent modifierFlags]);
if (myRequester == 0) return;
myRequester->KeyUp([theEvent keyCode], [theEvent modifierFlags]);
}
@end

View File

@ -33,13 +33,13 @@
////////////////////////////////////////////////////////
-(BOOL)acceptsFirstResponder {
return YES;
return YES;
}
////////////////////////////////////////////////////////
-(BOOL)canBecomeKeyWindow {
return YES;
return YES;
}
@end

View File

@ -33,10 +33,10 @@
/// Predefine some classes
////////////////////////////////////////////////////////////
namespace sf {
namespace priv {
class WindowImplCocoa;
}
class VideoMode;
namespace priv {
class WindowImplCocoa;
}
class VideoMode;
}
@class SFOpenGLView;
@ -56,9 +56,9 @@ namespace sf {
#else
@interface SFWindowController : NSResponder <WindowImplDelegateProtocol, NSWindowDelegate> {
#endif
NSWindow* myWindow;
SFOpenGLView* myOGLView;
sf::priv::WindowImplCocoa* myRequester;
NSWindow* myWindow;
SFOpenGLView* myOGLView;
sf::priv::WindowImplCocoa* myRequester;
}
-(id)initWithWindow:(NSWindow*)window;

View File

@ -46,146 +46,146 @@
////////////////////////////////////////////////////////
-(id)initWithWindow:(NSWindow*)window
{
if (self = [super init]) {
myRequester = 0;
// Retain the window for our own use.
myWindow = [window retain];
if (myWindow == nil) {
sf::Err()
<< "No window was given to initWithWindow:."
<< std::endl;
return self;
}
// Create the view.
myOGLView = [[SFOpenGLView alloc] initWithFrame:[[myWindow contentView] frame]];
if (myOGLView == nil) {
sf::Err()
<< "Could not create an instance of NSOpenGLView "
<< "in (SFWindowController -initWithMode:andStyle:)."
<< std::endl;
return self;
}
// Set the view to the window as its content view.
[myWindow setContentView:myOGLView];
}
return self;
if (self = [super init]) {
myRequester = 0;
// Retain the window for our own use.
myWindow = [window retain];
if (myWindow == nil) {
sf::Err()
<< "No window was given to initWithWindow:."
<< std::endl;
return self;
}
// Create the view.
myOGLView = [[SFOpenGLView alloc] initWithFrame:[[myWindow contentView] frame]];
if (myOGLView == nil) {
sf::Err()
<< "Could not create an instance of NSOpenGLView "
<< "in (SFWindowController -initWithMode:andStyle:)."
<< std::endl;
return self;
}
// Set the view to the window as its content view.
[myWindow setContentView:myOGLView];
}
return self;
}
////////////////////////////////////////////////////////
-(id)initWithMode:(sf::VideoMode const*)mode andStyle:(unsigned long)style
{
if (self = [super init]) {
myRequester = 0;
// Create our window size.
NSRect rect = NSMakeRect(0, 0, mode->Width, mode->Height);
// Convert the SFML window style to Cocoa window style.
unsigned int nsStyle = NSBorderlessWindowMask;
if (!(style & sf::Style::Fullscreen)) { // if fullscrean we keep our NSBorderlessWindowMask.
if (style & sf::Style::Titlebar) nsStyle |= NSTitledWindowMask | NSMiniaturizableWindowMask;
if (style & sf::Style::Resize) nsStyle |= NSResizableWindowMask;
if (style & sf::Style::Close) nsStyle |= NSClosableWindowMask;
}
// Create the window.
myWindow = [[SFWindow alloc] initWithContentRect:rect
styleMask:nsStyle
backing:NSBackingStoreBuffered
defer:NO];
/*
"YES" produces some "invalid drawable".
See http://www.cocoabuilder.com/archive/cocoa/152482-nsviews-and-nsopenglcontext-invalid-drawable-error.html
[...]
As best as I can figure, this is happening because the NSWindow (and
hence my view) are not visible onscreen yet, and the system doesn't like that.
[...]
*/
if (myWindow == nil) {
sf::Err()
<< "Could not create an instance of NSWindow "
<< "in (SFWindowController -initWithMode:andStyle:)."
<< std::endl;
return self;
}
// Apply special feature for fullscreen window.
if (style & sf::Style::Fullscreen) {
// We place the window above everything else.
[myWindow setLevel:NSMainMenuWindowLevel+1];
[myWindow setOpaque:YES];
[myWindow setHidesOnDeactivate:YES];
/* ---------------------------
* | Note for future version |
* ---------------------------
*
* starting with OS 10.5 NSView provides
* a new method -enterFullScreenMode:withOptions:
* which could be a good alternative.
*/
} else {
// Center the window to be cool =)
[myWindow center];
}
// Create the view.
myOGLView = [[SFOpenGLView alloc] initWithFrame:[[myWindow contentView] frame]];
if (myOGLView == nil) {
sf::Err()
<< "Could not create an instance of NSOpenGLView "
<< "in (SFWindowController -initWithMode:andStyle:)."
<< std::endl;
return self;
}
// Set the view to the window as its content view.
[myWindow setContentView:myOGLView];
// Register for event.
[myWindow setDelegate:self];
[myWindow setAcceptsMouseMovedEvents:YES];
[myWindow setIgnoresMouseEvents:NO];
// And some other things...
[myWindow setAutodisplay:YES];
[myWindow setReleasedWhenClosed:NO];
} // if super init ok
return self;
{
if (self = [super init]) {
myRequester = 0;
// Create our window size.
NSRect rect = NSMakeRect(0, 0, mode->Width, mode->Height);
// Convert the SFML window style to Cocoa window style.
unsigned int nsStyle = NSBorderlessWindowMask;
if (!(style & sf::Style::Fullscreen)) { // if fullscrean we keep our NSBorderlessWindowMask.
if (style & sf::Style::Titlebar) nsStyle |= NSTitledWindowMask | NSMiniaturizableWindowMask;
if (style & sf::Style::Resize) nsStyle |= NSResizableWindowMask;
if (style & sf::Style::Close) nsStyle |= NSClosableWindowMask;
}
// Create the window.
myWindow = [[SFWindow alloc] initWithContentRect:rect
styleMask:nsStyle
backing:NSBackingStoreBuffered
defer:NO];
/*
"YES" produces some "invalid drawable".
See http://www.cocoabuilder.com/archive/cocoa/152482-nsviews-and-nsopenglcontext-invalid-drawable-error.html
[...]
As best as I can figure, this is happening because the NSWindow (and
hence my view) are not visible onscreen yet, and the system doesn't like that.
[...]
*/
if (myWindow == nil) {
sf::Err()
<< "Could not create an instance of NSWindow "
<< "in (SFWindowController -initWithMode:andStyle:)."
<< std::endl;
return self;
}
// Apply special feature for fullscreen window.
if (style & sf::Style::Fullscreen) {
// We place the window above everything else.
[myWindow setLevel:NSMainMenuWindowLevel+1];
[myWindow setOpaque:YES];
[myWindow setHidesOnDeactivate:YES];
/* ---------------------------
* | Note for future version |
* ---------------------------
*
* starting with OS 10.5 NSView provides
* a new method -enterFullScreenMode:withOptions:
* which could be a good alternative.
*/
} else {
// Center the window to be cool =)
[myWindow center];
}
// Create the view.
myOGLView = [[SFOpenGLView alloc] initWithFrame:[[myWindow contentView] frame]];
if (myOGLView == nil) {
sf::Err()
<< "Could not create an instance of NSOpenGLView "
<< "in (SFWindowController -initWithMode:andStyle:)."
<< std::endl;
return self;
}
// Set the view to the window as its content view.
[myWindow setContentView:myOGLView];
// Register for event.
[myWindow setDelegate:self];
[myWindow setAcceptsMouseMovedEvents:YES];
[myWindow setIgnoresMouseEvents:NO];
// And some other things...
[myWindow setAutodisplay:YES];
[myWindow setReleasedWhenClosed:NO];
} // if super init ok
return self;
}
////////////////////////////////////////////////////////
-(void)dealloc
{
[self closeWindow];
[myWindow release];
[myOGLView release];
[super dealloc];
[self closeWindow];
[myWindow release];
[myOGLView release];
[super dealloc];
}
@ -196,195 +196,195 @@
////////////////////////////////////////////////////////
-(void)setRequesterTo:(sf::priv::WindowImplCocoa*)requester
{
// Forward to the view.
[myOGLView setRequesterTo:requester];
myRequester = requester;
// Forward to the view.
[myOGLView setRequesterTo:requester];
myRequester = requester;
}
////////////////////////////////////////////////////////
-(sf::WindowHandle)getSystemHandle
{
return myWindow;
return myWindow;
}
////////////////////////////////////////////////////////
-(void)hideMouseCursor
{
[NSCursor hide];
[NSCursor hide];
}
////////////////////////////////////////////////////////
-(void)showMouseCursor
{
[NSCursor unhide];
[NSCursor unhide];
}
////////////////////////////////////////////////////////
-(void)setCursorPositionToX:(unsigned int)x Y:(unsigned int)y
{
// Create a SFML event.
if (myRequester == 0) return;
myRequester->MouseMovedAt(x, y);
// Flip for SFML window coordinate system
y = NSHeight([myWindow frame]) - y;
// Adjust for view reference instead of window
y -= NSHeight([myWindow frame]) - NSHeight([myOGLView frame]);
// Convert to screen coordinates
NSPoint screenCoord = [myWindow convertBaseToScreen:NSMakePoint(x, y)];
// Flip screen coodinates
float const screenHeight = NSHeight([[myWindow screen] frame]);
screenCoord.y = screenHeight - screenCoord.y;
CGDirectDisplayID screenNumber = (CGDirectDisplayID)[[[[myWindow screen] deviceDescription] valueForKey:@"NSScreenNumber"] intValue];
// Place the cursor.
CGDisplayMoveCursorToPoint(screenNumber, CGPointMake(screenCoord.x, screenCoord.y));
/*
CGDisplayMoveCursorToPoint -- Discussion :
No events are generated as a result of this move.
Points that lie outside the desktop are clipped to the desktop.
*/
// Create a SFML event.
if (myRequester == 0) return;
myRequester->MouseMovedAt(x, y);
// Flip for SFML window coordinate system
y = NSHeight([myWindow frame]) - y;
// Adjust for view reference instead of window
y -= NSHeight([myWindow frame]) - NSHeight([myOGLView frame]);
// Convert to screen coordinates
NSPoint screenCoord = [myWindow convertBaseToScreen:NSMakePoint(x, y)];
// Flip screen coodinates
float const screenHeight = NSHeight([[myWindow screen] frame]);
screenCoord.y = screenHeight - screenCoord.y;
CGDirectDisplayID screenNumber = (CGDirectDisplayID)[[[[myWindow screen] deviceDescription] valueForKey:@"NSScreenNumber"] intValue];
// Place the cursor.
CGDisplayMoveCursorToPoint(screenNumber, CGPointMake(screenCoord.x, screenCoord.y));
/*
CGDisplayMoveCursorToPoint -- Discussion :
No events are generated as a result of this move.
Points that lie outside the desktop are clipped to the desktop.
*/
}
////////////////////////////////////////////////////////.
-(void)setWindowPositionToX:(unsigned int)x Y:(unsigned int)y
{
NSPoint point = NSMakePoint(x, y);
// Flip for SFML window coordinate system.
point.y = NSHeight([[myWindow screen] visibleFrame]) - point.y;
// Place the window.
[myWindow setFrameTopLeftPoint:point];
NSPoint point = NSMakePoint(x, y);
// Flip for SFML window coordinate system.
point.y = NSHeight([[myWindow screen] visibleFrame]) - point.y;
// Place the window.
[myWindow setFrameTopLeftPoint:point];
}
////////////////////////////////////////////////////////
-(void)resizeTo:(unsigned int)width by:(unsigned int)height
{
// Add titlebar height.
NSRect frame = NSMakeRect([myWindow frame].origin.x,
[myWindow frame].origin.y,
width,
height + [self titlebarHeight]);
[myWindow setFrame:frame display:YES];
// Add titlebar height.
NSRect frame = NSMakeRect([myWindow frame].origin.x,
[myWindow frame].origin.y,
width,
height + [self titlebarHeight]);
[myWindow setFrame:frame display:YES];
}
////////////////////////////////////////////////////////
-(void)changeTitle:(NSString*)title
{
[myWindow setTitle:title];
[myWindow setTitle:title];
}
////////////////////////////////////////////////////////
-(void)hideWindow
{
[myWindow orderOut:nil];
[myWindow orderOut:nil];
}
////////////////////////////////////////////////////////
-(void)showWindow
{
[myWindow makeKeyAndOrderFront:nil];
[myWindow makeKeyAndOrderFront:nil];
}
////////////////////////////////////////////////////////
-(void)closeWindow
{
[myWindow close];
[myWindow close];
}
////////////////////////////////////////////////////////
-(void)enableKeyRepeat
{
[myOGLView enableKeyRepeat];
[myOGLView enableKeyRepeat];
}
////////////////////////////////////////////////////////
-(void)disableKeyRepeat
{
[myOGLView disableKeyRepeat];
[myOGLView disableKeyRepeat];
}
////////////////////////////////////////////////////////
-(void)setIconTo:(unsigned int)width
by:(unsigned int)height
with:(sf::Uint8 const*)pixels
-(void)setIconTo:(unsigned int)width
by:(unsigned int)height
with:(sf::Uint8 const*)pixels
{
// Create an empty image representation.
NSBitmapImageRep* bitmap =
[[NSBitmapImageRep alloc] initWithBitmapDataPlanes:0 // if 0 : only allocate memory
pixelsWide:width
pixelsHigh:height
bitsPerSample:8 // The number of bits used to specify
// one pixel in a single component of the data.
samplesPerPixel:4 // 3 if no alpha, 4 with it
hasAlpha:YES
isPlanar:NO // I don't know what it is but it works
colorSpaceName:NSCalibratedRGBColorSpace
bytesPerRow:0 // 0 == determine automatically
bitsPerPixel:0]; // 0 == determine automatically
// Load data pixels.
// Create an empty image representation.
NSBitmapImageRep* bitmap =
[[NSBitmapImageRep alloc] initWithBitmapDataPlanes:0 // if 0 : only allocate memory
pixelsWide:width
pixelsHigh:height
bitsPerSample:8 // The number of bits used to specify
// one pixel in a single component of the data.
samplesPerPixel:4 // 3 if no alpha, 4 with it
hasAlpha:YES
isPlanar:NO // I don't know what it is but it works
colorSpaceName:NSCalibratedRGBColorSpace
bytesPerRow:0 // 0 == determine automatically
bitsPerPixel:0]; // 0 == determine automatically
// Load data pixels.
#if MAC_OS_X_VERSION_MAX_ALLOWED < 1050 // We may need to define NSUInteger.
#define NSUInteger unsigned int
#endif
for (unsigned int y = 0; y < height; ++y) {
for (unsigned int x = 0; x < width; ++x, pixels+=4) {
NSUInteger pixel[4] = { pixels[0], pixels[1], pixels[2], pixels[3] };
[bitmap setPixel:pixel
atX:x
y:y];
}
}
// Create an image from the representation.
NSImage* icon = [[NSImage alloc] initWithSize:NSMakeSize(width, height)];
[icon addRepresentation:bitmap];
// Set app icon.
[[NSApplication sharedApplication] setApplicationIconImage:icon];
// Free up.
[icon release];
[bitmap release];
for (unsigned int y = 0; y < height; ++y) {
for (unsigned int x = 0; x < width; ++x, pixels+=4) {
NSUInteger pixel[4] = { pixels[0], pixels[1], pixels[2], pixels[3] };
[bitmap setPixel:pixel
atX:x
y:y];
}
}
// Create an image from the representation.
NSImage* icon = [[NSImage alloc] initWithSize:NSMakeSize(width, height)];
[icon addRepresentation:bitmap];
// Set app icon.
[[NSApplication sharedApplication] setApplicationIconImage:icon];
// Free up.
[icon release];
[bitmap release];
}
////////////////////////////////////////////////////////
-(void)processEventWithBlockingMode:(BOOL)block
{
// If we don't have a requester we don't fetch event.
if (myRequester != 0) {
[SFApplication processEventWithBlockingMode:block];
}
// If we don't have a requester we don't fetch event.
if (myRequester != 0) {
[SFApplication processEventWithBlockingMode:block];
}
}
////////////////////////////////////////////////////////
-(void)applyContext:(NSOpenGLContext*)context
{
[myOGLView setOpenGLContext:context];
[context setView:myOGLView];
[myOGLView setOpenGLContext:context];
[context setView:myOGLView];
}
@ -395,26 +395,26 @@
////////////////////////////////////////////////////////
-(BOOL)windowShouldClose:(id)sender
{
if (myRequester == 0) return YES;
myRequester->WindowClosed();
return NO;
if (myRequester == 0) return YES;
myRequester->WindowClosed();
return NO;
}
////////////////////////////////////////////////////////
-(void)windowDidBecomeKey:(NSNotification*)notification {
if (myRequester == 0) return;
myRequester->WindowGainedFocus();
if (myRequester == 0) return;
myRequester->WindowGainedFocus();
}
////////////////////////////////////////////////////////
-(void)windowDidResignKey:(NSNotification*)notification {
if (myRequester == 0) return;
myRequester->WindowLostFocus();
if (myRequester == 0) return;
myRequester->WindowLostFocus();
}
@ -423,7 +423,7 @@
////////////////////////////////////////////////////////
-(float)titlebarHeight {
return NSHeight([myWindow frame]) - NSHeight([[myWindow contentView] frame]);
return NSHeight([myWindow frame]) - NSHeight([[myWindow contentView] frame]);
}
@end

View File

@ -45,71 +45,71 @@ namespace priv
size_t DisplayBitsPerPixel(CGDirectDisplayID displayId)
{
#if MAC_OS_X_VERSION_MAX_ALLOWED < 1060
return CGDisplayBitsPerPixel(displayId);
return CGDisplayBitsPerPixel(displayId);
#else // MAC_OS_X_VERSION_MAX_ALLOWED >= 1060
CGDisplayModeRef mode = CGDisplayCopyDisplayMode(displayId);
CGDisplayModeRef mode = CGDisplayCopyDisplayMode(displayId);
CFStringRef pixEnc = CGDisplayModeCopyPixelEncoding(mode);
if(CFStringCompare(pixEnc, CFSTR(IO32BitDirectPixels), kCFCompareCaseInsensitive) == kCFCompareEqualTo)
return 32;
else if(CFStringCompare(pixEnc, CFSTR(IO16BitDirectPixels), kCFCompareCaseInsensitive) == kCFCompareEqualTo)
return 16;
else if(CFStringCompare(pixEnc, CFSTR(IO8BitIndexedPixels), kCFCompareCaseInsensitive) == kCFCompareEqualTo)
return 8;
CFStringRef pixEnc = CGDisplayModeCopyPixelEncoding(mode);
if(CFStringCompare(pixEnc, CFSTR(IO32BitDirectPixels), kCFCompareCaseInsensitive) == kCFCompareEqualTo)
return 32;
else if(CFStringCompare(pixEnc, CFSTR(IO16BitDirectPixels), kCFCompareCaseInsensitive) == kCFCompareEqualTo)
return 16;
else if(CFStringCompare(pixEnc, CFSTR(IO8BitIndexedPixels), kCFCompareCaseInsensitive) == kCFCompareEqualTo)
return 8;
return 0; // no match
return 0; // no match
#endif
}
////////////////////////////////////////////////////////////
std::vector<VideoMode> VideoModeImpl::GetFullscreenModes()
{
std::vector<VideoMode> modes;
CGDisplayCount count = 0;
int err = CGGetActiveDisplayList(0, NULL, &count);
if (err != 0) {
sf::Err() << "Error when retrieving displays count";
return modes;
}
CGDirectDisplayID* displays = new CGDirectDisplayID[count];
err = CGGetActiveDisplayList(count, displays, &count);
if (err != 0) {
sf::Err() << "Error when retrieving displays array";
return modes;
}
for (int i = 0; i < count; ++i) {
VideoMode mode(CGDisplayPixelsWide(displays[i]),
CGDisplayPixelsHigh(displays[i]),
DisplayBitsPerPixel(displays[i]));
// Add it only if it isn't already in the array.
if (std::find(modes.begin(), modes.end(), mode) == modes.end())
modes.push_back(mode);
}
delete[] displays;
return modes;
std::vector<VideoMode> modes;
CGDisplayCount count = 0;
int err = CGGetActiveDisplayList(0, NULL, &count);
if (err != 0) {
sf::Err() << "Error when retrieving displays count";
return modes;
}
CGDirectDisplayID* displays = new CGDirectDisplayID[count];
err = CGGetActiveDisplayList(count, displays, &count);
if (err != 0) {
sf::Err() << "Error when retrieving displays array";
return modes;
}
for (int i = 0; i < count; ++i) {
VideoMode mode(CGDisplayPixelsWide(displays[i]),
CGDisplayPixelsHigh(displays[i]),
DisplayBitsPerPixel(displays[i]));
// Add it only if it isn't already in the array.
if (std::find(modes.begin(), modes.end(), mode) == modes.end())
modes.push_back(mode);
}
delete[] displays;
return modes;
}
////////////////////////////////////////////////////////////
VideoMode VideoModeImpl::GetDesktopMode()
{
CGDirectDisplayID display = CGMainDisplayID();
return VideoMode(CGDisplayPixelsWide(display),
CGDisplayPixelsHigh(display),
DisplayBitsPerPixel(display));
CGDirectDisplayID display = CGMainDisplayID();
return VideoMode(CGDisplayPixelsWide(display),
CGDisplayPixelsHigh(display),
DisplayBitsPerPixel(display));
}
} // namespace priv

View File

@ -65,157 +65,157 @@ namespace priv
class WindowImplCocoa : public WindowImpl
{
public:
////////////////////////////////////////////////////////////
/// \brief Construct the window implementation from an existing control
///
/// \param handle Platform-specific handle of the control
///
////////////////////////////////////////////////////////////
WindowImplCocoa(WindowHandle handle);
////////////////////////////////////////////////////////////
/// \brief Create the window implementation
///
/// \param mode Video mode to use
/// \param title Title of the window
/// \param style Window style (resizable, fixed, or fullscren)
///
////////////////////////////////////////////////////////////
WindowImplCocoa(VideoMode mode, const std::string& title, unsigned long style);
////////////////////////////////////////////////////////////
/// \brief Destructor
///
////////////////////////////////////////////////////////////
~WindowImplCocoa();
/// Events
void WindowClosed(void);
void WindowResized(unsigned int width, unsigned int height);
void WindowLostFocus(void);
void WindowGainedFocus(void);
void MouseDownAt(Mouse::Button button, int x, int y);
void MouseUpAt(Mouse::Button button, int x, int y);
void MouseMovedAt(int x, int y);
void MouseWheelScrolledAt(float delta, int x, int y);
void MouseMovedIn(void);
void MouseMovedOut(void);
void KeyDown(unsigned short keycode, unsigned int modifierFlags);
void KeyUp(unsigned short keycode, unsigned int modifierFlags);
void TextEntred(Uint32 charcode);
static Key::Code NSKeyCodeToSFMLKeyCode(unsigned short rawchar);
////////////////////////////////////////////////////////////
///
////////////////////////////////////////////////////////////
void ApplyContext(NSOpenGLContextRef context) const;
////////////////////////////////////////////////////////////
/// \brief Construct the window implementation from an existing control
///
/// \param handle Platform-specific handle of the control
///
////////////////////////////////////////////////////////////
WindowImplCocoa(WindowHandle handle);
////////////////////////////////////////////////////////////
/// \brief Create the window implementation
///
/// \param mode Video mode to use
/// \param title Title of the window
/// \param style Window style (resizable, fixed, or fullscren)
///
////////////////////////////////////////////////////////////
WindowImplCocoa(VideoMode mode, const std::string& title, unsigned long style);
////////////////////////////////////////////////////////////
/// \brief Destructor
///
////////////////////////////////////////////////////////////
~WindowImplCocoa();
/// Events
void WindowClosed(void);
void WindowResized(unsigned int width, unsigned int height);
void WindowLostFocus(void);
void WindowGainedFocus(void);
void MouseDownAt(Mouse::Button button, int x, int y);
void MouseUpAt(Mouse::Button button, int x, int y);
void MouseMovedAt(int x, int y);
void MouseWheelScrolledAt(float delta, int x, int y);
void MouseMovedIn(void);
void MouseMovedOut(void);
void KeyDown(unsigned short keycode, unsigned int modifierFlags);
void KeyUp(unsigned short keycode, unsigned int modifierFlags);
void TextEntred(Uint32 charcode);
static Key::Code NSKeyCodeToSFMLKeyCode(unsigned short rawchar);
////////////////////////////////////////////////////////////
///
////////////////////////////////////////////////////////////
void ApplyContext(NSOpenGLContextRef context) const;
private:
////////////////////////////////////////////////////////////
/// \brief Process incoming events from the operating system
///
/// \param block Use true to block the thread until an event arrives
///
////////////////////////////////////////////////////////////
virtual void ProcessEvents(bool block);
////////////////////////////////////////////////////////////
/// \brief Get the OS-specific handle of the window
///
/// \return Handle of the window
///
////////////////////////////////////////////////////////////
virtual WindowHandle GetSystemHandle() const;
////////////////////////////////////////////////////////////
/// \brief Show or hide the mouse cursor
///
/// \param show True to show, false to hide
///
////////////////////////////////////////////////////////////
virtual void ShowMouseCursor(bool show);
////////////////////////////////////////////////////////////
/// \brief Change the position of the mouse cursor
///
/// \param x Left coordinate of the cursor, relative to the window
/// \param y Top coordinate of the cursor, relative to the window
///
////////////////////////////////////////////////////////////
virtual void SetCursorPosition(unsigned int x, unsigned int y);
////////////////////////////////////////////////////////////
/// \brief Change the position of the window on screen
///
/// \param x Left position
/// \param y Top position
///
////////////////////////////////////////////////////////////
virtual void SetPosition(int x, int y);
////////////////////////////////////////////////////////////
/// \brief Change the size of the rendering region of the window
///
/// \param width New width
/// \param height New height
///
////////////////////////////////////////////////////////////
virtual void SetSize(unsigned int width, unsigned int height);
////////////////////////////////////////////////////////////
/// \brief Change the title of the window
///
/// \param title New title
///
////////////////////////////////////////////////////////////
virtual void SetTitle(const std::string& title);
////////////////////////////////////////////////////////////
/// \brief Show or hide the window
///
/// \param show True to show, false to hide
///
////////////////////////////////////////////////////////////
virtual void Show(bool show);
////////////////////////////////////////////////////////////
/// \brief Enable or disable automatic key-repeat
///
/// \param enabled True to enable, false to disable
///
////////////////////////////////////////////////////////////
virtual void EnableKeyRepeat(bool enabled);
////////////////////////////////////////////////////////////
/// \brief Change the window's icon
///
/// \param width Icon's width, in pixels
/// \param height Icon's height, in pixels
/// \param pixels Pointer to the pixels in memory, format must be RGBA 32 bits
///
////////////////////////////////////////////////////////////
virtual void SetIcon(unsigned int width, unsigned int height, const Uint8* pixels);
////////////////////////////////////////////////////////////
/// \brief Construct the pool after ensuring NSApp is valid.
////////////////////////////////////////////////////////////
void SetUpPoolAndApplication(void);
////////////////////////////////////////////////////////////
/// \brief Change the type of the current process to become a full GUI app.
////////////////////////////////////////////////////////////
static void SetUpProcessAsApplication(void);
////////////////////////////////////////////////////////////
// Member data
////////////////////////////////////////////////////////////
WindowImplDelegateRef myDelegate; ///< Implementation in Obj-C.
NSAutoreleasePoolRef myPool; ///< Memory manager for this class.
////////////////////////////////////////////////////////////
/// \brief Process incoming events from the operating system
///
/// \param block Use true to block the thread until an event arrives
///
////////////////////////////////////////////////////////////
virtual void ProcessEvents(bool block);
////////////////////////////////////////////////////////////
/// \brief Get the OS-specific handle of the window
///
/// \return Handle of the window
///
////////////////////////////////////////////////////////////
virtual WindowHandle GetSystemHandle() const;
////////////////////////////////////////////////////////////
/// \brief Show or hide the mouse cursor
///
/// \param show True to show, false to hide
///
////////////////////////////////////////////////////////////
virtual void ShowMouseCursor(bool show);
////////////////////////////////////////////////////////////
/// \brief Change the position of the mouse cursor
///
/// \param x Left coordinate of the cursor, relative to the window
/// \param y Top coordinate of the cursor, relative to the window
///
////////////////////////////////////////////////////////////
virtual void SetCursorPosition(unsigned int x, unsigned int y);
////////////////////////////////////////////////////////////
/// \brief Change the position of the window on screen
///
/// \param x Left position
/// \param y Top position
///
////////////////////////////////////////////////////////////
virtual void SetPosition(int x, int y);
////////////////////////////////////////////////////////////
/// \brief Change the size of the rendering region of the window
///
/// \param width New width
/// \param height New height
///
////////////////////////////////////////////////////////////
virtual void SetSize(unsigned int width, unsigned int height);
////////////////////////////////////////////////////////////
/// \brief Change the title of the window
///
/// \param title New title
///
////////////////////////////////////////////////////////////
virtual void SetTitle(const std::string& title);
////////////////////////////////////////////////////////////
/// \brief Show or hide the window
///
/// \param show True to show, false to hide
///
////////////////////////////////////////////////////////////
virtual void Show(bool show);
////////////////////////////////////////////////////////////
/// \brief Enable or disable automatic key-repeat
///
/// \param enabled True to enable, false to disable
///
////////////////////////////////////////////////////////////
virtual void EnableKeyRepeat(bool enabled);
////////////////////////////////////////////////////////////
/// \brief Change the window's icon
///
/// \param width Icon's width, in pixels
/// \param height Icon's height, in pixels
/// \param pixels Pointer to the pixels in memory, format must be RGBA 32 bits
///
////////////////////////////////////////////////////////////
virtual void SetIcon(unsigned int width, unsigned int height, const Uint8* pixels);
////////////////////////////////////////////////////////////
/// \brief Construct the pool after ensuring NSApp is valid.
////////////////////////////////////////////////////////////
void SetUpPoolAndApplication(void);
////////////////////////////////////////////////////////////
/// \brief Change the type of the current process to become a full GUI app.
////////////////////////////////////////////////////////////
static void SetUpProcessAsApplication(void);
////////////////////////////////////////////////////////////
// Member data
////////////////////////////////////////////////////////////
WindowImplDelegateRef myDelegate; ///< Implementation in Obj-C.
NSAutoreleasePoolRef myPool; ///< Memory manager for this class.
};
} // namespace priv
} // namespace sf

View File

@ -45,455 +45,454 @@ namespace priv
////////////////////////////////////////////////////////////
WindowImplCocoa::WindowImplCocoa(WindowHandle handle)
{
sf::Err() << "Not yet fully supported." << std::endl;
sf::Err() << "Not yet fully supported." << std::endl;
#warning WindowImplCocoa(WindowHandle handle) not yet fully implemented
SetUpPoolAndApplication();
// Treat the handle as it real type
id nsHandle = (id)handle;
if ([nsHandle isKindOfClass:[NSWindow class]]) {
// We have a window.
myDelegate = [[SFWindowController alloc] initWithWindow:nsHandle];
} /*else if ([nsHandle isKindOfClass:[NSView class]]) {
// We have a view.
myDelegate = [[SFViewController alloc] initWithView:nsHandle];
} */ else {
sf::Err()
<< "Cannot import this Window Handle because it is neither "
<< "a <NSWindow*> nor <NSView*> object "
<< "(or any of their subclasses). You gave a <"
<< [[nsHandle className] UTF8String]
<< "> object."
<< std::endl;
return;
}
// NO :
// [myDelegate setRequesterTo:this];
// because we don't handle event.
SetUpPoolAndApplication();
// Treat the handle as it real type
id nsHandle = (id)handle;
if ([nsHandle isKindOfClass:[NSWindow class]]) {
// We have a window.
myDelegate = [[SFWindowController alloc] initWithWindow:nsHandle];
} /*else if ([nsHandle isKindOfClass:[NSView class]]) {
// We have a view.
myDelegate = [[SFViewController alloc] initWithView:nsHandle];
} */ else {
sf::Err()
<< "Cannot import this Window Handle because it is neither "
<< "a <NSWindow*> nor <NSView*> object "
<< "(or any of their subclasses). You gave a <"
<< [[nsHandle className] UTF8String]
<< "> object."
<< std::endl;
return;
}
// NO :
// [myDelegate setRequesterTo:this];
// because we don't handle event.
}
////////////////////////////////////////////////////////////
WindowImplCocoa::WindowImplCocoa(VideoMode mode,
const std::string& title,
unsigned long style)
const std::string& title,
unsigned long style)
{
SetUpPoolAndApplication();
// Don't forget to update our parent (that is, WindowImpl) size :
myWidth = mode.Width;
myHeight = mode.Height;
myDelegate = [[SFWindowController alloc] initWithMode:&mode andStyle:style];
[myDelegate changeTitle:stringToNSString(title)];
[myDelegate setRequesterTo:this];
SetUpPoolAndApplication();
// Don't forget to update our parent (that is, WindowImpl) size :
myWidth = mode.Width;
myHeight = mode.Height;
myDelegate = [[SFWindowController alloc] initWithMode:&mode andStyle:style];
[myDelegate changeTitle:stringToNSString(title)];
[myDelegate setRequesterTo:this];
}
////////////////////////////////////////////////////////////
WindowImplCocoa::~WindowImplCocoa()
{
[myDelegate closeWindow];
[myDelegate release];
[myPool drain];
[myDelegate closeWindow];
[myDelegate release];
[myPool drain];
}
////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////
void WindowImplCocoa::ApplyContext(NSOpenGLContextRef context) const
{
[myDelegate applyContext:context];
[myDelegate applyContext:context];
}
#pragma mark
#pragma mark WindowImplCocoa's window-event methods
////////////////////////////////////////////////////////////
void WindowImplCocoa::WindowClosed(void)
{
Event event;
event.Type = Event::Closed;
PushEvent(event);
{
Event event;
event.Type = Event::Closed;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::WindowResized(unsigned int width, unsigned int height)
{
// Don't forget to update our parent (that is, WindowImpl) size :
myWidth = width;
myHeight = height;
Event event;
event.Type = Event::Resized;
event.Size.Width = myWidth;
event.Size.Height = myHeight;
PushEvent(event);
// Don't forget to update our parent (that is, WindowImpl) size :
myWidth = width;
myHeight = height;
Event event;
event.Type = Event::Resized;
event.Size.Width = myWidth;
event.Size.Height = myHeight;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::WindowLostFocus(void)
{
Event event;
event.Type = Event::LostFocus;
PushEvent(event);
Event event;
event.Type = Event::LostFocus;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::WindowGainedFocus(void)
{
Event event;
event.Type = Event::GainedFocus;
PushEvent(event);
Event event;
event.Type = Event::GainedFocus;
PushEvent(event);
}
#pragma mark
#pragma mark WindowImplCocoa's mouse-event methods
////////////////////////////////////////////////////////////
void WindowImplCocoa::MouseDownAt(Mouse::Button button, int x, int y)
{
Event event;
event.Type = Event::MouseButtonPressed;
event.MouseButton.Button = button;
event.MouseButton.X = x;
event.MouseButton.Y = y;
PushEvent(event);
Event event;
event.Type = Event::MouseButtonPressed;
event.MouseButton.Button = button;
event.MouseButton.X = x;
event.MouseButton.Y = y;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::MouseUpAt(Mouse::Button button, int x, int y)
{
Event event;
event.Type = Event::MouseButtonReleased;
event.MouseButton.Button = button;
event.MouseButton.X = x;
event.MouseButton.Y = y;
PushEvent(event);
Event event;
event.Type = Event::MouseButtonReleased;
event.MouseButton.Button = button;
event.MouseButton.X = x;
event.MouseButton.Y = y;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::MouseMovedAt(int x, int y)
{
Event event;
event.Type = Event::MouseMoved;
event.MouseMove.X = x;
event.MouseMove.Y = y;
PushEvent(event);
Event event;
event.Type = Event::MouseMoved;
event.MouseMove.X = x;
event.MouseMove.Y = y;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::MouseWheelScrolledAt(float delta, int x, int y)
{
Event event;
event.Type = Event::MouseWheelMoved;
event.MouseWheel.Delta = delta;
event.MouseWheel.X = x;
event.MouseWheel.Y = y;
PushEvent(event);
Event event;
event.Type = Event::MouseWheelMoved;
event.MouseWheel.Delta = delta;
event.MouseWheel.X = x;
event.MouseWheel.Y = y;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::MouseMovedIn(void)
{
Event event;
event.Type = Event::MouseEntered;
PushEvent(event);
Event event;
event.Type = Event::MouseEntered;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::MouseMovedOut(void)
{
Event event;
event.Type = Event::MouseLeft;
PushEvent(event);
Event event;
event.Type = Event::MouseLeft;
PushEvent(event);
}
#pragma mark
#pragma mark WindowImplCocoa's key-event methods
////////////////////////////////////////////////////////////
void WindowImplCocoa::KeyDown(unsigned short keycode, unsigned int modifierFlags)
{
Event event;
event.Type = Event::KeyPressed;
event.Key.Code = NSKeyCodeToSFMLKeyCode(keycode);
if (event.Key.Code == Key::Count) {
sf::Err() << "Unknown key (pressed)" << std::endl;
return; // Not a valid/supported key.
}
event.Key.Alt = modifierFlags & NSAlternateKeyMask;
event.Key.Control = modifierFlags & NSControlKeyMask;
event.Key.Shift = modifierFlags & NSShiftKeyMask;
PushEvent(event);
Event event;
event.Type = Event::KeyPressed;
event.Key.Code = NSKeyCodeToSFMLKeyCode(keycode);
if (event.Key.Code == Key::Count) {
sf::Err() << "Unknown key (pressed)" << std::endl;
return; // Not a valid/supported key.
}
event.Key.Alt = modifierFlags & NSAlternateKeyMask;
event.Key.Control = modifierFlags & NSControlKeyMask;
event.Key.Shift = modifierFlags & NSShiftKeyMask;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::KeyUp(unsigned short keycode, unsigned int modifierFlags)
{
Event event;
event.Type = Event::KeyReleased;
event.Key.Code = NSKeyCodeToSFMLKeyCode(keycode);
if (event.Key.Code == Key::Count) {
sf::Err() << "Unknown key (released)" << std::endl;
return; // Not a valid/supported key.
}
event.Key.Alt = modifierFlags & NSAlternateKeyMask;
event.Key.Control = modifierFlags & NSControlKeyMask;
event.Key.Shift = modifierFlags & NSShiftKeyMask;
PushEvent(event);
Event event;
event.Type = Event::KeyReleased;
event.Key.Code = NSKeyCodeToSFMLKeyCode(keycode);
if (event.Key.Code == Key::Count) {
sf::Err() << "Unknown key (released)" << std::endl;
return; // Not a valid/supported key.
}
event.Key.Alt = modifierFlags & NSAlternateKeyMask;
event.Key.Control = modifierFlags & NSControlKeyMask;
event.Key.Shift = modifierFlags & NSShiftKeyMask;
PushEvent(event);
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::TextEntred(Uint32 charcode)
{
Event event;
event.Type = Event::TextEntered;
event.Text.Unicode = charcode;
PushEvent(event);
Event event;
event.Type = Event::TextEntered;
event.Text.Unicode = charcode;
PushEvent(event);
}
////////////////////////////////////////////////////////////
Key::Code WindowImplCocoa::NSKeyCodeToSFMLKeyCode(unsigned short keycode) {
/* Based on http://forums.macrumors.com/showthread.php?t=780577 */
switch (keycode) {
case 0x00: return Key::A;
case 0x0b: return Key::B;
case 0x08: return Key::C;
case 0x02: return Key::D;
case 0x0e: return Key::E;
case 0x03: return Key::F;
case 0x05: return Key::G;
case 0x04: return Key::H;
case 0x22: return Key::I;
case 0x26: return Key::J;
case 0x28: return Key::K;
case 0x25: return Key::L;
case 0x2e: return Key::M;
case 0x2d: return Key::N;
case 0x1f: return Key::O;
case 0x23: return Key::P;
case 0x0c: return Key::Q;
case 0x0f: return Key::R;
case 0x01: return Key::S;
case 0x11: return Key::T;
case 0x20: return Key::U;
case 0x09: return Key::V;
case 0x0d: return Key::W;
case 0x07: return Key::X;
case 0x10: return Key::Y;
case 0x06: return Key::Z;
case 0x1d: return Key::Num0;
case 0x12: return Key::Num1;
case 0x13: return Key::Num2;
case 0x14: return Key::Num3;
case 0x15: return Key::Num4;
case 0x17: return Key::Num5;
case 0x16: return Key::Num6;
case 0x1a: return Key::Num7;
case 0x1c: return Key::Num8;
case 0x19: return Key::Num9;
case 0x35: return Key::Escape;
case 0x3b: return Key::LControl;
case 0x38: return Key::LShift;
case 0x3a: return Key::LAlt;
case 0x37: return Key::LSystem;
case 0x3e: return Key::RControl;
case 0x3c: return Key::RShift;
case 0x3d: return Key::RAlt;
case 0x36: return Key::RSystem;
/* Based on http://forums.macrumors.com/showthread.php?t=780577 */
switch (keycode) {
case 0x00: return Key::A;
case 0x0b: return Key::B;
case 0x08: return Key::C;
case 0x02: return Key::D;
case 0x0e: return Key::E;
case 0x03: return Key::F;
case 0x05: return Key::G;
case 0x04: return Key::H;
case 0x22: return Key::I;
case 0x26: return Key::J;
case 0x28: return Key::K;
case 0x25: return Key::L;
case 0x2e: return Key::M;
case 0x2d: return Key::N;
case 0x1f: return Key::O;
case 0x23: return Key::P;
case 0x0c: return Key::Q;
case 0x0f: return Key::R;
case 0x01: return Key::S;
case 0x11: return Key::T;
case 0x20: return Key::U;
case 0x09: return Key::V;
case 0x0d: return Key::W;
case 0x07: return Key::X;
case 0x10: return Key::Y;
case 0x06: return Key::Z;
case 0x1d: return Key::Num0;
case 0x12: return Key::Num1;
case 0x13: return Key::Num2;
case 0x14: return Key::Num3;
case 0x15: return Key::Num4;
case 0x17: return Key::Num5;
case 0x16: return Key::Num6;
case 0x1a: return Key::Num7;
case 0x1c: return Key::Num8;
case 0x19: return Key::Num9;
case 0x35: return Key::Escape;
case 0x3b: return Key::LControl;
case 0x38: return Key::LShift;
case 0x3a: return Key::LAlt;
case 0x37: return Key::LSystem;
case 0x3e: return Key::RControl;
case 0x3c: return Key::RShift;
case 0x3d: return Key::RAlt;
case 0x36: return Key::RSystem;
#warning unknown key code for Menu
// case 0x: return Key::Menu;
case 0x21: return Key::LBracket;
case 0x1e: return Key::RBracket;
case 0x29: return Key::SemiColon;
case 0x2b: return Key::Comma;
case 0x2f: return Key::Period;
case 0x27: return Key::Quote;
case 0x2c: return Key::Slash;
case 0x2a: return Key::BackSlash;
// case 0x: return Key::Menu;
case 0x21: return Key::LBracket;
case 0x1e: return Key::RBracket;
case 0x29: return Key::SemiColon;
case 0x2b: return Key::Comma;
case 0x2f: return Key::Period;
case 0x27: return Key::Quote;
case 0x2c: return Key::Slash;
case 0x2a: return Key::BackSlash;
#warning 0x0a is for "Non-US Backslash" (from HID Calibrator, a sample provided by Apple).
case 0x0a: return Key::Tilde;
case 0x18: return Key::Equal;
case 0x32: return Key::Dash;
case 0x31: return Key::Space;
case 0x24: return Key::Return;
case 0x0a: return Key::Tilde;
case 0x18: return Key::Equal;
case 0x32: return Key::Dash;
case 0x31: return Key::Space;
case 0x24: return Key::Return;
#warning unknown key code for Back
// case 0x: return Key::Back;
case 0x30: return Key::Tab;
case 0x74: return Key::PageUp;
case 0x79: return Key::PageDown;
case 0x77: return Key::End;
case 0x73: return Key::Home;
// case 0x: return Key::Back;
case 0x30: return Key::Tab;
case 0x74: return Key::PageUp;
case 0x79: return Key::PageDown;
case 0x77: return Key::End;
case 0x73: return Key::Home;
#warning unknown key code for Insert
// case 0x: return Key::Insert;
case 0x33: return Key::Delete;
case 0x45: return Key::Add;
case 0x4e: return Key::Subtract;
case 0x43: return Key::Multiply;
case 0x4b: return Key::Divide;
case 0x7b: return Key::Left;
case 0x7c: return Key::Right;
case 0x7e: return Key::Up;
case 0x7d: return Key::Down;
case 0x52: return Key::Numpad0;
case 0x53: return Key::Numpad1;
case 0x54: return Key::Numpad2;
case 0x55: return Key::Numpad3;
case 0x56: return Key::Numpad4;
case 0x57: return Key::Numpad5;
case 0x58: return Key::Numpad6;
case 0x59: return Key::Numpad7;
case 0x5b: return Key::Numpad8;
case 0x5c: return Key::Numpad9;
case 0x7a: return Key::F1;
case 0x78: return Key::F2;
case 0x63: return Key::F3;
case 0x76: return Key::F4;
case 0x60: return Key::F5;
case 0x61: return Key::F6;
case 0x62: return Key::F7;
case 0x64: return Key::F8;
case 0x65: return Key::F9;
case 0x6d: return Key::F10;
case 0x67: return Key::F11;
case 0x6f: return Key::F12;
case 0x69: return Key::F13;
case 0x6b: return Key::F14;
case 0x71: return Key::F15;
// case 0x: return Key::Insert;
case 0x33: return Key::Delete;
case 0x45: return Key::Add;
case 0x4e: return Key::Subtract;
case 0x43: return Key::Multiply;
case 0x4b: return Key::Divide;
case 0x7b: return Key::Left;
case 0x7c: return Key::Right;
case 0x7e: return Key::Up;
case 0x7d: return Key::Down;
case 0x52: return Key::Numpad0;
case 0x53: return Key::Numpad1;
case 0x54: return Key::Numpad2;
case 0x55: return Key::Numpad3;
case 0x56: return Key::Numpad4;
case 0x57: return Key::Numpad5;
case 0x58: return Key::Numpad6;
case 0x59: return Key::Numpad7;
case 0x5b: return Key::Numpad8;
case 0x5c: return Key::Numpad9;
case 0x7a: return Key::F1;
case 0x78: return Key::F2;
case 0x63: return Key::F3;
case 0x76: return Key::F4;
case 0x60: return Key::F5;
case 0x61: return Key::F6;
case 0x62: return Key::F7;
case 0x64: return Key::F8;
case 0x65: return Key::F9;
case 0x6d: return Key::F10;
case 0x67: return Key::F11;
case 0x6f: return Key::F12;
case 0x69: return Key::F13;
case 0x6b: return Key::F14;
case 0x71: return Key::F15;
#warning unknown key code for PAUSE
// case 0x: return Key::PAUSE;
default: return Key::Count; // An unknown key.
}
// case 0x: return Key::PAUSE;
default: return Key::Count; // An unknown key.
}
}
#pragma mark
#pragma mark WindowImplCocoa's event-related methods
////////////////////////////////////////////////////////////
void WindowImplCocoa::ProcessEvents(bool block)
{
[myDelegate processEventWithBlockingMode:(block ? YES : NO)];
[myDelegate processEventWithBlockingMode:(block ? YES : NO)];
}
#pragma mark
#pragma mark WindowImplCocoa's private methods
////////////////////////////////////////////////////////////
WindowHandle WindowImplCocoa::GetSystemHandle() const
{
return [myDelegate getSystemHandle];
return [myDelegate getSystemHandle];
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::ShowMouseCursor(bool show)
{
if (show) {
[myDelegate showMouseCursor];
} else {
[myDelegate hideMouseCursor];
}
if (show) {
[myDelegate showMouseCursor];
} else {
[myDelegate hideMouseCursor];
}
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::SetCursorPosition(unsigned int x, unsigned int y)
{
[myDelegate setCursorPositionToX:x Y:y];
[myDelegate setCursorPositionToX:x Y:y];
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::SetPosition(int x, int y)
{
[myDelegate setWindowPositionToX:x Y:y];
[myDelegate setWindowPositionToX:x Y:y];
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::SetSize(unsigned int width, unsigned int height)
{
// Don't forget to update our parent (that is, WindowImpl) size :
myWidth = width;
myHeight = height;
[myDelegate resizeTo:width by:height];
// Don't forget to update our parent (that is, WindowImpl) size :
myWidth = width;
myHeight = height;
[myDelegate resizeTo:width by:height];
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::SetTitle(const std::string& title)
{
[myDelegate changeTitle:stringToNSString(title)];
[myDelegate changeTitle:stringToNSString(title)];
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::Show(bool show)
{
if (show) {
[myDelegate showWindow];
} else {
[myDelegate hideWindow];
}
if (show) {
[myDelegate showWindow];
} else {
[myDelegate hideWindow];
}
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::EnableKeyRepeat(bool enabled)
{
if (enabled) {
[myDelegate enableKeyRepeat];
} else {
[myDelegate disableKeyRepeat];
}
if (enabled) {
[myDelegate enableKeyRepeat];
} else {
[myDelegate disableKeyRepeat];
}
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::SetIcon(unsigned int width, unsigned int height,
const Uint8* pixels)
void WindowImplCocoa::SetIcon(unsigned int width, unsigned int height, const Uint8* pixels)
{
[myDelegate setIconTo:width by:height with:pixels];
[myDelegate setIconTo:width by:height with:pixels];
}
#pragma mark
@ -502,40 +501,40 @@ void WindowImplCocoa::SetIcon(unsigned int width, unsigned int height,
////////////////////////////////////////////////////////////
void WindowImplCocoa::SetUpPoolAndApplication(void)
{
// Ensure NSApp exists.
[NSApplication sharedApplication];
// Create the pool.
myPool = [[NSAutoreleasePool alloc] init];
// Transform the app process.
SetUpProcessAsApplication();
// Ensure NSApp exists.
[NSApplication sharedApplication];
// Create the pool.
myPool = [[NSAutoreleasePool alloc] init];
// Transform the app process.
SetUpProcessAsApplication();
}
////////////////////////////////////////////////////////////
void WindowImplCocoa::SetUpProcessAsApplication(void)
{
static bool isTheProcessSetAsApplication = false;
if (!isTheProcessSetAsApplication) {
// Do it only once !
isTheProcessSetAsApplication = true;
// Set the process as a normal application so it can get focus.
ProcessSerialNumber psn;
if (!GetCurrentProcess(&psn)) {
TransformProcessType(&psn, kProcessTransformToForegroundApplication);
SetFrontProcess(&psn);
}
// Tell the application to stop bouncing in the Dock.
[[NSApplication sharedApplication] finishLaunching];
// NOTE : This last call won't harm anything even if SFML window was
// created with an external handle.
}
static bool isTheProcessSetAsApplication = false;
if (!isTheProcessSetAsApplication) {
// Do it only once !
isTheProcessSetAsApplication = true;
// Set the process as a normal application so it can get focus.
ProcessSerialNumber psn;
if (!GetCurrentProcess(&psn)) {
TransformProcessType(&psn, kProcessTransformToForegroundApplication);
SetFrontProcess(&psn);
}
// Tell the application to stop bouncing in the Dock.
[[NSApplication sharedApplication] finishLaunching];
// NOTE : This last call won't harm anything even if SFML window was
// created with an external handle.
}
}
} // namespace priv
} // namespace sf

View File

@ -32,9 +32,9 @@
#import <AppKit/AppKit.h>
namespace sf {
namespace priv {
class WindowImplCocoa;
}
namespace priv {
class WindowImplCocoa;
}
}
////////////////////////////////////////////////////////////

View File

@ -33,10 +33,10 @@
////////////////////////////////////////////////////////////
NSString* stringToNSString(std::string const& string)
{
std::string utf8; utf8.reserve(string.size() + 1);
sf::Utf8::FromAnsi(string.begin(), string.end(), std::back_inserter(utf8));
NSString* str = [NSString stringWithCString:utf8.c_str() encoding:NSUTF8StringEncoding];
return str;
std::string utf8; utf8.reserve(string.size() + 1);
sf::Utf8::FromAnsi(string.begin(), string.end(), std::back_inserter(utf8));
NSString* str = [NSString stringWithCString:utf8.c_str() encoding:NSUTF8StringEncoding];
return str;
}