{- |
Copyright  : Will Thompson, Iñaki García Etxebarria and Jonas Platte
License    : LGPL-2.1
Maintainer : Iñaki García Etxebarria (garetxe@gmail.com)

These functions allow querying informations about registered typefind
functions. How to create and register these functions is described in
the section \<link linkend=\"gstreamer-Writing-typefind-functions\">
\"Writing typefind functions\"\<\/link>.

The following example shows how to write a very simple typefinder that
identifies the given data. You can get quite a bit more complicated than
that though.

=== /C code/
>
>  typedef struct {
>    guint8 *data;
>    guint size;
>    guint probability;
>    GstCaps *data;
>  } MyTypeFind;
>  static void
>  my_peek (gpointer data, gint64 offset, guint size)
>  {
>    MyTypeFind *find = (MyTypeFind *) data;
>    if (offset &gt;= 0 &amp;&amp; offset + size &lt;= find->size) {
>      return find->data + offset;
>    }
>    return NULL;
>  }
>  static void
>  my_suggest (gpointer data, guint probability, GstCaps *caps)
>  {
>    MyTypeFind *find = (MyTypeFind *) data;
>    if (probability &gt; find->probability) {
>      find->probability = probability;
>      gst_caps_replace (&amp;find->caps, caps);
>    }
>  }
>  static GstCaps *
>  find_type (guint8 *data, guint size)
>  {
>    GList *walk, *type_list;
>    MyTypeFind find = {data, size, 0, NULL};
>    GstTypeFind gst_find = {my_peek, my_suggest, &amp;find, };
>    walk = type_list = gst_type_find_factory_get_list ();
>    while (walk) {
>      GstTypeFindFactory *factory = GST_TYPE_FIND_FACTORY (walk->data);
>      walk = g_list_next (walk)
>      gst_type_find_factory_call_function (factory, &amp;gst_find);
>    }
>    g_list_free (type_list);
>    return find.caps;
>  };

-}

module GI.Gst.Objects.TypeFindFactory
    ( 

-- * Exported types
    TypeFindFactory(..)                     ,
    IsTypeFindFactory                       ,
    toTypeFindFactory                       ,
    noTypeFindFactory                       ,


 -- * Methods
-- ** callFunction #method:callFunction#
#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
    TypeFindFactoryCallFunctionMethodInfo   ,
#endif
    typeFindFactoryCallFunction             ,


-- ** getCaps #method:getCaps#
#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
    TypeFindFactoryGetCapsMethodInfo        ,
#endif
    typeFindFactoryGetCaps                  ,


-- ** getExtensions #method:getExtensions#
#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
    TypeFindFactoryGetExtensionsMethodInfo  ,
#endif
    typeFindFactoryGetExtensions            ,


-- ** getList #method:getList#
    typeFindFactoryGetList                  ,


-- ** hasFunction #method:hasFunction#
#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
    TypeFindFactoryHasFunctionMethodInfo    ,
#endif
    typeFindFactoryHasFunction              ,




    ) where

import Data.GI.Base.ShortPrelude
import qualified Data.GI.Base.ShortPrelude as SP
import qualified Data.GI.Base.Overloading as O
import qualified Prelude as P

import qualified Data.GI.Base.Attributes as GI.Attributes
import qualified Data.GI.Base.ManagedPtr as B.ManagedPtr
import qualified Data.GI.Base.GError as B.GError
import qualified Data.GI.Base.GVariant as B.GVariant
import qualified Data.GI.Base.GParamSpec as B.GParamSpec
import qualified Data.GI.Base.CallStack as B.CallStack
import qualified Data.Text as T
import qualified Data.ByteString.Char8 as B
import qualified Data.Map as Map
import qualified Foreign.Ptr as FP

