mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer-rs.git
synced 2025-01-05 06:48:42 +00:00
Initial gstreamer-audio bindings
Only wrapping AudioInfo and AudioFormatInfo and related for now. https://github.com/sdroege/gstreamer-rs/issues/4
This commit is contained in:
parent
146b3092aa
commit
c8910aae08
13 changed files with 1662 additions and 2 deletions
51
Cargo.lock
generated
51
Cargo.lock
generated
|
@ -1,5 +1,5 @@
|
||||||
[root]
|
[root]
|
||||||
name = "gstreamer-app"
|
name = "gstreamer-audio"
|
||||||
version = "0.1.0"
|
version = "0.1.0"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"bitflags 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)",
|
"bitflags 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
@ -7,8 +7,9 @@ dependencies = [
|
||||||
"glib-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
"glib-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
||||||
"gobject-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
"gobject-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
||||||
"gstreamer 0.1.0",
|
"gstreamer 0.1.0",
|
||||||
"gstreamer-app-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
"gstreamer-audio-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
||||||
"gstreamer-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
"gstreamer-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
||||||
|
"lazy_static 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"libc 0.2.29 (registry+https://github.com/rust-lang/crates.io-index)",
|
"libc 0.2.29 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"rustdoc-stripper 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
"rustdoc-stripper 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
]
|
]
|
||||||
|
@ -246,6 +247,21 @@ dependencies = [
|
||||||
"rustdoc-stripper 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
"rustdoc-stripper 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "gstreamer-app"
|
||||||
|
version = "0.1.0"
|
||||||
|
dependencies = [
|
||||||
|
"bitflags 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
"glib 0.1.3 (git+https://github.com/gtk-rs/glib)",
|
||||||
|
"glib-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
||||||
|
"gobject-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
||||||
|
"gstreamer 0.1.0",
|
||||||
|
"gstreamer-app-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
||||||
|
"gstreamer-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
||||||
|
"libc 0.2.29 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
"rustdoc-stripper 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "gstreamer-app-sys"
|
name = "gstreamer-app-sys"
|
||||||
version = "0.1.1"
|
version = "0.1.1"
|
||||||
|
@ -260,6 +276,21 @@ dependencies = [
|
||||||
"pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)",
|
"pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "gstreamer-audio-sys"
|
||||||
|
version = "0.1.1"
|
||||||
|
source = "git+https://github.com/sdroege/gstreamer-sys#252abbaeda64a3fdd8ccab291297500e3cdf6499"
|
||||||
|
dependencies = [
|
||||||
|
"bitflags 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
"glib-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
||||||
|
"gobject-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
||||||
|
"gstreamer-base-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
||||||
|
"gstreamer-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
||||||
|
"gstreamer-tag-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
||||||
|
"libc 0.2.29 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
"pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "gstreamer-base-sys"
|
name = "gstreamer-base-sys"
|
||||||
version = "0.1.1"
|
version = "0.1.1"
|
||||||
|
@ -285,6 +316,20 @@ dependencies = [
|
||||||
"pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)",
|
"pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "gstreamer-tag-sys"
|
||||||
|
version = "0.1.1"
|
||||||
|
source = "git+https://github.com/sdroege/gstreamer-sys#252abbaeda64a3fdd8ccab291297500e3cdf6499"
|
||||||
|
dependencies = [
|
||||||
|
"bitflags 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
"glib-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
||||||
|
"gobject-sys 0.3.4 (git+https://github.com/gtk-rs/sys)",
|
||||||
|
"gstreamer-base-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
||||||
|
"gstreamer-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)",
|
||||||
|
"libc 0.2.29 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
"pkg-config 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "gtk"
|
name = "gtk"
|
||||||
version = "0.1.3"
|
version = "0.1.3"
|
||||||
|
@ -560,8 +605,10 @@ dependencies = [
|
||||||
"checksum glib-sys 0.3.4 (git+https://github.com/gtk-rs/sys)" = "<none>"
|
"checksum glib-sys 0.3.4 (git+https://github.com/gtk-rs/sys)" = "<none>"
|
||||||
"checksum gobject-sys 0.3.4 (git+https://github.com/gtk-rs/sys)" = "<none>"
|
"checksum gobject-sys 0.3.4 (git+https://github.com/gtk-rs/sys)" = "<none>"
|
||||||
"checksum gstreamer-app-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)" = "<none>"
|
"checksum gstreamer-app-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)" = "<none>"
|
||||||
|
"checksum gstreamer-audio-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)" = "<none>"
|
||||||
"checksum gstreamer-base-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)" = "<none>"
|
"checksum gstreamer-base-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)" = "<none>"
|
||||||
"checksum gstreamer-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)" = "<none>"
|
"checksum gstreamer-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)" = "<none>"
|
||||||
|
"checksum gstreamer-tag-sys 0.1.1 (git+https://github.com/sdroege/gstreamer-sys)" = "<none>"
|
||||||
"checksum gtk 0.1.3 (git+https://github.com/gtk-rs/gtk)" = "<none>"
|
"checksum gtk 0.1.3 (git+https://github.com/gtk-rs/gtk)" = "<none>"
|
||||||
"checksum gtk-sys 0.3.4 (git+https://github.com/gtk-rs/sys)" = "<none>"
|
"checksum gtk-sys 0.3.4 (git+https://github.com/gtk-rs/sys)" = "<none>"
|
||||||
"checksum iovec 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "29d062ee61fccdf25be172e70f34c9f6efc597e1fb8f6526e8437b2046ab26be"
|
"checksum iovec 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "29d062ee61fccdf25be172e70f34c9f6efc597e1fb8f6526e8437b2046ab26be"
|
||||||
|
|
|
@ -3,5 +3,6 @@
|
||||||
members = [
|
members = [
|
||||||
"gstreamer",
|
"gstreamer",
|
||||||
"gstreamer-app",
|
"gstreamer-app",
|
||||||
|
"gstreamer-audio",
|
||||||
"examples",
|
"examples",
|
||||||
]
|
]
|
||||||
|
|
37
Gir_GstAudio.toml
Normal file
37
Gir_GstAudio.toml
Normal file
|
@ -0,0 +1,37 @@
|
||||||
|
[options]
|
||||||
|
girs_dir = "gir-files"
|
||||||
|
library = "GstAudio"
|
||||||
|
version = "1.0"
|
||||||
|
min_cfg_version = "1.8"
|
||||||
|
target_path = "gstreamer-audio"
|
||||||
|
work_mode = "normal"
|
||||||
|
concurrency = "send+sync"
|
||||||
|
generate_safety_asserts = true
|
||||||
|
|
||||||
|
external_libraries = [
|
||||||
|
"GLib",
|
||||||
|
"GObject",
|
||||||
|
"Gst",
|
||||||
|
]
|
||||||
|
|
||||||
|
generate = [
|
||||||
|
"GstAudio.AudioFlags",
|
||||||
|
"GstAudio.AudioFormat",
|
||||||
|
"GstAudio.AudioFormatFlags",
|
||||||
|
"GstAudio.AudioLayout",
|
||||||
|
"GstAudio.AudioPackFlags",
|
||||||
|
"GstAudio.AudioChannelPosition",
|
||||||
|
]
|
||||||
|
|
||||||
|
manual = [
|
||||||
|
"GObject.Object",
|
||||||
|
"Gst.Object",
|
||||||
|
"GstAudio.AudioInfo",
|
||||||
|
"GstAudio.AudioFormatInfo",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[object]]
|
||||||
|
name = "Gst.Caps"
|
||||||
|
status = "manual"
|
||||||
|
ref_mode = "ref"
|
||||||
|
|
268
docs/gstreamer-audio/docs.md
Normal file
268
docs/gstreamer-audio/docs.md
Normal file
|
@ -0,0 +1,268 @@
|
||||||
|
<!-- file * -->
|
||||||
|
<!-- enum AudioChannelPosition -->
|
||||||
|
Audio channel positions.
|
||||||
|
|
||||||
|
These are the channels defined in SMPTE 2036-2-2008
|
||||||
|
Table 1 for 22.2 audio systems with the Surround and Wide channels from
|
||||||
|
DTS Coherent Acoustics (v.1.3.1) and 10.2 and 7.1 layouts. In the caps the
|
||||||
|
actual channel layout is expressed with a channel count and a channel mask,
|
||||||
|
which describes the existing channels. The positions in the bit mask correspond
|
||||||
|
to the enum values.
|
||||||
|
For negotiation it is allowed to have more bits set in the channel mask than
|
||||||
|
the number of channels to specify the allowed channel positions but this is
|
||||||
|
not allowed in negotiated caps. It is not allowed in any situation other
|
||||||
|
than the one mentioned below to have less bits set in the channel mask than
|
||||||
|
the number of channels.
|
||||||
|
|
||||||
|
`AudioChannelPosition::Mono` can only be used with a single mono channel that
|
||||||
|
has no direction information and would be mixed into all directional channels.
|
||||||
|
This is expressed in caps by having a single channel and no channel mask.
|
||||||
|
|
||||||
|
`AudioChannelPosition::None` can only be used if all channels have this position.
|
||||||
|
This is expressed in caps by having a channel mask with no bits set.
|
||||||
|
|
||||||
|
As another special case it is allowed to have two channels without a channel mask.
|
||||||
|
This implicitely means that this is a stereo stream with a front left and front right
|
||||||
|
channel.
|
||||||
|
<!-- enum AudioChannelPosition::variant None -->
|
||||||
|
used for position-less channels, e.g.
|
||||||
|
from a sound card that records 1024 channels; mutually exclusive with
|
||||||
|
any other channel position
|
||||||
|
<!-- enum AudioChannelPosition::variant Mono -->
|
||||||
|
Mono without direction;
|
||||||
|
can only be used with 1 channel
|
||||||
|
<!-- enum AudioChannelPosition::variant Invalid -->
|
||||||
|
invalid position
|
||||||
|
<!-- enum AudioChannelPosition::variant FrontLeft -->
|
||||||
|
Front left
|
||||||
|
<!-- enum AudioChannelPosition::variant FrontRight -->
|
||||||
|
Front right
|
||||||
|
<!-- enum AudioChannelPosition::variant FrontCenter -->
|
||||||
|
Front center
|
||||||
|
<!-- enum AudioChannelPosition::variant Lfe1 -->
|
||||||
|
Low-frequency effects 1 (subwoofer)
|
||||||
|
<!-- enum AudioChannelPosition::variant RearLeft -->
|
||||||
|
Rear left
|
||||||
|
<!-- enum AudioChannelPosition::variant RearRight -->
|
||||||
|
Rear right
|
||||||
|
<!-- enum AudioChannelPosition::variant FrontLeftOfCenter -->
|
||||||
|
Front left of center
|
||||||
|
<!-- enum AudioChannelPosition::variant FrontRightOfCenter -->
|
||||||
|
Front right of center
|
||||||
|
<!-- enum AudioChannelPosition::variant RearCenter -->
|
||||||
|
Rear center
|
||||||
|
<!-- enum AudioChannelPosition::variant Lfe2 -->
|
||||||
|
Low-frequency effects 2 (subwoofer)
|
||||||
|
<!-- enum AudioChannelPosition::variant SideLeft -->
|
||||||
|
Side left
|
||||||
|
<!-- enum AudioChannelPosition::variant SideRight -->
|
||||||
|
Side right
|
||||||
|
<!-- enum AudioChannelPosition::variant TopFrontLeft -->
|
||||||
|
Top front left
|
||||||
|
<!-- enum AudioChannelPosition::variant TopFrontRight -->
|
||||||
|
Top front right
|
||||||
|
<!-- enum AudioChannelPosition::variant TopFrontCenter -->
|
||||||
|
Top front center
|
||||||
|
<!-- enum AudioChannelPosition::variant TopCenter -->
|
||||||
|
Top center
|
||||||
|
<!-- enum AudioChannelPosition::variant TopRearLeft -->
|
||||||
|
Top rear left
|
||||||
|
<!-- enum AudioChannelPosition::variant TopRearRight -->
|
||||||
|
Top rear right
|
||||||
|
<!-- enum AudioChannelPosition::variant TopSideLeft -->
|
||||||
|
Top side right
|
||||||
|
<!-- enum AudioChannelPosition::variant TopSideRight -->
|
||||||
|
Top rear right
|
||||||
|
<!-- enum AudioChannelPosition::variant TopRearCenter -->
|
||||||
|
Top rear center
|
||||||
|
<!-- enum AudioChannelPosition::variant BottomFrontCenter -->
|
||||||
|
Bottom front center
|
||||||
|
<!-- enum AudioChannelPosition::variant BottomFrontLeft -->
|
||||||
|
Bottom front left
|
||||||
|
<!-- enum AudioChannelPosition::variant BottomFrontRight -->
|
||||||
|
Bottom front right
|
||||||
|
<!-- enum AudioChannelPosition::variant WideLeft -->
|
||||||
|
Wide left (between front left and side left)
|
||||||
|
<!-- enum AudioChannelPosition::variant WideRight -->
|
||||||
|
Wide right (between front right and side right)
|
||||||
|
<!-- enum AudioChannelPosition::variant SurroundLeft -->
|
||||||
|
Surround left (between rear left and side left)
|
||||||
|
<!-- enum AudioChannelPosition::variant SurroundRight -->
|
||||||
|
Surround right (between rear right and side right)
|
||||||
|
<!-- enum AudioFormat -->
|
||||||
|
Enum value describing the most common audio formats.
|
||||||
|
<!-- enum AudioFormat::variant Unknown -->
|
||||||
|
unknown or unset audio format
|
||||||
|
<!-- enum AudioFormat::variant Encoded -->
|
||||||
|
encoded audio format
|
||||||
|
<!-- enum AudioFormat::variant S8 -->
|
||||||
|
8 bits in 8 bits, signed
|
||||||
|
<!-- enum AudioFormat::variant U8 -->
|
||||||
|
8 bits in 8 bits, unsigned
|
||||||
|
<!-- enum AudioFormat::variant S16le -->
|
||||||
|
16 bits in 16 bits, signed, little endian
|
||||||
|
<!-- enum AudioFormat::variant S16be -->
|
||||||
|
16 bits in 16 bits, signed, big endian
|
||||||
|
<!-- enum AudioFormat::variant U16le -->
|
||||||
|
16 bits in 16 bits, unsigned, little endian
|
||||||
|
<!-- enum AudioFormat::variant U16be -->
|
||||||
|
16 bits in 16 bits, unsigned, big endian
|
||||||
|
<!-- enum AudioFormat::variant S2432le -->
|
||||||
|
24 bits in 32 bits, signed, little endian
|
||||||
|
<!-- enum AudioFormat::variant S2432be -->
|
||||||
|
24 bits in 32 bits, signed, big endian
|
||||||
|
<!-- enum AudioFormat::variant U2432le -->
|
||||||
|
24 bits in 32 bits, unsigned, little endian
|
||||||
|
<!-- enum AudioFormat::variant U2432be -->
|
||||||
|
24 bits in 32 bits, unsigned, big endian
|
||||||
|
<!-- enum AudioFormat::variant S32le -->
|
||||||
|
32 bits in 32 bits, signed, little endian
|
||||||
|
<!-- enum AudioFormat::variant S32be -->
|
||||||
|
32 bits in 32 bits, signed, big endian
|
||||||
|
<!-- enum AudioFormat::variant U32le -->
|
||||||
|
32 bits in 32 bits, unsigned, little endian
|
||||||
|
<!-- enum AudioFormat::variant U32be -->
|
||||||
|
32 bits in 32 bits, unsigned, big endian
|
||||||
|
<!-- enum AudioFormat::variant S24le -->
|
||||||
|
24 bits in 24 bits, signed, little endian
|
||||||
|
<!-- enum AudioFormat::variant S24be -->
|
||||||
|
24 bits in 24 bits, signed, big endian
|
||||||
|
<!-- enum AudioFormat::variant U24le -->
|
||||||
|
24 bits in 24 bits, unsigned, little endian
|
||||||
|
<!-- enum AudioFormat::variant U24be -->
|
||||||
|
24 bits in 24 bits, unsigned, big endian
|
||||||
|
<!-- enum AudioFormat::variant S20le -->
|
||||||
|
20 bits in 24 bits, signed, little endian
|
||||||
|
<!-- enum AudioFormat::variant S20be -->
|
||||||
|
20 bits in 24 bits, signed, big endian
|
||||||
|
<!-- enum AudioFormat::variant U20le -->
|
||||||
|
20 bits in 24 bits, unsigned, little endian
|
||||||
|
<!-- enum AudioFormat::variant U20be -->
|
||||||
|
20 bits in 24 bits, unsigned, big endian
|
||||||
|
<!-- enum AudioFormat::variant S18le -->
|
||||||
|
18 bits in 24 bits, signed, little endian
|
||||||
|
<!-- enum AudioFormat::variant S18be -->
|
||||||
|
18 bits in 24 bits, signed, big endian
|
||||||
|
<!-- enum AudioFormat::variant U18le -->
|
||||||
|
18 bits in 24 bits, unsigned, little endian
|
||||||
|
<!-- enum AudioFormat::variant U18be -->
|
||||||
|
18 bits in 24 bits, unsigned, big endian
|
||||||
|
<!-- enum AudioFormat::variant F32le -->
|
||||||
|
32-bit floating point samples, little endian
|
||||||
|
<!-- enum AudioFormat::variant F32be -->
|
||||||
|
32-bit floating point samples, big endian
|
||||||
|
<!-- enum AudioFormat::variant F64le -->
|
||||||
|
64-bit floating point samples, little endian
|
||||||
|
<!-- enum AudioFormat::variant F64be -->
|
||||||
|
64-bit floating point samples, big endian
|
||||||
|
<!-- enum AudioFormat::variant S16 -->
|
||||||
|
16 bits in 16 bits, signed, native endianness
|
||||||
|
<!-- enum AudioFormat::variant U16 -->
|
||||||
|
16 bits in 16 bits, unsigned, native endianness
|
||||||
|
<!-- enum AudioFormat::variant S2432 -->
|
||||||
|
24 bits in 32 bits, signed, native endianness
|
||||||
|
<!-- enum AudioFormat::variant U2432 -->
|
||||||
|
24 bits in 32 bits, unsigned, native endianness
|
||||||
|
<!-- enum AudioFormat::variant S32 -->
|
||||||
|
32 bits in 32 bits, signed, native endianness
|
||||||
|
<!-- enum AudioFormat::variant U32 -->
|
||||||
|
32 bits in 32 bits, unsigned, native endianness
|
||||||
|
<!-- enum AudioFormat::variant S24 -->
|
||||||
|
24 bits in 24 bits, signed, native endianness
|
||||||
|
<!-- enum AudioFormat::variant U24 -->
|
||||||
|
24 bits in 24 bits, unsigned, native endianness
|
||||||
|
<!-- enum AudioFormat::variant S20 -->
|
||||||
|
20 bits in 24 bits, signed, native endianness
|
||||||
|
<!-- enum AudioFormat::variant U20 -->
|
||||||
|
20 bits in 24 bits, unsigned, native endianness
|
||||||
|
<!-- enum AudioFormat::variant S18 -->
|
||||||
|
18 bits in 24 bits, signed, native endianness
|
||||||
|
<!-- enum AudioFormat::variant U18 -->
|
||||||
|
18 bits in 24 bits, unsigned, native endianness
|
||||||
|
<!-- enum AudioFormat::variant F32 -->
|
||||||
|
32-bit floating point samples, native endianness
|
||||||
|
<!-- enum AudioFormat::variant F64 -->
|
||||||
|
64-bit floating point samples, native endianness
|
||||||
|
<!-- struct AudioFormatInfo -->
|
||||||
|
Information for an audio format.
|
||||||
|
<!-- struct AudioInfo -->
|
||||||
|
Information describing audio properties. This information can be filled
|
||||||
|
in from GstCaps with `AudioInfo::from_caps`.
|
||||||
|
|
||||||
|
Use the provided macros to access the info in this structure.
|
||||||
|
<!-- impl AudioInfo::fn new -->
|
||||||
|
Allocate a new `AudioInfo` that is also initialized with
|
||||||
|
`AudioInfo::init`.
|
||||||
|
|
||||||
|
# Returns
|
||||||
|
|
||||||
|
a new `AudioInfo`. free with `AudioInfo::free`.
|
||||||
|
<!-- impl AudioInfo::fn convert -->
|
||||||
|
Converts among various `gst::Format` types. This function handles
|
||||||
|
GST_FORMAT_BYTES, GST_FORMAT_TIME, and GST_FORMAT_DEFAULT. For
|
||||||
|
raw audio, GST_FORMAT_DEFAULT corresponds to audio frames. This
|
||||||
|
function can be used to handle pad queries of the type GST_QUERY_CONVERT.
|
||||||
|
## `src_fmt`
|
||||||
|
`gst::Format` of the `src_val`
|
||||||
|
## `src_val`
|
||||||
|
value to convert
|
||||||
|
## `dest_fmt`
|
||||||
|
`gst::Format` of the `dest_val`
|
||||||
|
## `dest_val`
|
||||||
|
pointer to destination value
|
||||||
|
|
||||||
|
# Returns
|
||||||
|
|
||||||
|
TRUE if the conversion was successful.
|
||||||
|
<!-- impl AudioInfo::fn copy -->
|
||||||
|
Copy a GstAudioInfo structure.
|
||||||
|
|
||||||
|
# Returns
|
||||||
|
|
||||||
|
a new `AudioInfo`. free with gst_audio_info_free.
|
||||||
|
<!-- impl AudioInfo::fn free -->
|
||||||
|
Free a GstAudioInfo structure previously allocated with `AudioInfo::new`
|
||||||
|
or `AudioInfo::copy`.
|
||||||
|
<!-- impl AudioInfo::fn from_caps -->
|
||||||
|
Parse `caps` and update `self`.
|
||||||
|
## `caps`
|
||||||
|
a `gst::Caps`
|
||||||
|
|
||||||
|
# Returns
|
||||||
|
|
||||||
|
TRUE if `caps` could be parsed
|
||||||
|
<!-- impl AudioInfo::fn init -->
|
||||||
|
Initialize `self` with default values.
|
||||||
|
<!-- impl AudioInfo::fn is_equal -->
|
||||||
|
Compares two `AudioInfo` and returns whether they are equal or not
|
||||||
|
## `other`
|
||||||
|
a `AudioInfo`
|
||||||
|
|
||||||
|
# Returns
|
||||||
|
|
||||||
|
`true` if `self` and `other` are equal, else `false`.
|
||||||
|
<!-- impl AudioInfo::fn set_format -->
|
||||||
|
Set the default info for the audio info of `format` and `rate` and `channels`.
|
||||||
|
|
||||||
|
Note: This initializes `self` first, no values are preserved.
|
||||||
|
## `format`
|
||||||
|
the format
|
||||||
|
## `rate`
|
||||||
|
the samplerate
|
||||||
|
## `channels`
|
||||||
|
the number of channels
|
||||||
|
## `position`
|
||||||
|
the channel positions
|
||||||
|
<!-- impl AudioInfo::fn to_caps -->
|
||||||
|
Convert the values of `self` into a `gst::Caps`.
|
||||||
|
|
||||||
|
# Returns
|
||||||
|
|
||||||
|
the new `gst::Caps` containing the
|
||||||
|
info of `self`.
|
||||||
|
<!-- enum AudioLayout -->
|
||||||
|
Layout of the audio samples for the different channels.
|
||||||
|
<!-- enum AudioLayout::variant Interleaved -->
|
||||||
|
interleaved audio
|
||||||
|
<!-- enum AudioLayout::variant NonInterleaved -->
|
||||||
|
non-interleaved audio
|
33
gstreamer-audio/Cargo.toml
Normal file
33
gstreamer-audio/Cargo.toml
Normal file
|
@ -0,0 +1,33 @@
|
||||||
|
[package]
|
||||||
|
name = "gstreamer-audio"
|
||||||
|
version = "0.1.0"
|
||||||
|
authors = ["Sebastian Dröge <sebastian@centricular.com>"]
|
||||||
|
categories = ["api-bindings", "multimedia"]
|
||||||
|
description = "Rust bindings for GStreamer Audio library"
|
||||||
|
repository = "https://github.com/sdroege/gstreamer-rs"
|
||||||
|
license = "MIT/Apache-2.0"
|
||||||
|
documentation = "https://gstreamer.freedesktop.org"
|
||||||
|
keywords = ["gstreamer", "multimedia", "audio", "video", "gnome"]
|
||||||
|
build = "build.rs"
|
||||||
|
|
||||||
|
[dependencies]
|
||||||
|
bitflags = "0.9"
|
||||||
|
libc = "0.2"
|
||||||
|
glib-sys = { version = "0.3.4", git = "https://github.com/gtk-rs/sys" }
|
||||||
|
gobject-sys = { version = "0.3.4", git = "https://github.com/gtk-rs/sys" }
|
||||||
|
gstreamer-sys = { version = "0.1.1", git = "https://github.com/sdroege/gstreamer-sys", features = ["v1_8"] }
|
||||||
|
gstreamer-audio-sys = { version = "0.1.1", git = "https://github.com/sdroege/gstreamer-sys", features = ["v1_8"] }
|
||||||
|
glib = { version = "0.1.3", git = "https://github.com/gtk-rs/glib" }
|
||||||
|
gstreamer = { version = "0.1.0", path = "../gstreamer" }
|
||||||
|
lazy_static = "0.2"
|
||||||
|
|
||||||
|
[build-dependencies.rustdoc-stripper]
|
||||||
|
version = "0.1"
|
||||||
|
optional = true
|
||||||
|
|
||||||
|
[features]
|
||||||
|
v1_10 = ["gstreamer-sys/v1_10"]
|
||||||
|
v1_12 = ["gstreamer-sys/v1_12", "v1_10"]
|
||||||
|
embed-lgpl-docs = ["rustdoc-stripper"]
|
||||||
|
purge-lgpl-docs = ["rustdoc-stripper"]
|
||||||
|
default-features = []
|
34
gstreamer-audio/build.rs
Normal file
34
gstreamer-audio/build.rs
Normal file
|
@ -0,0 +1,34 @@
|
||||||
|
fn main() {
|
||||||
|
manage_docs();
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(any(feature = "embed-lgpl-docs", feature = "purge-lgpl-docs"))]
|
||||||
|
fn manage_docs() {
|
||||||
|
extern crate stripper_lib;
|
||||||
|
use std::io;
|
||||||
|
|
||||||
|
let path = "src";
|
||||||
|
let ignores: &[&str] = &[];
|
||||||
|
|
||||||
|
stripper_lib::loop_over_files(
|
||||||
|
path.as_ref(),
|
||||||
|
&mut |w, s| stripper_lib::strip_comments(w, s, &mut io::sink(), true),
|
||||||
|
&ignores,
|
||||||
|
false,
|
||||||
|
);
|
||||||
|
|
||||||
|
#[cfg(feature = "embed-lgpl-docs")]
|
||||||
|
{
|
||||||
|
let docs = include_str!("../docs/gstreamer-audio/docs.md");
|
||||||
|
let mut infos = stripper_lib::parse_cmts(docs.lines(), true);
|
||||||
|
stripper_lib::loop_over_files(
|
||||||
|
path.as_ref(),
|
||||||
|
&mut |w, s| stripper_lib::regenerate_comments(w, s, &mut infos, true, true),
|
||||||
|
&ignores,
|
||||||
|
false,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(not(any(feature = "embed-lgpl-docs", feature = "purge-lgpl-docs")))]
|
||||||
|
fn manage_docs() {}
|
363
gstreamer-audio/src/audio_format_info.rs
Normal file
363
gstreamer-audio/src/audio_format_info.rs
Normal file
|
@ -0,0 +1,363 @@
|
||||||
|
// Copyright (C) 2017 Sebastian Dröge <sebastian@centricular.com>
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||||
|
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||||
|
// option. This file may not be copied, modified, or distributed
|
||||||
|
// except according to those terms.
|
||||||
|
|
||||||
|
use ffi;
|
||||||
|
|
||||||
|
use std::ffi::CStr;
|
||||||
|
use std::fmt;
|
||||||
|
use std::str;
|
||||||
|
|
||||||
|
use glib::translate::{from_glib, FromGlib, ToGlib, ToGlibPtr};
|
||||||
|
|
||||||
|
#[derive(PartialEq, Eq, Debug)]
|
||||||
|
pub enum AudioEndianness {
|
||||||
|
Unknown,
|
||||||
|
LittleEndian = 1234,
|
||||||
|
BigEndian = 4321,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl FromGlib<i32> for AudioEndianness {
|
||||||
|
fn from_glib(value: i32) -> Self {
|
||||||
|
match value {
|
||||||
|
1234 => AudioEndianness::LittleEndian,
|
||||||
|
4321 => AudioEndianness::BigEndian,
|
||||||
|
_ => AudioEndianness::Unknown,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl ToGlib for AudioEndianness {
|
||||||
|
type GlibType = i32;
|
||||||
|
|
||||||
|
fn to_glib(&self) -> i32 {
|
||||||
|
match *self {
|
||||||
|
AudioEndianness::LittleEndian => 1234,
|
||||||
|
AudioEndianness::BigEndian => 4321,
|
||||||
|
_ => 0,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl ::AudioFormat {
|
||||||
|
pub fn build_integer(
|
||||||
|
sign: bool,
|
||||||
|
endianness: AudioEndianness,
|
||||||
|
width: i32,
|
||||||
|
depth: i32,
|
||||||
|
) -> ::AudioFormat {
|
||||||
|
unsafe {
|
||||||
|
from_glib(ffi::gst_audio_format_build_integer(
|
||||||
|
sign.to_glib(),
|
||||||
|
endianness.to_glib(),
|
||||||
|
width,
|
||||||
|
depth,
|
||||||
|
))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl str::FromStr for ::AudioFormat {
|
||||||
|
type Err = ();
|
||||||
|
|
||||||
|
fn from_str(s: &str) -> Result<Self, ()> {
|
||||||
|
unsafe {
|
||||||
|
let format = ffi::gst_audio_format_from_string(s.to_glib_none().0);
|
||||||
|
if format == ffi::GST_AUDIO_FORMAT_UNKNOWN {
|
||||||
|
Err(())
|
||||||
|
} else {
|
||||||
|
Ok(from_glib(format))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_S16: ::AudioFormat = ::AudioFormat::S16be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_U16: ::AudioFormat = ::AudioFormat::U16be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_S2432: ::AudioFormat = ::AudioFormat::S2432be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_U2432: ::AudioFormat = ::AudioFormat::U2432be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_S32: ::AudioFormat = ::AudioFormat::S32be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_U32: ::AudioFormat = ::AudioFormat::S32be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_S24: ::AudioFormat = ::AudioFormat::S24be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_U24: ::AudioFormat = ::AudioFormat::S24be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_S20: ::AudioFormat = ::AudioFormat::S20be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_U20: ::AudioFormat = ::AudioFormat::S20be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_S18: ::AudioFormat = ::AudioFormat::S18be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_U18: ::AudioFormat = ::AudioFormat::S18be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_F32: ::AudioFormat = ::AudioFormat::F32be;
|
||||||
|
#[cfg(target_endian = "big")]
|
||||||
|
pub const FORMAT_F64: ::AudioFormat = ::AudioFormat::F64be;
|
||||||
|
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_S16: ::AudioFormat = ::AudioFormat::S16le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_U16: ::AudioFormat = ::AudioFormat::U16le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_S2432: ::AudioFormat = ::AudioFormat::S2432le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_U2432: ::AudioFormat = ::AudioFormat::U2432le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_S32: ::AudioFormat = ::AudioFormat::S32le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_U32: ::AudioFormat = ::AudioFormat::S32le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_S24: ::AudioFormat = ::AudioFormat::S24le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_U24: ::AudioFormat = ::AudioFormat::S24le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_S20: ::AudioFormat = ::AudioFormat::S20le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_U20: ::AudioFormat = ::AudioFormat::S20le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_S18: ::AudioFormat = ::AudioFormat::S18le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_U18: ::AudioFormat = ::AudioFormat::S18le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_F32: ::AudioFormat = ::AudioFormat::F32le;
|
||||||
|
#[cfg(target_endian = "little")]
|
||||||
|
pub const FORMAT_F64: ::AudioFormat = ::AudioFormat::F64le;
|
||||||
|
|
||||||
|
pub struct AudioFormatInfo(&'static ffi::GstAudioFormatInfo);
|
||||||
|
|
||||||
|
impl AudioFormatInfo {
|
||||||
|
pub fn from_format(format: ::AudioFormat) -> AudioFormatInfo {
|
||||||
|
unsafe {
|
||||||
|
let info = ffi::gst_audio_format_get_info(format.to_glib());
|
||||||
|
assert!(!info.is_null());
|
||||||
|
|
||||||
|
AudioFormatInfo(&*info)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn format(&self) -> ::AudioFormat {
|
||||||
|
from_glib(self.0.format)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn name(&self) -> &'static str {
|
||||||
|
unsafe { CStr::from_ptr(self.0.name).to_str().unwrap() }
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn description(&self) -> &'static str {
|
||||||
|
unsafe { CStr::from_ptr(self.0.description).to_str().unwrap() }
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn flags(&self) -> ::AudioFormatFlags {
|
||||||
|
from_glib(self.0.flags)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn endianness(&self) -> AudioEndianness {
|
||||||
|
from_glib(self.0.endianness)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn width(&self) -> i32 {
|
||||||
|
self.0.width
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn depth(&self) -> i32 {
|
||||||
|
self.0.depth
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn unpack_format(&self) -> ::AudioFormat {
|
||||||
|
from_glib(self.0.unpack_format)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn silence(&self) -> &'static [u8] {
|
||||||
|
&self.0.silence
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn unpack(&self, flags: ::AudioPackFlags, dest: &mut [u8], src: &[u8]) {
|
||||||
|
let unpack_format = Self::from_format(self.unpack_format());
|
||||||
|
let unpack_width = unpack_format.width() as usize;
|
||||||
|
|
||||||
|
if unpack_width == 0 || self.0.unpack_func.is_none() {
|
||||||
|
panic!("No unpack format for {:?}", self);
|
||||||
|
}
|
||||||
|
|
||||||
|
let self_width = self.width() as usize;
|
||||||
|
if self_width == 0 {
|
||||||
|
panic!("No width for {:?}", self);
|
||||||
|
}
|
||||||
|
|
||||||
|
if src.len() % (self_width / 8) != 0 {
|
||||||
|
panic!("Incomplete number of samples in src");
|
||||||
|
}
|
||||||
|
|
||||||
|
let nsamples = src.len() / (self_width / 8);
|
||||||
|
|
||||||
|
if dest.len() != nsamples * (unpack_width / 8) {
|
||||||
|
panic!("Invalid dest length");
|
||||||
|
}
|
||||||
|
|
||||||
|
unsafe {
|
||||||
|
(self.0.unpack_func.as_ref().unwrap())(
|
||||||
|
self.0,
|
||||||
|
flags.to_glib(),
|
||||||
|
dest.as_mut_ptr() as *mut _,
|
||||||
|
src.as_ptr() as *mut _,
|
||||||
|
nsamples as i32,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn pack(&self, flags: ::AudioPackFlags, dest: &mut [u8], src: &[u8]) {
|
||||||
|
let unpack_format = Self::from_format(self.unpack_format());
|
||||||
|
let unpack_width = unpack_format.width() as usize;
|
||||||
|
|
||||||
|
if unpack_width == 0 || self.0.pack_func.is_none() {
|
||||||
|
panic!("No unpack format for {:?}", self);
|
||||||
|
}
|
||||||
|
|
||||||
|
let self_width = self.width() as usize;
|
||||||
|
if self_width == 0 {
|
||||||
|
panic!("No width for {:?}", self);
|
||||||
|
}
|
||||||
|
|
||||||
|
if src.len() % (unpack_width / 8) != 0 {
|
||||||
|
panic!("Incomplete number of samples in src");
|
||||||
|
}
|
||||||
|
|
||||||
|
let nsamples = src.len() / (unpack_width / 8);
|
||||||
|
|
||||||
|
if dest.len() != nsamples * (self_width / 8) {
|
||||||
|
panic!("Invalid dest length");
|
||||||
|
}
|
||||||
|
|
||||||
|
unsafe {
|
||||||
|
(self.0.pack_func.as_ref().unwrap())(
|
||||||
|
self.0,
|
||||||
|
flags.to_glib(),
|
||||||
|
src.as_ptr() as *mut _,
|
||||||
|
dest.as_mut_ptr() as *mut _,
|
||||||
|
nsamples as i32,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn fill_silence(&self, dest: &mut [u8]) {
|
||||||
|
let self_width = self.width() as usize;
|
||||||
|
|
||||||
|
if self_width == 0 {
|
||||||
|
panic!("Filling with silence unsupported");
|
||||||
|
}
|
||||||
|
|
||||||
|
if dest.len() % (self_width / 8) != 0 {
|
||||||
|
panic!("Incomplete number of samples in dest");
|
||||||
|
}
|
||||||
|
|
||||||
|
unsafe {
|
||||||
|
ffi::gst_audio_format_fill_silence(self.0, dest.as_mut_ptr() as *mut _, dest.len())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_float(&self) -> bool {
|
||||||
|
self.flags().contains(::AUDIO_FORMAT_FLAG_FLOAT)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_integer(&self) -> bool {
|
||||||
|
self.flags().contains(::AUDIO_FORMAT_FLAG_INTEGER)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_signed(&self) -> bool {
|
||||||
|
self.flags().contains(::AUDIO_FORMAT_FLAG_SIGNED)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
pub fn is_little_endian(&self) -> bool {
|
||||||
|
self.endianness() == AudioEndianness::LittleEndian
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_big_endian(&self) -> bool {
|
||||||
|
self.endianness() == AudioEndianness::BigEndian
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
unsafe impl Sync for AudioFormatInfo {}
|
||||||
|
unsafe impl Send for AudioFormatInfo {}
|
||||||
|
|
||||||
|
impl PartialEq for AudioFormatInfo {
|
||||||
|
fn eq(&self, other: &Self) -> bool {
|
||||||
|
self.format() == other.format()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Eq for AudioFormatInfo {}
|
||||||
|
|
||||||
|
impl fmt::Debug for AudioFormatInfo {
|
||||||
|
fn fmt(&self, f: &mut fmt::Formatter) -> Result<(), fmt::Error> {
|
||||||
|
f.write_str(self.name())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl From<::AudioFormat> for AudioFormatInfo {
|
||||||
|
fn from(f: ::AudioFormat) -> Self {
|
||||||
|
Self::from_format(f)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl str::FromStr for ::AudioFormatInfo {
|
||||||
|
type Err = ();
|
||||||
|
|
||||||
|
fn from_str(s: &str) -> Result<Self, ()> {
|
||||||
|
unsafe {
|
||||||
|
let format = ffi::gst_audio_format_from_string(s.to_glib_none().0);
|
||||||
|
if format == ffi::GST_AUDIO_FORMAT_UNKNOWN {
|
||||||
|
Err(())
|
||||||
|
} else {
|
||||||
|
Ok(AudioFormatInfo::from_format(from_glib(format)))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
use gst;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_get() {
|
||||||
|
gst::init().unwrap();
|
||||||
|
|
||||||
|
let info = AudioFormatInfo::from_format(::AudioFormat::S16le);
|
||||||
|
assert_eq!(info.name(), "S16LE");
|
||||||
|
|
||||||
|
let other_info = "S16LE".parse().unwrap();
|
||||||
|
assert_eq!(info, other_info);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn pack_unpack() {
|
||||||
|
gst::init().unwrap();
|
||||||
|
|
||||||
|
let info = AudioFormatInfo::from_format(::AudioFormat::S16le);
|
||||||
|
let unpack_info = AudioFormatInfo::from_format(info.unpack_format());
|
||||||
|
|
||||||
|
assert!(unpack_info.width() > 0);
|
||||||
|
|
||||||
|
let input = [0, 0, 255, 255, 128, 128, 64, 64];
|
||||||
|
let mut unpacked = [0; 16];
|
||||||
|
let mut output = [0; 8];
|
||||||
|
|
||||||
|
info.unpack(::AUDIO_PACK_FLAG_NONE, &mut unpacked, &input);
|
||||||
|
info.pack(::AUDIO_PACK_FLAG_NONE, &mut output, &unpacked);
|
||||||
|
|
||||||
|
assert_eq!(input, output);
|
||||||
|
}
|
||||||
|
}
|
286
gstreamer-audio/src/audio_info.rs
Normal file
286
gstreamer-audio/src/audio_info.rs
Normal file
|
@ -0,0 +1,286 @@
|
||||||
|
// Copyright (C) 2017 Sebastian Dröge <sebastian@centricular.com>
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||||
|
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||||
|
// option. This file may not be copied, modified, or distributed
|
||||||
|
// except according to those terms.
|
||||||
|
|
||||||
|
use ffi;
|
||||||
|
|
||||||
|
use gst;
|
||||||
|
use gst::miniobject::MiniObject;
|
||||||
|
use glib::translate::{from_glib, from_glib_full, ToGlib};
|
||||||
|
|
||||||
|
use std::mem;
|
||||||
|
use std::ptr;
|
||||||
|
|
||||||
|
pub struct AudioInfo(ffi::GstAudioInfo);
|
||||||
|
|
||||||
|
pub struct AudioInfoBuilder<'a> {
|
||||||
|
format: ::AudioFormat,
|
||||||
|
rate: u32,
|
||||||
|
channels: u32,
|
||||||
|
positions: Option<&'a [::AudioChannelPosition]>,
|
||||||
|
flags: Option<::AudioFlags>,
|
||||||
|
layout: Option<::AudioLayout>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> AudioInfoBuilder<'a> {
|
||||||
|
pub fn build(self) -> Option<AudioInfo> {
|
||||||
|
unsafe {
|
||||||
|
let mut info = mem::uninitialized();
|
||||||
|
let mut positions_raw = Vec::new();
|
||||||
|
|
||||||
|
let positions_ptr = match self.positions {
|
||||||
|
Some(p) => {
|
||||||
|
if p.len() != self.channels as usize {
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
|
||||||
|
positions_raw.reserve(self.channels as usize);
|
||||||
|
for i in p {
|
||||||
|
positions_raw.push(i.to_glib());
|
||||||
|
}
|
||||||
|
|
||||||
|
let valid: bool = from_glib(ffi::gst_audio_check_valid_channel_positions(
|
||||||
|
positions_raw.as_mut_ptr(),
|
||||||
|
self.channels as i32,
|
||||||
|
true.to_glib(),
|
||||||
|
));
|
||||||
|
if !valid {
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
|
||||||
|
positions_raw.as_ptr()
|
||||||
|
}
|
||||||
|
None => ptr::null(),
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
ffi::gst_audio_info_set_format(
|
||||||
|
&mut info,
|
||||||
|
self.format.to_glib(),
|
||||||
|
self.rate as i32,
|
||||||
|
self.channels as i32,
|
||||||
|
positions_ptr,
|
||||||
|
);
|
||||||
|
|
||||||
|
if info.finfo.is_null() || info.rate <= 0 || info.channels <= 0 {
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
|
||||||
|
if let Some(flags) = self.flags {
|
||||||
|
info.flags = flags.to_glib();
|
||||||
|
}
|
||||||
|
|
||||||
|
if let Some(layout) = self.layout {
|
||||||
|
info.layout = layout.to_glib();
|
||||||
|
}
|
||||||
|
|
||||||
|
Some(AudioInfo(info))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn positions(self, positions: &'a [::AudioChannelPosition]) -> AudioInfoBuilder<'a> {
|
||||||
|
Self {
|
||||||
|
positions: Some(positions),
|
||||||
|
..self
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn flags(self, flags: ::AudioFlags) -> Self {
|
||||||
|
Self {
|
||||||
|
flags: Some(flags),
|
||||||
|
..self
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn layout(self, layout: ::AudioLayout) -> Self {
|
||||||
|
Self {
|
||||||
|
layout: Some(layout),
|
||||||
|
..self
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl AudioInfo {
|
||||||
|
pub fn new<'a>(format: ::AudioFormat, rate: u32, channels: u32) -> AudioInfoBuilder<'a> {
|
||||||
|
AudioInfoBuilder {
|
||||||
|
format: format,
|
||||||
|
rate: rate,
|
||||||
|
channels: channels,
|
||||||
|
positions: None,
|
||||||
|
flags: None,
|
||||||
|
layout: None,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn from_caps(caps: &gst::Caps) -> Option<Self> {
|
||||||
|
unsafe {
|
||||||
|
let mut info = mem::uninitialized();
|
||||||
|
if from_glib(ffi::gst_audio_info_from_caps(&mut info, caps.as_ptr())) {
|
||||||
|
Some(AudioInfo(info))
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn to_caps(&self) -> Option<gst::Caps> {
|
||||||
|
unsafe {
|
||||||
|
let caps = ffi::gst_audio_info_to_caps(&self.0);
|
||||||
|
if caps.is_null() {
|
||||||
|
None
|
||||||
|
} else {
|
||||||
|
Some(from_glib_full(caps))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn convert(
|
||||||
|
&self,
|
||||||
|
src_fmt: gst::Format,
|
||||||
|
src_val: i64,
|
||||||
|
dest_fmt: gst::Format,
|
||||||
|
) -> Option<i64> {
|
||||||
|
unsafe {
|
||||||
|
let mut dest_val = mem::uninitialized();
|
||||||
|
if from_glib(ffi::gst_audio_info_convert(
|
||||||
|
&self.0,
|
||||||
|
src_fmt.to_glib(),
|
||||||
|
src_val,
|
||||||
|
dest_fmt.to_glib(),
|
||||||
|
&mut dest_val,
|
||||||
|
)) {
|
||||||
|
Some(dest_val)
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn format(&self) -> ::AudioFormat {
|
||||||
|
unsafe { from_glib((*self.0.finfo).format) }
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn format_info(&self) -> ::AudioFormatInfo {
|
||||||
|
::AudioFormatInfo::from_format(self.format())
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn layout(&self) -> ::AudioLayout {
|
||||||
|
from_glib(self.0.layout)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn rate(&self) -> u32 {
|
||||||
|
self.0.rate as u32
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn channels(&self) -> u32 {
|
||||||
|
self.0.channels as u32
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn bpf(&self) -> u32 {
|
||||||
|
self.0.bpf as u32
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn positions(&self) -> Vec<::AudioChannelPosition> {
|
||||||
|
let mut v = Vec::with_capacity(self.0.channels as usize);
|
||||||
|
for i in 0..(self.0.channels as usize) {
|
||||||
|
v.push(from_glib(self.0.position[i]));
|
||||||
|
}
|
||||||
|
|
||||||
|
v
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Clone for AudioInfo {
|
||||||
|
fn clone(&self) -> Self {
|
||||||
|
unsafe { AudioInfo(ptr::read(&self.0)) }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl PartialEq for AudioInfo {
|
||||||
|
fn eq(&self, other: &Self) -> bool {
|
||||||
|
unsafe { from_glib(ffi::gst_audio_info_is_equal(&self.0, &other.0)) }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Eq for AudioInfo {}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
use gst;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_new() {
|
||||||
|
gst::init().unwrap();
|
||||||
|
|
||||||
|
let info = AudioInfo::new(::AudioFormat::S16le, 48000, 2)
|
||||||
|
.build()
|
||||||
|
.unwrap();
|
||||||
|
assert_eq!(info.format(), ::AudioFormat::S16le);
|
||||||
|
assert_eq!(info.rate(), 48000);
|
||||||
|
assert_eq!(info.channels(), 2);
|
||||||
|
assert_eq!(
|
||||||
|
&info.positions(),
|
||||||
|
&[
|
||||||
|
::AudioChannelPosition::FrontLeft,
|
||||||
|
::AudioChannelPosition::FrontRight
|
||||||
|
]
|
||||||
|
);
|
||||||
|
|
||||||
|
let positions = [
|
||||||
|
::AudioChannelPosition::RearLeft,
|
||||||
|
::AudioChannelPosition::RearRight,
|
||||||
|
];
|
||||||
|
let info = AudioInfo::new(::AudioFormat::S16le, 48000, 2)
|
||||||
|
.positions(&positions)
|
||||||
|
.build()
|
||||||
|
.unwrap();
|
||||||
|
assert_eq!(info.format(), ::AudioFormat::S16le);
|
||||||
|
assert_eq!(info.rate(), 48000);
|
||||||
|
assert_eq!(info.channels(), 2);
|
||||||
|
assert_eq!(
|
||||||
|
&info.positions(),
|
||||||
|
&[
|
||||||
|
::AudioChannelPosition::RearLeft,
|
||||||
|
::AudioChannelPosition::RearRight
|
||||||
|
]
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_from_to_caps() {
|
||||||
|
gst::init().unwrap();
|
||||||
|
|
||||||
|
let caps = gst::Caps::new_simple(
|
||||||
|
"audio/x-raw",
|
||||||
|
&[
|
||||||
|
("format", &"S16LE"),
|
||||||
|
("rate", &48000),
|
||||||
|
("channels", &2),
|
||||||
|
("layout", &"interleaved"),
|
||||||
|
("channel-mask", &gst::Bitmask::new(0x3)),
|
||||||
|
],
|
||||||
|
);
|
||||||
|
let info = AudioInfo::from_caps(&caps).unwrap();
|
||||||
|
assert_eq!(info.format(), ::AudioFormat::S16le);
|
||||||
|
assert_eq!(info.rate(), 48000);
|
||||||
|
assert_eq!(info.channels(), 2);
|
||||||
|
assert_eq!(
|
||||||
|
&info.positions(),
|
||||||
|
&[
|
||||||
|
::AudioChannelPosition::FrontLeft,
|
||||||
|
::AudioChannelPosition::FrontRight
|
||||||
|
]
|
||||||
|
);
|
||||||
|
|
||||||
|
let caps2 = info.to_caps().unwrap();
|
||||||
|
assert_eq!(caps, caps2);
|
||||||
|
|
||||||
|
let info2 = AudioInfo::from_caps(&caps2).unwrap();
|
||||||
|
assert!(info == info2);
|
||||||
|
}
|
||||||
|
}
|
359
gstreamer-audio/src/auto/enums.rs
Normal file
359
gstreamer-audio/src/auto/enums.rs
Normal file
|
@ -0,0 +1,359 @@
|
||||||
|
// This file was generated by gir (3294959+) from gir-files (???)
|
||||||
|
// DO NOT EDIT
|
||||||
|
|
||||||
|
use ffi;
|
||||||
|
use glib::Type;
|
||||||
|
use glib::StaticType;
|
||||||
|
use glib::value::{Value, SetValue, FromValue, FromValueOptional};
|
||||||
|
use gobject_ffi;
|
||||||
|
use glib::translate::*;
|
||||||
|
use std;
|
||||||
|
|
||||||
|
#[derive(Clone, Copy, Debug, Eq, PartialEq, Hash)]
|
||||||
|
pub enum AudioChannelPosition {
|
||||||
|
None,
|
||||||
|
Mono,
|
||||||
|
Invalid,
|
||||||
|
FrontLeft,
|
||||||
|
FrontRight,
|
||||||
|
FrontCenter,
|
||||||
|
Lfe1,
|
||||||
|
RearLeft,
|
||||||
|
RearRight,
|
||||||
|
FrontLeftOfCenter,
|
||||||
|
FrontRightOfCenter,
|
||||||
|
RearCenter,
|
||||||
|
Lfe2,
|
||||||
|
SideLeft,
|
||||||
|
SideRight,
|
||||||
|
TopFrontLeft,
|
||||||
|
TopFrontRight,
|
||||||
|
TopFrontCenter,
|
||||||
|
TopCenter,
|
||||||
|
TopRearLeft,
|
||||||
|
TopRearRight,
|
||||||
|
TopSideLeft,
|
||||||
|
TopSideRight,
|
||||||
|
TopRearCenter,
|
||||||
|
BottomFrontCenter,
|
||||||
|
BottomFrontLeft,
|
||||||
|
BottomFrontRight,
|
||||||
|
WideLeft,
|
||||||
|
WideRight,
|
||||||
|
SurroundLeft,
|
||||||
|
SurroundRight,
|
||||||
|
#[doc(hidden)]
|
||||||
|
__Unknown(i32),
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl ToGlib for AudioChannelPosition {
|
||||||
|
type GlibType = ffi::GstAudioChannelPosition;
|
||||||
|
|
||||||
|
fn to_glib(&self) -> ffi::GstAudioChannelPosition {
|
||||||
|
match *self {
|
||||||
|
AudioChannelPosition::None => ffi::GST_AUDIO_CHANNEL_POSITION_NONE,
|
||||||
|
AudioChannelPosition::Mono => ffi::GST_AUDIO_CHANNEL_POSITION_MONO,
|
||||||
|
AudioChannelPosition::Invalid => ffi::GST_AUDIO_CHANNEL_POSITION_INVALID,
|
||||||
|
AudioChannelPosition::FrontLeft => ffi::GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT,
|
||||||
|
AudioChannelPosition::FrontRight => ffi::GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT,
|
||||||
|
AudioChannelPosition::FrontCenter => ffi::GST_AUDIO_CHANNEL_POSITION_FRONT_CENTER,
|
||||||
|
AudioChannelPosition::Lfe1 => ffi::GST_AUDIO_CHANNEL_POSITION_LFE1,
|
||||||
|
AudioChannelPosition::RearLeft => ffi::GST_AUDIO_CHANNEL_POSITION_REAR_LEFT,
|
||||||
|
AudioChannelPosition::RearRight => ffi::GST_AUDIO_CHANNEL_POSITION_REAR_RIGHT,
|
||||||
|
AudioChannelPosition::FrontLeftOfCenter => ffi::GST_AUDIO_CHANNEL_POSITION_FRONT_LEFT_OF_CENTER,
|
||||||
|
AudioChannelPosition::FrontRightOfCenter => ffi::GST_AUDIO_CHANNEL_POSITION_FRONT_RIGHT_OF_CENTER,
|
||||||
|
AudioChannelPosition::RearCenter => ffi::GST_AUDIO_CHANNEL_POSITION_REAR_CENTER,
|
||||||
|
AudioChannelPosition::Lfe2 => ffi::GST_AUDIO_CHANNEL_POSITION_LFE2,
|
||||||
|
AudioChannelPosition::SideLeft => ffi::GST_AUDIO_CHANNEL_POSITION_SIDE_LEFT,
|
||||||
|
AudioChannelPosition::SideRight => ffi::GST_AUDIO_CHANNEL_POSITION_SIDE_RIGHT,
|
||||||
|
AudioChannelPosition::TopFrontLeft => ffi::GST_AUDIO_CHANNEL_POSITION_TOP_FRONT_LEFT,
|
||||||
|
AudioChannelPosition::TopFrontRight => ffi::GST_AUDIO_CHANNEL_POSITION_TOP_FRONT_RIGHT,
|
||||||
|
AudioChannelPosition::TopFrontCenter => ffi::GST_AUDIO_CHANNEL_POSITION_TOP_FRONT_CENTER,
|
||||||
|
AudioChannelPosition::TopCenter => ffi::GST_AUDIO_CHANNEL_POSITION_TOP_CENTER,
|
||||||
|
AudioChannelPosition::TopRearLeft => ffi::GST_AUDIO_CHANNEL_POSITION_TOP_REAR_LEFT,
|
||||||
|
AudioChannelPosition::TopRearRight => ffi::GST_AUDIO_CHANNEL_POSITION_TOP_REAR_RIGHT,
|
||||||
|
AudioChannelPosition::TopSideLeft => ffi::GST_AUDIO_CHANNEL_POSITION_TOP_SIDE_LEFT,
|
||||||
|
AudioChannelPosition::TopSideRight => ffi::GST_AUDIO_CHANNEL_POSITION_TOP_SIDE_RIGHT,
|
||||||
|
AudioChannelPosition::TopRearCenter => ffi::GST_AUDIO_CHANNEL_POSITION_TOP_REAR_CENTER,
|
||||||
|
AudioChannelPosition::BottomFrontCenter => ffi::GST_AUDIO_CHANNEL_POSITION_BOTTOM_FRONT_CENTER,
|
||||||
|
AudioChannelPosition::BottomFrontLeft => ffi::GST_AUDIO_CHANNEL_POSITION_BOTTOM_FRONT_LEFT,
|
||||||
|
AudioChannelPosition::BottomFrontRight => ffi::GST_AUDIO_CHANNEL_POSITION_BOTTOM_FRONT_RIGHT,
|
||||||
|
AudioChannelPosition::WideLeft => ffi::GST_AUDIO_CHANNEL_POSITION_WIDE_LEFT,
|
||||||
|
AudioChannelPosition::WideRight => ffi::GST_AUDIO_CHANNEL_POSITION_WIDE_RIGHT,
|
||||||
|
AudioChannelPosition::SurroundLeft => ffi::GST_AUDIO_CHANNEL_POSITION_SURROUND_LEFT,
|
||||||
|
AudioChannelPosition::SurroundRight => ffi::GST_AUDIO_CHANNEL_POSITION_SURROUND_RIGHT,
|
||||||
|
AudioChannelPosition::__Unknown(value) => unsafe{std::mem::transmute(value)}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl FromGlib<ffi::GstAudioChannelPosition> for AudioChannelPosition {
|
||||||
|
fn from_glib(value: ffi::GstAudioChannelPosition) -> Self {
|
||||||
|
skip_assert_initialized!();
|
||||||
|
match value as i32 {
|
||||||
|
-3 => AudioChannelPosition::None,
|
||||||
|
-2 => AudioChannelPosition::Mono,
|
||||||
|
-1 => AudioChannelPosition::Invalid,
|
||||||
|
0 => AudioChannelPosition::FrontLeft,
|
||||||
|
1 => AudioChannelPosition::FrontRight,
|
||||||
|
2 => AudioChannelPosition::FrontCenter,
|
||||||
|
3 => AudioChannelPosition::Lfe1,
|
||||||
|
4 => AudioChannelPosition::RearLeft,
|
||||||
|
5 => AudioChannelPosition::RearRight,
|
||||||
|
6 => AudioChannelPosition::FrontLeftOfCenter,
|
||||||
|
7 => AudioChannelPosition::FrontRightOfCenter,
|
||||||
|
8 => AudioChannelPosition::RearCenter,
|
||||||
|
9 => AudioChannelPosition::Lfe2,
|
||||||
|
10 => AudioChannelPosition::SideLeft,
|
||||||
|
11 => AudioChannelPosition::SideRight,
|
||||||
|
12 => AudioChannelPosition::TopFrontLeft,
|
||||||
|
13 => AudioChannelPosition::TopFrontRight,
|
||||||
|
14 => AudioChannelPosition::TopFrontCenter,
|
||||||
|
15 => AudioChannelPosition::TopCenter,
|
||||||
|
16 => AudioChannelPosition::TopRearLeft,
|
||||||
|
17 => AudioChannelPosition::TopRearRight,
|
||||||
|
18 => AudioChannelPosition::TopSideLeft,
|
||||||
|
19 => AudioChannelPosition::TopSideRight,
|
||||||
|
20 => AudioChannelPosition::TopRearCenter,
|
||||||
|
21 => AudioChannelPosition::BottomFrontCenter,
|
||||||
|
22 => AudioChannelPosition::BottomFrontLeft,
|
||||||
|
23 => AudioChannelPosition::BottomFrontRight,
|
||||||
|
24 => AudioChannelPosition::WideLeft,
|
||||||
|
25 => AudioChannelPosition::WideRight,
|
||||||
|
26 => AudioChannelPosition::SurroundLeft,
|
||||||
|
27 => AudioChannelPosition::SurroundRight,
|
||||||
|
value => AudioChannelPosition::__Unknown(value),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl StaticType for AudioChannelPosition {
|
||||||
|
fn static_type() -> Type {
|
||||||
|
unsafe { from_glib(ffi::gst_audio_channel_position_get_type()) }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValueOptional<'a> for AudioChannelPosition {
|
||||||
|
unsafe fn from_value_optional(value: &Value) -> Option<Self> {
|
||||||
|
Some(FromValue::from_value(value))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValue<'a> for AudioChannelPosition {
|
||||||
|
unsafe fn from_value(value: &Value) -> Self {
|
||||||
|
from_glib(std::mem::transmute::<i32, ffi::GstAudioChannelPosition>(gobject_ffi::g_value_get_enum(value.to_glib_none().0)))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl SetValue for AudioChannelPosition {
|
||||||
|
unsafe fn set_value(value: &mut Value, this: &Self) {
|
||||||
|
gobject_ffi::g_value_set_enum(value.to_glib_none_mut().0, this.to_glib() as i32)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Clone, Copy, Debug, Eq, PartialEq, Hash)]
|
||||||
|
pub enum AudioFormat {
|
||||||
|
Unknown,
|
||||||
|
Encoded,
|
||||||
|
S8,
|
||||||
|
U8,
|
||||||
|
S16le,
|
||||||
|
S16be,
|
||||||
|
U16le,
|
||||||
|
U16be,
|
||||||
|
S2432le,
|
||||||
|
S2432be,
|
||||||
|
U2432le,
|
||||||
|
U2432be,
|
||||||
|
S32le,
|
||||||
|
S32be,
|
||||||
|
U32le,
|
||||||
|
U32be,
|
||||||
|
S24le,
|
||||||
|
S24be,
|
||||||
|
U24le,
|
||||||
|
U24be,
|
||||||
|
S20le,
|
||||||
|
S20be,
|
||||||
|
U20le,
|
||||||
|
U20be,
|
||||||
|
S18le,
|
||||||
|
S18be,
|
||||||
|
U18le,
|
||||||
|
U18be,
|
||||||
|
F32le,
|
||||||
|
F32be,
|
||||||
|
F64le,
|
||||||
|
F64be,
|
||||||
|
#[doc(hidden)]
|
||||||
|
__Unknown(i32),
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl ToGlib for AudioFormat {
|
||||||
|
type GlibType = ffi::GstAudioFormat;
|
||||||
|
|
||||||
|
fn to_glib(&self) -> ffi::GstAudioFormat {
|
||||||
|
match *self {
|
||||||
|
AudioFormat::Unknown => ffi::GST_AUDIO_FORMAT_UNKNOWN,
|
||||||
|
AudioFormat::Encoded => ffi::GST_AUDIO_FORMAT_ENCODED,
|
||||||
|
AudioFormat::S8 => ffi::GST_AUDIO_FORMAT_S8,
|
||||||
|
AudioFormat::U8 => ffi::GST_AUDIO_FORMAT_U8,
|
||||||
|
AudioFormat::S16le => ffi::GST_AUDIO_FORMAT_S16LE,
|
||||||
|
AudioFormat::S16be => ffi::GST_AUDIO_FORMAT_S16BE,
|
||||||
|
AudioFormat::U16le => ffi::GST_AUDIO_FORMAT_U16LE,
|
||||||
|
AudioFormat::U16be => ffi::GST_AUDIO_FORMAT_U16BE,
|
||||||
|
AudioFormat::S2432le => ffi::GST_AUDIO_FORMAT_S24_32LE,
|
||||||
|
AudioFormat::S2432be => ffi::GST_AUDIO_FORMAT_S24_32BE,
|
||||||
|
AudioFormat::U2432le => ffi::GST_AUDIO_FORMAT_U24_32LE,
|
||||||
|
AudioFormat::U2432be => ffi::GST_AUDIO_FORMAT_U24_32BE,
|
||||||
|
AudioFormat::S32le => ffi::GST_AUDIO_FORMAT_S32LE,
|
||||||
|
AudioFormat::S32be => ffi::GST_AUDIO_FORMAT_S32BE,
|
||||||
|
AudioFormat::U32le => ffi::GST_AUDIO_FORMAT_U32LE,
|
||||||
|
AudioFormat::U32be => ffi::GST_AUDIO_FORMAT_U32BE,
|
||||||
|
AudioFormat::S24le => ffi::GST_AUDIO_FORMAT_S24LE,
|
||||||
|
AudioFormat::S24be => ffi::GST_AUDIO_FORMAT_S24BE,
|
||||||
|
AudioFormat::U24le => ffi::GST_AUDIO_FORMAT_U24LE,
|
||||||
|
AudioFormat::U24be => ffi::GST_AUDIO_FORMAT_U24BE,
|
||||||
|
AudioFormat::S20le => ffi::GST_AUDIO_FORMAT_S20LE,
|
||||||
|
AudioFormat::S20be => ffi::GST_AUDIO_FORMAT_S20BE,
|
||||||
|
AudioFormat::U20le => ffi::GST_AUDIO_FORMAT_U20LE,
|
||||||
|
AudioFormat::U20be => ffi::GST_AUDIO_FORMAT_U20BE,
|
||||||
|
AudioFormat::S18le => ffi::GST_AUDIO_FORMAT_S18LE,
|
||||||
|
AudioFormat::S18be => ffi::GST_AUDIO_FORMAT_S18BE,
|
||||||
|
AudioFormat::U18le => ffi::GST_AUDIO_FORMAT_U18LE,
|
||||||
|
AudioFormat::U18be => ffi::GST_AUDIO_FORMAT_U18BE,
|
||||||
|
AudioFormat::F32le => ffi::GST_AUDIO_FORMAT_F32LE,
|
||||||
|
AudioFormat::F32be => ffi::GST_AUDIO_FORMAT_F32BE,
|
||||||
|
AudioFormat::F64le => ffi::GST_AUDIO_FORMAT_F64LE,
|
||||||
|
AudioFormat::F64be => ffi::GST_AUDIO_FORMAT_F64BE,
|
||||||
|
AudioFormat::__Unknown(value) => unsafe{std::mem::transmute(value)}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl FromGlib<ffi::GstAudioFormat> for AudioFormat {
|
||||||
|
fn from_glib(value: ffi::GstAudioFormat) -> Self {
|
||||||
|
skip_assert_initialized!();
|
||||||
|
match value as i32 {
|
||||||
|
0 => AudioFormat::Unknown,
|
||||||
|
1 => AudioFormat::Encoded,
|
||||||
|
2 => AudioFormat::S8,
|
||||||
|
3 => AudioFormat::U8,
|
||||||
|
4 => AudioFormat::S16le,
|
||||||
|
5 => AudioFormat::S16be,
|
||||||
|
6 => AudioFormat::U16le,
|
||||||
|
7 => AudioFormat::U16be,
|
||||||
|
8 => AudioFormat::S2432le,
|
||||||
|
9 => AudioFormat::S2432be,
|
||||||
|
10 => AudioFormat::U2432le,
|
||||||
|
11 => AudioFormat::U2432be,
|
||||||
|
12 => AudioFormat::S32le,
|
||||||
|
13 => AudioFormat::S32be,
|
||||||
|
14 => AudioFormat::U32le,
|
||||||
|
15 => AudioFormat::U32be,
|
||||||
|
16 => AudioFormat::S24le,
|
||||||
|
17 => AudioFormat::S24be,
|
||||||
|
18 => AudioFormat::U24le,
|
||||||
|
19 => AudioFormat::U24be,
|
||||||
|
20 => AudioFormat::S20le,
|
||||||
|
21 => AudioFormat::S20be,
|
||||||
|
22 => AudioFormat::U20le,
|
||||||
|
23 => AudioFormat::U20be,
|
||||||
|
24 => AudioFormat::S18le,
|
||||||
|
25 => AudioFormat::S18be,
|
||||||
|
26 => AudioFormat::U18le,
|
||||||
|
27 => AudioFormat::U18be,
|
||||||
|
28 => AudioFormat::F32le,
|
||||||
|
29 => AudioFormat::F32be,
|
||||||
|
30 => AudioFormat::F64le,
|
||||||
|
31 => AudioFormat::F64be,
|
||||||
|
value => AudioFormat::__Unknown(value),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl StaticType for AudioFormat {
|
||||||
|
fn static_type() -> Type {
|
||||||
|
unsafe { from_glib(ffi::gst_audio_format_get_type()) }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValueOptional<'a> for AudioFormat {
|
||||||
|
unsafe fn from_value_optional(value: &Value) -> Option<Self> {
|
||||||
|
Some(FromValue::from_value(value))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValue<'a> for AudioFormat {
|
||||||
|
unsafe fn from_value(value: &Value) -> Self {
|
||||||
|
from_glib(std::mem::transmute::<i32, ffi::GstAudioFormat>(gobject_ffi::g_value_get_enum(value.to_glib_none().0)))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl SetValue for AudioFormat {
|
||||||
|
unsafe fn set_value(value: &mut Value, this: &Self) {
|
||||||
|
gobject_ffi::g_value_set_enum(value.to_glib_none_mut().0, this.to_glib() as i32)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Clone, Copy, Debug, Eq, PartialEq, Hash)]
|
||||||
|
pub enum AudioLayout {
|
||||||
|
Interleaved,
|
||||||
|
NonInterleaved,
|
||||||
|
#[doc(hidden)]
|
||||||
|
__Unknown(i32),
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl ToGlib for AudioLayout {
|
||||||
|
type GlibType = ffi::GstAudioLayout;
|
||||||
|
|
||||||
|
fn to_glib(&self) -> ffi::GstAudioLayout {
|
||||||
|
match *self {
|
||||||
|
AudioLayout::Interleaved => ffi::GST_AUDIO_LAYOUT_INTERLEAVED,
|
||||||
|
AudioLayout::NonInterleaved => ffi::GST_AUDIO_LAYOUT_NON_INTERLEAVED,
|
||||||
|
AudioLayout::__Unknown(value) => unsafe{std::mem::transmute(value)}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl FromGlib<ffi::GstAudioLayout> for AudioLayout {
|
||||||
|
fn from_glib(value: ffi::GstAudioLayout) -> Self {
|
||||||
|
skip_assert_initialized!();
|
||||||
|
match value as i32 {
|
||||||
|
0 => AudioLayout::Interleaved,
|
||||||
|
1 => AudioLayout::NonInterleaved,
|
||||||
|
value => AudioLayout::__Unknown(value),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl StaticType for AudioLayout {
|
||||||
|
fn static_type() -> Type {
|
||||||
|
unsafe { from_glib(ffi::gst_audio_layout_get_type()) }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValueOptional<'a> for AudioLayout {
|
||||||
|
unsafe fn from_value_optional(value: &Value) -> Option<Self> {
|
||||||
|
Some(FromValue::from_value(value))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValue<'a> for AudioLayout {
|
||||||
|
unsafe fn from_value(value: &Value) -> Self {
|
||||||
|
from_glib(std::mem::transmute::<i32, ffi::GstAudioLayout>(gobject_ffi::g_value_get_enum(value.to_glib_none().0)))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl SetValue for AudioLayout {
|
||||||
|
unsafe fn set_value(value: &mut Value, this: &Self) {
|
||||||
|
gobject_ffi::g_value_set_enum(value.to_glib_none_mut().0, this.to_glib() as i32)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
157
gstreamer-audio/src/auto/flags.rs
Normal file
157
gstreamer-audio/src/auto/flags.rs
Normal file
|
@ -0,0 +1,157 @@
|
||||||
|
// This file was generated by gir (3294959+) from gir-files (???)
|
||||||
|
// DO NOT EDIT
|
||||||
|
|
||||||
|
use ffi;
|
||||||
|
use glib::Type;
|
||||||
|
use glib::StaticType;
|
||||||
|
use glib::value::{Value, SetValue, FromValue, FromValueOptional};
|
||||||
|
use gobject_ffi;
|
||||||
|
use glib::translate::*;
|
||||||
|
|
||||||
|
bitflags! {
|
||||||
|
pub struct AudioFlags: u32 {
|
||||||
|
const AUDIO_FLAG_NONE = 0;
|
||||||
|
const AUDIO_FLAG_UNPOSITIONED = 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl ToGlib for AudioFlags {
|
||||||
|
type GlibType = ffi::GstAudioFlags;
|
||||||
|
|
||||||
|
fn to_glib(&self) -> ffi::GstAudioFlags {
|
||||||
|
ffi::GstAudioFlags::from_bits_truncate(self.bits())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl FromGlib<ffi::GstAudioFlags> for AudioFlags {
|
||||||
|
fn from_glib(value: ffi::GstAudioFlags) -> AudioFlags {
|
||||||
|
skip_assert_initialized!();
|
||||||
|
AudioFlags::from_bits_truncate(value.bits())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl StaticType for AudioFlags {
|
||||||
|
fn static_type() -> Type {
|
||||||
|
unsafe { from_glib(ffi::gst_audio_flags_get_type()) }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValueOptional<'a> for AudioFlags {
|
||||||
|
unsafe fn from_value_optional(value: &Value) -> Option<Self> {
|
||||||
|
Some(FromValue::from_value(value))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValue<'a> for AudioFlags {
|
||||||
|
unsafe fn from_value(value: &Value) -> Self {
|
||||||
|
from_glib(ffi::GstAudioFlags::from_bits_truncate(gobject_ffi::g_value_get_flags(value.to_glib_none().0)))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl SetValue for AudioFlags {
|
||||||
|
unsafe fn set_value(value: &mut Value, this: &Self) {
|
||||||
|
gobject_ffi::g_value_set_flags(value.to_glib_none_mut().0, this.to_glib().bits())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bitflags! {
|
||||||
|
pub struct AudioFormatFlags: u32 {
|
||||||
|
const AUDIO_FORMAT_FLAG_INTEGER = 1;
|
||||||
|
const AUDIO_FORMAT_FLAG_FLOAT = 2;
|
||||||
|
const AUDIO_FORMAT_FLAG_SIGNED = 4;
|
||||||
|
const AUDIO_FORMAT_FLAG_COMPLEX = 16;
|
||||||
|
const AUDIO_FORMAT_FLAG_UNPACK = 32;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl ToGlib for AudioFormatFlags {
|
||||||
|
type GlibType = ffi::GstAudioFormatFlags;
|
||||||
|
|
||||||
|
fn to_glib(&self) -> ffi::GstAudioFormatFlags {
|
||||||
|
ffi::GstAudioFormatFlags::from_bits_truncate(self.bits())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl FromGlib<ffi::GstAudioFormatFlags> for AudioFormatFlags {
|
||||||
|
fn from_glib(value: ffi::GstAudioFormatFlags) -> AudioFormatFlags {
|
||||||
|
skip_assert_initialized!();
|
||||||
|
AudioFormatFlags::from_bits_truncate(value.bits())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl StaticType for AudioFormatFlags {
|
||||||
|
fn static_type() -> Type {
|
||||||
|
unsafe { from_glib(ffi::gst_audio_format_flags_get_type()) }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValueOptional<'a> for AudioFormatFlags {
|
||||||
|
unsafe fn from_value_optional(value: &Value) -> Option<Self> {
|
||||||
|
Some(FromValue::from_value(value))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValue<'a> for AudioFormatFlags {
|
||||||
|
unsafe fn from_value(value: &Value) -> Self {
|
||||||
|
from_glib(ffi::GstAudioFormatFlags::from_bits_truncate(gobject_ffi::g_value_get_flags(value.to_glib_none().0)))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl SetValue for AudioFormatFlags {
|
||||||
|
unsafe fn set_value(value: &mut Value, this: &Self) {
|
||||||
|
gobject_ffi::g_value_set_flags(value.to_glib_none_mut().0, this.to_glib().bits())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bitflags! {
|
||||||
|
pub struct AudioPackFlags: u32 {
|
||||||
|
const AUDIO_PACK_FLAG_NONE = 0;
|
||||||
|
const AUDIO_PACK_FLAG_TRUNCATE_RANGE = 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl ToGlib for AudioPackFlags {
|
||||||
|
type GlibType = ffi::GstAudioPackFlags;
|
||||||
|
|
||||||
|
fn to_glib(&self) -> ffi::GstAudioPackFlags {
|
||||||
|
ffi::GstAudioPackFlags::from_bits_truncate(self.bits())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
impl FromGlib<ffi::GstAudioPackFlags> for AudioPackFlags {
|
||||||
|
fn from_glib(value: ffi::GstAudioPackFlags) -> AudioPackFlags {
|
||||||
|
skip_assert_initialized!();
|
||||||
|
AudioPackFlags::from_bits_truncate(value.bits())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl StaticType for AudioPackFlags {
|
||||||
|
fn static_type() -> Type {
|
||||||
|
unsafe { from_glib(ffi::gst_audio_pack_flags_get_type()) }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValueOptional<'a> for AudioPackFlags {
|
||||||
|
unsafe fn from_value_optional(value: &Value) -> Option<Self> {
|
||||||
|
Some(FromValue::from_value(value))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FromValue<'a> for AudioPackFlags {
|
||||||
|
unsafe fn from_value(value: &Value) -> Self {
|
||||||
|
from_glib(ffi::GstAudioPackFlags::from_bits_truncate(gobject_ffi::g_value_get_flags(value.to_glib_none().0)))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl SetValue for AudioPackFlags {
|
||||||
|
unsafe fn set_value(value: &mut Value, this: &Self) {
|
||||||
|
gobject_ffi::g_value_set_flags(value.to_glib_none_mut().0, this.to_glib().bits())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
25
gstreamer-audio/src/auto/mod.rs
Normal file
25
gstreamer-audio/src/auto/mod.rs
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
// This file was generated by gir (3294959+) from gir-files (???)
|
||||||
|
// DO NOT EDIT
|
||||||
|
|
||||||
|
mod enums;
|
||||||
|
pub use self::enums::AudioChannelPosition;
|
||||||
|
pub use self::enums::AudioFormat;
|
||||||
|
pub use self::enums::AudioLayout;
|
||||||
|
|
||||||
|
mod flags;
|
||||||
|
pub use self::flags::AudioFlags;
|
||||||
|
pub use self::flags::AUDIO_FLAG_NONE;
|
||||||
|
pub use self::flags::AUDIO_FLAG_UNPOSITIONED;
|
||||||
|
pub use self::flags::AudioFormatFlags;
|
||||||
|
pub use self::flags::AUDIO_FORMAT_FLAG_INTEGER;
|
||||||
|
pub use self::flags::AUDIO_FORMAT_FLAG_FLOAT;
|
||||||
|
pub use self::flags::AUDIO_FORMAT_FLAG_SIGNED;
|
||||||
|
pub use self::flags::AUDIO_FORMAT_FLAG_COMPLEX;
|
||||||
|
pub use self::flags::AUDIO_FORMAT_FLAG_UNPACK;
|
||||||
|
pub use self::flags::AudioPackFlags;
|
||||||
|
pub use self::flags::AUDIO_PACK_FLAG_NONE;
|
||||||
|
pub use self::flags::AUDIO_PACK_FLAG_TRUNCATE_RANGE;
|
||||||
|
|
||||||
|
#[doc(hidden)]
|
||||||
|
pub mod traits {
|
||||||
|
}
|
48
gstreamer-audio/src/lib.rs
Normal file
48
gstreamer-audio/src/lib.rs
Normal file
|
@ -0,0 +1,48 @@
|
||||||
|
// Copyright (C) 2017 Sebastian Dröge <sebastian@centricular.com>
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||||
|
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||||
|
// option. This file may not be copied, modified, or distributed
|
||||||
|
// except according to those terms.
|
||||||
|
|
||||||
|
#[macro_use]
|
||||||
|
extern crate bitflags;
|
||||||
|
extern crate libc;
|
||||||
|
#[macro_use]
|
||||||
|
extern crate lazy_static;
|
||||||
|
|
||||||
|
extern crate glib_sys as glib_ffi;
|
||||||
|
extern crate gobject_sys as gobject_ffi;
|
||||||
|
extern crate gstreamer_sys as gst_ffi;
|
||||||
|
extern crate gstreamer_audio_sys as ffi;
|
||||||
|
extern crate gstreamer as gst;
|
||||||
|
|
||||||
|
#[macro_use]
|
||||||
|
extern crate glib;
|
||||||
|
|
||||||
|
macro_rules! callback_guard {
|
||||||
|
() => (
|
||||||
|
let _guard = ::glib::CallbackGuard::new();
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
macro_rules! skip_assert_initialized {
|
||||||
|
() => (
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub use glib::{Cast, Continue, Error, IsA, StaticType, ToValue, Type, TypedValue, Value};
|
||||||
|
|
||||||
|
#[cfg_attr(feature = "cargo-clippy", allow(unreadable_literal))]
|
||||||
|
#[cfg_attr(feature = "cargo-clippy", allow(transmute_ptr_to_ref))]
|
||||||
|
#[cfg_attr(feature = "cargo-clippy", allow(too_many_arguments))]
|
||||||
|
#[cfg_attr(feature = "cargo-clippy", allow(match_same_arms))]
|
||||||
|
mod auto;
|
||||||
|
pub use auto::*;
|
||||||
|
pub use auto::traits::*;
|
||||||
|
|
||||||
|
mod audio_format_info;
|
||||||
|
pub use audio_format_info::*;
|
||||||
|
mod audio_info;
|
||||||
|
pub use audio_info::*;
|
|
@ -206,6 +206,8 @@ impl Segment {
|
||||||
(ret, stream_time)
|
(ret, stream_time)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO getter/setter
|
||||||
}
|
}
|
||||||
|
|
||||||
impl PartialEq for Segment {
|
impl PartialEq for Segment {
|
||||||
|
|
Loading…
Reference in a new issue