diff --git a/Graphics/UI/SDL.hs b/Graphics/UI/SDL.hs
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL.hs
@@ -0,0 +1,23 @@
+module Graphics.UI.SDL (
+	module Graphics.UI.SDL.Audio,
+	module Graphics.UI.SDL.Basic,
+	module Graphics.UI.SDL.Enum,
+	module Graphics.UI.SDL.Event,
+	module Graphics.UI.SDL.Filesystem,
+	module Graphics.UI.SDL.Haptic,
+	module Graphics.UI.SDL.Power,
+	module Graphics.UI.SDL.Timer,
+	module Graphics.UI.SDL.Types,
+	module Graphics.UI.SDL.Video
+) where
+
+import Graphics.UI.SDL.Audio
+import Graphics.UI.SDL.Basic
+import Graphics.UI.SDL.Enum
+import Graphics.UI.SDL.Event
+import Graphics.UI.SDL.Filesystem
+import Graphics.UI.SDL.Haptic
+import Graphics.UI.SDL.Power
+import Graphics.UI.SDL.Timer
+import Graphics.UI.SDL.Types
+import Graphics.UI.SDL.Video
diff --git a/Graphics/UI/SDL/Audio.hs b/Graphics/UI/SDL/Audio.hs
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Audio.hs
@@ -0,0 +1,68 @@
+module Graphics.UI.SDL.Audio (
+	-- * Audio Device Management, Playing and Recording
+	audioInit,
+	audioQuit,
+	buildAudioCVT,
+	closeAudio,
+	closeAudioDevice,
+	convertAudio,
+	freeWAV,
+	getAudioDeviceName,
+	getAudioDeviceStatus,
+	getAudioDriver,
+	getAudioStatus,
+	getCurrentAudioDriver,
+	getNumAudioDevices,
+	getNumAudioDrivers,
+	loadWAV,
+	loadWAV_RW,
+	lockAudio,
+	lockAudioDevice,
+	mixAudio,
+	mixAudioFormat,
+	openAudio,
+	openAudioDevice,
+	pauseAudio,
+	pauseAudioDevice,
+	unlockAudio,
+	unlockAudioDevice
+) where
+
+import Data.Word
+import Foreign.C.String
+import Foreign.C.Types
+import Foreign.Ptr
+import Graphics.UI.SDL.Enum
+import Graphics.UI.SDL.Filesystem
+import Graphics.UI.SDL.Types
+
+foreign import ccall "SDL.h SDL_AudioInit" audioInit :: CString -> IO CInt
+foreign import ccall "SDL.h SDL_AudioQuit" audioQuit :: IO ()
+foreign import ccall "SDL.h SDL_BuildAudioCVT" buildAudioCVT :: Ptr AudioCVT -> AudioFormat -> Word8 -> CInt -> AudioFormat -> Word8 -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_CloseAudio" closeAudio :: IO ()
+foreign import ccall "SDL.h SDL_CloseAudioDevice" closeAudioDevice :: AudioDeviceID -> IO ()
+foreign import ccall "SDL.h SDL_ConvertAudio" convertAudio :: Ptr AudioCVT -> IO CInt
+foreign import ccall "SDL.h SDL_FreeWAV" freeWAV :: Ptr Word8 -> IO ()
+foreign import ccall "SDL.h SDL_GetAudioDeviceName" getAudioDeviceName :: CInt -> CInt -> IO CString
+foreign import ccall "SDL.h SDL_GetAudioDeviceStatus" getAudioDeviceStatus :: AudioDeviceID -> IO AudioStatus
+foreign import ccall "SDL.h SDL_GetAudioDriver" getAudioDriver :: CInt -> IO CString
+foreign import ccall "SDL.h SDL_GetAudioStatus" getAudioStatus :: IO AudioStatus
+foreign import ccall "SDL.h SDL_GetCurrentAudioDriver" getCurrentAudioDriver :: IO CString
+foreign import ccall "SDL.h SDL_GetNumAudioDevices" getNumAudioDevices :: CInt -> IO CInt
+foreign import ccall "SDL.h SDL_GetNumAudioDrivers" getNumAudioDrivers :: IO CInt
+foreign import ccall "SDL.h SDL_LoadWAV_RW" loadWAV_RW :: Ptr RWops -> CInt -> Ptr AudioSpec -> Ptr (Ptr Word8) -> Ptr Word32 -> IO (Ptr AudioSpec)
+foreign import ccall "SDL.h SDL_LockAudio" lockAudio :: IO ()
+foreign import ccall "SDL.h SDL_LockAudioDevice" lockAudioDevice :: AudioDeviceID -> IO () 
+foreign import ccall "SDL.h SDL_MixAudio" mixAudio :: Ptr Word8 -> Ptr Word8 -> Word32 -> CInt -> IO ()
+foreign import ccall "SDL.h SDL_MixAudioFormat" mixAudioFormat :: Ptr Word8 -> Ptr Word8 -> AudioFormat -> Word32 -> CInt -> IO ()
+foreign import ccall "SDL.h SDL_OpenAudio" openAudio :: Ptr AudioSpec -> Ptr AudioSpec -> IO CInt
+foreign import ccall "SDL.h SDL_OpenAudioDevice" openAudioDevice :: CString -> CInt -> Ptr AudioSpec -> Ptr AudioSpec -> CInt -> IO AudioDeviceID
+foreign import ccall "SDL.h SDL_PauseAudio" pauseAudio :: CInt -> IO ()
+foreign import ccall "SDL.h SDL_PauseAudioDevice" pauseAudioDevice :: AudioDeviceID -> CInt -> IO ()
+foreign import ccall "SDL.h SDL_UnlockAudio" unlockAudio :: IO ()
+foreign import ccall "SDL.h SDL_UnlockAudioDevice" unlockAudioDevice :: AudioDeviceID -> IO ()
+
+loadWAV :: CString -> Ptr AudioSpec -> Ptr (Ptr Word8) -> Ptr Word32 -> IO (Ptr AudioSpec)
+loadWAV file spec audio_buf audio_len = do
+	rw <- withCString "rb" $ rwFromFile file
+	loadWAV_RW rw 1 spec audio_buf audio_len
diff --git a/Graphics/UI/SDL/Basic.hs b/Graphics/UI/SDL/Basic.hs
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Basic.hs
@@ -0,0 +1,83 @@
+module Graphics.UI.SDL.Basic (
+	-- * Initialization and Shutdown
+	init,
+	initSubSystem,
+	quit,
+	quitSubSystem,
+	setMainReady,
+	wasInit,
+
+	-- * Configuration Variables
+	addHintCallback,
+	clearHints,
+	delHintCallback,
+	getHint,
+	setHint,
+	setHintWithPriority,
+
+	-- * Error Handling
+	clearError,
+	getError,
+	-- setError,
+
+	-- * Log Handling
+	-- log,
+	-- logCritical,
+	-- logDebug,
+	-- logError,
+	logGetOutputFunction,
+	logGetPriority,
+	-- logInfo,
+	-- logMessage,
+	-- logMessageV,
+	logResetPriorities,
+	logSetAllPriority,
+	logSetOutputFunction,
+	logSetPriority,
+	-- logVerbose,
+	-- logWarn,
+
+	-- * Assertions
+	-- | Use Haskell's own assertion primitives rather than SDL's.
+
+	-- * Querying SDL Version
+	getRevision,
+	getRevisionNumber,
+	getVersion
+) where
+
+import Data.Word
+import Foreign.C.String
+import Foreign.C.Types
+import Foreign.Ptr
+import Graphics.UI.SDL.Enum
+import Graphics.UI.SDL.Types
+import Prelude hiding (init)
+
+foreign import ccall "SDL.h SDL_Init" init :: Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_InitSubSystem" initSubSystem :: Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_Quit" quit :: IO ()
+foreign import ccall "SDL.h SDL_QuitSubSystem" quitSubSystem :: Word32 -> IO ()
+foreign import ccall "SDL.h SDL_SetMainReady" setMainReady :: IO ()
+foreign import ccall "SDL.h SDL_WasInit" wasInit :: Word32 -> IO Word32
+
+foreign import ccall "SDL.h SDL_AddHintCallback" addHintCallback :: CString -> FunPtr (Ptr () -> CString -> CString -> CString -> IO ()) -> Ptr () -> IO ()
+foreign import ccall "SDL.h SDL_ClearHints" clearHints :: IO ()
+foreign import ccall "SDL.h SDL_DelHintCallback" delHintCallback :: CString -> FunPtr (Ptr () -> CString -> CString -> CString -> IO ()) -> Ptr () -> IO ()
+foreign import ccall "SDL.h SDL_GetHint" getHint :: CString -> IO CString
+foreign import ccall "SDL.h SDL_SetHint" setHint :: CString -> CString -> IO Bool
+foreign import ccall "SDL.h SDL_SetHintWithPriority" setHintWithPriority :: CString -> CString -> HintPriority -> IO Bool
+
+foreign import ccall "SDL.h SDL_ClearError" clearError :: IO ()
+foreign import ccall "SDL.h SDL_GetError" getError :: IO CString
+
+foreign import ccall "SDL.h SDL_LogGetOutputFunction" logGetOutputFunction :: Ptr LogOutputFunction -> Ptr (Ptr ()) -> IO ()
+foreign import ccall "SDL.h SDL_LogGetPriority" logGetPriority :: CInt -> IO LogPriority
+foreign import ccall "SDL.h SDL_LogResetPriorities" logResetPriorities :: IO ()
+foreign import ccall "SDL.h SDL_LogSetAllPriority" logSetAllPriority :: LogPriority -> IO ()
+foreign import ccall "SDL.h SDL_LogSetOutputFunction" logSetOutputFunction :: LogOutputFunction -> Ptr () -> IO ()
+foreign import ccall "SDL.h SDL_LogSetPriority" logSetPriority :: CInt -> LogPriority -> IO ()
+
+foreign import ccall "SDL.h SDL_GetRevision" getRevision :: IO CString
+foreign import ccall "SDL.h SDL_GetRevisionNumber" getRevisionNumber :: IO CInt
+foreign import ccall "SDL.h SDL_GetVersion" getVersion :: Ptr () -> IO ()
diff --git a/Graphics/UI/SDL/Enum.hsc b/Graphics/UI/SDL/Enum.hsc
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Enum.hsc
@@ -0,0 +1,1525 @@
+module Graphics.UI.SDL.Enum (
+	-- * Enumerations
+
+	-- ** Audio Status
+	AudioStatus,
+	audioStatusStopped,
+	audioStatusPlaying,
+	audioStatusPaused,
+
+	-- ** Blend Mode
+	BlendMode,
+	blendModeNone,
+	blendModeBlend,
+	blendModeAdd,
+	blendModeMod,
+
+	-- ** Event Action
+	EventAction,
+	eventActionAddEvent,
+	eventActionPeekEvent,
+	eventActionGetEvent,
+
+	-- ** Game Controller Axis
+	GameControllerAxis,
+	gameControllerAxisInvalid,
+	gameControllerAxisLeftX,
+	gameControllerAxisLeftY,
+	gameControllerAxisRightX,
+	gameControllerAxisRightY,
+	gameControllerAxisTriggerLeft,
+	gameControllerAxisTriggerRight,
+	gameControllerAxisMax,
+
+	-- ** Game Controller Button
+	GameControllerButton,
+	gameControllerButtonInvalid,
+	gameControllerButtonA,
+	gameControllerButtonB,
+	gameControllerButtonX,
+	gameControllerButtonY,
+	gameControllerButtonBack,
+	gameControllerButtonGuide,
+	gameControllerButtonStart,
+	gameControllerButtonLeftStick,
+	gameControllerButtonRightStick,
+	gameControllerButtonLeftShoulder,
+	gameControllerButtonRightShoulder,
+	gameControllerButtonDPadUp,
+	gameControllerButtonDPadDown,
+	gameControllerButtonDPadLeft,
+	gameControllerButtonDPadRight,
+	gameControllerButtonMax,
+
+	-- ** OpenGL Attribute
+	GLattr,
+	glAttrRedSize,
+	glAttrGreenSize,
+	glAttrBlueSize,
+	glAttrAlphaSize,
+	glAttrBufferSize,
+	glAttrDoubleBuffer,
+	glAttrDepthSize,
+	glAttrStencilSize,
+	glAttrAccumRedSize,
+	glAttrAccumGreenSize,
+	glAttrAccumBlueSize,
+	glAttrAccumAlphaSize,
+	glAttrStereo,
+	glAttrMultiSampleBuffers,
+	glAttrMultiSampleSamples,
+	glAttrAcceleratedVisual,
+	glAttrRetainedBacking,
+	glAttrContextMajorVersion,
+	glAttrContextMinorVersion,
+	glAttrContextEGL,
+	glAttrContextFlags,
+	glAttrContextProfileMask,
+	glAttrShareWithCurrentContext,
+	glAttrFramebufferSRGBCapable,
+
+	-- ** Hint Priority
+	HintPriority,
+	hintPriorityDefault,
+	hintPriorityNormal,
+	hintPriorityOverride,
+
+	-- ** Key Modifier
+	Keymod,
+	keymodNone,
+	keymodLShift,
+	keymodRShift,
+	keymodLCtrl,
+	keymodRCtrl,
+	keymodLAlt,
+	keymodRAlt,
+	keymodLGUI,
+	keymodRGUI,
+	keymodNum,
+	keymodCaps,
+	keymodMode,
+	keymodReserved,
+
+	-- ** Log Priority
+	LogPriority,
+	logPriorityVerbose,
+	logPriorityDebug,
+	logPriorityInfo,
+	logPriorityWarn,
+	logPriorityError,
+	logPriorityCritical,
+	logPriorityPriorities,
+
+	-- ** Power State
+	PowerState,
+	powerStateUnknown,
+	powerStateOnBattery,
+	powerStateNoBattery,
+	powerStateCharging,
+	powerStateCharged,
+
+	-- ** Renderer Flip
+	RendererFlip,
+	rendererFlipNone,
+	rendererFlipHorizontal,
+	rendererFlipVertical,
+
+	-- ** Scancode
+	Scancode,
+	scancodeUnknown,
+	scancodeA,
+	scancodeB,
+	scancodeC,
+	scancodeD,
+	scancodeE,
+	scancodeF,
+	scancodeG,
+	scancodeH,
+	scancodeI,
+	scancodeJ,
+	scancodeK,
+	scancodeL,
+	scancodeM,
+	scancodeN,
+	scancodeO,
+	scancodeP,
+	scancodeQ,
+	scancodeR,
+	scancodeS,
+	scancodeT,
+	scancodeU,
+	scancodeV,
+	scancodeW,
+	scancodeX,
+	scancodeY,
+	scancodeZ,
+	scancode1,
+	scancode2,
+	scancode3,
+	scancode4,
+	scancode5,
+	scancode6,
+	scancode7,
+	scancode8,
+	scancode9,
+	scancode0,
+	scancodeReturn,
+	scancodeEscape,
+	scancodeBackspace,
+	scancodeTab,
+	scancodeSpace,
+	scancodeMinus,
+	scancodeEquals,
+	scancodeLeftBracket,
+	scancodeRightBracket,
+	scancodeBackslash,
+	scancodeNonUSHash,
+	scancodeSemicolon,
+	scancodeApostrophe,
+	scancodeGrave,
+	scancodeComma,
+	scancodePeriod,
+	scancodeSlash,
+	scancodeCapsLock,
+	scancodeF1,
+	scancodeF2,
+	scancodeF3,
+	scancodeF4,
+	scancodeF5,
+	scancodeF6,
+	scancodeF7,
+	scancodeF8,
+	scancodeF9,
+	scancodeF10,
+	scancodeF11,
+	scancodeF12,
+	scancodePrintScreen,
+	scancodeScrollLock,
+	scancodePause,
+	scancodeInsert,
+	scancodeHome,
+	scancodePageUp,
+	scancodeDelete,
+	scancodeEnd,
+	scancodePageDown,
+	scancodeRight,
+	scancodeLeft,
+	scancodeDown,
+	scancodeUp,
+	scancodeNumLockClear,
+	scancodeKPDivide,
+	scancodeKPMultiply,
+	scancodeKPMinus,
+	scancodeKPPlus,
+	scancodeKPEnter,
+	scancodeKP1,
+	scancodeKP2,
+	scancodeKP3,
+	scancodeKP4,
+	scancodeKP5,
+	scancodeKP6,
+	scancodeKP7,
+	scancodeKP8,
+	scancodeKP9,
+	scancodeKP0,
+	scancodeKPPeriod,
+	scancodeNonUSBackslash,
+	scancodeApplication,
+	scancodePower,
+	scancodeKPEquals,
+	scancodeF13,
+	scancodeF14,
+	scancodeF15,
+	scancodeF16,
+	scancodeF17,
+	scancodeF18,
+	scancodeF19,
+	scancodeF20,
+	scancodeF21,
+	scancodeF22,
+	scancodeF23,
+	scancodeF24,
+	scancodeExecute,
+	scancodeHelp,
+	scancodeMenu,
+	scancodeSelect,
+	scancodeStop,
+	scancodeAgain,
+	scancodeUndo,
+	scancodeCut,
+	scancodeCopy,
+	scancodePaste,
+	scancodeFind,
+	scancodeMute,
+	scancodeVolumeUp,
+	scancodeVolumeDown,
+	scancodeKPComma,
+	scancodeEqualsAs400,
+	scancodeInternational1,
+	scancodeInternational2,
+	scancodeInternational3,
+	scancodeInternational4,
+	scancodeInternational5,
+	scancodeInternational6,
+	scancodeInternational7,
+	scancodeInternational8,
+	scancodeInternational9,
+	scancodeLang1,
+	scancodeLang2,
+	scancodeLang3,
+	scancodeLang4,
+	scancodeLang5,
+	scancodeLang6,
+	scancodeLang7,
+	scancodeLang8,
+	scancodeLang9,
+	scancodeAltErase,
+	scancodeSysReq,
+	scancodeCancel,
+	scancodeClear,
+	scancodePrior,
+	scancodeReturn2,
+	scancodeSeparator,
+	scancodeOut,
+	scancodeOper,
+	scancodeClearAgain,
+	scancodeCrSel,
+	scancodeExSel,
+	scancodeKP00,
+	scancodeKP000,
+	scancodeThousandsSeparator,
+	scancodeDecimalSeparator,
+	scancodeCurrencyUnit,
+	scancodeCurrencySubunit,
+	scancodeLeftParen,
+	scancodeRightParen,
+	scancodeLeftBrace,
+	scancodeRightBrace,
+	scancodeKPTab,
+	scancodeKPBackspace,
+	scancodeKPA,
+	scancodeKPB,
+	scancodeKPC,
+	scancodeKPD,
+	scancodeKPE,
+	scancodeKPF,
+	scancodeKPXOR,
+	scancodeKPPower,
+	scancodeKPPercent,
+	scancodeKPLess,
+	scancodeKPGreater,
+	scancodeKPAmpersand,
+	scancodeKPDBLAmpersand,
+	scancodeKPVerticalBar,
+	scancodeKPDBLVerticalBar,
+	scancodeKPColon,
+	scancodeKPHash,
+	scancodeKPSpace,
+	scancodeKPAt,
+	scancodeKPExclam,
+	scancodeKPMemStore,
+	scancodeKPMemRecall,
+	scancodeKPMemClear,
+	scancodeKPMemAdd,
+	scancodeKPMemSubtract,
+	scancodeKPMemMultiply,
+	scancodeKPMemDivide,
+	scancodeKPPlusMinus,
+	scancodeKPClear,
+	scancodeKPClearEntry,
+	scancodeKPBinary,
+	scancodeKPOctal,
+	scancodeKPDecimal,
+	scancodeKPHexadecimal,
+	scancodeLCtrl,
+	scancodeLShift,
+	scancodeLAlt,
+	scancodeLGUI,
+	scancodeRCtrl,
+	scancodeRShift,
+	scancodeRAlt,
+	scancodeRGUI,
+	scancodeMode,
+	scancodeAudioNext,
+	scancodeAudioPrev,
+	scancodeAudioStop,
+	scancodeAudioPlay,
+	scancodeAudioMute,
+	scancodeMediaSelect,
+	scancodeWWW,
+	scancodeMail,
+	scancodeCalculator,
+	scancodeComputer,
+	scancodeACSearch,
+	scancodeACHome,
+	scancodeACBack,
+	scancodeACForward,
+	scancodeACStop,
+	scancodeACRefresh,
+	scancodeACBookmarks,
+	scancodeBrightnessDown,
+	scancodeBrightnessUp,
+	scancodeDisplaySwitch,
+	scancodeKBDIllumToggle,
+	scancodeKBDIllumDown,
+	scancodeKBDIllumUp,
+	scancodeEject,
+	scancodeSleep,
+	scancodeApp1,
+	scancodeApp2,
+	scancodeNum,
+
+	-- ** System Cursor
+	SystemCursor,
+	systemCursorArrow,
+	systemCursorIBeam,
+	systemCursorWait,
+	systemCursorCrosshair,
+	systemCursorWaitArrow,
+	systemCursorSizeNWSE,
+	systemCursorSizeNESW,
+	systemCursorSizeWE,
+	systemCursorSizeNS,
+	systemCursorSizeAll,
+	systemCursorNo,
+	systemCursorHand,
+	systemCursorNum,
+
+	-- * Miscellaneous Enumerations
+	-- | These enumerations are not used directly by any SDL function, thus they have a polymorphic type.
+
+	-- ** Event Type
+	eventTypeFirstEvent,
+	eventTypeQuit,
+	eventTypeAppTerminating,
+	eventTypeAppLowMemory,
+	eventTypeAppWillEnterBackground,
+	eventTypeAppDidEnterBackground,
+	eventTypeAppWillEnterForeground,
+	eventTypeAppDidEnterForeground,
+	eventTypeWindowEvent,
+	eventTypeSysWMEvent,
+	eventTypeKeyDown,
+	eventTypeKeyUp,
+	eventTypeTextEditing,
+	eventTypeTextInput,
+	eventTypeMouseMotion,
+	eventTypeMouseButtonDown,
+	eventTypeMouseButtonUp,
+	eventTypeMouseWheel,
+	eventTypeJoyAxisMotion,
+	eventTypeJoyBallMotion,
+	eventTypeJoyHatMotion,
+	eventTypeJoyButtonDown,
+	eventTypeJoyButtonUp,
+	eventTypeJoyDeviceAdded,
+	eventTypeJoyDeviceRemoved,
+	eventTypeControllerAxisMotion,
+	eventTypeControllerButtonDown,
+	eventTypeControllerButtonUp,
+	eventTypeControllerDeviceAdded,
+	eventTypeControllerDeviceRemoved,
+	eventTypeControllerDeviceRemapped,
+	eventTypeFingerDown,
+	eventTypeFingerUp,
+	eventTypeFingerMotion,
+	eventTypeDollarGesture,
+	eventTypeDollarRecord,
+	eventTypeMultiGesture,
+	eventTypeClipboardUpdate,
+	eventTypeDropFile,
+	eventTypeUserEvent,
+	eventTypeLastEvent,
+
+	-- ** OpenGL Profile
+	glProfileCore,
+	glProfileCompatibility,
+	glProfileES,
+
+	-- ** OpenGL Context Flag
+	glContextFlagDebug,
+	glContextFlagForwardCompatible,
+	glContextFlagRobustAccess,
+	glContextFlagResetIsolation,
+
+	-- ** Initialization Flag
+	initFlagTimer,
+	initFlagAudio,
+	initFlagVideo,
+	initFlagJoystick,
+	initFlagHaptic,
+	initFlagGameController,
+	initFlagEvents,
+	initFlagNoParachute,
+	initFlagEverything,
+
+	-- ** Joystick Hat Position
+	joystickHatCentered,
+	joystickHatUp,
+	joystickHatRight,
+	joystickHatDown,
+	joystickHatLeft,
+	joystickHatRightUp,
+	joystickHatRightDown,
+	joystickHatLeftUp,
+	joystickHatLeftDown,
+
+	-- ** Message Box Flags
+	messageBoxFlagError,
+	messageBoxFlagWarning,
+	messageBoxFlagInformation,
+
+	-- ** Message Box Button Flags
+	messageBoxButtonFlagReturnKeyDefault,
+	messageBoxButtonFlagEscapeKeyDefault,
+
+	-- ** Renderer Flags
+	rendererFlagSoftware,
+	rendererFlagAccelerated,
+	rendererFlagPresentVSync,
+	rendererFlagTargetTexture,
+
+	-- ** Texture Access
+	textureAccessStatic,
+	textureAccessStreaming,
+	textureAccessTarget,
+
+	-- ** Texture Modulate
+	textureModulateNone,
+	textureModulateColor,
+	textureModulateAlpha,
+
+	-- ** Window Event
+	windowEventNone,
+	windowEventShown,
+	windowEventHidden,
+	windowEventExposed,
+	windowEventMoved,
+	windowEventResized,
+	windowEventSizeChanged,
+	windowEventMinimized,
+	windowEventMaximized,
+	windowEventRestored,
+	windowEventEnter,
+	windowEventLeave,
+	windowEventFocusGained,
+	windowEventFocusLost,
+	windowEventClose,
+
+	-- ** Window Flags
+	windowFlagFullscreen,
+	windowFlagOpenGL,
+	windowFlagShown,
+	windowFlagHidden,
+	windowFlagBorderless,
+	windowFlagResizable,
+	windowFlagMinimized,
+	windowFlagMaximized,
+	windowFlagInputGrabbed,
+	windowFlagInputFocus,
+	windowFlagMouseFocus,
+	windowFlagFullscreenDesktop,
+	windowFlagForeign,
+	windowFlagAllowHighDPI,
+
+	-- * Window Positioning
+	windowPosUndefined,
+	windowPosCentered
+) where
+
+#include "SDL.h"
+
+import Data.Int
+import Data.Word
+
+type AudioStatus = Word32 -- (#type SDL_AudioStatus)
+
+audioStatusStopped :: AudioStatus
+audioStatusPlaying :: AudioStatus
+audioStatusPaused :: AudioStatus
+
+audioStatusStopped = (#const SDL_AUDIO_STOPPED)
+audioStatusPlaying = (#const SDL_AUDIO_PLAYING)
+audioStatusPaused = (#const SDL_AUDIO_PAUSED)
+
+type BlendMode = Word32 -- (#type SDL_BlendMode)
+
+blendModeNone :: BlendMode
+blendModeBlend :: BlendMode
+blendModeAdd :: BlendMode
+blendModeMod :: BlendMode
+
+blendModeNone = (#const SDL_BLENDMODE_NONE)
+blendModeBlend = (#const SDL_BLENDMODE_BLEND)
+blendModeAdd = (#const SDL_BLENDMODE_ADD)
+blendModeMod = (#const SDL_BLENDMODE_MOD)
+
+type EventAction = Word32 -- (#type SDL_eventaction)
+
+eventActionAddEvent :: EventAction
+eventActionPeekEvent :: EventAction
+eventActionGetEvent :: EventAction
+
+eventActionAddEvent = (#const SDL_ADDEVENT)
+eventActionPeekEvent = (#const SDL_PEEKEVENT)
+eventActionGetEvent = (#const SDL_GETEVENT)
+
+type GameControllerAxis = Int32 -- (#type SDL_GameControllerAxis)
+
+gameControllerAxisInvalid :: GameControllerAxis
+gameControllerAxisLeftX :: GameControllerAxis
+gameControllerAxisLeftY :: GameControllerAxis
+gameControllerAxisRightX :: GameControllerAxis
+gameControllerAxisRightY :: GameControllerAxis
+gameControllerAxisTriggerLeft :: GameControllerAxis
+gameControllerAxisTriggerRight :: GameControllerAxis
+gameControllerAxisMax :: GameControllerAxis
+
+gameControllerAxisInvalid = (#const SDL_CONTROLLER_AXIS_INVALID)
+gameControllerAxisLeftX = (#const SDL_CONTROLLER_AXIS_LEFTX)
+gameControllerAxisLeftY = (#const SDL_CONTROLLER_AXIS_LEFTY)
+gameControllerAxisRightX = (#const SDL_CONTROLLER_AXIS_RIGHTX)
+gameControllerAxisRightY = (#const SDL_CONTROLLER_AXIS_RIGHTY)
+gameControllerAxisTriggerLeft = (#const SDL_CONTROLLER_AXIS_TRIGGERLEFT)
+gameControllerAxisTriggerRight = (#const SDL_CONTROLLER_AXIS_TRIGGERRIGHT)
+gameControllerAxisMax = (#const SDL_CONTROLLER_AXIS_MAX)
+
+type GameControllerButton = Int32 -- (#type SDL_GameControllerButton)
+
+gameControllerButtonInvalid :: GameControllerButton
+gameControllerButtonA :: GameControllerButton
+gameControllerButtonB :: GameControllerButton
+gameControllerButtonX :: GameControllerButton
+gameControllerButtonY :: GameControllerButton
+gameControllerButtonBack :: GameControllerButton
+gameControllerButtonGuide :: GameControllerButton
+gameControllerButtonStart :: GameControllerButton
+gameControllerButtonLeftStick :: GameControllerButton
+gameControllerButtonRightStick :: GameControllerButton
+gameControllerButtonLeftShoulder :: GameControllerButton
+gameControllerButtonRightShoulder :: GameControllerButton
+gameControllerButtonDPadUp :: GameControllerButton
+gameControllerButtonDPadDown :: GameControllerButton
+gameControllerButtonDPadLeft :: GameControllerButton
+gameControllerButtonDPadRight :: GameControllerButton
+gameControllerButtonMax :: GameControllerButton
+
+gameControllerButtonInvalid = (#const SDL_CONTROLLER_BUTTON_INVALID)
+gameControllerButtonA = (#const SDL_CONTROLLER_BUTTON_A)
+gameControllerButtonB = (#const SDL_CONTROLLER_BUTTON_B)
+gameControllerButtonX = (#const SDL_CONTROLLER_BUTTON_X)
+gameControllerButtonY = (#const SDL_CONTROLLER_BUTTON_Y)
+gameControllerButtonBack = (#const SDL_CONTROLLER_BUTTON_BACK)
+gameControllerButtonGuide = (#const SDL_CONTROLLER_BUTTON_GUIDE)
+gameControllerButtonStart = (#const SDL_CONTROLLER_BUTTON_START)
+gameControllerButtonLeftStick = (#const SDL_CONTROLLER_BUTTON_LEFTSTICK)
+gameControllerButtonRightStick = (#const SDL_CONTROLLER_BUTTON_RIGHTSTICK)
+gameControllerButtonLeftShoulder = (#const SDL_CONTROLLER_BUTTON_LEFTSHOULDER)
+gameControllerButtonRightShoulder = (#const SDL_CONTROLLER_BUTTON_RIGHTSHOULDER)
+gameControllerButtonDPadUp = (#const SDL_CONTROLLER_BUTTON_DPAD_UP)
+gameControllerButtonDPadDown = (#const SDL_CONTROLLER_BUTTON_DPAD_DOWN)
+gameControllerButtonDPadLeft = (#const SDL_CONTROLLER_BUTTON_DPAD_LEFT)
+gameControllerButtonDPadRight = (#const SDL_CONTROLLER_BUTTON_DPAD_RIGHT)
+gameControllerButtonMax = (#const SDL_CONTROLLER_BUTTON_MAX)
+
+type GLattr = Word32 -- (#type SDL_GLattr)
+
+glAttrRedSize :: GLattr
+glAttrGreenSize :: GLattr
+glAttrBlueSize :: GLattr
+glAttrAlphaSize :: GLattr
+glAttrBufferSize :: GLattr
+glAttrDoubleBuffer :: GLattr
+glAttrDepthSize :: GLattr
+glAttrStencilSize :: GLattr
+glAttrAccumRedSize :: GLattr
+glAttrAccumGreenSize :: GLattr
+glAttrAccumBlueSize :: GLattr
+glAttrAccumAlphaSize :: GLattr
+glAttrStereo :: GLattr
+glAttrMultiSampleBuffers :: GLattr
+glAttrMultiSampleSamples :: GLattr
+glAttrAcceleratedVisual :: GLattr
+glAttrRetainedBacking :: GLattr
+glAttrContextMajorVersion :: GLattr
+glAttrContextMinorVersion :: GLattr
+glAttrContextEGL :: GLattr
+glAttrContextFlags :: GLattr
+glAttrContextProfileMask :: GLattr
+glAttrShareWithCurrentContext :: GLattr
+glAttrFramebufferSRGBCapable :: GLattr
+
+glAttrRedSize = (#const SDL_GL_RED_SIZE)
+glAttrGreenSize = (#const SDL_GL_GREEN_SIZE)
+glAttrBlueSize = (#const SDL_GL_BLUE_SIZE)
+glAttrAlphaSize = (#const SDL_GL_ALPHA_SIZE)
+glAttrBufferSize = (#const SDL_GL_BUFFER_SIZE)
+glAttrDoubleBuffer = (#const SDL_GL_DOUBLEBUFFER)
+glAttrDepthSize = (#const SDL_GL_DEPTH_SIZE)
+glAttrStencilSize = (#const SDL_GL_STENCIL_SIZE)
+glAttrAccumRedSize = (#const SDL_GL_ACCUM_RED_SIZE)
+glAttrAccumGreenSize = (#const SDL_GL_ACCUM_GREEN_SIZE)
+glAttrAccumBlueSize = (#const SDL_GL_ACCUM_BLUE_SIZE)
+glAttrAccumAlphaSize = (#const SDL_GL_ACCUM_ALPHA_SIZE)
+glAttrStereo = (#const SDL_GL_STEREO)
+glAttrMultiSampleBuffers = (#const SDL_GL_MULTISAMPLEBUFFERS)
+glAttrMultiSampleSamples = (#const SDL_GL_MULTISAMPLESAMPLES)
+glAttrAcceleratedVisual = (#const SDL_GL_ACCELERATED_VISUAL)
+glAttrRetainedBacking = (#const SDL_GL_RETAINED_BACKING)
+glAttrContextMajorVersion = (#const SDL_GL_CONTEXT_MAJOR_VERSION)
+glAttrContextMinorVersion = (#const SDL_GL_CONTEXT_MINOR_VERSION)
+glAttrContextEGL = (#const SDL_GL_CONTEXT_EGL)
+glAttrContextFlags = (#const SDL_GL_CONTEXT_FLAGS)
+glAttrContextProfileMask = (#const SDL_GL_CONTEXT_PROFILE_MASK)
+glAttrShareWithCurrentContext = (#const SDL_GL_SHARE_WITH_CURRENT_CONTEXT)
+glAttrFramebufferSRGBCapable = (#const SDL_GL_FRAMEBUFFER_SRGB_CAPABLE)
+
+type HintPriority = Word32 -- (#type SDL_HintPriority)
+
+hintPriorityDefault :: HintPriority
+hintPriorityNormal :: HintPriority
+hintPriorityOverride :: HintPriority
+
+hintPriorityDefault = (#const SDL_HINT_DEFAULT)
+hintPriorityNormal = (#const SDL_HINT_NORMAL)
+hintPriorityOverride = (#const SDL_HINT_OVERRIDE)
+
+type Keymod = Word32 -- (#type SDL_Keymod)
+
+keymodNone :: Keymod
+keymodLShift :: Keymod
+keymodRShift :: Keymod
+keymodLCtrl :: Keymod
+keymodRCtrl :: Keymod
+keymodLAlt :: Keymod
+keymodRAlt :: Keymod
+keymodLGUI :: Keymod
+keymodRGUI :: Keymod
+keymodNum :: Keymod
+keymodCaps :: Keymod
+keymodMode :: Keymod
+keymodReserved :: Keymod
+
+keymodNone = (#const KMOD_NONE)
+keymodLShift = (#const KMOD_LSHIFT)
+keymodRShift = (#const KMOD_RSHIFT)
+keymodLCtrl = (#const KMOD_LCTRL)
+keymodRCtrl = (#const KMOD_RCTRL)
+keymodLAlt = (#const KMOD_LALT)
+keymodRAlt = (#const KMOD_RALT)
+keymodLGUI = (#const KMOD_LGUI)
+keymodRGUI = (#const KMOD_RGUI)
+keymodNum = (#const KMOD_NUM)
+keymodCaps = (#const KMOD_CAPS)
+keymodMode = (#const KMOD_MODE)
+keymodReserved = (#const KMOD_RESERVED)
+
+type LogPriority = Word32 -- (#type SDL_LogPriority)
+
+logPriorityVerbose :: LogPriority
+logPriorityDebug :: LogPriority
+logPriorityInfo :: LogPriority
+logPriorityWarn :: LogPriority
+logPriorityError :: LogPriority
+logPriorityCritical :: LogPriority
+logPriorityPriorities :: LogPriority
+
+logPriorityVerbose = (#const SDL_LOG_PRIORITY_VERBOSE)
+logPriorityDebug = (#const SDL_LOG_PRIORITY_DEBUG)
+logPriorityInfo = (#const SDL_LOG_PRIORITY_INFO)
+logPriorityWarn = (#const SDL_LOG_PRIORITY_WARN)
+logPriorityError = (#const SDL_LOG_PRIORITY_ERROR)
+logPriorityCritical = (#const SDL_LOG_PRIORITY_CRITICAL)
+logPriorityPriorities = (#const SDL_NUM_LOG_PRIORITIES)
+
+type PowerState = Word32 -- (#type SDL_PowerState)
+
+powerStateUnknown :: PowerState
+powerStateOnBattery :: PowerState
+powerStateNoBattery :: PowerState
+powerStateCharging :: PowerState
+powerStateCharged :: PowerState
+
+powerStateUnknown = (#const SDL_POWERSTATE_UNKNOWN)
+powerStateOnBattery = (#const SDL_POWERSTATE_ON_BATTERY)
+powerStateNoBattery = (#const SDL_POWERSTATE_NO_BATTERY)
+powerStateCharging = (#const SDL_POWERSTATE_CHARGING)
+powerStateCharged = (#const SDL_POWERSTATE_CHARGED)
+
+type RendererFlip = Word32 -- (#type SDL_RendererFlip)
+
+rendererFlipNone :: RendererFlip
+rendererFlipHorizontal :: RendererFlip
+rendererFlipVertical :: RendererFlip
+
+rendererFlipNone = (#const SDL_FLIP_NONE)
+rendererFlipHorizontal = (#const SDL_FLIP_HORIZONTAL)
+rendererFlipVertical = (#const SDL_FLIP_VERTICAL)
+
+type Scancode = Word32 -- (#type SDL_Scancode)
+
+scancodeUnknown :: Scancode
+scancodeA :: Scancode
+scancodeB :: Scancode
+scancodeC :: Scancode
+scancodeD :: Scancode
+scancodeE :: Scancode
+scancodeF :: Scancode
+scancodeG :: Scancode
+scancodeH :: Scancode
+scancodeI :: Scancode
+scancodeJ :: Scancode
+scancodeK :: Scancode
+scancodeL :: Scancode
+scancodeM :: Scancode
+scancodeN :: Scancode
+scancodeO :: Scancode
+scancodeP :: Scancode
+scancodeQ :: Scancode
+scancodeR :: Scancode
+scancodeS :: Scancode
+scancodeT :: Scancode
+scancodeU :: Scancode
+scancodeV :: Scancode
+scancodeW :: Scancode
+scancodeX :: Scancode
+scancodeY :: Scancode
+scancodeZ :: Scancode
+scancode1 :: Scancode
+scancode2 :: Scancode
+scancode3 :: Scancode
+scancode4 :: Scancode
+scancode5 :: Scancode
+scancode6 :: Scancode
+scancode7 :: Scancode
+scancode8 :: Scancode
+scancode9 :: Scancode
+scancode0 :: Scancode
+scancodeReturn :: Scancode
+scancodeEscape :: Scancode
+scancodeBackspace :: Scancode
+scancodeTab :: Scancode
+scancodeSpace :: Scancode
+scancodeMinus :: Scancode
+scancodeEquals :: Scancode
+scancodeLeftBracket :: Scancode
+scancodeRightBracket :: Scancode
+scancodeBackslash :: Scancode
+scancodeNonUSHash :: Scancode
+scancodeSemicolon :: Scancode
+scancodeApostrophe :: Scancode
+scancodeGrave :: Scancode
+scancodeComma :: Scancode
+scancodePeriod :: Scancode
+scancodeSlash :: Scancode
+scancodeCapsLock :: Scancode
+scancodeF1 :: Scancode
+scancodeF2 :: Scancode
+scancodeF3 :: Scancode
+scancodeF4 :: Scancode
+scancodeF5 :: Scancode
+scancodeF6 :: Scancode
+scancodeF7 :: Scancode
+scancodeF8 :: Scancode
+scancodeF9 :: Scancode
+scancodeF10 :: Scancode
+scancodeF11 :: Scancode
+scancodeF12 :: Scancode
+scancodePrintScreen :: Scancode
+scancodeScrollLock :: Scancode
+scancodePause :: Scancode
+scancodeInsert :: Scancode
+scancodeHome :: Scancode
+scancodePageUp :: Scancode
+scancodeDelete :: Scancode
+scancodeEnd :: Scancode
+scancodePageDown :: Scancode
+scancodeRight :: Scancode
+scancodeLeft :: Scancode
+scancodeDown :: Scancode
+scancodeUp :: Scancode
+scancodeNumLockClear :: Scancode
+scancodeKPDivide :: Scancode
+scancodeKPMultiply :: Scancode
+scancodeKPMinus :: Scancode
+scancodeKPPlus :: Scancode
+scancodeKPEnter :: Scancode
+scancodeKP1 :: Scancode
+scancodeKP2 :: Scancode
+scancodeKP3 :: Scancode
+scancodeKP4 :: Scancode
+scancodeKP5 :: Scancode
+scancodeKP6 :: Scancode
+scancodeKP7 :: Scancode
+scancodeKP8 :: Scancode
+scancodeKP9 :: Scancode
+scancodeKP0 :: Scancode
+scancodeKPPeriod :: Scancode
+scancodeNonUSBackslash :: Scancode
+scancodeApplication :: Scancode
+scancodePower :: Scancode
+scancodeKPEquals :: Scancode
+scancodeF13 :: Scancode
+scancodeF14 :: Scancode
+scancodeF15 :: Scancode
+scancodeF16 :: Scancode
+scancodeF17 :: Scancode
+scancodeF18 :: Scancode
+scancodeF19 :: Scancode
+scancodeF20 :: Scancode
+scancodeF21 :: Scancode
+scancodeF22 :: Scancode
+scancodeF23 :: Scancode
+scancodeF24 :: Scancode
+scancodeExecute :: Scancode
+scancodeHelp :: Scancode
+scancodeMenu :: Scancode
+scancodeSelect :: Scancode
+scancodeStop :: Scancode
+scancodeAgain :: Scancode
+scancodeUndo :: Scancode
+scancodeCut :: Scancode
+scancodeCopy :: Scancode
+scancodePaste :: Scancode
+scancodeFind :: Scancode
+scancodeMute :: Scancode
+scancodeVolumeUp :: Scancode
+scancodeVolumeDown :: Scancode
+scancodeKPComma :: Scancode
+scancodeEqualsAs400 :: Scancode
+scancodeInternational1 :: Scancode
+scancodeInternational2 :: Scancode
+scancodeInternational3 :: Scancode
+scancodeInternational4 :: Scancode
+scancodeInternational5 :: Scancode
+scancodeInternational6 :: Scancode
+scancodeInternational7 :: Scancode
+scancodeInternational8 :: Scancode
+scancodeInternational9 :: Scancode
+scancodeLang1 :: Scancode
+scancodeLang2 :: Scancode
+scancodeLang3 :: Scancode
+scancodeLang4 :: Scancode
+scancodeLang5 :: Scancode
+scancodeLang6 :: Scancode
+scancodeLang7 :: Scancode
+scancodeLang8 :: Scancode
+scancodeLang9 :: Scancode
+scancodeAltErase :: Scancode
+scancodeSysReq :: Scancode
+scancodeCancel :: Scancode
+scancodeClear :: Scancode
+scancodePrior :: Scancode
+scancodeReturn2 :: Scancode
+scancodeSeparator :: Scancode
+scancodeOut :: Scancode
+scancodeOper :: Scancode
+scancodeClearAgain :: Scancode
+scancodeCrSel :: Scancode
+scancodeExSel :: Scancode
+scancodeKP00 :: Scancode
+scancodeKP000 :: Scancode
+scancodeThousandsSeparator :: Scancode
+scancodeDecimalSeparator :: Scancode
+scancodeCurrencyUnit :: Scancode
+scancodeCurrencySubunit :: Scancode
+scancodeLeftParen :: Scancode
+scancodeRightParen :: Scancode
+scancodeLeftBrace :: Scancode
+scancodeRightBrace :: Scancode
+scancodeKPTab :: Scancode
+scancodeKPBackspace :: Scancode
+scancodeKPA :: Scancode
+scancodeKPB :: Scancode
+scancodeKPC :: Scancode
+scancodeKPD :: Scancode
+scancodeKPE :: Scancode
+scancodeKPF :: Scancode
+scancodeKPXOR :: Scancode
+scancodeKPPower :: Scancode
+scancodeKPPercent :: Scancode
+scancodeKPLess :: Scancode
+scancodeKPGreater :: Scancode
+scancodeKPAmpersand :: Scancode
+scancodeKPDBLAmpersand :: Scancode
+scancodeKPVerticalBar :: Scancode
+scancodeKPDBLVerticalBar :: Scancode
+scancodeKPColon :: Scancode
+scancodeKPHash :: Scancode
+scancodeKPSpace :: Scancode
+scancodeKPAt :: Scancode
+scancodeKPExclam :: Scancode
+scancodeKPMemStore :: Scancode
+scancodeKPMemRecall :: Scancode
+scancodeKPMemClear :: Scancode
+scancodeKPMemAdd :: Scancode
+scancodeKPMemSubtract :: Scancode
+scancodeKPMemMultiply :: Scancode
+scancodeKPMemDivide :: Scancode
+scancodeKPPlusMinus :: Scancode
+scancodeKPClear :: Scancode
+scancodeKPClearEntry :: Scancode
+scancodeKPBinary :: Scancode
+scancodeKPOctal :: Scancode
+scancodeKPDecimal :: Scancode
+scancodeKPHexadecimal :: Scancode
+scancodeLCtrl :: Scancode
+scancodeLShift :: Scancode
+scancodeLAlt :: Scancode
+scancodeLGUI :: Scancode
+scancodeRCtrl :: Scancode
+scancodeRShift :: Scancode
+scancodeRAlt :: Scancode
+scancodeRGUI :: Scancode
+scancodeMode :: Scancode
+scancodeAudioNext :: Scancode
+scancodeAudioPrev :: Scancode
+scancodeAudioStop :: Scancode
+scancodeAudioPlay :: Scancode
+scancodeAudioMute :: Scancode
+scancodeMediaSelect :: Scancode
+scancodeWWW :: Scancode
+scancodeMail :: Scancode
+scancodeCalculator :: Scancode
+scancodeComputer :: Scancode
+scancodeACSearch :: Scancode
+scancodeACHome :: Scancode
+scancodeACBack :: Scancode
+scancodeACForward :: Scancode
+scancodeACStop :: Scancode
+scancodeACRefresh :: Scancode
+scancodeACBookmarks :: Scancode
+scancodeBrightnessDown :: Scancode
+scancodeBrightnessUp :: Scancode
+scancodeDisplaySwitch :: Scancode
+scancodeKBDIllumToggle :: Scancode
+scancodeKBDIllumDown :: Scancode
+scancodeKBDIllumUp :: Scancode
+scancodeEject :: Scancode
+scancodeSleep :: Scancode
+scancodeApp1 :: Scancode
+scancodeApp2 :: Scancode
+scancodeNum :: Scancode
+
+scancodeUnknown = (#const SDL_SCANCODE_UNKNOWN)
+scancodeA = (#const SDL_SCANCODE_A)
+scancodeB = (#const SDL_SCANCODE_B)
+scancodeC = (#const SDL_SCANCODE_C)
+scancodeD = (#const SDL_SCANCODE_D)
+scancodeE = (#const SDL_SCANCODE_E)
+scancodeF = (#const SDL_SCANCODE_F)
+scancodeG = (#const SDL_SCANCODE_G)
+scancodeH = (#const SDL_SCANCODE_H)
+scancodeI = (#const SDL_SCANCODE_I)
+scancodeJ = (#const SDL_SCANCODE_J)
+scancodeK = (#const SDL_SCANCODE_K)
+scancodeL = (#const SDL_SCANCODE_L)
+scancodeM = (#const SDL_SCANCODE_M)
+scancodeN = (#const SDL_SCANCODE_N)
+scancodeO = (#const SDL_SCANCODE_O)
+scancodeP = (#const SDL_SCANCODE_P)
+scancodeQ = (#const SDL_SCANCODE_Q)
+scancodeR = (#const SDL_SCANCODE_R)
+scancodeS = (#const SDL_SCANCODE_S)
+scancodeT = (#const SDL_SCANCODE_T)
+scancodeU = (#const SDL_SCANCODE_U)
+scancodeV = (#const SDL_SCANCODE_V)
+scancodeW = (#const SDL_SCANCODE_W)
+scancodeX = (#const SDL_SCANCODE_X)
+scancodeY = (#const SDL_SCANCODE_Y)
+scancodeZ = (#const SDL_SCANCODE_Z)
+scancode1 = (#const SDL_SCANCODE_1)
+scancode2 = (#const SDL_SCANCODE_2)
+scancode3 = (#const SDL_SCANCODE_3)
+scancode4 = (#const SDL_SCANCODE_4)
+scancode5 = (#const SDL_SCANCODE_5)
+scancode6 = (#const SDL_SCANCODE_6)
+scancode7 = (#const SDL_SCANCODE_7)
+scancode8 = (#const SDL_SCANCODE_8)
+scancode9 = (#const SDL_SCANCODE_9)
+scancode0 = (#const SDL_SCANCODE_0)
+scancodeReturn = (#const SDL_SCANCODE_RETURN)
+scancodeEscape = (#const SDL_SCANCODE_ESCAPE)
+scancodeBackspace = (#const SDL_SCANCODE_BACKSPACE)
+scancodeTab = (#const SDL_SCANCODE_TAB)
+scancodeSpace = (#const SDL_SCANCODE_SPACE)
+scancodeMinus = (#const SDL_SCANCODE_MINUS)
+scancodeEquals = (#const SDL_SCANCODE_EQUALS)
+scancodeLeftBracket = (#const SDL_SCANCODE_LEFTBRACKET)
+scancodeRightBracket = (#const SDL_SCANCODE_RIGHTBRACKET)
+scancodeBackslash = (#const SDL_SCANCODE_BACKSLASH)
+scancodeNonUSHash = (#const SDL_SCANCODE_NONUSHASH)
+scancodeSemicolon = (#const SDL_SCANCODE_SEMICOLON)
+scancodeApostrophe = (#const SDL_SCANCODE_APOSTROPHE)
+scancodeGrave = (#const SDL_SCANCODE_GRAVE)
+scancodeComma = (#const SDL_SCANCODE_COMMA)
+scancodePeriod = (#const SDL_SCANCODE_PERIOD)
+scancodeSlash = (#const SDL_SCANCODE_SLASH)
+scancodeCapsLock = (#const SDL_SCANCODE_CAPSLOCK)
+scancodeF1 = (#const SDL_SCANCODE_F1)
+scancodeF2 = (#const SDL_SCANCODE_F2)
+scancodeF3 = (#const SDL_SCANCODE_F3)
+scancodeF4 = (#const SDL_SCANCODE_F4)
+scancodeF5 = (#const SDL_SCANCODE_F5)
+scancodeF6 = (#const SDL_SCANCODE_F6)
+scancodeF7 = (#const SDL_SCANCODE_F7)
+scancodeF8 = (#const SDL_SCANCODE_F8)
+scancodeF9 = (#const SDL_SCANCODE_F9)
+scancodeF10 = (#const SDL_SCANCODE_F10)
+scancodeF11 = (#const SDL_SCANCODE_F11)
+scancodeF12 = (#const SDL_SCANCODE_F12)
+scancodePrintScreen = (#const SDL_SCANCODE_PRINTSCREEN)
+scancodeScrollLock = (#const SDL_SCANCODE_SCROLLLOCK)
+scancodePause = (#const SDL_SCANCODE_PAUSE)
+scancodeInsert = (#const SDL_SCANCODE_INSERT)
+scancodeHome = (#const SDL_SCANCODE_HOME)
+scancodePageUp = (#const SDL_SCANCODE_PAGEUP)
+scancodeDelete = (#const SDL_SCANCODE_DELETE)
+scancodeEnd = (#const SDL_SCANCODE_END)
+scancodePageDown = (#const SDL_SCANCODE_PAGEDOWN)
+scancodeRight = (#const SDL_SCANCODE_RIGHT)
+scancodeLeft = (#const SDL_SCANCODE_LEFT)
+scancodeDown = (#const SDL_SCANCODE_DOWN)
+scancodeUp = (#const SDL_SCANCODE_UP)
+scancodeNumLockClear = (#const SDL_SCANCODE_NUMLOCKCLEAR)
+scancodeKPDivide = (#const SDL_SCANCODE_KP_DIVIDE)
+scancodeKPMultiply = (#const SDL_SCANCODE_KP_MULTIPLY)
+scancodeKPMinus = (#const SDL_SCANCODE_KP_MINUS)
+scancodeKPPlus = (#const SDL_SCANCODE_KP_PLUS)
+scancodeKPEnter = (#const SDL_SCANCODE_KP_ENTER)
+scancodeKP1 = (#const SDL_SCANCODE_KP_1)
+scancodeKP2 = (#const SDL_SCANCODE_KP_2)
+scancodeKP3 = (#const SDL_SCANCODE_KP_3)
+scancodeKP4 = (#const SDL_SCANCODE_KP_4)
+scancodeKP5 = (#const SDL_SCANCODE_KP_5)
+scancodeKP6 = (#const SDL_SCANCODE_KP_6)
+scancodeKP7 = (#const SDL_SCANCODE_KP_7)
+scancodeKP8 = (#const SDL_SCANCODE_KP_8)
+scancodeKP9 = (#const SDL_SCANCODE_KP_9)
+scancodeKP0 = (#const SDL_SCANCODE_KP_0)
+scancodeKPPeriod = (#const SDL_SCANCODE_KP_PERIOD)
+scancodeNonUSBackslash = (#const SDL_SCANCODE_NONUSBACKSLASH)
+scancodeApplication = (#const SDL_SCANCODE_APPLICATION)
+scancodePower = (#const SDL_SCANCODE_POWER)
+scancodeKPEquals = (#const SDL_SCANCODE_KP_EQUALS)
+scancodeF13 = (#const SDL_SCANCODE_F13)
+scancodeF14 = (#const SDL_SCANCODE_F14)
+scancodeF15 = (#const SDL_SCANCODE_F15)
+scancodeF16 = (#const SDL_SCANCODE_F16)
+scancodeF17 = (#const SDL_SCANCODE_F17)
+scancodeF18 = (#const SDL_SCANCODE_F18)
+scancodeF19 = (#const SDL_SCANCODE_F19)
+scancodeF20 = (#const SDL_SCANCODE_F20)
+scancodeF21 = (#const SDL_SCANCODE_F21)
+scancodeF22 = (#const SDL_SCANCODE_F22)
+scancodeF23 = (#const SDL_SCANCODE_F23)
+scancodeF24 = (#const SDL_SCANCODE_F24)
+scancodeExecute = (#const SDL_SCANCODE_EXECUTE)
+scancodeHelp = (#const SDL_SCANCODE_HELP)
+scancodeMenu = (#const SDL_SCANCODE_MENU)
+scancodeSelect = (#const SDL_SCANCODE_SELECT)
+scancodeStop = (#const SDL_SCANCODE_STOP)
+scancodeAgain = (#const SDL_SCANCODE_AGAIN)
+scancodeUndo = (#const SDL_SCANCODE_UNDO)
+scancodeCut = (#const SDL_SCANCODE_CUT)
+scancodeCopy = (#const SDL_SCANCODE_COPY)
+scancodePaste = (#const SDL_SCANCODE_PASTE)
+scancodeFind = (#const SDL_SCANCODE_FIND)
+scancodeMute = (#const SDL_SCANCODE_MUTE)
+scancodeVolumeUp = (#const SDL_SCANCODE_VOLUMEUP)
+scancodeVolumeDown = (#const SDL_SCANCODE_VOLUMEDOWN)
+scancodeKPComma = (#const SDL_SCANCODE_KP_COMMA)
+scancodeEqualsAs400 = (#const SDL_SCANCODE_KP_EQUALSAS400)
+scancodeInternational1 = (#const SDL_SCANCODE_INTERNATIONAL1)
+scancodeInternational2 = (#const SDL_SCANCODE_INTERNATIONAL2)
+scancodeInternational3 = (#const SDL_SCANCODE_INTERNATIONAL3)
+scancodeInternational4 = (#const SDL_SCANCODE_INTERNATIONAL4)
+scancodeInternational5 = (#const SDL_SCANCODE_INTERNATIONAL5)
+scancodeInternational6 = (#const SDL_SCANCODE_INTERNATIONAL6)
+scancodeInternational7 = (#const SDL_SCANCODE_INTERNATIONAL7)
+scancodeInternational8 = (#const SDL_SCANCODE_INTERNATIONAL8)
+scancodeInternational9 = (#const SDL_SCANCODE_INTERNATIONAL9)
+scancodeLang1 = (#const SDL_SCANCODE_LANG1)
+scancodeLang2 = (#const SDL_SCANCODE_LANG2)
+scancodeLang3 = (#const SDL_SCANCODE_LANG3)
+scancodeLang4 = (#const SDL_SCANCODE_LANG4)
+scancodeLang5 = (#const SDL_SCANCODE_LANG5)
+scancodeLang6 = (#const SDL_SCANCODE_LANG6)
+scancodeLang7 = (#const SDL_SCANCODE_LANG7)
+scancodeLang8 = (#const SDL_SCANCODE_LANG8)
+scancodeLang9 = (#const SDL_SCANCODE_LANG9)
+scancodeAltErase = (#const SDL_SCANCODE_ALTERASE)
+scancodeSysReq = (#const SDL_SCANCODE_SYSREQ)
+scancodeCancel = (#const SDL_SCANCODE_CANCEL)
+scancodeClear = (#const SDL_SCANCODE_CLEAR)
+scancodePrior = (#const SDL_SCANCODE_PRIOR)
+scancodeReturn2 = (#const SDL_SCANCODE_RETURN2)
+scancodeSeparator = (#const SDL_SCANCODE_SEPARATOR)
+scancodeOut = (#const SDL_SCANCODE_OUT)
+scancodeOper = (#const SDL_SCANCODE_OPER)
+scancodeClearAgain = (#const SDL_SCANCODE_CLEARAGAIN)
+scancodeCrSel = (#const SDL_SCANCODE_CRSEL)
+scancodeExSel = (#const SDL_SCANCODE_EXSEL)
+scancodeKP00 = (#const SDL_SCANCODE_KP_00)
+scancodeKP000 = (#const SDL_SCANCODE_KP_000)
+scancodeThousandsSeparator = (#const SDL_SCANCODE_THOUSANDSSEPARATOR)
+scancodeDecimalSeparator = (#const SDL_SCANCODE_DECIMALSEPARATOR)
+scancodeCurrencyUnit = (#const SDL_SCANCODE_CURRENCYUNIT)
+scancodeCurrencySubunit = (#const SDL_SCANCODE_CURRENCYSUBUNIT)
+scancodeLeftParen = (#const SDL_SCANCODE_KP_LEFTPAREN)
+scancodeRightParen = (#const SDL_SCANCODE_KP_RIGHTPAREN)
+scancodeLeftBrace = (#const SDL_SCANCODE_KP_LEFTBRACE)
+scancodeRightBrace = (#const SDL_SCANCODE_KP_RIGHTBRACE)
+scancodeKPTab = (#const SDL_SCANCODE_KP_TAB)
+scancodeKPBackspace = (#const SDL_SCANCODE_KP_BACKSPACE)
+scancodeKPA = (#const SDL_SCANCODE_KP_A)
+scancodeKPB = (#const SDL_SCANCODE_KP_B)
+scancodeKPC = (#const SDL_SCANCODE_KP_C)
+scancodeKPD = (#const SDL_SCANCODE_KP_D)
+scancodeKPE = (#const SDL_SCANCODE_KP_E)
+scancodeKPF = (#const SDL_SCANCODE_KP_F)
+scancodeKPXOR = (#const SDL_SCANCODE_KP_XOR)
+scancodeKPPower = (#const SDL_SCANCODE_KP_POWER)
+scancodeKPPercent = (#const SDL_SCANCODE_KP_PERCENT)
+scancodeKPLess = (#const SDL_SCANCODE_KP_LESS)
+scancodeKPGreater = (#const SDL_SCANCODE_KP_GREATER)
+scancodeKPAmpersand = (#const SDL_SCANCODE_KP_AMPERSAND)
+scancodeKPDBLAmpersand = (#const SDL_SCANCODE_KP_DBLAMPERSAND)
+scancodeKPVerticalBar = (#const SDL_SCANCODE_KP_VERTICALBAR)
+scancodeKPDBLVerticalBar = (#const SDL_SCANCODE_KP_DBLVERTICALBAR)
+scancodeKPColon = (#const SDL_SCANCODE_KP_COLON)
+scancodeKPHash = (#const SDL_SCANCODE_KP_HASH)
+scancodeKPSpace = (#const SDL_SCANCODE_KP_SPACE)
+scancodeKPAt = (#const SDL_SCANCODE_KP_AT)
+scancodeKPExclam = (#const SDL_SCANCODE_KP_EXCLAM)
+scancodeKPMemStore = (#const SDL_SCANCODE_KP_MEMSTORE)
+scancodeKPMemRecall = (#const SDL_SCANCODE_KP_MEMRECALL)
+scancodeKPMemClear = (#const SDL_SCANCODE_KP_MEMCLEAR)
+scancodeKPMemAdd = (#const SDL_SCANCODE_KP_MEMADD)
+scancodeKPMemSubtract = (#const SDL_SCANCODE_KP_MEMSUBTRACT)
+scancodeKPMemMultiply = (#const SDL_SCANCODE_KP_MEMMULTIPLY)
+scancodeKPMemDivide = (#const SDL_SCANCODE_KP_MEMDIVIDE)
+scancodeKPPlusMinus = (#const SDL_SCANCODE_KP_PLUSMINUS)
+scancodeKPClear = (#const SDL_SCANCODE_KP_CLEAR)
+scancodeKPClearEntry = (#const SDL_SCANCODE_KP_CLEARENTRY)
+scancodeKPBinary = (#const SDL_SCANCODE_KP_BINARY)
+scancodeKPOctal = (#const SDL_SCANCODE_KP_OCTAL)
+scancodeKPDecimal = (#const SDL_SCANCODE_KP_DECIMAL)
+scancodeKPHexadecimal = (#const SDL_SCANCODE_KP_HEXADECIMAL)
+scancodeLCtrl = (#const SDL_SCANCODE_LCTRL)
+scancodeLShift = (#const SDL_SCANCODE_LSHIFT)
+scancodeLAlt = (#const SDL_SCANCODE_LALT)
+scancodeLGUI = (#const SDL_SCANCODE_LGUI)
+scancodeRCtrl = (#const SDL_SCANCODE_RCTRL)
+scancodeRShift = (#const SDL_SCANCODE_RSHIFT)
+scancodeRAlt = (#const SDL_SCANCODE_RALT)
+scancodeRGUI = (#const SDL_SCANCODE_RGUI)
+scancodeMode = (#const SDL_SCANCODE_MODE)
+scancodeAudioNext = (#const SDL_SCANCODE_AUDIONEXT)
+scancodeAudioPrev = (#const SDL_SCANCODE_AUDIOPREV)
+scancodeAudioStop = (#const SDL_SCANCODE_AUDIOSTOP)
+scancodeAudioPlay = (#const SDL_SCANCODE_AUDIOPLAY)
+scancodeAudioMute = (#const SDL_SCANCODE_AUDIOMUTE)
+scancodeMediaSelect = (#const SDL_SCANCODE_MEDIASELECT)
+scancodeWWW = (#const SDL_SCANCODE_WWW)
+scancodeMail = (#const SDL_SCANCODE_MAIL)
+scancodeCalculator = (#const SDL_SCANCODE_CALCULATOR)
+scancodeComputer = (#const SDL_SCANCODE_COMPUTER)
+scancodeACSearch = (#const SDL_SCANCODE_AC_SEARCH)
+scancodeACHome = (#const SDL_SCANCODE_AC_HOME)
+scancodeACBack = (#const SDL_SCANCODE_AC_BACK)
+scancodeACForward = (#const SDL_SCANCODE_AC_FORWARD)
+scancodeACStop = (#const SDL_SCANCODE_AC_STOP)
+scancodeACRefresh = (#const SDL_SCANCODE_AC_REFRESH)
+scancodeACBookmarks = (#const SDL_SCANCODE_AC_BOOKMARKS)
+scancodeBrightnessDown = (#const SDL_SCANCODE_BRIGHTNESSDOWN)
+scancodeBrightnessUp = (#const SDL_SCANCODE_BRIGHTNESSUP)
+scancodeDisplaySwitch = (#const SDL_SCANCODE_DISPLAYSWITCH)
+scancodeKBDIllumToggle = (#const SDL_SCANCODE_KBDILLUMTOGGLE)
+scancodeKBDIllumDown = (#const SDL_SCANCODE_KBDILLUMDOWN)
+scancodeKBDIllumUp = (#const SDL_SCANCODE_KBDILLUMUP)
+scancodeEject = (#const SDL_SCANCODE_EJECT)
+scancodeSleep = (#const SDL_SCANCODE_SLEEP)
+scancodeApp1 = (#const SDL_SCANCODE_APP1)
+scancodeApp2 = (#const SDL_SCANCODE_APP2)
+scancodeNum = (#const SDL_NUM_SCANCODES)
+
+type SystemCursor = Word32 -- (#type SDL_SystemCursor)
+
+systemCursorArrow :: SystemCursor
+systemCursorIBeam :: SystemCursor
+systemCursorWait :: SystemCursor
+systemCursorCrosshair :: SystemCursor
+systemCursorWaitArrow :: SystemCursor
+systemCursorSizeNWSE :: SystemCursor
+systemCursorSizeNESW :: SystemCursor
+systemCursorSizeWE :: SystemCursor
+systemCursorSizeNS :: SystemCursor
+systemCursorSizeAll :: SystemCursor
+systemCursorNo :: SystemCursor
+systemCursorHand :: SystemCursor
+systemCursorNum :: SystemCursor
+
+systemCursorArrow = (#const SDL_SYSTEM_CURSOR_ARROW)
+systemCursorIBeam = (#const SDL_SYSTEM_CURSOR_IBEAM)
+systemCursorWait = (#const SDL_SYSTEM_CURSOR_WAIT)
+systemCursorCrosshair = (#const SDL_SYSTEM_CURSOR_CROSSHAIR)
+systemCursorWaitArrow = (#const SDL_SYSTEM_CURSOR_WAITARROW)
+systemCursorSizeNWSE = (#const SDL_SYSTEM_CURSOR_SIZENWSE)
+systemCursorSizeNESW = (#const SDL_SYSTEM_CURSOR_SIZENESW)
+systemCursorSizeWE = (#const SDL_SYSTEM_CURSOR_SIZEWE)
+systemCursorSizeNS = (#const SDL_SYSTEM_CURSOR_SIZENS)
+systemCursorSizeAll = (#const SDL_SYSTEM_CURSOR_SIZEALL)
+systemCursorNo = (#const SDL_SYSTEM_CURSOR_NO)
+systemCursorHand = (#const SDL_SYSTEM_CURSOR_HAND)
+systemCursorNum = (#const SDL_NUM_SYSTEM_CURSORS)
+
+eventTypeFirstEvent :: (Num a) => a
+eventTypeQuit :: (Num a) => a
+eventTypeAppTerminating :: (Num a) => a
+eventTypeAppLowMemory :: (Num a) => a
+eventTypeAppWillEnterBackground :: (Num a) => a
+eventTypeAppDidEnterBackground :: (Num a) => a
+eventTypeAppWillEnterForeground :: (Num a) => a
+eventTypeAppDidEnterForeground :: (Num a) => a
+eventTypeWindowEvent :: (Num a) => a
+eventTypeSysWMEvent :: (Num a) => a
+eventTypeKeyDown :: (Num a) => a
+eventTypeKeyUp :: (Num a) => a
+eventTypeTextEditing :: (Num a) => a
+eventTypeTextInput :: (Num a) => a
+eventTypeMouseMotion :: (Num a) => a
+eventTypeMouseButtonDown :: (Num a) => a
+eventTypeMouseButtonUp :: (Num a) => a
+eventTypeMouseWheel :: (Num a) => a
+eventTypeJoyAxisMotion :: (Num a) => a
+eventTypeJoyBallMotion :: (Num a) => a
+eventTypeJoyHatMotion :: (Num a) => a
+eventTypeJoyButtonDown :: (Num a) => a
+eventTypeJoyButtonUp :: (Num a) => a
+eventTypeJoyDeviceAdded :: (Num a) => a
+eventTypeJoyDeviceRemoved :: (Num a) => a
+eventTypeControllerAxisMotion :: (Num a) => a
+eventTypeControllerButtonDown :: (Num a) => a
+eventTypeControllerButtonUp :: (Num a) => a
+eventTypeControllerDeviceAdded :: (Num a) => a
+eventTypeControllerDeviceRemoved :: (Num a) => a
+eventTypeControllerDeviceRemapped :: (Num a) => a
+eventTypeFingerDown :: (Num a) => a
+eventTypeFingerUp :: (Num a) => a
+eventTypeFingerMotion :: (Num a) => a
+eventTypeDollarGesture :: (Num a) => a
+eventTypeDollarRecord :: (Num a) => a
+eventTypeMultiGesture :: (Num a) => a
+eventTypeClipboardUpdate :: (Num a) => a
+eventTypeDropFile :: (Num a) => a
+eventTypeUserEvent :: (Num a) => a
+eventTypeLastEvent :: (Num a) => a
+
+eventTypeFirstEvent = (#const SDL_FIRSTEVENT)
+eventTypeQuit = (#const SDL_QUIT)
+eventTypeAppTerminating = (#const SDL_APP_TERMINATING)
+eventTypeAppLowMemory = (#const SDL_APP_LOWMEMORY)
+eventTypeAppWillEnterBackground = (#const SDL_APP_WILLENTERBACKGROUND)
+eventTypeAppDidEnterBackground = (#const SDL_APP_DIDENTERBACKGROUND)
+eventTypeAppWillEnterForeground = (#const SDL_APP_WILLENTERFOREGROUND)
+eventTypeAppDidEnterForeground = (#const SDL_APP_DIDENTERFOREGROUND)
+eventTypeWindowEvent = (#const SDL_WINDOWEVENT)
+eventTypeSysWMEvent = (#const SDL_SYSWMEVENT)
+eventTypeKeyDown = (#const SDL_KEYDOWN)
+eventTypeKeyUp = (#const SDL_KEYUP)
+eventTypeTextEditing = (#const SDL_TEXTEDITING)
+eventTypeTextInput = (#const SDL_TEXTINPUT)
+eventTypeMouseMotion = (#const SDL_MOUSEMOTION)
+eventTypeMouseButtonDown = (#const SDL_MOUSEBUTTONDOWN)
+eventTypeMouseButtonUp = (#const SDL_MOUSEBUTTONUP)
+eventTypeMouseWheel = (#const SDL_MOUSEWHEEL)
+eventTypeJoyAxisMotion = (#const SDL_JOYAXISMOTION)
+eventTypeJoyBallMotion = (#const SDL_JOYBALLMOTION)
+eventTypeJoyHatMotion = (#const SDL_JOYHATMOTION)
+eventTypeJoyButtonDown = (#const SDL_JOYBUTTONDOWN)
+eventTypeJoyButtonUp = (#const SDL_JOYBUTTONUP)
+eventTypeJoyDeviceAdded = (#const SDL_JOYDEVICEADDED)
+eventTypeJoyDeviceRemoved = (#const SDL_JOYDEVICEREMOVED)
+eventTypeControllerAxisMotion = (#const SDL_CONTROLLERAXISMOTION)
+eventTypeControllerButtonDown = (#const SDL_CONTROLLERBUTTONDOWN)
+eventTypeControllerButtonUp = (#const SDL_CONTROLLERBUTTONUP)
+eventTypeControllerDeviceAdded = (#const SDL_CONTROLLERDEVICEADDED)
+eventTypeControllerDeviceRemoved = (#const SDL_CONTROLLERDEVICEREMOVED)
+eventTypeControllerDeviceRemapped = (#const SDL_CONTROLLERDEVICEREMAPPED)
+eventTypeFingerDown = (#const SDL_FINGERDOWN)
+eventTypeFingerUp = (#const SDL_FINGERUP)
+eventTypeFingerMotion = (#const SDL_FINGERMOTION)
+eventTypeDollarGesture = (#const SDL_DOLLARGESTURE)
+eventTypeDollarRecord = (#const SDL_DOLLARRECORD)
+eventTypeMultiGesture = (#const SDL_MULTIGESTURE)
+eventTypeClipboardUpdate = (#const SDL_CLIPBOARDUPDATE)
+eventTypeDropFile = (#const SDL_DROPFILE)
+eventTypeUserEvent = (#const SDL_USEREVENT)
+eventTypeLastEvent = (#const SDL_LASTEVENT)
+
+glProfileCore :: (Num a) => a
+glProfileCompatibility :: (Num a) => a
+glProfileES :: (Num a) => a
+
+glProfileCore = (#const SDL_GL_CONTEXT_PROFILE_CORE)
+glProfileCompatibility = (#const SDL_GL_CONTEXT_PROFILE_COMPATIBILITY)
+glProfileES = (#const SDL_GL_CONTEXT_PROFILE_ES)
+
+glContextFlagDebug :: (Num a) => a
+glContextFlagForwardCompatible :: (Num a) => a
+glContextFlagRobustAccess :: (Num a) => a
+glContextFlagResetIsolation :: (Num a) => a
+
+glContextFlagDebug = (#const SDL_GL_CONTEXT_DEBUG_FLAG)
+glContextFlagForwardCompatible = (#const SDL_GL_CONTEXT_FORWARD_COMPATIBLE_FLAG)
+glContextFlagRobustAccess = (#const SDL_GL_CONTEXT_ROBUST_ACCESS_FLAG)
+glContextFlagResetIsolation = (#const SDL_GL_CONTEXT_RESET_ISOLATION_FLAG)
+
+initFlagTimer :: (Num a) => a
+initFlagAudio :: (Num a) => a
+initFlagVideo :: (Num a) => a
+initFlagJoystick :: (Num a) => a
+initFlagHaptic :: (Num a) => a
+initFlagGameController :: (Num a) => a
+initFlagEvents :: (Num a) => a
+initFlagNoParachute :: (Num a) => a
+initFlagEverything :: (Num a) => a
+
+initFlagTimer = (#const SDL_INIT_TIMER)
+initFlagAudio = (#const SDL_INIT_AUDIO)
+initFlagVideo = (#const SDL_INIT_VIDEO)
+initFlagJoystick = (#const SDL_INIT_JOYSTICK)
+initFlagHaptic = (#const SDL_INIT_HAPTIC)
+initFlagGameController = (#const SDL_INIT_GAMECONTROLLER)
+initFlagEvents = (#const SDL_INIT_EVENTS)
+initFlagNoParachute = (#const SDL_INIT_NOPARACHUTE)
+initFlagEverything = (#const SDL_INIT_EVERYTHING)
+
+joystickHatCentered :: (Num a) => a
+joystickHatUp :: (Num a) => a
+joystickHatRight :: (Num a) => a
+joystickHatDown :: (Num a) => a
+joystickHatLeft :: (Num a) => a
+joystickHatRightUp :: (Num a) => a
+joystickHatRightDown :: (Num a) => a
+joystickHatLeftUp :: (Num a) => a
+joystickHatLeftDown :: (Num a) => a
+
+joystickHatCentered = (#const SDL_HAT_CENTERED)
+joystickHatUp = (#const SDL_HAT_UP)
+joystickHatRight = (#const SDL_HAT_RIGHT)
+joystickHatDown = (#const SDL_HAT_DOWN)
+joystickHatLeft = (#const SDL_HAT_LEFT)
+joystickHatRightUp = (#const SDL_HAT_RIGHTUP)
+joystickHatRightDown = (#const SDL_HAT_RIGHTDOWN)
+joystickHatLeftUp = (#const SDL_HAT_LEFTUP)
+joystickHatLeftDown = (#const SDL_HAT_LEFTDOWN)
+
+messageBoxFlagError :: (Num a) => a
+messageBoxFlagWarning :: (Num a) => a
+messageBoxFlagInformation :: (Num a) => a
+
+messageBoxFlagError = (#const SDL_MESSAGEBOX_ERROR)
+messageBoxFlagWarning = (#const SDL_MESSAGEBOX_WARNING)
+messageBoxFlagInformation = (#const SDL_MESSAGEBOX_INFORMATION)
+
+messageBoxButtonFlagReturnKeyDefault :: (Num a) => a
+messageBoxButtonFlagEscapeKeyDefault :: (Num a) => a
+
+messageBoxButtonFlagReturnKeyDefault = (#const SDL_MESSAGEBOX_BUTTON_RETURNKEY_DEFAULT)
+messageBoxButtonFlagEscapeKeyDefault = (#const SDL_MESSAGEBOX_BUTTON_ESCAPEKEY_DEFAULT)
+
+rendererFlagSoftware :: (Num a) => a
+rendererFlagAccelerated :: (Num a) => a
+rendererFlagPresentVSync :: (Num a) => a
+rendererFlagTargetTexture :: (Num a) => a
+
+rendererFlagSoftware = (#const SDL_RENDERER_SOFTWARE)
+rendererFlagAccelerated = (#const SDL_RENDERER_ACCELERATED)
+rendererFlagPresentVSync = (#const SDL_RENDERER_PRESENTVSYNC)
+rendererFlagTargetTexture = (#const SDL_RENDERER_TARGETTEXTURE)
+
+textureAccessStatic :: (Num a) => a
+textureAccessStreaming :: (Num a) => a
+textureAccessTarget :: (Num a) => a
+
+textureAccessStatic = (#const SDL_TEXTUREACCESS_STATIC)
+textureAccessStreaming = (#const SDL_TEXTUREACCESS_STREAMING)
+textureAccessTarget = (#const SDL_TEXTUREACCESS_TARGET)
+
+textureModulateNone :: (Num a) => a
+textureModulateColor :: (Num a) => a
+textureModulateAlpha :: (Num a) => a
+
+textureModulateNone = (#const SDL_TEXTUREMODULATE_NONE)
+textureModulateColor = (#const SDL_TEXTUREMODULATE_COLOR)
+textureModulateAlpha = (#const SDL_TEXTUREMODULATE_ALPHA)
+
+windowEventNone :: (Num a) => a
+windowEventShown :: (Num a) => a
+windowEventHidden :: (Num a) => a
+windowEventExposed :: (Num a) => a
+windowEventMoved :: (Num a) => a
+windowEventResized :: (Num a) => a
+windowEventSizeChanged :: (Num a) => a
+windowEventMinimized :: (Num a) => a
+windowEventMaximized :: (Num a) => a
+windowEventRestored :: (Num a) => a
+windowEventEnter :: (Num a) => a
+windowEventLeave :: (Num a) => a
+windowEventFocusGained :: (Num a) => a
+windowEventFocusLost :: (Num a) => a
+windowEventClose :: (Num a) => a
+
+windowEventNone = (#const SDL_WINDOWEVENT_NONE)
+windowEventShown = (#const SDL_WINDOWEVENT_SHOWN)
+windowEventHidden = (#const SDL_WINDOWEVENT_HIDDEN)
+windowEventExposed = (#const SDL_WINDOWEVENT_EXPOSED)
+windowEventMoved = (#const SDL_WINDOWEVENT_MOVED)
+windowEventResized = (#const SDL_WINDOWEVENT_RESIZED)
+windowEventSizeChanged = (#const SDL_WINDOWEVENT_SIZE_CHANGED)
+windowEventMinimized = (#const SDL_WINDOWEVENT_MINIMIZED)
+windowEventMaximized = (#const SDL_WINDOWEVENT_MAXIMIZED)
+windowEventRestored = (#const SDL_WINDOWEVENT_RESTORED)
+windowEventEnter = (#const SDL_WINDOWEVENT_ENTER)
+windowEventLeave = (#const SDL_WINDOWEVENT_LEAVE)
+windowEventFocusGained = (#const SDL_WINDOWEVENT_FOCUS_GAINED)
+windowEventFocusLost = (#const SDL_WINDOWEVENT_FOCUS_LOST)
+windowEventClose = (#const SDL_WINDOWEVENT_CLOSE)
+
+windowFlagFullscreen :: (Num a) => a
+windowFlagOpenGL :: (Num a) => a
+windowFlagShown :: (Num a) => a
+windowFlagHidden :: (Num a) => a
+windowFlagBorderless :: (Num a) => a
+windowFlagResizable :: (Num a) => a
+windowFlagMinimized :: (Num a) => a
+windowFlagMaximized :: (Num a) => a
+windowFlagInputGrabbed :: (Num a) => a
+windowFlagInputFocus :: (Num a) => a
+windowFlagMouseFocus :: (Num a) => a
+windowFlagFullscreenDesktop :: (Num a) => a
+windowFlagForeign :: (Num a) => a
+windowFlagAllowHighDPI :: (Num a) => a
+
+windowFlagFullscreen = (#const SDL_WINDOW_FULLSCREEN)
+windowFlagOpenGL = (#const SDL_WINDOW_OPENGL)
+windowFlagShown = (#const SDL_WINDOW_SHOWN)
+windowFlagHidden = (#const SDL_WINDOW_HIDDEN)
+windowFlagBorderless = (#const SDL_WINDOW_BORDERLESS)
+windowFlagResizable = (#const SDL_WINDOW_RESIZABLE)
+windowFlagMinimized = (#const SDL_WINDOW_MINIMIZED)
+windowFlagMaximized = (#const SDL_WINDOW_MAXIMIZED)
+windowFlagInputGrabbed = (#const SDL_WINDOW_INPUT_GRABBED)
+windowFlagInputFocus = (#const SDL_WINDOW_INPUT_FOCUS)
+windowFlagMouseFocus = (#const SDL_WINDOW_MOUSE_FOCUS)
+windowFlagFullscreenDesktop = (#const SDL_WINDOW_FULLSCREEN_DESKTOP)
+windowFlagForeign = (#const SDL_WINDOW_FOREIGN)
+windowFlagAllowHighDPI = (#const SDL_WINDOW_ALLOW_HIGHDPI)
+
+windowPosUndefined :: (Num a) => a
+windowPosCentered :: (Num a) => a
+
+windowPosUndefined = (#const SDL_WINDOWPOS_UNDEFINED)
+windowPosCentered = (#const SDL_WINDOWPOS_CENTERED)
diff --git a/Graphics/UI/SDL/Event.hs b/Graphics/UI/SDL/Event.hs
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Event.hs
@@ -0,0 +1,263 @@
+module Graphics.UI.SDL.Event (
+	-- * Event Handling
+	addEventWatch,
+	delEventWatch,
+	eventState,
+	filterEvents,
+	flushEvent,
+	flushEvents,
+	getEventFilter,
+	getNumTouchDevices,
+	getNumTouchFingers,
+	getTouchDevice,
+	getTouchFinger,
+	hasEvent,
+	hasEvents,
+	loadDollarTemplates,
+	peepEvents,
+	pollEvent,
+	pumpEvents,
+	pushEvent,
+	quitRequested,
+	recordGesture,
+	registerEvents,
+	saveAllDollarTemplates,
+	saveDollarTemplate,
+	setEventFilter,
+	waitEvent,
+	waitEventTimeout,
+
+	-- * Keyboard Support
+	getKeyFromName,
+	getKeyFromScancode,
+	getKeyName,
+	getKeyboardFocus,
+	getKeyboardState,
+	getModState,
+	getScancodeFromKey,
+	getScancodeFromName,
+	getScancodeName,
+	hasScreenKeyboardSupport,
+	isScreenKeyboardShown,
+	isTextInputActive,
+	setModState,
+	setTextInputRect,
+	startTextInput,
+	stopTextInput,
+
+	-- * Mouse Support
+	createColorCursor,
+	createCursor,
+	createSystemCursor,
+	freeCursor,
+	getCursor,
+	getDefaultCursor,
+	getMouseFocus,
+	getMouseState,
+	getRelativeMouseMode,
+	getRelativeMouseState,
+	setCursor,
+	setRelativeMouseMode,
+	showCursor,
+	warpMouseInWindow,
+
+	-- * Joystick Support
+	joystickClose,
+	joystickEventState,
+	joystickGetAttached,
+	joystickGetAxis,
+	joystickGetBall,
+	joystickGetButton,
+	joystickGetDeviceGUID,
+	joystickGetGUID,
+	joystickGetGUIDFromString,
+	joystickGetGUIDString,
+	joystickGetHat,
+	joystickInstanceID,
+	joystickName,
+	joystickNameForIndex,
+	joystickNumAxes,
+	joystickNumBalls,
+	joystickNumButtons,
+	joystickNumHats,
+	joystickOpen,
+	joystickUpdate,
+	numJoysticks,
+
+	-- * Game Controller Support
+	gameControllerAddMapping,
+	-- gameControllerAddMappingsFromFile,
+	gameControllerClose,
+	gameControllerEventState,
+	gameControllerGetAttached,
+	gameControllerGetAxis,
+	gameControllerGetAxisFromString,
+	gameControllerGetBindForAxis,
+	gameControllerGetBindForButton,
+	gameControllerGetButton,
+	gameControllerGetButtonFromString,
+	gameControllerGetJoystick,
+	gameControllerGetStringForAxis,
+	gameControllerGetStringForButton,
+	gameControllerMapping,
+	gameControllerMappingForGUID,
+	gameControllerName,
+	gameControllerNameForIndex,
+	gameControllerOpen,
+	gameControllerUpdate,
+	isGameController
+) where
+
+import Data.Int
+import Data.Word
+import Foreign.C.String
+import Foreign.C.Types
+import Foreign.Marshal.Alloc
+import Foreign.Ptr
+import Foreign.Storable
+import Graphics.UI.SDL.Enum
+import Graphics.UI.SDL.Types
+
+foreign import ccall "SDL.h SDL_AddEventWatch" addEventWatch :: EventFilter -> Ptr () -> IO ()
+foreign import ccall "SDL.h SDL_DelEventWatch" delEventWatch :: EventFilter -> Ptr () -> IO ()
+foreign import ccall "SDL.h SDL_EventState" eventState :: Word32 -> CInt -> IO Word8
+foreign import ccall "SDL.h SDL_FilterEvents" filterEvents :: EventFilter -> Ptr () -> IO ()
+foreign import ccall "SDL.h SDL_FlushEvent" flushEvent :: Word32 -> IO ()
+foreign import ccall "SDL.h SDL_FlushEvents" flushEvents :: Word32 -> Word32 -> IO ()
+foreign import ccall "SDL.h SDL_GetEventFilter" getEventFilter :: Ptr EventFilter -> Ptr (Ptr ()) -> IO Bool
+foreign import ccall "SDL.h SDL_GetNumTouchDevices" getNumTouchDevices :: IO CInt
+foreign import ccall "SDL.h SDL_GetNumTouchFingers" getNumTouchFingers :: TouchID -> CInt
+foreign import ccall "SDL.h SDL_GetTouchDevice" getTouchDevice :: CInt -> IO TouchID
+foreign import ccall "SDL.h SDL_GetTouchFinger" getTouchFinger :: TouchID -> CInt -> IO (Ptr Finger)
+foreign import ccall "SDL.h SDL_HasEvent" hasEvent :: Word32 -> IO Bool
+foreign import ccall "SDL.h SDL_HasEvents" hasEvents :: Word32 -> Word32 -> IO Bool
+foreign import ccall "SDL.h SDL_LoadDollarTemplates" loadDollarTemplates :: TouchID -> Ptr RWops -> IO CInt
+foreign import ccall "SDL.h SDL_PeepEvents" peepEvents :: Ptr Event -> CInt -> EventAction -> Word32 -> Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_PollEvent" pollEvent :: Ptr Event -> IO CInt
+foreign import ccall "SDL.h SDL_PumpEvents" pumpEvents :: IO ()
+foreign import ccall "SDL.h SDL_PushEvent" pushEvent :: Ptr Event -> IO CInt
+-- foreign import ccall "SDL.h SDL_QuitRequested" quitRequested :: IO Bool
+foreign import ccall "SDL.h SDL_RecordGesture" recordGesture :: TouchID -> IO CInt
+foreign import ccall "SDL.h SDL_RegisterEvents" registerEvents :: CInt -> IO Word32
+foreign import ccall "SDL.h SDL_SaveAllDollarTemplates" saveAllDollarTemplates :: Ptr RWops -> IO CInt
+foreign import ccall "SDL.h SDL_SaveDollarTemplate" saveDollarTemplate :: GestureID -> Ptr RWops -> IO CInt
+foreign import ccall "SDL.h SDL_SetEventFilter" setEventFilter :: EventFilter -> Ptr () -> IO ()
+foreign import ccall "SDL.h SDL_WaitEvent" waitEvent :: Ptr Event -> IO CInt
+foreign import ccall "SDL.h SDL_WaitEventTimeout" waitEventTimeout :: Ptr Event -> CInt -> IO CInt
+
+foreign import ccall "SDL.h SDL_GetKeyFromName" getKeyFromName :: CString -> IO Keycode
+foreign import ccall "SDL.h SDL_GetKeyFromScancode" getKeyFromScancode :: Scancode -> IO Keycode
+foreign import ccall "SDL.h SDL_GetKeyName" getKeyName :: Keycode -> IO CString
+foreign import ccall "SDL.h SDL_GetKeyboardFocus" getKeyboardFocus :: IO Window
+foreign import ccall "SDL.h SDL_GetKeyboardState" getKeyboardState :: Ptr CInt -> IO (Ptr Word8)
+foreign import ccall "SDL.h SDL_GetModState" getModState :: IO Keymod
+foreign import ccall "SDL.h SDL_GetScancodeFromKey" getScancodeFromKey :: Keycode -> IO Scancode
+foreign import ccall "SDL.h SDL_GetScancodeFromName" getScancodeFromName :: CString -> IO Scancode
+foreign import ccall "SDL.h SDL_GetScancodeName" getScancodeName :: Scancode -> IO CString
+foreign import ccall "SDL.h SDL_HasScreenKeyboardSupport" hasScreenKeyboardSupport :: IO Bool
+foreign import ccall "SDL.h SDL_IsScreenKeyboardShown" isScreenKeyboardShown :: Window -> IO Bool
+foreign import ccall "SDL.h SDL_IsTextInputActive" isTextInputActive :: IO Bool
+foreign import ccall "SDL.h SDL_SetModState" setModState :: Keymod -> IO ()
+foreign import ccall "SDL.h SDL_SetTextInputRect" setTextInputRect :: Ptr Rect -> IO ()
+foreign import ccall "SDL.h SDL_StartTextInput" startTextInput :: IO ()
+foreign import ccall "SDL.h SDL_StopTextInput" stopTextInput :: IO ()
+
+foreign import ccall "SDL.h SDL_CreateColorCursor" createColorCursor :: Ptr Surface -> CInt -> CInt -> IO Cursor
+foreign import ccall "SDL.h SDL_CreateCursor" createCursor :: Ptr Word8 -> Ptr Word8 -> CInt -> CInt -> CInt -> CInt -> IO Cursor
+foreign import ccall "SDL.h SDL_CreateSystemCursor" createSystemCursor :: SystemCursor -> IO Cursor
+foreign import ccall "SDL.h SDL_FreeCursor" freeCursor :: Cursor -> IO ()
+foreign import ccall "SDL.h SDL_GetCursor" getCursor :: IO Cursor
+foreign import ccall "SDL.h SDL_GetDefaultCursor" getDefaultCursor :: IO Cursor
+foreign import ccall "SDL.h SDL_GetMouseFocus" getMouseFocus :: IO Window
+foreign import ccall "SDL.h SDL_GetMouseState" getMouseState :: Ptr CInt -> Ptr CInt -> IO Word32
+foreign import ccall "SDL.h SDL_GetRelativeMouseMode" getRelativeMouseMode :: IO Bool
+foreign import ccall "SDL.h SDL_GetRelativeMouseState" getRelativeMouseState :: Ptr CInt -> Ptr CInt -> IO Word32
+foreign import ccall "SDL.h SDL_SetCursor" setCursor :: Cursor -> IO ()
+foreign import ccall "SDL.h SDL_SetRelativeMouseMode" setRelativeMouseMode :: Bool -> IO CInt
+foreign import ccall "SDL.h SDL_ShowCursor" showCursor :: CInt -> IO CInt
+foreign import ccall "SDL.h SDL_WarpMouseInWindow" warpMouseInWindow :: Window -> CInt -> CInt -> IO ()
+
+foreign import ccall "SDL.h SDL_JoystickClose" joystickClose :: Joystick -> IO ()
+foreign import ccall "SDL.h SDL_JoystickEventState" joystickEventState :: CInt -> IO CInt
+foreign import ccall "SDL.h SDL_JoystickGetAttached" joystickGetAttached :: Joystick -> IO Bool
+foreign import ccall "SDL.h SDL_JoystickGetAxis" joystickGetAxis :: Joystick -> CInt -> IO Int16
+foreign import ccall "SDL.h SDL_JoystickGetBall" joystickGetBall :: Joystick -> CInt -> Ptr CInt -> Ptr CInt -> IO CInt
+foreign import ccall "SDL.h SDL_JoystickGetButton" joystickGetButton :: Joystick -> CInt -> IO Word8
+foreign import ccall "sdlhelper.h SDLHelper_JoystickGetDeviceGUID" joystickGetDeviceGUID' :: CInt -> Ptr JoystickGUID -> IO ()
+foreign import ccall "sdlhelper.h SDLHelper_JoystickGetGUID" joystickGetGUID' :: Joystick -> Ptr JoystickGUID -> IO ()
+foreign import ccall "sdlhelper.h SDLHelper_JoystickGetGUIDFromString" joystickGetGUIDFromString' :: CString -> Ptr JoystickGUID -> IO ()
+foreign import ccall "sdlhelper.h SDLHelper_JoystickGetGUIDString" joystickGetGUIDString' :: Ptr JoystickGUID -> CString -> CInt -> IO ()
+foreign import ccall "SDL.h SDL_JoystickGetHat" joystickGetHat :: Joystick -> CInt -> IO Word8
+foreign import ccall "SDL.h SDL_JoystickInstanceID" joystickInstanceID :: Joystick -> IO JoystickID
+foreign import ccall "SDL.h SDL_JoystickName" joystickName :: Joystick -> IO CString
+foreign import ccall "SDL.h SDL_JoystickNameForIndex" joystickNameForIndex :: CInt -> IO CString
+foreign import ccall "SDL.h SDL_JoystickNumAxes" joystickNumAxes :: Joystick -> IO CInt
+foreign import ccall "SDL.h SDL_JoystickNumBalls" joystickNumBalls :: Joystick -> IO CInt
+foreign import ccall "SDL.h SDL_JoystickNumButtons" joystickNumButtons :: Joystick -> IO CInt
+foreign import ccall "SDL.h SDL_JoystickNumHats" joystickNumHats :: Joystick -> IO CInt
+foreign import ccall "SDL.h SDL_JoystickOpen" joystickOpen :: CInt -> IO Joystick
+foreign import ccall "SDL.h SDL_JoystickUpdate" joystickUpdate :: IO ()
+foreign import ccall "SDL.h SDL_NumJoysticks" numJoysticks :: IO CInt
+
+foreign import ccall "SDL.h SDL_GameControllerAddMapping" gameControllerAddMapping :: CString -> IO CInt
+-- foreign import ccall "SDL.h SDL_GameControllerAddMappingsFromFile" gameControllerAddMappingsFromFile :: CString -> IO CInt -- Available in SDL 2.0.2
+foreign import ccall "SDL.h SDL_GameControllerClose" gameControllerClose :: GameController -> IO ()
+foreign import ccall "SDL.h SDL_GameControllerEventState" gameControllerEventState :: CInt -> IO CInt
+foreign import ccall "SDL.h SDL_GameControllerGetAttached" gameControllerGetAttached :: GameController -> IO Bool
+foreign import ccall "SDL.h SDL_GameControllerGetAxis" gameControllerGetAxis :: GameController -> GameControllerAxis -> IO Int16
+foreign import ccall "SDL.h SDL_GameControllerGetAxisFromString" gameControllerGetAxisFromString :: CString -> IO GameControllerAxis
+foreign import ccall "sdlhelper.h SDLHelper_GameControllerGetBindForAxis" gameControllerGetBindForAxis' :: GameController -> GameControllerAxis -> Ptr GameControllerButtonBind -> IO ()
+foreign import ccall "sdlhelper.h SDLHelper_GameControllerGetBindForButton" gameControllerGetBindForButton' :: GameController -> GameControllerButton -> Ptr GameControllerButtonBind -> IO ()
+foreign import ccall "SDL.h SDL_GameControllerGetButton" gameControllerGetButton :: GameController -> GameControllerButton -> IO Word8
+foreign import ccall "SDL.h SDL_GameControllerGetButtonFromString" gameControllerGetButtonFromString :: CString -> IO GameControllerButton
+foreign import ccall "SDL.h SDL_GameControllerGetJoystick" gameControllerGetJoystick :: GameController -> IO Joystick
+foreign import ccall "SDL.h SDL_GameControllerGetStringForAxis" gameControllerGetStringForAxis :: GameControllerAxis -> IO CString
+foreign import ccall "SDL.h SDL_GameControllerGetStringForButton" gameControllerGetStringForButton :: GameControllerButton -> IO CString
+foreign import ccall "SDL.h SDL_GameControllerMapping" gameControllerMapping :: GameController -> IO CString
+foreign import ccall "sdlhelper.h SDLHelper_GameControllerMappingForGUID" gameControllerMappingForGUID' :: Ptr JoystickGUID -> IO CString
+foreign import ccall "SDL.h SDL_GameControllerName" gameControllerName :: GameController -> IO CString
+foreign import ccall "SDL.h SDL_GameControllerNameForIndex" gameControllerNameForIndex :: CInt -> IO CString
+foreign import ccall "SDL.h SDL_GameControllerOpen" gameControllerOpen :: CInt -> IO GameController
+foreign import ccall "SDL.h SDL_GameControllerUpdate" gameControllerUpdate :: IO ()
+foreign import ccall "SDL.h SDL_IsGameController" isGameController :: CInt -> IO Bool
+
+quitRequested :: IO Bool
+quitRequested = do
+	pumpEvents
+	ev <- peepEvents nullPtr 0 eventActionPeekEvent eventTypeQuit eventTypeQuit
+	return $ ev > 0
+
+joystickGetDeviceGUID :: CInt -> IO JoystickGUID
+joystickGetDeviceGUID device_index = alloca $ \ptr -> do
+	joystickGetDeviceGUID' device_index ptr
+	peek ptr
+
+joystickGetGUID :: Joystick -> IO JoystickGUID
+joystickGetGUID joystick = alloca $ \ptr -> do
+	joystickGetGUID' joystick ptr
+	peek ptr
+
+joystickGetGUIDFromString :: CString -> IO JoystickGUID
+joystickGetGUIDFromString pchGUID = alloca $ \ptr -> do
+	joystickGetGUIDFromString' pchGUID ptr
+	peek ptr
+
+joystickGetGUIDString :: JoystickGUID -> CString -> CInt -> IO ()
+joystickGetGUIDString guid pszGUID cbGUID = alloca $ \ptr -> do
+	poke ptr guid
+	joystickGetGUIDString' ptr pszGUID cbGUID
+
+gameControllerGetBindForAxis :: GameController -> GameControllerAxis -> IO GameControllerButtonBind
+gameControllerGetBindForAxis gamecontroller axis = alloca $ \ptr -> do
+	gameControllerGetBindForAxis' gamecontroller axis ptr
+	peek ptr
+
+gameControllerGetBindForButton :: GameController -> GameControllerButton -> IO GameControllerButtonBind
+gameControllerGetBindForButton gamecontroller button = alloca $ \ptr -> do
+	gameControllerGetBindForButton' gamecontroller button ptr
+	peek ptr
+
+gameControllerMappingForGUID :: JoystickGUID -> IO CString
+gameControllerMappingForGUID guid = alloca $ \ptr -> do
+	poke ptr guid
+	gameControllerMappingForGUID' ptr
diff --git a/Graphics/UI/SDL/Filesystem.hs b/Graphics/UI/SDL/Filesystem.hs
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Filesystem.hs
@@ -0,0 +1,64 @@
+module Graphics.UI.SDL.Filesystem (
+	-- * Filesystem Paths
+	getBasePath,
+	getPrefPath,
+
+	-- * File I/O Abstraction
+	allocRW,
+	freeRW,
+	rwFromConstMem,
+	rwFromFP,
+	rwFromFile,
+	rwFromMem,
+	rwClose,
+	rwRead,
+	rwSeek,
+	rwTell,
+	rwWrite,
+	readBE16,
+	readBE32,
+	readBE64,
+	readLE16,
+	readLE32,
+	readLE64,
+	writeBE16,
+	writeBE32,
+	writeBE64,
+	writeLE16,
+	writeLE32,
+	writeLE64
+) where
+
+import Data.Int
+import Data.Word
+import Foreign.C.String
+import Foreign.C.Types
+import Foreign.Ptr
+import Graphics.UI.SDL.Types
+
+foreign import ccall "SDL.H SDL_GetBasePath" getBasePath :: IO CString
+foreign import ccall "SDL.H SDL_GetPrefPath" getPrefPath :: CString -> CString -> IO CString
+
+foreign import ccall "SDL.h SDL_AllocRW" allocRW :: IO (Ptr RWops)
+foreign import ccall "SDL.h SDL_FreeRW" freeRW :: Ptr RWops -> IO ()
+foreign import ccall "SDL.h SDL_RWFromConstMem" rwFromConstMem :: Ptr () -> CInt -> IO (Ptr RWops)
+foreign import ccall "SDL.h SDL_RWFromFP" rwFromFP :: Ptr () -> Bool -> IO (Ptr RWops)
+foreign import ccall "SDL.h SDL_RWFromFile" rwFromFile :: CString -> CString -> IO (Ptr RWops)
+foreign import ccall "SDL.h SDL_RWFromMem" rwFromMem :: Ptr () -> CInt -> IO (Ptr RWops)
+foreign import ccall "sdlhelper.h SDLHelper_RWclose" rwClose :: Ptr RWops -> IO CInt
+foreign import ccall "sdlhelper.h SDLHelper_RWread" rwRead :: Ptr RWops -> Ptr () -> CSize -> CSize -> IO CSize
+foreign import ccall "sdlhelper.h SDLHelper_RWseek" rwSeek :: Ptr RWops -> Int64 -> CInt -> IO Int64
+foreign import ccall "sdlhelper.h SDLHelper_RWtell" rwTell :: Ptr RWops -> IO Int64
+foreign import ccall "sdlhelper.h SDLHelper_RWwrite" rwWrite :: Ptr RWops -> Ptr () -> CSize -> CSize -> IO CSize
+foreign import ccall "SDL.h SDL_ReadBE16" readBE16 :: Ptr RWops -> IO Word16
+foreign import ccall "SDL.h SDL_ReadBE32" readBE32 :: Ptr RWops -> IO Word32
+foreign import ccall "SDL.h SDL_ReadBE64" readBE64 :: Ptr RWops -> IO Word64
+foreign import ccall "SDL.h SDL_ReadLE16" readLE16 :: Ptr RWops -> IO Word16
+foreign import ccall "SDL.h SDL_ReadLE32" readLE32 :: Ptr RWops -> IO Word32
+foreign import ccall "SDL.h SDL_ReadLE64" readLE64 :: Ptr RWops -> IO Word64
+foreign import ccall "SDL.h SDL_WriteBE16" writeBE16 :: Ptr RWops -> Word16 -> IO CSize
+foreign import ccall "SDL.h SDL_WriteBE32" writeBE32 :: Ptr RWops -> Word32 -> IO CSize
+foreign import ccall "SDL.h SDL_WriteBE64" writeBE64 :: Ptr RWops -> Word64 -> IO CSize
+foreign import ccall "SDL.h SDL_WriteLE16" writeLE16 :: Ptr RWops -> Word16 -> IO CSize
+foreign import ccall "SDL.h SDL_WriteLE32" writeLE32 :: Ptr RWops -> Word32 -> IO CSize
+foreign import ccall "SDL.h SDL_WriteLE64" writeLE64 :: Ptr RWops -> Word64 -> IO CSize
diff --git a/Graphics/UI/SDL/Haptic.hs b/Graphics/UI/SDL/Haptic.hs
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Haptic.hs
@@ -0,0 +1,70 @@
+module Graphics.UI.SDL.Haptic (
+	-- * Force Feedback Support
+	hapticClose,
+	hapticDestroyEffect,
+	hapticEffectSupported,
+	hapticGetEffectStatus,
+	hapticIndex,
+	hapticName,
+	hapticNewEffect,
+	hapticNumAxes,
+	hapticNumEffects,
+	hapticNumEffectsPlaying,
+	hapticOpen,
+	hapticOpenFromJoystick,
+	hapticOpenFromMouse,
+	hapticOpened,
+	hapticPause,
+	hapticQuery,
+	hapticRumbleInit,
+	hapticRumblePlay,
+	hapticRumbleStop,
+	hapticRumbleSupported,
+	hapticRunEffect,
+	hapticSetAutocenter,
+	hapticSetGain,
+	hapticStopAll,
+	hapticStopEffect,
+	hapticUnpause,
+	hapticUpdateEffect,
+	joystickIsHaptic,
+	mouseIsHaptic,
+	numHaptics
+) where
+
+import Data.Word
+import Foreign.C.String
+import Foreign.C.Types
+import Foreign.Ptr
+import Graphics.UI.SDL.Types
+
+foreign import ccall "SDL.h SDL_HapticClose" hapticClose :: Haptic -> IO ()
+foreign import ccall "SDL.h SDL_HapticDestroyEffect" hapticDestroyEffect :: Haptic -> CInt -> IO ()
+foreign import ccall "SDL.h SDL_HapticEffectSupported" hapticEffectSupported :: Haptic -> Ptr HapticEffect -> IO CInt
+foreign import ccall "SDL.h SDL_HapticGetEffectStatus" hapticGetEffectStatus :: Haptic -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_HapticIndex" hapticIndex :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticName" hapticName :: CInt -> IO CString
+foreign import ccall "SDL.h SDL_HapticNewEffect" hapticNewEffect :: Haptic -> Ptr HapticEffect -> IO CInt
+foreign import ccall "SDL.h SDL_HapticNumAxes" hapticNumAxes :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticNumEffects" hapticNumEffects :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticNumEffectsPlaying" hapticNumEffectsPlaying :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticOpen" hapticOpen :: CInt -> IO Haptic
+foreign import ccall "SDL.h SDL_HapticOpenFromJoystick" hapticOpenFromJoystick :: Joystick -> IO Haptic
+foreign import ccall "SDL.h SDL_HapticOpenFromMouse" hapticOpenFromMouse :: IO Haptic
+foreign import ccall "SDL.h SDL_HapticOpened" hapticOpened :: CInt -> IO CInt
+foreign import ccall "SDL.h SDL_HapticPause" hapticPause :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticQuery" hapticQuery :: Haptic -> IO CUInt
+foreign import ccall "SDL.h SDL_HapticRumbleInit" hapticRumbleInit :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticRumblePlay" hapticRumblePlay :: Haptic -> CFloat -> Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_HapticRumbleStop" hapticRumbleStop :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticRumbleSupported" hapticRumbleSupported :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticRunEffect" hapticRunEffect :: Haptic -> CInt -> Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_HapticSetAutocenter" hapticSetAutocenter :: Haptic -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_HapticSetGain" hapticSetGain :: Haptic -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_HapticStopAll" hapticStopAll :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticStopEffect" hapticStopEffect :: Haptic -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_HapticUnpause" hapticUnpause :: Haptic -> IO CInt
+foreign import ccall "SDL.h SDL_HapticUpdateEffect" hapticUpdateEffect :: Haptic -> CInt -> Ptr HapticEffect -> IO CInt
+foreign import ccall "SDL.h SDL_JoystickIsHaptic" joystickIsHaptic :: Joystick -> IO CInt
+foreign import ccall "SDL.h SDL_MouseIsHaptic" mouseIsHaptic :: IO CInt
+foreign import ccall "SDL.h SDL_NumHaptics" numHaptics :: IO CInt
diff --git a/Graphics/UI/SDL/Power.hs b/Graphics/UI/SDL/Power.hs
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Power.hs
@@ -0,0 +1,10 @@
+module Graphics.UI.SDL.Power (
+	-- * Power Management Status
+	getPowerInfo
+) where
+
+import Foreign.C.Types
+import Foreign.Ptr
+import Graphics.UI.SDL.Enum
+
+foreign import ccall "SDL.h SDL_GetPowerInfo" getPowerInfo :: Ptr CInt -> Ptr CInt -> IO PowerState
diff --git a/Graphics/UI/SDL/Timer.hs b/Graphics/UI/SDL/Timer.hs
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Timer.hs
@@ -0,0 +1,21 @@
+module Graphics.UI.SDL.Timer (
+	-- * Timer Support
+	addTimer,
+	delay,
+	getPerformanceCounter,
+	getPerformanceFrequency,
+	getTicks,
+	removeTimer
+) where
+
+import Data.Word
+import Foreign.C.Types
+import Foreign.Ptr
+import Graphics.UI.SDL.Types
+
+foreign import ccall "SDL.h SDL_AddTimer" addTimer :: Word32 -> TimerCallback -> Ptr () -> IO TimerID
+foreign import ccall "SDL.h SDL_Delay" delay :: Word32 -> IO ()
+foreign import ccall "SDL.h SDL_GetPerformanceCounter" getPerformanceCounter :: IO Word64
+foreign import ccall "SDL.h SDL_GetPerformanceFrequency" getPerformanceFrequency :: IO Word64
+foreign import ccall "SDL.h SDL_GetTicks" getTicks :: IO Word32
+foreign import ccall "SDL.h SDL_RemoveTimer" removeTimer :: TimerID -> IO Bool
diff --git a/Graphics/UI/SDL/Types.hsc b/Graphics/UI/SDL/Types.hsc
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Types.hsc
@@ -0,0 +1,1303 @@
+module Graphics.UI.SDL.Types (
+	-- * Type Aliases
+	AudioCallback,
+	AudioDeviceID,
+	AudioFormat,
+	Cursor,
+	EventFilter,
+	FingerID,
+	GameController,
+	GestureID,
+	GLContext,
+	Haptic,
+	Joystick,
+	JoystickID,
+	Keycode,
+	LogOutputFunction,
+	Renderer,
+	SysWMmsg,
+	Texture,
+	TimerCallback,
+	TimerID,
+	TouchID,
+	Window,
+
+	-- * Data Structures
+	AudioCVT(..),
+	AudioSpec(..),
+	Color(..),
+	DisplayMode(..),
+	Event(..),
+	Finger(..),
+	GameControllerButtonBind(..),
+	HapticDirection(..),
+	HapticEffect(..),
+	JoystickGUID(..),
+	Keysym(..),
+	MessageBoxButtonData(..),
+	MessageBoxColor(..),
+	MessageBoxColorScheme(..),
+	MessageBoxData(..),
+	Palette(..),
+	PixelFormat(..),
+	Point(..),
+	Rect(..),
+	RendererInfo(..),
+	RWops(..),
+	Surface(..)
+) where
+
+#include "SDL.h"
+
+import Data.Int
+import Data.Word
+import Foreign.C.String
+import Foreign.C.Types
+import Foreign.Marshal.Array
+import Foreign.Ptr
+import Foreign.Storable
+import Graphics.UI.SDL.Enum
+
+type AudioCallback = FunPtr (Ptr () -> Ptr Word8 -> CInt -> IO ())
+type AudioDeviceID = Word32
+type AudioFormat = Word16
+type Cursor = Ptr ()
+type EventFilter = FunPtr (Ptr () -> Ptr Event -> IO CInt)
+type FingerID = Int64
+type GameController = Ptr ()
+type GestureID = Int64
+type GLContext = Ptr ()
+type Haptic = Ptr ()
+type Joystick = Ptr ()
+type JoystickID = Int32
+type Keycode = Int32
+type LogOutputFunction = FunPtr (Ptr () -> CInt -> LogPriority -> CString -> IO ())
+type Renderer = Ptr ()
+type SysWMmsg = Ptr ()
+type Texture = Ptr ()
+type TimerCallback = FunPtr (Word32 -> Ptr () -> IO Word32)
+type TimerID = CInt
+type TouchID = Int64
+type Window = Ptr ()
+
+data AudioCVT = AudioCVT {
+                audioCVTNeeded :: CInt
+              , audioCVTSrcFormat :: AudioFormat
+              , audioCVTDstFormat :: AudioFormat
+              , audioCVTRateIncr :: CDouble
+              , audioCVTBuf :: Ptr Word8
+              , audioCVTLen :: CInt
+              , audioCVTLenCvt :: CInt
+              , audioCVTLenMult :: CInt
+              , audioCVTLenRatio :: CDouble
+              } deriving (Eq, Show)
+
+instance Storable AudioCVT where
+	sizeOf _ = (#size SDL_AudioCVT)
+	alignment = sizeOf
+	peek ptr = do
+		needed <- (#peek SDL_AudioCVT, needed) ptr
+		src_format <- (#peek SDL_AudioCVT, src_format) ptr
+		dst_format <- (#peek SDL_AudioCVT, dst_format) ptr
+		rate_incr <- (#peek SDL_AudioCVT, rate_incr) ptr
+		buf <- (#peek SDL_AudioCVT, buf) ptr
+		len <- (#peek SDL_AudioCVT, len) ptr
+		len_cvt <- (#peek SDL_AudioCVT, len_cvt) ptr
+		len_mult <- (#peek SDL_AudioCVT, len_mult) ptr
+		len_ratio <- (#peek SDL_AudioCVT, len_ratio) ptr
+		return $! AudioCVT needed src_format dst_format rate_incr buf len len_cvt len_mult len_ratio
+	poke ptr (AudioCVT needed src_format dst_format rate_incr buf len len_cvt len_mult len_ratio) = do
+		(#poke SDL_AudioCVT, needed) ptr needed
+		(#poke SDL_AudioCVT, src_format) ptr src_format
+		(#poke SDL_AudioCVT, dst_format) ptr dst_format
+		(#poke SDL_AudioCVT, rate_incr) ptr rate_incr
+		(#poke SDL_AudioCVT, buf) ptr buf
+		(#poke SDL_AudioCVT, len) ptr len
+		(#poke SDL_AudioCVT, len_cvt) ptr len_cvt
+		(#poke SDL_AudioCVT, len_mult) ptr len_mult
+		(#poke SDL_AudioCVT, len_ratio) ptr len_ratio
+
+data AudioSpec = AudioSpec {
+                 audioSpecFreq :: CInt
+               , audioSpecFormat :: AudioFormat
+               , audioSpecChannels :: Word8
+               , audioSpecSilence :: Word8
+               , audioSpecSamples :: Word16
+               , audioSpecSize :: Word32
+               , audioSpecCallback :: AudioCallback
+               , audioSpecUserdata :: Ptr ()
+               } deriving (Eq, Show)
+
+instance Storable AudioSpec where
+	sizeOf _ = (#size SDL_AudioSpec)
+	alignment = sizeOf
+	peek ptr = do
+		freq <- (#peek SDL_AudioSpec, freq) ptr
+		format <- (#peek SDL_AudioSpec, format) ptr
+		channels <- (#peek SDL_AudioSpec, channels) ptr
+		silence <- (#peek SDL_AudioSpec, silence) ptr
+		samples <- (#peek SDL_AudioSpec, samples) ptr
+		size <- (#peek SDL_AudioSpec, size) ptr
+		callback <- (#peek SDL_AudioSpec, callback) ptr
+		userdata <- (#peek SDL_AudioSpec, userdata) ptr
+		return $! AudioSpec freq format channels silence samples size callback userdata
+	poke ptr (AudioSpec freq format channels silence samples size callback userdata) = do
+		(#poke SDL_AudioSpec, freq) ptr freq
+		(#poke SDL_AudioSpec, format) ptr format
+		(#poke SDL_AudioSpec, channels) ptr channels
+		(#poke SDL_AudioSpec, silence) ptr silence
+		(#poke SDL_AudioSpec, samples) ptr samples
+		(#poke SDL_AudioSpec, size) ptr size
+		(#poke SDL_AudioSpec, callback) ptr callback
+		(#poke SDL_AudioSpec, userdata) ptr userdata
+
+data Color = Color {
+             colorR :: Word8
+           , colorG :: Word8
+           , colorB :: Word8
+           , colorA :: Word8
+           } deriving (Eq, Show)
+
+instance Storable Color where
+	sizeOf _ = (#size SDL_Color)
+	alignment = sizeOf
+	peek ptr = do
+		r <- (#peek SDL_Color, r) ptr
+		g <- (#peek SDL_Color, g) ptr
+		b <- (#peek SDL_Color, b) ptr
+		a <- (#peek SDL_Color, a) ptr
+		return $! Color r g b a
+	poke ptr (Color r g b a) = do
+		(#poke SDL_Color, r) ptr r
+		(#poke SDL_Color, g) ptr g
+		(#poke SDL_Color, b) ptr b
+		(#poke SDL_Color, a) ptr a
+
+data DisplayMode = DisplayMode {
+                   displayModeFormat :: Word32
+                 , displayModeW :: CInt
+                 , displayModeH :: CInt
+                 , displayModeRefreshRate :: CInt
+                 , displayModeDriverData :: Ptr ()
+                 } deriving (Eq, Show)
+
+instance Storable DisplayMode where
+	sizeOf _ = (#size SDL_DisplayMode)
+	alignment = sizeOf
+	peek ptr = do
+		format <- (#peek SDL_DisplayMode, format) ptr
+		w <- (#peek SDL_DisplayMode, w) ptr
+		h <- (#peek SDL_DisplayMode, h) ptr
+		refresh_rate <- (#peek SDL_DisplayMode, refresh_rate) ptr
+		driverdata <- (#peek SDL_DisplayMode, driverdata) ptr
+		return $! DisplayMode format w h refresh_rate driverdata
+	poke ptr (DisplayMode format w h refresh_rate driverdata) = do
+		(#poke SDL_DisplayMode, format) ptr format
+		(#poke SDL_DisplayMode, w) ptr w
+		(#poke SDL_DisplayMode, h) ptr h
+		(#poke SDL_DisplayMode, refresh_rate) ptr refresh_rate
+		(#poke SDL_DisplayMode, driverdata) ptr driverdata
+
+data Event = WindowEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , windowEventWindowID :: Word32
+           , windowEventEvent :: Word8
+           , windowEventData1 :: Int32
+           , windowEventData2 :: Int32
+           }
+           | KeyboardEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , keyboardEventWindowID :: Word32
+           , keyboardEventState :: Word8
+           , keyboardEventRepeat :: Word8
+           , keyboardEventKeysym :: Keysym
+           }
+           | TextEditingEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , textEditingEventWindowID :: Word32
+           , textEditingEventText :: [CChar]
+           , textEditingEventStart :: Int32
+           , textEditingEventLength :: Int32
+           }
+           | TextInputEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , textInputEventWindowID :: Word32
+           , textInputEventText :: [CChar]
+           }
+           | MouseMotionEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , mouseMotionEventWindowID :: Word32
+           , mouseMotionEventWhich :: Word32
+           , mouseMotionEventState :: Word32
+           , mouseMotionEventX :: Int32
+           , mouseMotionEventY :: Int32
+           , mouseMotionEventXRel :: Int32
+           , mouseMotionEventYRel :: Int32
+           }
+           | MouseButtonEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , mouseButtonEventWindowID :: Word32
+           , mouseButtonEventWhich :: Word32
+           , mouseButtonEventButton :: Word8
+           , mouseButtonEventState :: Word8
+           , mouseButtonEventX :: Int32
+           , mouseButtonEventY :: Int32
+           }
+           | MouseWheelEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , mouseWheelEventWindowID :: Word32
+           , mouseWheelEventWhich :: Word32
+           , mouseWheelEventX :: Int32
+           , mouseWheelEventY :: Int32
+           }
+           | JoyAxisEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , joyAxisEventWhich :: JoystickID
+           , joyAxisEventAxis :: Word8
+           , joyAxisEventValue :: Int16
+           }
+           | JoyBallEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , joyBallEventWhich :: JoystickID
+           , joyBallEventBall :: Word8
+           , joyBallEventXRel :: Int16
+           , joyBallEventYRel :: Int16
+           }
+           | JoyHatEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , joyHatEventWhich :: JoystickID
+           , joyHatEventHat :: Word8
+           , joyHatEventValue :: Word8
+           }
+           | JoyButtonEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , joyButtonEventWhich :: JoystickID
+           , joyButtonEventButton :: Word8
+           , joyButtonEventState :: Word8
+           }
+           | JoyDeviceEvent{
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , joyDeviceEventWhich :: Int32
+           }
+           | ControllerAxisEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , controllerAxisEventWhich :: JoystickID
+           , controllerAxisEventAxis :: Word8
+           , controllerAxisEventValue :: Int16
+           }
+           | ControllerButtonEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , controllerButtonEventWhich :: JoystickID
+           , controllerButtonEventButton :: Word8
+           , controllerButtonEventState :: Word8
+           }
+           | ControllerDeviceEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , controllerDeviceEventWhich :: Int32
+           }
+           | QuitEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           }
+           | UserEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , userEventWindowID :: Word32
+           , userEventCode :: Int32
+           , userEventData1 :: Ptr ()
+           , userEventData2 :: Ptr ()
+           }
+           | SysWMEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , sysWMEventMsg :: SysWMmsg
+           }
+           | TouchFingerEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , touchFingerEventTouchID :: TouchID
+           , touchFingerEventFingerID :: FingerID
+           , touchFingerEventX :: CFloat
+           , touchFingerEventY :: CFloat
+           , touchFingerEventDX :: CFloat
+           , touchFingerEventDY :: CFloat
+           , touchFingerEventPressure :: CFloat
+           }
+           | MultiGestureEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , multiGestureEventTouchID :: TouchID
+           , multiGestureEventDTheta :: CFloat
+           , multiGestureEventDDist :: CFloat
+           , multiGestureEventX :: CFloat
+           , multiGestureEventY :: CFloat
+           , multiGestureEventNumFingers :: Word16
+           }
+           | DollarGestureEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , dollarGestureEventTouchID :: TouchID
+           , dollarGestureEventGestureID :: GestureID
+           , dollarGestureEventNumFingers :: Word32
+           , dollarGestureEventError :: CFloat
+           , dollarGestureEventX :: CFloat
+           , dollarGestureEventY :: CFloat
+           }
+           | DropEvent {
+             eventType :: Word32
+           , eventTimestamp :: Word32
+           , dropEventFile :: CString
+           }
+           deriving (Eq, Show)
+
+instance Storable Event where
+	sizeOf _ = (#size SDL_Event)
+	alignment = sizeOf
+	peek ptr = do
+		typ <- (#peek SDL_Event, common.type) ptr
+		timestamp <- (#peek SDL_Event, common.timestamp) ptr
+		case typ of
+			(#const SDL_QUIT) ->
+				return $! QuitEvent typ timestamp
+			(#const SDL_WINDOWEVENT) -> do
+				wid <- (#peek SDL_Event, window.windowID) ptr
+				event <- (#peek SDL_Event, window.event) ptr
+				data1 <- (#peek SDL_Event, window.data1) ptr
+				data2 <- (#peek SDL_Event, window.data2) ptr
+				return $! WindowEvent typ timestamp wid event data1 data2
+			(#const SDL_SYSWMEVENT) -> do
+				msg <- (#peek SDL_Event, syswm.msg) ptr
+				return $! SysWMEvent typ timestamp msg
+			(#const SDL_KEYDOWN) -> key $ KeyboardEvent typ timestamp
+			(#const SDL_KEYUP) -> key $ KeyboardEvent typ timestamp
+			(#const SDL_TEXTEDITING) -> do
+				wid <- (#peek SDL_Event, edit.windowID) ptr
+				text <- peekArray (#const SDL_TEXTEDITINGEVENT_TEXT_SIZE) $ (#ptr SDL_Event, edit.text) ptr
+				start <- (#peek SDL_Event, edit.start) ptr
+				len <- (#peek SDL_Event, edit.length) ptr
+				return $! TextEditingEvent typ timestamp wid text start len
+			(#const SDL_TEXTINPUT) -> do
+				wid <- (#peek SDL_Event, text.windowID) ptr
+				text <- peekArray (#const SDL_TEXTINPUTEVENT_TEXT_SIZE) $ (#ptr SDL_Event, text.text) ptr
+				return $! TextInputEvent typ timestamp wid text
+			(#const SDL_MOUSEMOTION) -> do
+				wid <- (#peek SDL_Event, motion.windowID) ptr
+				which <- (#peek SDL_Event, motion.which) ptr
+				state <- (#peek SDL_Event, motion.state) ptr
+				x <- (#peek SDL_Event, motion.x) ptr
+				y <- (#peek SDL_Event, motion.y) ptr
+				xrel <- (#peek SDL_Event, motion.xrel) ptr
+				yrel <- (#peek SDL_Event, motion.yrel) ptr
+				return $! MouseMotionEvent typ timestamp wid which state x y xrel yrel
+			(#const SDL_MOUSEBUTTONDOWN) -> mouse $ MouseButtonEvent typ timestamp
+			(#const SDL_MOUSEBUTTONUP) -> mouse $ MouseButtonEvent typ timestamp
+			(#const SDL_MOUSEWHEEL) -> do
+				wid <- (#peek SDL_Event, wheel.windowID) ptr
+				which <- (#peek SDL_Event, wheel.which) ptr
+				x <- (#peek SDL_Event, wheel.x) ptr
+				y <- (#peek SDL_Event, wheel.y) ptr
+				return $! MouseWheelEvent typ timestamp wid which x y
+			(#const SDL_JOYAXISMOTION) -> do
+				which <- (#peek SDL_Event, jaxis.which) ptr
+				axis <- (#peek SDL_Event, jaxis.axis) ptr
+				value <- (#peek SDL_Event, jaxis.value) ptr
+				return $! JoyAxisEvent typ timestamp which axis value
+			(#const SDL_JOYBALLMOTION) -> do
+				which <- (#peek SDL_Event, jball.which) ptr
+				ball <- (#peek SDL_Event, jball.ball) ptr
+				xrel <- (#peek SDL_Event, jball.xrel) ptr
+				yrel <- (#peek SDL_Event, jball.yrel) ptr
+				return $! JoyBallEvent typ timestamp which ball xrel yrel
+			(#const SDL_JOYHATMOTION) -> do
+				which <- (#peek SDL_Event, jhat.which) ptr
+				hat <- (#peek SDL_Event, jhat.hat) ptr
+				value <- (#peek SDL_Event, jhat.value) ptr
+				return $! JoyHatEvent typ timestamp which hat value
+			(#const SDL_JOYBUTTONDOWN) -> joybutton $ JoyButtonEvent typ timestamp
+			(#const SDL_JOYBUTTONUP) -> joybutton $ JoyButtonEvent typ timestamp
+			(#const SDL_JOYDEVICEADDED) -> joydevice $ JoyDeviceEvent typ timestamp
+			(#const SDL_JOYDEVICEREMOVED) -> joydevice $ JoyDeviceEvent typ timestamp
+			(#const SDL_CONTROLLERAXISMOTION) -> do
+				which <- (#peek SDL_Event, caxis.which) ptr
+				axis <- (#peek SDL_Event, caxis.axis) ptr
+				value <- (#peek SDL_Event, caxis.value) ptr
+				return $! ControllerButtonEvent typ timestamp which axis value
+			(#const SDL_CONTROLLERBUTTONDOWN) -> controllerbutton $ ControllerButtonEvent typ timestamp
+			(#const SDL_CONTROLLERBUTTONUP) -> controllerbutton $ ControllerButtonEvent typ timestamp
+			(#const SDL_CONTROLLERDEVICEADDED) -> controllerdevice $ ControllerDeviceEvent typ timestamp
+			(#const SDL_CONTROLLERDEVICEREMOVED) -> controllerdevice $ ControllerDeviceEvent typ timestamp
+			(#const SDL_CONTROLLERDEVICEREMAPPED) -> controllerdevice $ ControllerDeviceEvent typ timestamp
+			(#const SDL_FINGERDOWN) -> finger $ TouchFingerEvent typ timestamp
+			(#const SDL_FINGERUP) -> finger $ TouchFingerEvent typ timestamp
+			(#const SDL_FINGERMOTION) -> finger $ TouchFingerEvent typ timestamp
+			(#const SDL_DOLLARGESTURE) -> dollargesture $ DollarGestureEvent typ timestamp
+			(#const SDL_DOLLARRECORD) -> dollargesture $ DollarGestureEvent typ timestamp
+			(#const SDL_MULTIGESTURE) -> do
+				touchId <- (#peek SDL_Event, mgesture.touchId) ptr
+				dTheta <- (#peek SDL_Event, mgesture.dTheta) ptr
+				dDist <- (#peek SDL_Event, mgesture.dDist) ptr
+				x <- (#peek SDL_Event, mgesture.x) ptr
+				y <- (#peek SDL_Event, mgesture.y) ptr
+				numFingers <- (#peek SDL_Event, mgesture.numFingers) ptr
+				return $! MultiGestureEvent typ timestamp touchId dTheta dDist x y numFingers
+			(#const SDL_DROPFILE) -> do
+				file <- (#peek SDL_Event, drop.file) ptr
+				return $! DropEvent typ timestamp file
+			x | x >= (#const SDL_USEREVENT) -> do
+				wid <- (#peek SDL_Event, user.windowID) ptr
+				code <- (#peek SDL_Event, user.code) ptr
+				data1 <- (#peek SDL_Event, user.data1) ptr
+				data2 <- (#peek SDL_Event, user.data2) ptr
+				return $! UserEvent typ timestamp wid code data1 data2
+			_ -> error $ "Unknown type " ++ show typ ++ " for SDL_Event"
+		where
+		key f = do
+			wid <- (#peek SDL_Event, key.windowID) ptr
+			state <- (#peek SDL_Event, key.state) ptr
+			repeat' <- (#peek SDL_Event, key.repeat) ptr
+			keysym <- (#peek SDL_Event, key.keysym) ptr
+			return $! f wid state repeat' keysym
+
+		mouse f = do
+			wid <- (#peek SDL_Event, button.windowID) ptr
+			which <- (#peek SDL_Event, button.which) ptr
+			button <- (#peek SDL_Event, button.button) ptr
+			state <- (#peek SDL_Event, button.state) ptr
+			x <- (#peek SDL_Event, button.x) ptr
+			y <- (#peek SDL_Event, button.y) ptr
+			return $! f wid which button state x y
+
+		joybutton f = do
+			which <- (#peek SDL_Event, jbutton.which) ptr
+			button <- (#peek SDL_Event, jbutton.button) ptr
+			state <- (#peek SDL_Event, jbutton.state) ptr
+			return $! f which button state
+
+		joydevice f = do
+			which <- (#peek SDL_Event, jdevice.which) ptr
+			return $! f which
+
+		controllerbutton f = do
+			which <- (#peek SDL_Event, cbutton.which) ptr
+			button <- (#peek SDL_Event, cbutton.button) ptr
+			state <- (#peek SDL_Event, cbutton.state) ptr
+			return $! f which button state
+
+		controllerdevice f = do
+			which <- (#peek SDL_Event, cdevice.which) ptr
+			return $! f which
+
+		finger f = do
+			touchId <- (#peek SDL_Event, tfinger.touchId) ptr
+			fingerId <- (#peek SDL_Event, tfinger.fingerId) ptr
+			x <- (#peek SDL_Event, tfinger.x) ptr
+			y <- (#peek SDL_Event, tfinger.y) ptr
+			dx <- (#peek SDL_Event, tfinger.dx) ptr
+			dy <- (#peek SDL_Event, tfinger.dy) ptr
+			pressure <- (#peek SDL_Event, tfinger.pressure) ptr
+			return $! f touchId fingerId x y dx dy pressure
+
+		dollargesture f = do
+			touchId <- (#peek SDL_Event, dgesture.touchId) ptr
+			gestureId <- (#peek SDL_Event, dgesture.gestureId) ptr
+			numFingers <- (#peek SDL_Event, dgesture.numFingers) ptr
+			err <- (#peek SDL_Event, dgesture.error) ptr
+			x <- (#peek SDL_Event, dgesture.x) ptr
+			y <- (#peek SDL_Event, dgesture.y) ptr
+			return $! f touchId gestureId numFingers err x y
+	poke ptr ev = case ev of
+		WindowEvent typ timestamp wid event data1 data2 -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, window.windowID) ptr wid
+			(#poke SDL_Event, window.event) ptr event
+			(#poke SDL_Event, window.data1) ptr data1
+			(#poke SDL_Event, window.data2) ptr data2
+		KeyboardEvent typ timestamp wid state repeat' keysym -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, key.windowID) ptr wid
+			(#poke SDL_Event, key.state) ptr state
+			(#poke SDL_Event, key.repeat) ptr repeat'
+			(#poke SDL_Event, key.keysym) ptr keysym
+		TextEditingEvent typ timestamp wid text start len -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, edit.windowID) ptr wid
+			pokeArray ((#ptr SDL_Event, edit.text) ptr) text
+			(#poke SDL_Event, edit.start) ptr start
+			(#poke SDL_Event, edit.length) ptr len
+		TextInputEvent typ timestamp wid text -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, text.windowID) ptr wid
+			pokeArray ((#ptr SDL_Event, text.text) ptr) text
+		MouseMotionEvent typ timestamp wid which state x y xrel yrel -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, motion.windowID) ptr wid
+			(#poke SDL_Event, motion.which) ptr which
+			(#poke SDL_Event, motion.state) ptr state
+			(#poke SDL_Event, motion.x) ptr x
+			(#poke SDL_Event, motion.y) ptr y
+			(#poke SDL_Event, motion.xrel) ptr xrel
+			(#poke SDL_Event, motion.yrel) ptr yrel
+		MouseButtonEvent typ timestamp wid which button state x y -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, button.windowID) ptr wid
+			(#poke SDL_Event, button.which) ptr which
+			(#poke SDL_Event, button.button) ptr button
+			(#poke SDL_Event, button.state) ptr state
+			(#poke SDL_Event, button.x) ptr x
+			(#poke SDL_Event, button.y) ptr y
+		MouseWheelEvent typ timestamp wid which x y -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, wheel.windowID) ptr wid
+			(#poke SDL_Event, wheel.which) ptr which
+			(#poke SDL_Event, wheel.x) ptr x
+			(#poke SDL_Event, wheel.y) ptr y
+		JoyAxisEvent typ timestamp which axis value -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, jaxis.which) ptr which
+			(#poke SDL_Event, jaxis.axis) ptr axis
+			(#poke SDL_Event, jaxis.value) ptr value
+		JoyBallEvent typ timestamp which ball xrel yrel -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, jball.which) ptr which
+			(#poke SDL_Event, jball.ball) ptr ball
+			(#poke SDL_Event, jball.xrel) ptr xrel
+			(#poke SDL_Event, jball.yrel) ptr yrel
+		JoyHatEvent typ timestamp which hat value -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, jhat.which) ptr which
+			(#poke SDL_Event, jhat.hat) ptr hat
+			(#poke SDL_Event, jhat.value) ptr value
+		JoyButtonEvent typ timestamp which button state -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, jbutton.which) ptr which
+			(#poke SDL_Event, jbutton.button) ptr button
+			(#poke SDL_Event, jbutton.state) ptr state
+		JoyDeviceEvent typ timestamp which -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, jdevice.which) ptr which
+		ControllerAxisEvent typ timestamp which axis value -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, caxis.which) ptr which
+			(#poke SDL_Event, caxis.axis) ptr axis
+			(#poke SDL_Event, caxis.value) ptr value
+		ControllerButtonEvent typ timestamp which button state -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, cbutton.which) ptr which
+			(#poke SDL_Event, cbutton.button) ptr button
+			(#poke SDL_Event, cbutton.state) ptr state
+		ControllerDeviceEvent typ timestamp which -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, cdevice.which) ptr which
+		QuitEvent typ timestamp -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+		UserEvent typ timestamp wid code data1 data2 -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, user.windowID) ptr wid
+			(#poke SDL_Event, user.code) ptr code
+			(#poke SDL_Event, user.data1) ptr data1
+			(#poke SDL_Event, user.data2) ptr data2
+		SysWMEvent typ timestamp msg -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, syswm.msg) ptr msg
+		TouchFingerEvent typ timestamp touchid fingerid x y dx dy pressure -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, tfinger.touchId) ptr touchid
+			(#poke SDL_Event, tfinger.fingerId) ptr fingerid
+			(#poke SDL_Event, tfinger.x) ptr x
+			(#poke SDL_Event, tfinger.y) ptr y
+			(#poke SDL_Event, tfinger.dx) ptr dx
+			(#poke SDL_Event, tfinger.dy) ptr dy
+			(#poke SDL_Event, tfinger.pressure) ptr pressure
+		MultiGestureEvent typ timestamp touchid dtheta ddist x y numfingers -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, mgesture.touchId) ptr touchid
+			(#poke SDL_Event, mgesture.dTheta) ptr dtheta
+			(#poke SDL_Event, mgesture.dDist) ptr ddist
+			(#poke SDL_Event, mgesture.x) ptr x
+			(#poke SDL_Event, mgesture.y) ptr y
+			(#poke SDL_Event, mgesture.numFingers) ptr numfingers
+		DollarGestureEvent typ timestamp touchid gestureid numfingers err x y -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, dgesture.touchId) ptr touchid
+			(#poke SDL_Event, dgesture.gestureId) ptr gestureid
+			(#poke SDL_Event, dgesture.numFingers) ptr numfingers
+			(#poke SDL_Event, dgesture.error) ptr err
+			(#poke SDL_Event, dgesture.x) ptr x
+			(#poke SDL_Event, dgesture.y) ptr y
+		DropEvent typ timestamp file -> do
+			(#poke SDL_Event, common.type) ptr typ
+			(#poke SDL_Event, common.timestamp) ptr timestamp
+			(#poke SDL_Event, drop.file) ptr file
+
+data Finger = Finger {
+              fingerID :: FingerID
+            , fingerX :: CFloat
+            , fingerY :: CFloat
+            , fingerPressure :: CFloat
+            } deriving (Eq, Show)
+
+instance Storable Finger where
+	sizeOf _ = (#size SDL_Finger)
+	alignment = sizeOf
+	peek ptr = do
+		fingerId <- (#peek SDL_Finger, id) ptr
+		x <- (#peek SDL_Finger, x) ptr
+		y <- (#peek SDL_Finger, y) ptr
+		pressure <- (#peek SDL_Finger, pressure) ptr
+		return $! Finger fingerId x y pressure
+	poke ptr (Finger fingerId x y pressure) = do
+		(#poke SDL_Finger, id) ptr fingerId
+		(#poke SDL_Finger, x) ptr x
+		(#poke SDL_Finger, y) ptr y
+		(#poke SDL_Finger, pressure) ptr pressure
+
+data GameControllerButtonBind = GameControllerButtonBindNone
+                              | GameControllerButtonBindButton {
+                                gameControllerButtonBindButton :: CInt
+                              }
+                              | GameControllerButtonBindAxis {
+                                gameControllerButtonBindAxis :: CInt
+                              }
+                              | GameControllerButtonBindHat {
+                                gameControllerButtonBindHat :: CInt
+                              , gameControllerButtonBindHatMask :: CInt
+                              } deriving (Eq, Show)
+
+instance Storable GameControllerButtonBind where
+	sizeOf _ = (#size SDL_GameControllerButtonBind)
+	alignment = sizeOf
+	peek ptr = do
+		bind_type <- (#peek SDL_GameControllerButtonBind, bindType) ptr
+		case bind_type :: (#type SDL_GameControllerBindType) of
+			(#const SDL_CONTROLLER_BINDTYPE_NONE) -> do
+				return $! GameControllerButtonBindNone
+			(#const SDL_CONTROLLER_BINDTYPE_BUTTON) -> do
+				button <- (#peek SDL_GameControllerButtonBind, value.button) ptr
+				return $! GameControllerButtonBindButton button
+			(#const SDL_CONTROLLER_BINDTYPE_AXIS) -> do
+				axis <- (#peek SDL_GameControllerButtonBind, value.axis) ptr
+				return $! GameControllerButtonBindAxis axis
+			(#const SDL_CONTROLLER_BINDTYPE_HAT) -> do
+				hat <- (#peek SDL_GameControllerButtonBind, value.hat.hat) ptr
+				hat_mask <- (#peek SDL_GameControllerButtonBind, value.hat.hat_mask) ptr
+				return $! GameControllerButtonBindHat hat hat_mask
+			_ -> error $ "Unknown type " ++ show bind_type ++ " for SDL_GameControllerButtonBind"
+	poke ptr bind = case bind of
+		GameControllerButtonBindNone -> do
+			(#poke SDL_GameControllerButtonBind, bindType) ptr ((#const SDL_CONTROLLER_BINDTYPE_NONE) :: (#type SDL_GameControllerBindType))
+		GameControllerButtonBindButton button -> do
+			(#poke SDL_GameControllerButtonBind, bindType) ptr ((#const SDL_CONTROLLER_BINDTYPE_BUTTON) :: (#type SDL_GameControllerBindType))
+			(#poke SDL_GameControllerButtonBind, value.button) ptr button
+		GameControllerButtonBindAxis axis -> do
+			(#poke SDL_GameControllerButtonBind, bindType) ptr ((#const SDL_CONTROLLER_BINDTYPE_AXIS) :: (#type SDL_GameControllerBindType))
+			(#poke SDL_GameControllerButtonBind, value.axis) ptr axis
+		GameControllerButtonBindHat hat hat_mask -> do
+			(#poke SDL_GameControllerButtonBind, bindType) ptr ((#const SDL_CONTROLLER_BINDTYPE_HAT) :: (#type SDL_GameControllerBindType))
+			(#poke SDL_GameControllerButtonBind, value.hat.hat) ptr hat
+			(#poke SDL_GameControllerButtonBind, value.hat.hat_mask) ptr hat_mask
+
+data HapticDirection = HapticDirection {
+                       hapticDirectionType :: Word8
+                     , hapticDirectionX :: Int32
+                     , hapticDirectionY :: Int32
+                     , hapticDirectionZ :: Int32
+                     } deriving (Eq, Show)
+
+instance Storable HapticDirection where
+	sizeOf _ = (#size SDL_HapticDirection)
+	alignment = sizeOf
+	peek ptr = do
+		typ <- (#peek SDL_HapticDirection, type) ptr
+		x <- (#peek SDL_HapticDirection, dir[0]) ptr
+		y <- (#peek SDL_HapticDirection, dir[1]) ptr
+		z <- (#peek SDL_HapticDirection, dir[2]) ptr
+		return $! HapticDirection typ x y z
+	poke ptr (HapticDirection typ x y z) = do
+		(#poke SDL_HapticDirection, type) ptr typ
+		(#poke SDL_HapticDirection, dir[0]) ptr x
+		(#poke SDL_HapticDirection, dir[1]) ptr y
+		(#poke SDL_HapticDirection, dir[2]) ptr z
+
+data HapticEffect = HapticConstant {
+                    hapticEffectType :: Word16
+                  , hapticConstantDirection :: HapticDirection
+                  , hapticConstantLength :: Word32
+                  , hapticConstantDelay :: Word16
+                  , hapticConstantButton :: Word16
+                  , hapticConstantInterval :: Word16
+                  , hapticConstantLevel :: Int16
+                  , hapticConstantAttackLength :: Word16
+                  , hapticConstantAttackLevel :: Word16
+                  , hapticConstantFadeLength :: Word16
+                  , hapticConstantFadeLevel :: Word16
+                  }
+                  | HapticPeriodic {
+                    hapticEffectType :: Word16
+                  , hapticPeriodicDirection :: HapticDirection
+                  , hapticPeriodicLength :: Word32
+                  , hapticPeriodicDelay :: Word16
+                  , hapticPeriodicButton :: Word16
+                  , hapticPeriodicInterval :: Word16
+                  , hapticPeriodicPeriod :: Word16
+                  , hapticPeriodicMagnitude :: Int16
+                  , hapticPeriodicOffset :: Int16
+                  , hapticPeriodicPhase :: Word16
+                  , hapticPeriodicAttackLength :: Word16
+                  , hapticPeriodicAttackLevel :: Word16
+                  , hapticPeriodicFadeLength :: Word16
+                  , hapticPeriodicFadeLevel :: Word16
+                  }
+                  | HapticCondition {
+                    hapticEffectType :: Word16
+                  , hapticConditionLength :: Word32
+                  , hapticConditionDelay :: Word16
+                  , hapticConditionButton :: Word16
+                  , hapticConditionInterval :: Word16
+                  , hapticConditionRightSat :: [Word16]
+                  , hapticConditionLeftSat :: [Word16]
+                  , hapticConditionRightCoeff :: [Int16]
+                  , hapticConditionLeftCoeff :: [Int16]
+                  , hapticConditionDeadband :: [Word16]
+                  , hapticConditionCenter :: [Int16]
+                  }
+                  | HapticRamp {
+                    hapticEffectType :: Word16
+                  , hapticRampDirection :: HapticDirection
+                  , hapticRampLength :: Word32
+                  , hapticRampDelay :: Word16
+                  , hapticRampButton :: Word16
+                  , hapticRampInterval :: Word16
+                  , hapticRampStart :: Int16
+                  , hapticRampEnd :: Int16
+                  , hapticRampAttackLength :: Word16
+                  , hapticRampAttackLevel :: Word16
+                  , hapticRampFadeLength :: Word16
+                  , hapticRampFadeLevel :: Word16
+                  }
+                  | HapticLeftRight {
+                    hapticEffectType :: Word16
+                  , hapticLeftRightLength :: Word32
+                  , hapticLeftRightLargeMagnitude :: Word16
+                  , hapticLeftRightSmallMagnitude :: Word16
+                  }
+                  | HapticCustom {
+                    hapticEffectType :: Word16
+                  , hapticCustomDirection :: HapticDirection
+                  , hapticCustomLength :: Word32
+                  , hapticCustomDelay :: Word16
+                  , hapticCustomButton :: Word16
+                  , hapticCustomInterval :: Word16
+                  , hapticCustomChannels :: Word8
+                  , hapticCustomPeriod :: Word16
+                  , hapticCustomSamples :: Word16
+                  , hapticCustomData :: Ptr Word16
+                  , hapticCustomAttackLength :: Word16
+                  , hapticCustomAttackLevel :: Word16
+                  , hapticCustomFadeLength :: Word16
+                  , hapticCustomFadeLevel :: Word16
+                  } deriving (Eq, Show)
+
+instance Storable HapticEffect where
+	sizeOf _ = (#size SDL_HapticEffect)
+	alignment = sizeOf
+	peek ptr = do
+		typ <- (#peek SDL_HapticEffect, type) ptr
+		case typ of
+			(#const SDL_HAPTIC_CONSTANT) -> do
+				direction <- (#peek SDL_HapticEffect, constant.direction) ptr
+				len <- (#peek SDL_HapticEffect, constant.length) ptr
+				delay <- (#peek SDL_HapticEffect, constant.delay) ptr
+				button <- (#peek SDL_HapticEffect, constant.button) ptr
+				interval <- (#peek SDL_HapticEffect, constant.interval) ptr
+				level <- (#peek SDL_HapticEffect, constant.level) ptr
+				attack_length <- (#peek SDL_HapticEffect, constant.attack_length) ptr
+				attack_level <- (#peek SDL_HapticEffect, constant.attack_level) ptr
+				fade_length <- (#peek SDL_HapticEffect, constant.fade_length) ptr
+				fade_level <- (#peek SDL_HapticEffect, constant.fade_level) ptr
+				return $! HapticConstant typ direction len delay button interval level attack_length attack_level fade_length fade_level
+
+			(#const SDL_HAPTIC_SINE) -> hapticperiodic $ HapticPeriodic typ
+			(#const SDL_HAPTIC_TRIANGLE) -> hapticperiodic $ HapticPeriodic typ
+			(#const SDL_HAPTIC_SAWTOOTHUP) -> hapticperiodic $ HapticPeriodic typ
+			(#const SDL_HAPTIC_SAWTOOTHDOWN) -> hapticperiodic $ HapticPeriodic typ
+
+			(#const SDL_HAPTIC_RAMP) -> do
+				direction <- (#peek SDL_HapticEffect, ramp.direction) ptr
+				len <- (#peek SDL_HapticEffect, ramp.length) ptr
+				delay <- (#peek SDL_HapticEffect, ramp.delay) ptr
+				button <- (#peek SDL_HapticEffect, ramp.button) ptr
+				interval <- (#peek SDL_HapticEffect, ramp.interval) ptr
+				start <- (#peek SDL_HapticEffect, ramp.start) ptr
+				end <- (#peek SDL_HapticEffect, ramp.end) ptr
+				attack_length <- (#peek SDL_HapticEffect, ramp.attack_length) ptr
+				attack_level <- (#peek SDL_HapticEffect, ramp.attack_level) ptr
+				fade_length <- (#peek SDL_HapticEffect, ramp.fade_length) ptr
+				fade_level <- (#peek SDL_HapticEffect, ramp.fade_level) ptr
+				return $! HapticRamp typ direction len delay button interval start end attack_length attack_level fade_length fade_level
+
+			(#const SDL_HAPTIC_SPRING) -> hapticcondition $ HapticCondition typ
+			(#const SDL_HAPTIC_DAMPER) -> hapticcondition $ HapticCondition typ
+			(#const SDL_HAPTIC_INERTIA) -> hapticcondition $ HapticCondition typ
+			(#const SDL_HAPTIC_FRICTION) -> hapticcondition $ HapticCondition typ
+
+			(#const SDL_HAPTIC_LEFTRIGHT) -> do
+				len <- (#peek SDL_HapticEffect, leftright.length) ptr
+				large_magnitude <- (#peek SDL_HapticEffect, leftright.large_magnitude) ptr
+				small_magnitude <- (#peek SDL_HapticEffect, leftright.small_magnitude) ptr
+				return $! HapticLeftRight typ len large_magnitude small_magnitude
+
+			(#const SDL_HAPTIC_CUSTOM) -> do
+				direction <- (#peek SDL_HapticEffect, custom.direction) ptr
+				len <- (#peek SDL_HapticEffect, custom.length) ptr
+				delay <- (#peek SDL_HapticEffect, custom.delay) ptr
+				button <- (#peek SDL_HapticEffect, custom.button) ptr
+				interval <- (#peek SDL_HapticEffect, custom.interval) ptr
+				channels <- (#peek SDL_HapticEffect, custom.channels) ptr
+				period <- (#peek SDL_HapticEffect, custom.period) ptr
+				samples <- (#peek SDL_HapticEffect, custom.samples) ptr
+				datum <- (#peek SDL_HapticEffect, custom.data) ptr
+				attack_length <- (#peek SDL_HapticEffect, custom.attack_length) ptr
+				attack_level <- (#peek SDL_HapticEffect, custom.attack_level) ptr
+				fade_length <- (#peek SDL_HapticEffect, custom.fade_length) ptr
+				fade_level <- (#peek SDL_HapticEffect, custom.fade_level) ptr
+				return $! HapticCustom typ direction len delay button interval channels period samples datum attack_length attack_level fade_length fade_level
+			_ -> error $ "Unknown type " ++ show typ ++ " for SDL_HapticEffect"
+		where
+		hapticperiodic f = do
+			direction <- (#peek SDL_HapticEffect, periodic.direction) ptr
+			len <- (#peek SDL_HapticEffect, periodic.length) ptr
+			delay <- (#peek SDL_HapticEffect, periodic.delay) ptr
+			button <- (#peek SDL_HapticEffect, periodic.button) ptr
+			interval <- (#peek SDL_HapticEffect, periodic.interval) ptr
+			period <- (#peek SDL_HapticEffect, periodic.period) ptr
+			magnitude <- (#peek SDL_HapticEffect, periodic.magnitude) ptr
+			offset <- (#peek SDL_HapticEffect, periodic.offset) ptr
+			phase <- (#peek SDL_HapticEffect, periodic.phase) ptr
+			attack_length <- (#peek SDL_HapticEffect, periodic.attack_length) ptr
+			attack_level <- (#peek SDL_HapticEffect, periodic.attack_level) ptr
+			fade_length <- (#peek SDL_HapticEffect, periodic.fade_length) ptr
+			fade_level <- (#peek SDL_HapticEffect, periodic.fade_level) ptr
+			return $! f direction len delay button interval period magnitude offset phase attack_length attack_level fade_length fade_level
+
+		hapticcondition f = do
+			len <- (#peek SDL_HapticEffect, condition.length) ptr
+			delay <- (#peek SDL_HapticEffect, condition.delay) ptr
+			button <- (#peek SDL_HapticEffect, condition.button) ptr
+			interval <- (#peek SDL_HapticEffect, condition.interval) ptr
+			right_sat <- peekArray 3 $ (#ptr SDL_HapticEffect, condition.right_sat) ptr
+			left_sat <- peekArray 3 $ (#ptr SDL_HapticEffect, condition.left_sat) ptr
+			right_coeff <- peekArray 3 $ (#ptr SDL_HapticEffect, condition.right_coeff) ptr
+			left_coeff <- peekArray 3 $ (#ptr SDL_HapticEffect, condition.left_coeff) ptr
+			deadband <- peekArray 3 $ (#ptr SDL_HapticEffect, condition.deadband) ptr
+			center <- peekArray 3 $ (#ptr SDL_HapticEffect, condition.center) ptr
+			return $! f len delay button interval right_sat left_sat right_coeff left_coeff deadband center
+	poke ptr event = case event of
+		HapticConstant typ direction len delay button interval level attack_length attack_level fade_length fade_level -> do
+			(#poke SDL_HapticEffect, type) ptr typ
+			(#poke SDL_HapticEffect, constant.direction) ptr direction
+			(#poke SDL_HapticEffect, constant.length) ptr len
+			(#poke SDL_HapticEffect, constant.delay) ptr delay
+			(#poke SDL_HapticEffect, constant.button) ptr button
+			(#poke SDL_HapticEffect, constant.interval) ptr interval
+			(#poke SDL_HapticEffect, constant.level) ptr level
+			(#poke SDL_HapticEffect, constant.attack_length) ptr attack_length
+			(#poke SDL_HapticEffect, constant.attack_level) ptr attack_level
+			(#poke SDL_HapticEffect, constant.fade_length) ptr fade_length
+			(#poke SDL_HapticEffect, constant.fade_level) ptr fade_level
+		HapticPeriodic typ direction len delay button interval period magnitude offset phase attack_length attack_level fade_length fade_level -> do
+			(#poke SDL_HapticEffect, type) ptr typ
+			(#poke SDL_HapticEffect, periodic.direction) ptr direction
+			(#poke SDL_HapticEffect, periodic.length) ptr len
+			(#poke SDL_HapticEffect, periodic.delay) ptr delay
+			(#poke SDL_HapticEffect, periodic.button) ptr button
+			(#poke SDL_HapticEffect, periodic.interval) ptr interval
+			(#poke SDL_HapticEffect, periodic.period) ptr period
+			(#poke SDL_HapticEffect, periodic.magnitude) ptr magnitude
+			(#poke SDL_HapticEffect, periodic.offset) ptr offset
+			(#poke SDL_HapticEffect, periodic.phase) ptr phase
+			(#poke SDL_HapticEffect, periodic.attack_length) ptr attack_length
+			(#poke SDL_HapticEffect, periodic.attack_level) ptr attack_level
+			(#poke SDL_HapticEffect, periodic.fade_length) ptr fade_length
+			(#poke SDL_HapticEffect, periodic.fade_level) ptr fade_level
+		HapticCondition typ len delay button interval right_sat left_sat right_coeff left_coeff deadband center -> do
+			(#poke SDL_HapticEffect, type) ptr typ
+			(#poke SDL_HapticEffect, condition.length) ptr len
+			(#poke SDL_HapticEffect, condition.delay) ptr delay
+			(#poke SDL_HapticEffect, condition.button) ptr button
+			(#poke SDL_HapticEffect, condition.interval) ptr interval
+			pokeArray ((#ptr SDL_HapticEffect, condition.right_sat) ptr) right_sat
+			pokeArray ((#ptr SDL_HapticEffect, condition.left_sat) ptr) left_sat
+			pokeArray ((#ptr SDL_HapticEffect, condition.right_coeff) ptr) right_coeff
+			pokeArray ((#ptr SDL_HapticEffect, condition.left_coeff) ptr) left_coeff
+			pokeArray ((#ptr SDL_HapticEffect, condition.deadband) ptr) deadband
+			pokeArray ((#ptr SDL_HapticEffect, condition.center) ptr) center
+		HapticRamp typ direction len delay button interval start end attack_length attack_level fade_length fade_level -> do
+			(#poke SDL_HapticEffect, type) ptr typ
+			(#poke SDL_HapticEffect, ramp.direction) ptr direction
+			(#poke SDL_HapticEffect, ramp.length) ptr len
+			(#poke SDL_HapticEffect, ramp.delay) ptr delay
+			(#poke SDL_HapticEffect, ramp.button) ptr button
+			(#poke SDL_HapticEffect, ramp.interval) ptr interval
+			(#poke SDL_HapticEffect, ramp.start) ptr start
+			(#poke SDL_HapticEffect, ramp.end) ptr end
+			(#poke SDL_HapticEffect, ramp.attack_length) ptr attack_length
+			(#poke SDL_HapticEffect, ramp.attack_level) ptr attack_level
+			(#poke SDL_HapticEffect, ramp.fade_length) ptr fade_length
+			(#poke SDL_HapticEffect, ramp.fade_level) ptr fade_level
+		HapticLeftRight typ len large_magnitude small_magnitude -> do
+			(#poke SDL_HapticEffect, type) ptr typ
+			(#poke SDL_HapticEffect, leftright.length) ptr len
+			(#poke SDL_HapticEffect, leftright.large_magnitude) ptr large_magnitude
+			(#poke SDL_HapticEffect, leftright.small_magnitude) ptr small_magnitude
+		HapticCustom typ direction len delay button interval channels period samples datum attack_length attack_level fade_length fade_level -> do
+			(#poke SDL_HapticEffect, type) ptr typ
+			(#poke SDL_HapticEffect, custom.direction) ptr direction
+			(#poke SDL_HapticEffect, custom.length) ptr len
+			(#poke SDL_HapticEffect, custom.delay) ptr delay
+			(#poke SDL_HapticEffect, custom.button) ptr button
+			(#poke SDL_HapticEffect, custom.interval) ptr interval
+			(#poke SDL_HapticEffect, custom.channels) ptr channels
+			(#poke SDL_HapticEffect, custom.period) ptr period
+			(#poke SDL_HapticEffect, custom.samples) ptr samples
+			(#poke SDL_HapticEffect, custom.data) ptr datum
+			(#poke SDL_HapticEffect, custom.attack_length) ptr attack_length
+			(#poke SDL_HapticEffect, custom.attack_level) ptr attack_level
+			(#poke SDL_HapticEffect, custom.fade_length) ptr fade_length
+			(#poke SDL_HapticEffect, custom.fade_level) ptr fade_level
+
+data JoystickGUID = JoystickGUID {
+                    joystickGUID :: [Word8]
+                  } deriving (Eq, Show)
+
+instance Storable JoystickGUID where
+	sizeOf _ = (#size SDL_JoystickGUID)
+	alignment = sizeOf
+	peek ptr = do
+		guid <- peekArray 16 $ (#ptr SDL_JoystickGUID, data) ptr
+		return $! JoystickGUID guid
+	poke ptr (JoystickGUID guid) =
+		pokeArray ((#ptr SDL_JoystickGUID, data) ptr) guid
+
+data Keysym = Keysym {
+              keysymScancode :: Scancode
+            , keysymKeycode :: Keycode
+            , keysymMod :: Word16
+            } deriving (Eq, Show)
+
+instance Storable Keysym where
+	sizeOf _ = (#size SDL_Keysym)
+	alignment = sizeOf
+	peek ptr = do
+		scancode <- (#peek SDL_Keysym, scancode) ptr
+		sym <- (#peek SDL_Keysym, sym) ptr
+		mod' <- (#peek SDL_Keysym, mod) ptr
+		return $! Keysym scancode sym mod'
+	poke ptr (Keysym scancode sym mod') = do
+		(#poke SDL_Keysym, scancode) ptr scancode
+		(#poke SDL_Keysym, sym) ptr sym
+		(#poke SDL_Keysym, mod) ptr mod'
+
+data MessageBoxButtonData = MessageBoxButtonData {
+                            messageBoxButtonDataFlags :: Word32
+                          , messageBoxButtonButtonID :: CInt
+                          , messageBoxButtonText :: CString
+                          } deriving (Eq, Show)
+
+instance Storable MessageBoxButtonData where
+	sizeOf _ = (#size SDL_MessageBoxButtonData)
+	alignment = sizeOf
+	peek ptr = do
+		flags <- (#peek SDL_MessageBoxButtonData, flags) ptr
+		buttonid <- (#peek SDL_MessageBoxButtonData, buttonid) ptr
+		text <- (#peek SDL_MessageBoxButtonData, text) ptr
+		return $! MessageBoxButtonData flags buttonid text
+	poke ptr (MessageBoxButtonData flags buttonid text) = do
+		(#poke SDL_MessageBoxButtonData, flags) ptr flags
+		(#poke SDL_MessageBoxButtonData, buttonid) ptr buttonid
+		(#poke SDL_MessageBoxButtonData, text) ptr text
+
+data MessageBoxColor = MessageBoxColor {
+                       messageBoxColorR :: Word8
+                     , messageBoxColorG :: Word8
+                     , messageBoxColorB :: Word8
+                     } deriving (Eq, Show)
+
+instance Storable MessageBoxColor where
+	sizeOf _ = (#size SDL_MessageBoxColor)
+	alignment = sizeOf
+	peek ptr = do
+		r <- (#peek SDL_MessageBoxColor, r) ptr
+		g <- (#peek SDL_MessageBoxColor, g) ptr
+		b <- (#peek SDL_MessageBoxColor, b) ptr
+		return $! MessageBoxColor r g b
+	poke ptr (MessageBoxColor r g b) = do
+		(#poke SDL_MessageBoxColor, r) ptr r
+		(#poke SDL_MessageBoxColor, g) ptr g
+		(#poke SDL_MessageBoxColor, b) ptr b
+
+data MessageBoxColorScheme = MessageBoxColorScheme {
+                             messageBoxColorSchemeColorBackground :: MessageBoxColor
+                           , messageBoxColorSchemeColorText :: MessageBoxColor
+                           , messageBoxColorSchemeColorButtonBorder :: MessageBoxColor
+                           , messageBoxColorSchemeColorButtonBackground :: MessageBoxColor
+                           , messageBoxColorSchemeColorButtonSelected :: MessageBoxColor
+                           } deriving (Eq, Show)
+
+instance Storable MessageBoxColorScheme where
+	sizeOf _ = (#size SDL_MessageBoxColorScheme)
+	alignment = sizeOf
+	peek ptr = do
+		background <- (#peek SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_BACKGROUND]) ptr
+		text <- (#peek SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_TEXT]) ptr
+		button_border <- (#peek SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_BUTTON_BORDER]) ptr
+		button_background <- (#peek SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_BUTTON_BACKGROUND]) ptr
+		button_selected <- (#peek SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_BUTTON_SELECTED]) ptr
+		return $! MessageBoxColorScheme background text button_border button_background button_selected
+	poke ptr (MessageBoxColorScheme background text button_border button_background button_selected) = do
+		(#poke SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_BACKGROUND]) ptr background
+		(#poke SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_TEXT]) ptr text
+		(#poke SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_BUTTON_BORDER]) ptr button_border
+		(#poke SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_BUTTON_BACKGROUND]) ptr button_background
+		(#poke SDL_MessageBoxColorScheme, colors[SDL_MESSAGEBOX_COLOR_BUTTON_SELECTED]) ptr button_selected
+
+data MessageBoxData = MessageBoxData {
+                      messageBoxDataFlags :: Word32
+                    , messageBoxDataWindow :: Window
+                    , messageBoxDataTitle :: CString
+                    , messageBoxDataMessage :: CString
+                    , messageBoxDataNumButtons :: CInt
+                    , messageBoxDataButtons :: Ptr MessageBoxButtonData
+                    , messageBoxDataColorScheme :: Ptr MessageBoxColorScheme
+                    } deriving (Eq, Show)
+
+instance Storable MessageBoxData where
+	sizeOf _ = (#size SDL_MessageBoxData)
+	alignment = sizeOf
+	peek ptr = do
+		flags <- (#peek SDL_MessageBoxData, flags) ptr
+		window <- (#peek SDL_MessageBoxData, window) ptr
+		title <- (#peek SDL_MessageBoxData, title) ptr
+		message <- (#peek SDL_MessageBoxData, message) ptr
+		numbuttons <- (#peek SDL_MessageBoxData, numbuttons) ptr
+		buttons <- (#peek SDL_MessageBoxData, buttons) ptr
+		color_scheme <- (#peek SDL_MessageBoxData, colorScheme) ptr
+		return $! MessageBoxData flags window title message numbuttons buttons color_scheme
+	poke ptr (MessageBoxData flags window title message numbuttons buttons color_scheme) = do
+		(#poke SDL_MessageBoxData, flags) ptr flags
+		(#poke SDL_MessageBoxData, window) ptr window
+		(#poke SDL_MessageBoxData, title) ptr title
+		(#poke SDL_MessageBoxData, message) ptr message
+		(#poke SDL_MessageBoxData, numbuttons) ptr numbuttons
+		(#poke SDL_MessageBoxData, buttons) ptr buttons
+		(#poke SDL_MessageBoxData, colorScheme) ptr color_scheme
+
+data Palette = Palette {
+               paletteNColors :: CInt
+             , paletteColors :: Ptr Color
+             } deriving (Eq, Show)
+
+instance Storable Palette where
+	sizeOf _ = (#size SDL_Palette)
+	alignment = sizeOf
+	peek ptr = do
+		ncolors <- (#peek SDL_Palette, ncolors) ptr
+		colors <- (#peek SDL_Palette, colors) ptr
+		return $! Palette ncolors colors
+	poke ptr (Palette ncolors colors) = do
+		(#poke SDL_Palette, ncolors) ptr ncolors
+		(#poke SDL_Palette, colors) ptr colors
+
+data PixelFormat = PixelFormat {
+                   pixelFormatFormat :: Word32
+                 , pixelFormatPalette :: Ptr Palette
+                 , pixelFormatBitsPerPixel :: Word8
+                 , pixelFormatBytesPerPixel :: Word8
+                 , pixelFormatRMask :: Word32
+                 , pixelFormatGMask :: Word32
+                 , pixelFormatBMask :: Word32
+                 , pixelFormatAMask :: Word32
+                 } deriving (Eq, Show)
+
+instance Storable PixelFormat where
+	sizeOf _ = (#size SDL_PixelFormat)
+	alignment = sizeOf
+	peek ptr = do
+		format <- (#peek SDL_PixelFormat, format) ptr
+		palette <- (#peek SDL_PixelFormat, palette) ptr
+		bits_per_pixel <- (#peek SDL_PixelFormat, BitsPerPixel) ptr
+		bytes_per_pixel <- (#peek SDL_PixelFormat, BytesPerPixel) ptr
+		rmask <- (#peek SDL_PixelFormat, Rmask) ptr
+		gmask <- (#peek SDL_PixelFormat, Gmask) ptr
+		bmask <- (#peek SDL_PixelFormat, Bmask) ptr
+		amask <- (#peek SDL_PixelFormat, Amask) ptr
+		return $! PixelFormat format palette bits_per_pixel bytes_per_pixel rmask gmask bmask amask
+	poke ptr (PixelFormat format palette bits_per_pixel bytes_per_pixel rmask gmask bmask amask) = do
+		(#poke SDL_PixelFormat, format) ptr format
+		(#poke SDL_PixelFormat, palette) ptr palette
+		(#poke SDL_PixelFormat, BitsPerPixel) ptr bits_per_pixel
+		(#poke SDL_PixelFormat, BytesPerPixel) ptr bytes_per_pixel
+		(#poke SDL_PixelFormat, Rmask) ptr rmask
+		(#poke SDL_PixelFormat, Gmask) ptr gmask
+		(#poke SDL_PixelFormat, Bmask) ptr bmask
+		(#poke SDL_PixelFormat, Amask) ptr amask
+
+data Point = Point {
+             pointX :: CInt
+           , pointY :: CInt
+           } deriving (Eq, Show)
+
+instance Storable Point where
+	sizeOf _ = (#size SDL_Point)
+	alignment = sizeOf
+	peek ptr = do
+		x <- (#peek SDL_Point, x) ptr
+		y <- (#peek SDL_Point, y) ptr
+		return $! Point x y
+	poke ptr (Point x y) = do
+		(#poke SDL_Point, x) ptr x
+		(#poke SDL_Point, y) ptr y
+
+data Rect = Rect {
+            rectX :: CInt
+          , rectY :: CInt
+          , rectW :: CInt
+          , rectH :: CInt
+          } deriving (Eq, Show)
+
+instance Storable Rect where
+	sizeOf _ = (#size SDL_Rect)
+	alignment = sizeOf
+	peek ptr = do
+		x <- (#peek SDL_Rect, x) ptr
+		y <- (#peek SDL_Rect, y) ptr
+		w <- (#peek SDL_Rect, w) ptr
+		h <- (#peek SDL_Rect, h) ptr
+		return $! Rect x y w h
+	poke ptr (Rect x y w h) = do
+		(#poke SDL_Rect, x) ptr x
+		(#poke SDL_Rect, y) ptr y
+		(#poke SDL_Rect, w) ptr w
+		(#poke SDL_Rect, h) ptr h
+
+data RendererInfo = RendererInfo {
+                    rendererInfoName :: CString
+                  , rendererInfoFlags :: Word32
+                  , rendererInfoNumTextureFormats :: Word32
+                  , rendererInfoTextureFormats :: [Word32]
+                  , rendererInfoMaxTextureWidth :: CInt
+                  , rendererInfoMaxTextureHeight :: CInt
+                  } deriving (Eq, Show)
+
+instance Storable RendererInfo where
+	sizeOf _ = (#size SDL_RendererInfo)
+	alignment = sizeOf
+	peek ptr = do
+		name <- (#peek SDL_RendererInfo, name) ptr
+		flags <- (#peek SDL_RendererInfo, flags) ptr
+		num_texture_formats <- (#peek SDL_RendererInfo, num_texture_formats) ptr
+		texture_formats <- peekArray 16 $ (#ptr SDL_RendererInfo, texture_formats) ptr
+		max_texture_width <- (#peek SDL_RendererInfo, max_texture_width) ptr
+		max_texture_height <- (#peek SDL_RendererInfo, max_texture_height) ptr
+		return $! RendererInfo name flags num_texture_formats texture_formats max_texture_width max_texture_height
+	poke ptr (RendererInfo name flags num_texture_formats texture_formats max_texture_width max_texture_height) = do
+		(#poke SDL_RendererInfo, name) ptr name
+		(#poke SDL_RendererInfo, flags) ptr flags
+		(#poke SDL_RendererInfo, num_texture_formats) ptr num_texture_formats
+		pokeArray ((#ptr SDL_RendererInfo, texture_formats) ptr) texture_formats
+		(#poke SDL_RendererInfo, max_texture_width) ptr max_texture_width
+		(#poke SDL_RendererInfo, max_texture_height) ptr max_texture_height
+
+data RWops = RWops {
+             rwopsSize :: FunPtr (Ptr RWops -> IO Int64)
+           , rwopsSeek :: FunPtr (Ptr RWops -> Int64 -> CInt -> IO Int64)
+           , rwopsRead :: FunPtr (Ptr RWops -> Ptr () -> CSize -> CSize -> IO CSize)
+           , rwopsWrite :: FunPtr (Ptr RWops -> Ptr () -> CSize -> CSize -> IO CSize)
+           , rwopsClose :: FunPtr (Ptr RWops -> IO CInt)
+           , rwopsType :: Word32
+           } deriving (Eq, Show)
+
+instance Storable RWops where
+	sizeOf _ = (#size SDL_RWops)
+	alignment = sizeOf
+	peek ptr = do
+		size <- (#peek SDL_RWops, size) ptr
+		seek <- (#peek SDL_RWops, seek) ptr
+		read' <- (#peek SDL_RWops, read) ptr
+		write <- (#peek SDL_RWops, write) ptr
+		close <- (#peek SDL_RWops, close) ptr
+		typ <- (#peek SDL_RWops, type) ptr
+		return $! RWops size seek read' write close typ
+	poke ptr (RWops size seek read' write close typ) = do
+		(#poke SDL_RWops, size) ptr size
+		(#poke SDL_RWops, seek) ptr seek
+		(#poke SDL_RWops, read) ptr read'
+		(#poke SDL_RWops, write) ptr write
+		(#poke SDL_RWops, close) ptr close
+		(#poke SDL_RWops, type) ptr typ
+
+data Surface = Surface {
+               surfaceFormat :: Ptr PixelFormat
+             , surfaceW :: CInt
+             , surfaceH :: CInt
+             , surfacePixels :: Ptr ()
+             , surfaceUserdata :: Ptr ()
+             , surfaceClipRect :: Rect
+             , surfaceRefcount :: CInt
+             } deriving (Eq, Show)
+
+instance Storable Surface where
+	sizeOf _ = (#size SDL_Surface)
+	alignment = sizeOf
+	peek ptr = do
+		format <- (#peek SDL_Surface, format) ptr
+		w <- (#peek SDL_Surface, w) ptr
+		h <- (#peek SDL_Surface, h) ptr
+		pixels <- (#peek SDL_Surface, pixels) ptr
+		userdata <- (#peek SDL_Surface, userdata) ptr
+		cliprect <- (#peek SDL_Surface, clip_rect) ptr
+		refcount <- (#peek SDL_Surface, refcount) ptr
+		return $! Surface format w h pixels userdata cliprect refcount
+	poke ptr (Surface format w h pixels userdata cliprect refcount) = do
+		(#poke SDL_Surface, format) ptr format
+		(#poke SDL_Surface, w) ptr w
+		(#poke SDL_Surface, h) ptr h
+		(#poke SDL_Surface, pixels) ptr pixels
+		(#poke SDL_Surface, userdata) ptr userdata
+		(#poke SDL_Surface, clip_rect) ptr cliprect
+		(#poke SDL_Surface, refcount) ptr refcount
diff --git a/Graphics/UI/SDL/Video.hs b/Graphics/UI/SDL/Video.hs
new file mode 100644
--- /dev/null
+++ b/Graphics/UI/SDL/Video.hs
@@ -0,0 +1,397 @@
+module Graphics.UI.SDL.Video (
+	-- * Display and Window Management
+	createWindow,
+	createWindowAndRenderer,
+	createWindowFrom,
+	destroyWindow,
+	disableScreenSaver,
+	enableScreenSaver,
+	glBindTexture,
+	glCreateContext,
+	glDeleteContext,
+	glExtensionSupported,
+	glGetAttribute,
+	glGetCurrentContext,
+	glGetCurrentWindow,
+	glGetDrawableSize,
+	glGetProcAddress,
+	glGetSwapInterval,
+	glLoadLibrary,
+	glMakeCurrent,
+	glSetAttribute,
+	glSetSwapInterval,
+	glSwapWindow,
+	glUnbindTexture,
+	glUnloadLibrary,
+	getClosestDisplayMode,
+	getCurrentDisplayMode,
+	getCurrentVideoDriver,
+	getDesktopDisplayMode,
+	getDisplayBounds,
+	getDisplayMode,
+	getDisplayName,
+	getNumDisplayModes,
+	getNumVideoDisplays,
+	getNumVideoDrivers,
+	getVideoDriver,
+	getWindowBrightness,
+	getWindowData,
+	getWindowDisplayIndex,
+	getWindowDisplayMode,
+	getWindowFlags,
+	getWindowFromID,
+	getWindowGammaRamp,
+	getWindowGrab,
+	getWindowID,
+	getWindowMaximumSize,
+	getWindowMinimumSize,
+	getWindowPixelFormat,
+	getWindowPosition,
+	getWindowSize,
+	getWindowSurface,
+	getWindowTitle,
+	-- getWindowWMInfo,
+	hideWindow,
+	isScreenSaverEnabled,
+	maximizeWindow,
+	minimizeWindow,
+	raiseWindow,
+	restoreWindow,
+	setWindowBordered,
+	setWindowBrightness,
+	setWindowData,
+	setWindowDisplayMode,
+	setWindowFullscreen,
+	setWindowGammaRamp,
+	setWindowGrab,
+	setWindowIcon,
+	setWindowMaximumSize,
+	setWindowMinimumSize,
+	setWindowPosition,
+	setWindowSize,
+	setWindowTitle,
+	showMessageBox,
+	showSimpleMessageBox,
+	showWindow,
+	updateWindowSurface,
+	updateWindowSurfaceRects,
+	videoInit,
+	videoQuit,
+
+	-- * 2D Accelerated Rendering
+	createRenderer,
+	createSoftwareRenderer,
+	createTexture,
+	createTextureFromSurface,
+	destroyRenderer,
+	destroyTexture,
+	getNumRenderDrivers,
+	getRenderDrawBlendMode,
+	getRenderDrawColor,
+	getRenderDriverInfo,
+	getRenderTarget,
+	getRenderer,
+	getRendererInfo,
+	getRendererOutputSize,
+	getTextureAlphaMod,
+	getTextureBlendMode,
+	getTextureColorMod,
+	lockTexture,
+	queryTexture,
+	renderClear,
+	renderCopy,
+	renderCopyEx,
+	renderDrawLine,
+	renderDrawLines,
+	renderDrawPoint,
+	renderDrawPoints,
+	renderDrawRect,
+	renderDrawRects,
+	renderFillRect,
+	renderFillRects,
+	renderGetClipRect,
+	renderGetLogicalSize,
+	renderGetScale,
+	renderGetViewport,
+	renderPresent,
+	renderReadPixels,
+	renderSetClipRect,
+	renderSetLogicalSize,
+	renderSetScale,
+	renderSetViewport,
+	renderTargetSupported,
+	setRenderDrawBlendMode,
+	setRenderDrawColor,
+	setRenderTarget,
+	setTextureAlphaMod,
+	setTextureBlendMode,
+	setTextureColorMod,
+	unlockTexture,
+	updateTexture,
+	updateYUVTexture,
+
+	-- * Pixel Formats and Conversion Routines
+	allocFormat,
+	allocPalette,
+	calculateGammaRamp,
+	freeFormat,
+	freePalette,
+	getPixelFormatName,
+	getRGB,
+	getRGBA,
+	mapRGB,
+	mapRGBA,
+	masksToPixelFormatEnum,
+	pixelFormatEnumToMasks,
+	setPaletteColors,
+	setPixelFormatPalette,
+
+	-- * Rectangle Functions
+	enclosePoints,
+	hasIntersection,
+	intersectRect,
+	intersectRectAndLine,
+	unionRect,
+
+	-- * Surface Creation and Simple Drawing
+	blitScaled,
+	blitSurface,
+	convertPixels,
+	convertSurface,
+	convertSurfaceFormat,
+	createRGBSurface,
+	createRGBSurfaceFrom,
+	fillRect,
+	fillRects,
+	freeSurface,
+	getClipRect,
+	getColorKey,
+	getSurfaceAlphaMod,
+	getSurfaceBlendMode,
+	getSurfaceColorMod,
+	loadBMP,
+	loadBMP_RW,
+	lockSurface,
+	lowerBlit,
+	lowerBlitScaled,
+	saveBMP,
+	saveBMP_RW,
+	setClipRect,
+	setColorKey,
+	setSurfaceAlphaMod,
+	setSurfaceBlendMode,
+	setSurfaceColorMod,
+	setSurfacePalette,
+	setSurfaceRLE,
+	unlockSurface,
+
+	-- * Platform-specific Window Management
+	-- getWindowWMInfo,
+
+	-- * Clipboard Handling
+	getClipboardText,
+	hasClipboardText,
+	setClipboardText
+) where
+
+import Data.Word
+import Foreign.C.String
+import Foreign.C.Types
+import Foreign.Ptr
+import Graphics.UI.SDL.Enum
+import Graphics.UI.SDL.Filesystem
+import Graphics.UI.SDL.Types
+
+foreign import ccall "SDL.h SDL_CreateWindow" createWindow :: CString -> CInt -> CInt -> CInt -> CInt -> Word32 -> IO Window
+foreign import ccall "SDL.h SDL_CreateWindowAndRenderer" createWindowAndRenderer :: CInt -> CInt -> Word32 -> Ptr Window -> Ptr Renderer -> IO CInt
+foreign import ccall "SDL.h SDL_CreateWindowFrom" createWindowFrom :: Ptr () -> IO Window
+foreign import ccall "SDL.h SDL_DestroyWindow" destroyWindow :: Window -> IO ()
+foreign import ccall "SDL.h SDL_DisableScreenSaver" disableScreenSaver :: IO ()
+foreign import ccall "SDL.h SDL_EnableScreenSaver" enableScreenSaver :: IO ()
+foreign import ccall "SDL.h SDL_GL_BindTexture" glBindTexture :: Texture -> Ptr CFloat -> Ptr CFloat -> IO CInt
+foreign import ccall "SDL.h SDL_GL_CreateContext" glCreateContext :: Window -> IO GLContext
+foreign import ccall "SDL.h SDL_GL_DeleteContext" glDeleteContext :: GLContext -> IO ()
+foreign import ccall "SDL.h SDL_GL_ExtensionSupported" glExtensionSupported :: CString -> IO Bool
+foreign import ccall "SDL.h SDL_GL_GetAttribute" glGetAttribute :: GLattr -> Ptr CInt -> IO CInt
+foreign import ccall "SDL.h SDL_GL_GetCurrentContext" glGetCurrentContext :: IO GLContext
+foreign import ccall "SDL.h SDL_GL_GetCurrentWindow" glGetCurrentWindow :: IO Window
+foreign import ccall "SDL.h SDL_GL_GetDrawableSize" glGetDrawableSize :: Window -> Ptr CInt -> Ptr CInt -> IO ()
+foreign import ccall "SDL.h SDL_GL_GetProcAddress" glGetProcAddress :: CString -> IO (Ptr ())
+foreign import ccall "SDL.h SDL_GL_GetSwapInterval" glGetSwapInterval :: IO CInt
+foreign import ccall "SDL.h SDL_GL_LoadLibrary" glLoadLibrary :: CString -> IO CInt
+foreign import ccall "SDL.h SDL_GL_MakeCurrent" glMakeCurrent :: Window -> GLContext -> IO CInt
+foreign import ccall "SDL.h SDL_GL_SetAttribute" glSetAttribute :: GLattr -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_GL_SetSwapInterval" glSetSwapInterval :: CInt -> IO CInt
+foreign import ccall "SDL.h SDL_GL_SwapWindow" glSwapWindow :: Window -> IO ()
+foreign import ccall "SDL.h SDL_GL_UnbindTexture" glUnbindTexture :: Texture -> IO CInt
+foreign import ccall "SDL.h SDL_GL_UnloadLibrary" glUnloadLibrary :: IO ()
+foreign import ccall "SDL.h SDL_GetClosestDisplayMode" getClosestDisplayMode :: CInt -> Ptr DisplayMode -> Ptr DisplayMode -> IO (Ptr DisplayMode)
+foreign import ccall "SDL.h SDL_GetCurrentDisplayMode" getCurrentDisplayMode :: CInt -> Ptr DisplayMode -> IO CInt
+foreign import ccall "SDL.h SDL_GetCurrentVideoDriver" getCurrentVideoDriver :: IO CString
+foreign import ccall "SDL.h SDL_GetDesktopDisplayMode" getDesktopDisplayMode :: CInt -> Ptr DisplayMode -> IO CInt
+foreign import ccall "SDL.h SDL_GetDisplayBounds" getDisplayBounds :: CInt -> Ptr Rect -> IO CInt
+foreign import ccall "SDL.h SDL_GetDisplayMode" getDisplayMode :: CInt -> CInt -> Ptr DisplayMode -> IO CInt
+foreign import ccall "SDL.h SDL_GetDisplayName" getDisplayName :: CInt -> IO CString
+foreign import ccall "SDL.h SDL_GetNumDisplayModes" getNumDisplayModes :: CInt -> IO CInt
+foreign import ccall "SDL.h SDL_GetNumVideoDisplays" getNumVideoDisplays :: IO CInt
+foreign import ccall "SDL.h SDL_GetNumVideoDrivers" getNumVideoDrivers :: IO CInt
+foreign import ccall "SDL.h SDL_GetVideoDriver" getVideoDriver :: CInt -> IO CString
+foreign import ccall "SDL.h SDL_GetWindowBrightness" getWindowBrightness :: Window -> IO CFloat
+foreign import ccall "SDL.h SDL_GetWindowData" getWindowData :: Window -> CString -> IO (Ptr ())
+foreign import ccall "SDL.h SDL_GetWindowDisplayIndex" getWindowDisplayIndex :: Window -> IO CInt
+foreign import ccall "SDL.h SDL_GetWindowDisplayMode" getWindowDisplayMode :: Window -> Ptr DisplayMode -> IO CInt
+foreign import ccall "SDL.h SDL_GetWindowFlags" getWindowFlags :: Window -> IO Word32
+foreign import ccall "SDL.h SDL_GetWindowFromID" getWindowFromID :: Word32 -> IO Window
+foreign import ccall "SDL.h SDL_GetWindowGammaRamp" getWindowGammaRamp :: Window -> Ptr Word16 -> Ptr Word16 -> Ptr Word16 -> IO CInt
+foreign import ccall "SDL.h SDL_GetWindowGrab" getWindowGrab :: Window -> IO Bool
+foreign import ccall "SDL.h SDL_GetWindowID" getWindowID :: Window -> IO Word32
+foreign import ccall "SDL.h SDL_GetWindowMaximumSize" getWindowMaximumSize :: Window -> Ptr CInt -> Ptr CInt -> IO ()
+foreign import ccall "SDL.h SDL_GetWindowMinimumSize" getWindowMinimumSize :: Window -> Ptr CInt -> Ptr CInt -> IO ()
+foreign import ccall "SDL.h SDL_GetWindowPixelFormat" getWindowPixelFormat :: Window -> IO Word32
+foreign import ccall "SDL.h SDL_GetWindowPosition" getWindowPosition :: Window -> Ptr CInt -> Ptr CInt -> IO ()
+foreign import ccall "SDL.h SDL_GetWindowSize" getWindowSize :: Window -> Ptr CInt -> Ptr CInt -> IO ()
+foreign import ccall "SDL.h SDL_GetWindowSurface" getWindowSurface :: Window -> IO (Ptr Surface)
+foreign import ccall "SDL.h SDL_GetWindowTitle" getWindowTitle :: Window -> IO CString
+foreign import ccall "SDL.h SDL_HideWindow" hideWindow :: Window -> IO ()
+foreign import ccall "SDL.h SDL_IsScreenSaverEnabled" isScreenSaverEnabled :: IO Bool
+foreign import ccall "SDL.h SDL_MaximizeWindow" maximizeWindow :: Window -> IO ()
+foreign import ccall "SDL.h SDL_MinimizeWindow" minimizeWindow :: Window -> IO ()
+foreign import ccall "SDL.h SDL_RaiseWindow" raiseWindow :: Window -> IO ()
+foreign import ccall "SDL.h SDL_RestoreWindow" restoreWindow :: Window -> IO ()
+foreign import ccall "SDL.h SDL_SetWindowBordered" setWindowBordered :: Window -> Bool -> IO ()
+foreign import ccall "SDL.h SDL_SetWindowBrightness" setWindowBrightness :: Window -> CFloat -> IO CInt
+foreign import ccall "SDL.h SDL_SetWindowData" setWindowData :: Window -> CString -> Ptr () -> IO (Ptr ())
+foreign import ccall "SDL.h SDL_SetWindowDisplayMode" setWindowDisplayMode :: Window -> Ptr DisplayMode -> IO CInt
+foreign import ccall "SDL.h SDL_SetWindowFullscreen" setWindowFullscreen :: Window -> Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_SetWindowGammaRamp" setWindowGammaRamp :: Window -> Ptr Word16 -> Ptr Word16 -> Ptr Word16 -> IO CInt
+foreign import ccall "SDL.h SDL_SetWindowGrab" setWindowGrab :: Window -> Bool -> IO ()
+foreign import ccall "SDL.h SDL_SetWindowIcon" setWindowIcon :: Window -> Ptr Surface -> IO ()
+foreign import ccall "SDL.h SDL_SetWindowMaximumSize" setWindowMaximumSize :: Window -> CInt -> CInt -> IO ()
+foreign import ccall "SDL.h SDL_SetWindowMinimumSize" setWindowMinimumSize :: Window -> CInt -> CInt -> IO ()
+foreign import ccall "SDL.h SDL_SetWindowPosition" setWindowPosition :: Window -> CInt -> CInt -> IO ()
+foreign import ccall "SDL.h SDL_SetWindowSize" setWindowSize :: Window -> CInt -> CInt -> IO ()
+foreign import ccall "SDL.h SDL_SetWindowTitle" setWindowTitle :: Window -> CString -> IO ()
+foreign import ccall "SDL.h SDL_ShowMessageBox" showMessageBox :: Ptr MessageBoxData -> Ptr CInt -> IO CInt
+foreign import ccall "SDL.h SDL_ShowSimpleMessageBox" showSimpleMessageBox :: Word32 -> CString -> CString -> Window -> IO CInt
+foreign import ccall "SDL.h SDL_ShowWindow" showWindow :: Window -> IO ()
+foreign import ccall "SDL.h SDL_UpdateWindowSurface" updateWindowSurface :: Window -> IO CInt
+foreign import ccall "SDL.h SDL_UpdateWindowSurfaceRects" updateWindowSurfaceRects :: Window -> Ptr Rect -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_VideoInit" videoInit :: CString -> IO CInt
+foreign import ccall "SDL.h SDL_VideoQuit" videoQuit :: IO ()
+
+foreign import ccall "SDL.h SDL_CreateRenderer" createRenderer :: Window -> CInt -> Word32 -> IO Renderer
+foreign import ccall "SDL.h SDL_CreateSoftwareRenderer" createSoftwareRenderer :: Ptr Surface -> IO Renderer
+foreign import ccall "SDL.h SDL_CreateTexture" createTexture :: Renderer -> Word32 -> CInt -> CInt -> CInt -> IO Texture 
+foreign import ccall "SDL.h SDL_CreateTextureFromSurface" createTextureFromSurface :: Renderer -> Ptr Surface -> IO Texture
+foreign import ccall "SDL.h SDL_DestroyRenderer" destroyRenderer :: Renderer -> IO ()
+foreign import ccall "SDL.h SDL_DestroyTexture" destroyTexture :: Texture -> IO ()
+foreign import ccall "SDL.h SDL_GetNumRenderDrivers" getNumRenderDrivers :: IO CInt
+foreign import ccall "SDL.h SDL_GetRenderDrawBlendMode" getRenderDrawBlendMode :: Renderer -> IO Int
+foreign import ccall "SDL.h SDL_GetRenderDrawColor" getRenderDrawColor :: Renderer -> Ptr Word8 -> Ptr Word8 -> Ptr Word8 -> Ptr Word8 -> IO CInt
+foreign import ccall "SDL.h SDL_GetRenderDriverInfo" getRenderDriverInfo :: CInt -> Ptr RendererInfo -> IO CInt
+foreign import ccall "SDL.h SDL_GetRenderTarget" getRenderTarget :: Renderer -> IO Texture
+foreign import ccall "SDL.h SDL_GetRenderer" getRenderer :: Window -> IO Renderer
+foreign import ccall "SDL.h SDL_GetRendererInfo" getRendererInfo :: Renderer -> Ptr RendererInfo -> IO CInt
+foreign import ccall "SDL.h SDL_GetRendererOutputSize" getRendererOutputSize :: Renderer -> Ptr CInt -> Ptr CInt -> IO CInt
+foreign import ccall "SDL.h SDL_GetTextureAlphaMod" getTextureAlphaMod :: Texture -> Ptr Word8 -> IO CInt
+foreign import ccall "SDL.h SDL_GetTextureBlendMode" getTextureBlendMode :: Texture -> Ptr BlendMode -> IO CInt
+foreign import ccall "SDL.h SDL_GetTextureColorMod" getTextureColorMod :: Texture -> Ptr Word8 -> Ptr Word8 -> Ptr Word8 -> IO CInt
+foreign import ccall "SDL.h SDL_LockTexture" lockTexture :: Texture -> Ptr Rect -> Ptr (Ptr ()) -> Ptr CInt -> IO CInt
+foreign import ccall "SDL.h SDL_QueryTexture" queryTexture :: Texture -> Word32 -> Ptr CInt -> Ptr CInt -> Ptr CInt -> IO CInt
+foreign import ccall "SDL.h SDL_RenderClear" renderClear :: Renderer -> IO CInt
+foreign import ccall "SDL.h SDL_RenderCopy" renderCopy :: Renderer -> Texture -> Ptr Rect -> Ptr Rect -> IO CInt
+foreign import ccall "SDL.h SDL_RenderCopyEx" renderCopyEx :: Renderer -> Texture -> Ptr Rect -> Ptr Rect -> CDouble -> Ptr Point -> RendererFlip -> IO CInt
+foreign import ccall "SDL.h SDL_RenderDrawLine" renderDrawLine :: Renderer -> CInt -> CInt -> CInt -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_RenderDrawLines" renderDrawLines :: Renderer -> Ptr Point -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_RenderDrawPoint" renderDrawPoint :: Renderer -> CInt -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_RenderDrawPoints" renderDrawPoints :: Renderer -> Ptr Point -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_RenderDrawRect" renderDrawRect :: Renderer -> Ptr Rect -> IO CInt
+foreign import ccall "SDL.h SDL_RenderDrawRects" renderDrawRects :: Renderer -> Ptr Rect -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_RenderFillRect" renderFillRect :: Renderer -> Ptr Rect -> IO CInt
+foreign import ccall "SDL.h SDL_RenderFillRects" renderFillRects :: Renderer -> Ptr Rect -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_RenderGetClipRect" renderGetClipRect :: Renderer -> Ptr Rect -> IO ()
+foreign import ccall "SDL.h SDL_RenderGetLogicalSize" renderGetLogicalSize :: Renderer -> Ptr CInt -> Ptr CInt -> IO ()
+foreign import ccall "SDL.h SDL_RenderGetScale" renderGetScale :: Renderer -> Ptr CFloat -> Ptr CFloat -> IO ()
+foreign import ccall "SDL.h SDL_RenderGetViewport" renderGetViewport :: Renderer -> Ptr Rect -> IO ()
+foreign import ccall "SDL.h SDL_RenderPresent" renderPresent :: Renderer -> IO ()
+foreign import ccall "SDL.h SDL_RenderReadPixels" renderReadPixels :: Renderer -> Ptr Rect -> Word32 -> Ptr () -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_RenderSetClipRect" renderSetClipRect :: Renderer -> Ptr Rect -> IO CInt
+foreign import ccall "SDL.h SDL_RenderSetLogicalSize" renderSetLogicalSize :: Renderer -> CInt -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_RenderSetScale" renderSetScale :: Renderer -> CFloat -> CFloat -> IO CInt
+foreign import ccall "SDL.h SDL_RenderSetViewport" renderSetViewport :: Renderer -> Ptr Rect -> IO CInt
+foreign import ccall "SDL.h SDL_RenderTargetSupported" renderTargetSupported :: Renderer -> IO Bool
+foreign import ccall "SDL.h SDL_SetRenderDrawBlendMode" setRenderDrawBlendMode :: Renderer -> BlendMode -> IO CInt
+foreign import ccall "SDL.h SDL_SetRenderDrawColor" setRenderDrawColor :: Renderer -> Word8 -> Word8 -> Word8 -> Word8 -> IO CInt
+foreign import ccall "SDL.h SDL_SetRenderTarget" setRenderTarget :: Renderer -> Texture -> IO CInt
+foreign import ccall "SDL.h SDL_SetTextureAlphaMod" setTextureAlphaMod :: Texture -> Word8 -> IO CInt
+foreign import ccall "SDL.h SDL_SetTextureBlendMode" setTextureBlendMode :: Texture -> BlendMode -> IO CInt
+foreign import ccall "SDL.h SDL_SetTextureColorMod" setTextureColorMod :: Texture -> Word8 -> Word8 -> Word8 -> IO CInt
+foreign import ccall "SDL.h SDL_UnlockTexture" unlockTexture :: Texture -> IO ()
+foreign import ccall "SDL.h SDL_UpdateTexture" updateTexture :: Texture -> Ptr Rect -> Ptr () -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_UpdateYUVTexture" updateYUVTexture :: Texture -> Ptr Rect -> Ptr Word8 -> CInt -> Ptr Word8 -> CInt -> Ptr Word8 -> CInt -> IO CInt
+
+foreign import ccall "SDL.h SDL_AllocFormat" allocFormat :: Word32 -> IO (Ptr PixelFormat)
+foreign import ccall "SDL.h SDL_AllocPalette" allocPalette :: CInt -> IO (Ptr Palette)
+foreign import ccall "SDL.h SDL_CalculateGammaRamp" calculateGammaRamp :: CFloat -> Ptr Word16 -> IO ()
+foreign import ccall "SDL.h SDL_FreeFormat" freeFormat :: Ptr PixelFormat -> IO ()
+foreign import ccall "SDL.h SDL_FreePalette" freePalette :: Ptr Palette -> IO ()
+foreign import ccall "SDL.h SDL_GetPixelFormatName" getPixelFormatName :: Word32 -> IO CString
+foreign import ccall "SDL.h SDL_GetRGB" getRGB :: Word32 -> Ptr PixelFormat -> Ptr Word8 -> Ptr Word8 -> Ptr Word8 -> IO ()
+foreign import ccall "SDL.h SDL_GetRGBA" getRGBA :: Word32 -> Ptr PixelFormat -> Ptr Word8 -> Ptr Word8 -> Ptr Word8 -> Ptr Word8 -> IO ()
+foreign import ccall "SDL.h SDL_MapRGB" mapRGB :: Ptr PixelFormat -> Word8 -> Word8 -> Word8 -> IO Word32
+foreign import ccall "SDL.h SDL_MapRGBA" mapRGBA :: Ptr PixelFormat -> Word8 -> Word8 -> Word8 -> Word8 -> IO Word32
+foreign import ccall "SDL.h SDL_MasksToPixelFormatEnum" masksToPixelFormatEnum :: CInt -> Word32 -> Word32 -> Word32 -> Word32 -> IO Word32
+foreign import ccall "SDL.h SDL_PixelFormatEnumToMasks" pixelFormatEnumToMasks :: Word32 -> Ptr CInt -> Ptr Word32 -> Ptr Word32 -> Ptr Word32 -> Ptr Word32 -> IO Bool
+foreign import ccall "SDL.h SDL_SetPaletteColors" setPaletteColors :: Ptr Palette -> Ptr Color -> CInt -> CInt -> IO CInt 
+foreign import ccall "SDL.h SDL_SetPixelFormatPalette" setPixelFormatPalette :: Ptr PixelFormat -> Ptr Palette -> IO CInt
+
+foreign import ccall "SDL.h SDL_EnclosePoints" enclosePoints :: Ptr Point -> CInt -> Ptr Rect -> Ptr Rect -> IO Bool
+foreign import ccall "SDL.h SDL_HasIntersection" hasIntersection :: Ptr Rect -> Ptr Rect -> IO Bool
+foreign import ccall "SDL.h SDL_IntersectRect" intersectRect :: Ptr Rect -> Ptr Rect -> Ptr Rect -> IO Bool
+foreign import ccall "SDL.h SDL_IntersectRectAndLine" intersectRectAndLine :: Ptr Rect -> Ptr CInt -> Ptr CInt -> Ptr CInt -> Ptr CInt -> IO Bool
+foreign import ccall "SDL.h SDL_UnionRect" unionRect :: Ptr Rect -> Ptr Rect -> Ptr Rect -> IO ()
+
+foreign import ccall "SDL.h SDL_UpperBlitScaled" blitScaled :: Ptr Surface -> Ptr Rect -> Ptr Surface -> Ptr Rect -> IO CInt
+foreign import ccall "SDL.h SDL_UpperBlit" blitSurface :: Ptr Surface -> Ptr Rect -> Ptr Surface -> Ptr Rect -> IO CInt
+foreign import ccall "SDL.h SDL_ConvertPixels" convertPixels :: CInt -> CInt -> Word32 -> Ptr () -> CInt -> Word32 -> Ptr () -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_ConvertSurface" convertSurface :: Ptr Surface -> Ptr PixelFormat -> Word32 -> IO (Ptr Surface)
+foreign import ccall "SDL.h SDL_ConvertSurfaceFormat" convertSurfaceFormat :: Ptr Surface -> Word32 -> Word32 -> IO (Ptr Surface)
+foreign import ccall "SDL.h SDL_CreateRGBSurface" createRGBSurface :: Word32 -> CInt -> CInt -> CInt -> Word32 -> Word32 -> Word32 -> Word32 -> IO (Ptr Surface)
+foreign import ccall "SDL.h SDL_CreateRGBSurfaceFrom" createRGBSurfaceFrom :: Ptr () -> CInt -> CInt -> CInt -> CInt -> Word32 -> Word32 -> Word32 -> Word32 -> IO (Ptr Surface)
+foreign import ccall "SDL.h SDL_FillRect" fillRect :: Ptr Surface -> Ptr Rect -> Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_FillRects" fillRects :: Ptr Surface -> Ptr Rect -> CInt -> Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_FreeSurface" freeSurface :: Ptr Surface -> IO ()
+foreign import ccall "SDL.h SDL_GetClipRect" getClipRect :: Ptr Surface -> Ptr Rect -> IO ()
+foreign import ccall "SDL.h SDL_GetColorKey" getColorKey :: Ptr Surface -> Ptr Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_GetSurfaceAlphaMod" getSurfaceAlphaMod :: Ptr Surface -> Ptr Word8 -> IO CInt
+foreign import ccall "SDL.h SDL_GetSurfaceBlendMode" getSurfaceBlendMode :: Ptr Surface -> BlendMode -> IO CInt
+foreign import ccall "SDL.h SDL_GetSurfaceColorMod" getSurfaceColorMod :: Ptr Surface -> Ptr Word8 -> Ptr Word8 -> Ptr Word8 -> IO CInt
+-- foreign import ccall "SDL.h SDL_LoadBMP" loadBMP :: CString -> IO (Ptr Surface)
+foreign import ccall "SDL.h SDL_LoadBMP_RW" loadBMP_RW :: Ptr RWops -> CInt -> IO (Ptr Surface)
+foreign import ccall "SDL.h SDL_LockSurface" lockSurface :: Ptr Surface -> IO CInt
+foreign import ccall "SDL.h SDL_LowerBlit" lowerBlit :: Ptr Surface -> Ptr Rect -> Ptr Surface -> Ptr Rect -> IO CInt
+foreign import ccall "SDL.h SDL_LowerBlitScaled" lowerBlitScaled :: Ptr Surface -> Ptr Rect -> Ptr Surface -> Ptr Rect -> IO CInt
+-- foreign import ccall "SDL.h SDL_SaveBMP" saveBMP :: Ptr Surface -> CString -> IO CInt
+foreign import ccall "SDL.h SDL_SaveBMP_RW" saveBMP_RW :: Ptr Surface -> Ptr RWops -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_SetClipRect" setClipRect :: Ptr Surface -> Ptr Rect -> IO Bool
+foreign import ccall "SDL.h SDL_SetColorKey" setColorKey :: Ptr Surface -> CInt -> Word32 -> IO CInt
+foreign import ccall "SDL.h SDL_SetSurfaceAlphaMod" setSurfaceAlphaMod :: Ptr Surface -> Word8 -> IO CInt
+foreign import ccall "SDL.h SDL_SetSurfaceBlendMode" setSurfaceBlendMode :: Ptr Surface -> BlendMode -> IO CInt
+foreign import ccall "SDL.h SDL_SetSurfaceColorMod" setSurfaceColorMod :: Ptr Surface -> Word8 -> Word8 -> Word8 -> IO CInt
+foreign import ccall "SDL.h SDL_SetSurfacePalette" setSurfacePalette :: Ptr Surface -> Ptr Palette -> IO CInt
+foreign import ccall "SDL.h SDL_SetSurfaceRLE" setSurfaceRLE :: Ptr Surface -> CInt -> IO CInt
+foreign import ccall "SDL.h SDL_UnlockSurface" unlockSurface :: Ptr Surface -> IO ()
+
+foreign import ccall "SDL.h SDL_GetClipboardText" getClipboardText :: IO CString
+foreign import ccall "SDL.h SDL_HasClipboardText" hasClipboardText :: IO Bool
+foreign import ccall "SDL.h SDL_SetClipboardText" setClipboardText :: CString -> IO CInt
+
+loadBMP :: CString -> IO (Ptr Surface)
+loadBMP file = do
+	rw <- withCString "rb" $ rwFromFile file
+	loadBMP_RW rw 1
+
+saveBMP :: Ptr Surface -> CString -> IO CInt
+saveBMP surface file = do
+	rw <- withCString "wb" $ rwFromFile file
+	saveBMP_RW surface rw 1
diff --git a/LICENSE b/LICENSE
new file mode 100644
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,30 @@
+Copyright (c) 2013, Gabríel Arthúr Pétursson
+
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+
+    * Neither the name of Gabríel Arthúr Pétursson nor the names of other
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/Setup.hs b/Setup.hs
new file mode 100644
--- /dev/null
+++ b/Setup.hs
@@ -0,0 +1,2 @@
+import Distribution.Simple
+main = defaultMain
diff --git a/cbits/sdlhelper.c b/cbits/sdlhelper.c
new file mode 100644
--- /dev/null
+++ b/cbits/sdlhelper.c
@@ -0,0 +1,67 @@
+#include <string.h>
+#include "sdlhelper.h"
+
+void SDLHelper_JoystickGetDeviceGUID(int device_index, SDL_JoystickGUID *guid)
+{
+	SDL_JoystickGUID t = SDL_JoystickGetDeviceGUID(device_index);
+	memcpy(guid, &t, sizeof(*guid));
+}
+
+void SDLHelper_JoystickGetGUID(SDL_Joystick *joystick, SDL_JoystickGUID *guid)
+{
+	SDL_JoystickGUID t = SDL_JoystickGetGUID(joystick);
+	memcpy(guid, &t, sizeof(*guid));
+}
+
+void SDLHelper_JoystickGetGUIDFromString(const char *pchGUID, SDL_JoystickGUID *guid)
+{
+	SDL_JoystickGUID t = SDL_JoystickGetGUIDFromString(pchGUID);
+	memcpy(guid, &t, sizeof(*guid));
+}
+
+void SDLHelper_JoystickGetGUIDString(const SDL_JoystickGUID *guid, char *gszGUID, int cbGUID)
+{
+	SDL_JoystickGetGUIDString(*guid, gszGUID, cbGUID);
+}
+
+void SDLHelper_GameControllerGetBindForAxis(SDL_GameController *gamecontroller, SDL_GameControllerAxis axis, SDL_GameControllerButtonBind *bind)
+{
+	SDL_GameControllerButtonBind t = SDL_GameControllerGetBindForAxis(gamecontroller, axis);
+	memcpy(bind, &t, sizeof(*bind));
+}
+
+void SDLHelper_GameControllerGetBindForButton(SDL_GameController *gamecontroller, SDL_GameControllerButton button, SDL_GameControllerButtonBind *bind)
+{
+	SDL_GameControllerButtonBind t = SDL_GameControllerGetBindForButton(gamecontroller, button);
+	memcpy(bind, &t, sizeof(*bind));
+}
+
+char *SDLHelper_GameControllerMappingForGUID(const SDL_JoystickGUID *guid)
+{
+	return SDL_GameControllerMappingForGUID(*guid);
+}
+
+int SDLHelper_RWclose(SDL_RWops *ctx)
+{
+	return SDL_RWclose(ctx);
+}
+
+size_t SDLHelper_RWread(SDL_RWops *ctx, void *ptr, size_t size, size_t maxnum)
+{
+	return SDL_RWread(ctx, ptr, size, maxnum);
+}
+
+Sint64 SDLHelper_RWseek(SDL_RWops *ctx, Sint64 offset, int whence)
+{
+	return SDL_RWseek(ctx, offset, whence);
+}
+
+Sint64 SDLHelper_RWtell(SDL_RWops *ctx)
+{
+	return SDL_RWtell(ctx);
+}
+
+size_t SDLHelper_RWwrite(SDL_RWops *ctx, const void *ptr, size_t size, size_t num)
+{
+	return SDL_RWwrite(ctx, ptr, size, num);
+}
diff --git a/include/sdlhelper.h b/include/sdlhelper.h
new file mode 100644
--- /dev/null
+++ b/include/sdlhelper.h
@@ -0,0 +1,22 @@
+#ifndef _HS_SDL2_HELPER_H_
+#define _HS_SDL2_HELPER_H_
+
+#include <stddef.h>
+#include "SDL.h"
+
+void SDLHelper_JoystickGetDeviceGUID(int device_index, SDL_JoystickGUID *guid);
+void SDLHelper_JoystickGetGUID(SDL_Joystick *joystick, SDL_JoystickGUID *guid);
+void SDLHelper_JoystickGetGUIDFromString(const char *pchGUID, SDL_JoystickGUID *guid);
+void SDLHelper_JoystickGetGUIDString(const SDL_JoystickGUID *guid, char *gszGUID, int cbGUID);
+
+void SDLHelper_GameControllerGetBindForAxis(SDL_GameController *gamecontroller, SDL_GameControllerAxis axis, SDL_GameControllerButtonBind *bind);
+void SDLHelper_GameControllerGetBindForButton(SDL_GameController *gamecontroller, SDL_GameControllerButton button, SDL_GameControllerButtonBind *bind);
+char *SDLHelper_GameControllerMappingForGUID(const SDL_JoystickGUID *guid);
+
+int SDLHelper_RWclose(SDL_RWops *ctx);
+size_t SDLHelper_RWread(SDL_RWops *ctx, void *ptr, size_t size, size_t maxnum);
+Sint64 SDLHelper_RWseek(SDL_RWops *ctx, Sint64 offset, int whence);
+Sint64 SDLHelper_RWtell(SDL_RWops *ctx);
+size_t SDLHelper_RWwrite(SDL_RWops *ctx, const void *ptr, size_t size, size_t num);
+
+#endif
diff --git a/sdl2.cabal b/sdl2.cabal
new file mode 100644
--- /dev/null
+++ b/sdl2.cabal
@@ -0,0 +1,54 @@
+name:                sdl2
+version:             1.0.0
+synopsis:            Bindings to SDL2
+description:         Bindings to the SDL2 library, version 2.0.1.
+license:             BSD3
+license-file:        LICENSE
+author:              Gabríel Arthúr Pétursson
+maintainer:          gabriel@system.is
+copyright:           Copyright © 2013, 2014  Gabríel Arthúr Pétursson
+category:            Graphics
+build-type:          Simple
+cabal-version:       >= 1.10
+
+extra-source-files:
+  cbits/sdlhelper.c,
+  include/sdlhelper.h
+
+library
+  ghc-options: -Wall
+
+  exposed-modules:
+    Graphics.UI.SDL
+    Graphics.UI.SDL.Audio
+    Graphics.UI.SDL.Basic
+    Graphics.UI.SDL.Enum
+    Graphics.UI.SDL.Event
+    Graphics.UI.SDL.Filesystem
+    Graphics.UI.SDL.Haptic
+    Graphics.UI.SDL.Power
+    Graphics.UI.SDL.Timer
+    Graphics.UI.SDL.Types
+    Graphics.UI.SDL.Video
+
+  c-sources:
+    cbits/sdlhelper.c
+
+  include-dirs:
+    include
+
+  includes:
+    SDL.h
+    sdlhelper.h
+
+  extra-libraries:
+    SDL2
+
+  pkgconfig-depends:
+    sdl2 >= 2.0.1
+
+  build-depends:
+    base == 4.*
+
+  default-language:
+    Haskell2010