import qualified GI.GObject.Objects.Object as GObject.Object
import {-# SOURCE #-} qualified GI.Gst.Objects.Object as Gst.Object
import {-# SOURCE #-} qualified GI.Gst.Objects.PluginFeature as Gst.PluginFeature
import {-# SOURCE #-} qualified GI.Gst.Structs.Caps as Gst.Caps
import {-# SOURCE #-} qualified GI.Gst.Structs.TypeFind as Gst.TypeFind

newtype TypeFindFactory = TypeFindFactory (ManagedPtr TypeFindFactory)
foreign import ccall "gst_type_find_factory_get_type"
    c_gst_type_find_factory_get_type :: IO GType

instance GObject TypeFindFactory where
    gobjectType _ = c_gst_type_find_factory_get_type
    

class GObject o => IsTypeFindFactory o
#if MIN_VERSION_base(4,9,0)
instance {-# OVERLAPPABLE #-} (GObject a, O.UnknownAncestorError TypeFindFactory a) =>
    IsTypeFindFactory a
#endif
instance IsTypeFindFactory TypeFindFactory
instance Gst.PluginFeature.IsPluginFeature TypeFindFactory
instance Gst.Object.IsObject TypeFindFactory
instance GObject.Object.IsObject TypeFindFactory

toTypeFindFactory :: (MonadIO m, IsTypeFindFactory o) => o -> m TypeFindFactory
toTypeFindFactory = liftIO . unsafeCastTo TypeFindFactory

noTypeFindFactory :: Maybe TypeFindFactory
noTypeFindFactory = Nothing

#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
type family ResolveTypeFindFactoryMethod (t :: Symbol) (o :: *) :: * where
    ResolveTypeFindFactoryMethod "addControlBinding" o = Gst.Object.ObjectAddControlBindingMethodInfo
    ResolveTypeFindFactoryMethod "bindProperty" o = GObject.Object.ObjectBindPropertyMethodInfo
    ResolveTypeFindFactoryMethod "bindPropertyFull" o = GObject.Object.ObjectBindPropertyFullMethodInfo
    ResolveTypeFindFactoryMethod "callFunction" o = TypeFindFactoryCallFunctionMethodInfo
    ResolveTypeFindFactoryMethod "checkVersion" o = Gst.PluginFeature.PluginFeatureCheckVersionMethodInfo
    ResolveTypeFindFactoryMethod "defaultError" o = Gst.Object.ObjectDefaultErrorMethodInfo
    ResolveTypeFindFactoryMethod "forceFloating" o = GObject.Object.ObjectForceFloatingMethodInfo
    ResolveTypeFindFactoryMethod "freezeNotify" o = GObject.Object.ObjectFreezeNotifyMethodInfo
    ResolveTypeFindFactoryMethod "hasActiveControlBindings" o = Gst.Object.ObjectHasActiveControlBindingsMethodInfo
    ResolveTypeFindFactoryMethod "hasAncestor" o = Gst.Object.ObjectHasAncestorMethodInfo
    ResolveTypeFindFactoryMethod "hasAsAncestor" o = Gst.Object.ObjectHasAsAncestorMethodInfo
    ResolveTypeFindFactoryMethod "hasAsParent" o = Gst.Object.ObjectHasAsParentMethodInfo
    ResolveTypeFindFactoryMethod "hasFunction" o = TypeFindFactoryHasFunctionMethodInfo
    ResolveTypeFindFactoryMethod "isFloating" o = GObject.Object.ObjectIsFloatingMethodInfo
    ResolveTypeFindFactoryMethod "load" o = Gst.PluginFeature.PluginFeatureLoadMethodInfo
    ResolveTypeFindFactoryMethod "notify" o = GObject.Object.ObjectNotifyMethodInfo
    ResolveTypeFindFactoryMethod "notifyByPspec" o = GObject.Object.ObjectNotifyByPspecMethodInfo
    ResolveTypeFindFactoryMethod "ref" o = Gst.Object.ObjectRefMethodInfo
    ResolveTypeFindFactoryMethod "refSink" o = GObject.Object.ObjectRefSinkMethodInfo
    ResolveTypeFindFactoryMethod "removeControlBinding" o = Gst.Object.ObjectRemoveControlBindingMethodInfo
    ResolveTypeFindFactoryMethod "replaceData" o = GObject.Object.ObjectReplaceDataMethodInfo
    ResolveTypeFindFactoryMethod "replaceQdata" o = GObject.Object.ObjectReplaceQdataMethodInfo
    ResolveTypeFindFactoryMethod "runDispose" o = GObject.Object.ObjectRunDisposeMethodInfo
    ResolveTypeFindFactoryMethod "stealData" o = GObject.Object.ObjectStealDataMethodInfo
    ResolveTypeFindFactoryMethod "stealQdata" o = GObject.Object.ObjectStealQdataMethodInfo
    ResolveTypeFindFactoryMethod "suggestNextSync" o = Gst.Object.ObjectSuggestNextSyncMethodInfo
    ResolveTypeFindFactoryMethod "syncValues" o = Gst.Object.ObjectSyncValuesMethodInfo
    ResolveTypeFindFactoryMethod "thawNotify" o = GObject.Object.ObjectThawNotifyMethodInfo
    ResolveTypeFindFactoryMethod "unparent" o = Gst.Object.ObjectUnparentMethodInfo
    ResolveTypeFindFactoryMethod "unref" o = Gst.Object.ObjectUnrefMethodInfo
    ResolveTypeFindFactoryMethod "watchClosure" o = GObject.Object.ObjectWatchClosureMethodInfo
    ResolveTypeFindFactoryMethod "getCaps" o = TypeFindFactoryGetCapsMethodInfo
    ResolveTypeFindFactoryMethod "getControlBinding" o = Gst.Object.ObjectGetControlBindingMethodInfo
    ResolveTypeFindFactoryMethod "getControlRate" o = Gst.Object.ObjectGetControlRateMethodInfo
    ResolveTypeFindFactoryMethod "getData" o = GObject.Object.ObjectGetDataMethodInfo
    ResolveTypeFindFactoryMethod "getExtensions" o = TypeFindFactoryGetExtensionsMethodInfo
    ResolveTypeFindFactoryMethod "getGValueArray" o = Gst.Object.ObjectGetGValueArrayMethodInfo
    ResolveTypeFindFactoryMethod "getName" o = Gst.Object.ObjectGetNameMethodInfo
    ResolveTypeFindFactoryMethod "getParent" o = Gst.Object.ObjectGetParentMethodInfo
    ResolveTypeFindFactoryMethod "getPathString" o = Gst.Object.ObjectGetPathStringMethodInfo
    ResolveTypeFindFactoryMethod "getPlugin" o = Gst.PluginFeature.PluginFeatureGetPluginMethodInfo
    ResolveTypeFindFactoryMethod "getPluginName" o = Gst.PluginFeature.PluginFeatureGetPluginNameMethodInfo
    ResolveTypeFindFactoryMethod "getProperty" o = GObject.Object.ObjectGetPropertyMethodInfo
    ResolveTypeFindFactoryMethod "getQdata" o = GObject.Object.ObjectGetQdataMethodInfo
    ResolveTypeFindFactoryMethod "getRank" o = Gst.PluginFeature.PluginFeatureGetRankMethodInfo
    ResolveTypeFindFactoryMethod "getValue" o = Gst.Object.ObjectGetValueMethodInfo
    ResolveTypeFindFactoryMethod "setControlBindingDisabled" o = Gst.Object.ObjectSetControlBindingDisabledMethodInfo
    ResolveTypeFindFactoryMethod "setControlBindingsDisabled" o = Gst.Object.ObjectSetControlBindingsDisabledMethodInfo
    ResolveTypeFindFactoryMethod "setControlRate" o = Gst.Object.ObjectSetControlRateMethodInfo
    ResolveTypeFindFactoryMethod "setData" o = GObject.Object.ObjectSetDataMethodInfo
    ResolveTypeFindFactoryMethod "setName" o = Gst.Object.ObjectSetNameMethodInfo
    ResolveTypeFindFactoryMethod "setParent" o = Gst.Object.ObjectSetParentMethodInfo
    ResolveTypeFindFactoryMethod "setProperty" o = GObject.Object.ObjectSetPropertyMethodInfo
    ResolveTypeFindFactoryMethod "setRank" o = Gst.PluginFeature.PluginFeatureSetRankMethodInfo
    ResolveTypeFindFactoryMethod l o = O.MethodResolutionFailed l o

instance (info ~ ResolveTypeFindFactoryMethod t TypeFindFactory, O.MethodInfo info TypeFindFactory p) => O.IsLabelProxy t (TypeFindFactory -> p) where
    fromLabelProxy _ = O.overloadedMethod (O.MethodProxy :: O.MethodProxy info)

#if MIN_VERSION_base(4,9,0)
instance (info ~ ResolveTypeFindFactoryMethod t TypeFindFactory, O.MethodInfo info TypeFindFactory p) => O.IsLabel t (TypeFindFactory -> p) where
#if MIN_VERSION_base(4,10,0)
    fromLabel = O.overloadedMethod (O.MethodProxy :: O.MethodProxy info)
#else
    fromLabel _ = O.overloadedMethod (O.MethodProxy :: O.MethodProxy info)
#endif
#endif

#endif

#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
instance O.HasAttributeList TypeFindFactory
type instance O.AttributeList TypeFindFactory = TypeFindFactoryAttributeList
type TypeFindFactoryAttributeList = ('[ '("name", Gst.Object.ObjectNamePropertyInfo), '("parent", Gst.Object.ObjectParentPropertyInfo)] :: [(Symbol, *)])
#endif

#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
#endif

#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
type instance O.SignalList TypeFindFactory = TypeFindFactorySignalList
type TypeFindFactorySignalList = ('[ '("deepNotify", Gst.Object.ObjectDeepNotifySignalInfo), '("notify", GObject.Object.ObjectNotifySignalInfo)] :: [(Symbol, *)])

#endif

-- method TypeFindFactory::call_function
-- method type : OrdinaryMethod
-- Args : [Arg {argCName = "factory", argType = TInterface (Name {namespace = "Gst", name = "TypeFindFactory"}), direction = DirectionIn, mayBeNull = False, argDoc = Documentation {rawDocText = Just "A #GstTypeFindFactory", sinceVersion = Nothing}, argScope = ScopeTypeInvalid, argClosure = -1, argDestroy = -1, argCallerAllocates = False, transfer = TransferNothing},Arg {argCName = "find", argType = TInterface (Name {namespace = "Gst", name = "TypeFind"}), direction = DirectionIn, mayBeNull = False, argDoc = Documentation {rawDocText = Just "a properly setup #GstTypeFind entry. The get_data\n    and suggest_type members must be set.", sinceVersion = Nothing}, argScope = ScopeTypeInvalid, argClosure = -1, argDestroy = -1, argCallerAllocates = False, transfer = TransferNothing}]
-- Lengths : []
-- returnType : Nothing
-- throws : False
-- Skip return : False

foreign import ccall "gst_type_find_factory_call_function" gst_type_find_factory_call_function :: 
    Ptr TypeFindFactory ->                  -- factory : TInterface (Name {namespace = "Gst", name = "TypeFindFactory"})
    Ptr Gst.TypeFind.TypeFind ->            -- find : TInterface (Name {namespace = "Gst", name = "TypeFind"})
    IO ()

{- |
Calls the 'GI.Gst.Callbacks.TypeFindFunction' associated with this factory.
-}
typeFindFactoryCallFunction ::
    (B.CallStack.HasCallStack, MonadIO m, IsTypeFindFactory a) =>
    a
    {- ^ /@factory@/: A 'GI.Gst.Objects.TypeFindFactory.TypeFindFactory' -}
    -> Gst.TypeFind.TypeFind
    {- ^ /@find@/: a properly setup 'GI.Gst.Structs.TypeFind.TypeFind' entry. The get_data
    and suggest_type members must be set. -}
    -> m ()
typeFindFactoryCallFunction factory find = liftIO $ do
    factory' <- unsafeManagedPtrCastPtr factory
    find' <- unsafeManagedPtrGetPtr find
    gst_type_find_factory_call_function factory' find'
    touchManagedPtr factory
    touchManagedPtr find
    return ()

#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
data TypeFindFactoryCallFunctionMethodInfo
instance (signature ~ (Gst.TypeFind.TypeFind -> m ()), MonadIO m, IsTypeFindFactory a) => O.MethodInfo TypeFindFactoryCallFunctionMethodInfo a signature where
    overloadedMethod _ = typeFindFactoryCallFunction

#endif

-- method TypeFindFactory::get_caps
-- method type : OrdinaryMethod
-- Args : [Arg {argCName = "factory", argType = TInterface (Name {namespace = "Gst", name = "TypeFindFactory"}), direction = DirectionIn, mayBeNull = False, argDoc = Documentation {rawDocText = Just "A #GstTypeFindFactory", sinceVersion = Nothing}, argScope = ScopeTypeInvalid, argClosure = -1, argDestroy = -1, argCallerAllocates = False, transfer = TransferNothing}]
-- Lengths : []
-- returnType : Just (TInterface (Name {namespace = "Gst", name = "Caps"}))
-- throws : False
-- Skip return : False

foreign import ccall "gst_type_find_factory_get_caps" gst_type_find_factory_get_caps :: 
    Ptr TypeFindFactory ->                  -- factory : TInterface (Name {namespace = "Gst", name = "TypeFindFactory"})
    IO (Ptr Gst.Caps.Caps)

{- |
Gets the 'GI.Gst.Structs.Caps.Caps' associated with a typefind factory.
-}
typeFindFactoryGetCaps ::
    (B.CallStack.HasCallStack, MonadIO m, IsTypeFindFactory a) =>
    a
    {- ^ /@factory@/: A 'GI.Gst.Objects.TypeFindFactory.TypeFindFactory' -}
    -> m Gst.Caps.Caps
    {- ^ __Returns:__ the 'GI.Gst.Structs.Caps.Caps' associated with this factory -}
typeFindFactoryGetCaps factory = liftIO $ do
    factory' <- unsafeManagedPtrCastPtr factory
    result <- gst_type_find_factory_get_caps factory'
    checkUnexpectedReturnNULL "typeFindFactoryGetCaps" result
    result' <- (newBoxed Gst.Caps.Caps) result
    touchManagedPtr factory
    return result'

#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
data TypeFindFactoryGetCapsMethodInfo
instance (signature ~ (m Gst.Caps.Caps), MonadIO m, IsTypeFindFactory a) => O.MethodInfo TypeFindFactoryGetCapsMethodInfo a signature where
    overloadedMethod _ = typeFindFactoryGetCaps

#endif

-- method TypeFindFactory::get_extensions
-- method type : OrdinaryMethod
-- Args : [Arg {argCName = "factory", argType = TInterface (Name {namespace = "Gst", name = "TypeFindFactory"}), direction = DirectionIn, mayBeNull = False, argDoc = Documentation {rawDocText = Just "A #GstTypeFindFactory", sinceVersion = Nothing}, argScope = ScopeTypeInvalid, argClosure = -1, argDestroy = -1, argCallerAllocates = False, transfer = TransferNothing}]
-- Lengths : []
-- returnType : Just (TCArray True (-1) (-1) (TBasicType TUTF8))
-- throws : False
-- Skip return : False

foreign import ccall "gst_type_find_factory_get_extensions" gst_type_find_factory_get_extensions :: 
    Ptr TypeFindFactory ->                  -- factory : TInterface (Name {namespace = "Gst", name = "TypeFindFactory"})
    IO (Ptr CString)

{- |
Gets the extensions associated with a 'GI.Gst.Objects.TypeFindFactory.TypeFindFactory'. The returned
array should not be changed. If you need to change stuff in it, you should
copy it using @/g_strdupv()/@.  This function may return 'Nothing' to indicate
a 0-length list.
-}
typeFindFactoryGetExtensions ::
    (B.CallStack.HasCallStack, MonadIO m, IsTypeFindFactory a) =>
    a
    {- ^ /@factory@/: A 'GI.Gst.Objects.TypeFindFactory.TypeFindFactory' -}
    -> m (Maybe [T.Text])
    {- ^ __Returns:__ 
    a 'Nothing'-terminated array of extensions associated with this factory -}
typeFindFactoryGetExtensions factory = liftIO $ do
    factory' <- unsafeManagedPtrCastPtr factory
    result <- gst_type_find_factory_get_extensions factory'
    maybeResult <- convertIfNonNull result $ \result' -> do
        result'' <- unpackZeroTerminatedUTF8CArray result'
        return result''
    touchManagedPtr factory
    return maybeResult

#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
data TypeFindFactoryGetExtensionsMethodInfo
instance (signature ~ (m (Maybe [T.Text])), MonadIO m, IsTypeFindFactory a) => O.MethodInfo TypeFindFactoryGetExtensionsMethodInfo a signature where
    overloadedMethod _ = typeFindFactoryGetExtensions

#endif

-- method TypeFindFactory::has_function
-- method type : OrdinaryMethod
-- Args : [Arg {argCName = "factory", argType = TInterface (Name {namespace = "Gst", name = "TypeFindFactory"}), direction = DirectionIn, mayBeNull = False, argDoc = Documentation {rawDocText = Just "A #GstTypeFindFactory", sinceVersion = Nothing}, argScope = ScopeTypeInvalid, argClosure = -1, argDestroy = -1, argCallerAllocates = False, transfer = TransferNothing}]
-- Lengths : []
-- returnType : Just (TBasicType TBoolean)
-- throws : False
-- Skip return : False

foreign import ccall "gst_type_find_factory_has_function" gst_type_find_factory_has_function :: 
    Ptr TypeFindFactory ->                  -- factory : TInterface (Name {namespace = "Gst", name = "TypeFindFactory"})
    IO CInt

{- |
Check whether the factory has a typefind function. Typefind factories
without typefind functions are a last-effort fallback mechanism to
e.g. assume a certain media type based on the file extension.
-}
typeFindFactoryHasFunction ::
    (B.CallStack.HasCallStack, MonadIO m, IsTypeFindFactory a) =>
    a
    {- ^ /@factory@/: A 'GI.Gst.Objects.TypeFindFactory.TypeFindFactory' -}
    -> m Bool
    {- ^ __Returns:__ 'True' if the factory has a typefind functions set, otherwise 'False' -}
typeFindFactoryHasFunction factory = liftIO $ do
    factory' <- unsafeManagedPtrCastPtr factory
    result <- gst_type_find_factory_has_function factory'
    let result' = (/= 0) result
    touchManagedPtr factory
    return result'

#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
data TypeFindFactoryHasFunctionMethodInfo
instance (signature ~ (m Bool), MonadIO m, IsTypeFindFactory a) => O.MethodInfo TypeFindFactoryHasFunctionMethodInfo a signature where
    overloadedMethod _ = typeFindFactoryHasFunction

#endif

-- method TypeFindFactory::get_list
-- method type : MemberFunction
-- Args : []
-- Lengths : []
-- returnType : Just (TGList (TInterface (Name {namespace = "Gst", name = "TypeFindFactory"})))
-- throws : False
-- Skip return : False

foreign import ccall "gst_type_find_factory_get_list" gst_type_find_factory_get_list :: 
    IO (Ptr (GList (Ptr TypeFindFactory)))

{- |
Gets the list of all registered typefind factories. You must free the
list using 'GI.Gst.Objects.PluginFeature.pluginFeatureListFree'.

The returned factories are sorted by highest rank first, and then by
factory name.

Free-function: gst_plugin_feature_list_free
-}
typeFindFactoryGetList ::
    (B.CallStack.HasCallStack, MonadIO m) =>
    m [TypeFindFactory]
    {- ^ __Returns:__ the list of all
    registered 'GI.Gst.Objects.TypeFindFactory.TypeFindFactory'. -}
typeFindFactoryGetList  = liftIO $ do
    result <- gst_type_find_factory_get_list
    result' <- unpackGList result
    result'' <- mapM (wrapObject TypeFindFactory) result'
    g_list_free result
    return result''

#if defined(ENABLE_OVERLOADING) && !defined(__HADDOCK_VERSION__)
#endif