docs: improve documentations
This commit is contained in:
parent
ed2497cbf1
commit
2cbefdee7c
6 changed files with 29 additions and 1 deletions
|
|
@ -6,6 +6,7 @@ import (
|
||||||
"go.uber.org/zap"
|
"go.uber.org/zap"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Config imagorvideo config.Option
|
||||||
func Config(fs *flag.FlagSet, cb func() (*zap.Logger, bool)) imagor.Option {
|
func Config(fs *flag.FlagSet, cb func() (*zap.Logger, bool)) imagor.Option {
|
||||||
var (
|
var (
|
||||||
ffmpegFallbackImage = fs.String("ffmpeg-fallback-image", "",
|
ffmpegFallbackImage = fs.String("ffmpeg-fallback-image", "",
|
||||||
|
|
|
||||||
|
|
@ -5,6 +5,7 @@ import "C"
|
||||||
|
|
||||||
type avError int
|
type avError int
|
||||||
|
|
||||||
|
// AV Error enum
|
||||||
const (
|
const (
|
||||||
ErrNoMem = avError(-C.ENOMEM)
|
ErrNoMem = avError(-C.ENOMEM)
|
||||||
ErrEOF = avError(C.AVERROR_EOF)
|
ErrEOF = avError(C.AVERROR_EOF)
|
||||||
|
|
@ -31,6 +32,7 @@ func (e avError) errorString() string {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Error implements error interface
|
||||||
func (e avError) Error() string {
|
func (e avError) Error() string {
|
||||||
return "ffmpeg: " + e.errorString()
|
return "ffmpeg: " + e.errorString()
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -20,6 +20,7 @@ const (
|
||||||
hasAudio = 2
|
hasAudio = 2
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Metadata AV metadata
|
||||||
type Metadata struct {
|
type Metadata struct {
|
||||||
Orientation int `json:"orientation"`
|
Orientation int `json:"orientation"`
|
||||||
Duration int `json:"duration,omitempty"`
|
Duration int `json:"duration,omitempty"`
|
||||||
|
|
@ -32,6 +33,7 @@ type Metadata struct {
|
||||||
HasAudio bool `json:"has_audio"`
|
HasAudio bool `json:"has_audio"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AVContext manages lifecycle of AV contexts and reader stream
|
||||||
type AVContext struct {
|
type AVContext struct {
|
||||||
opaque unsafe.Pointer
|
opaque unsafe.Pointer
|
||||||
reader io.Reader
|
reader io.Reader
|
||||||
|
|
@ -55,6 +57,7 @@ type AVContext struct {
|
||||||
closed bool
|
closed bool
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// LoadAVContext load and create AVContext from reader stream
|
||||||
func LoadAVContext(reader io.Reader, size int64) (*AVContext, error) {
|
func LoadAVContext(reader io.Reader, size int64) (*AVContext, error) {
|
||||||
av := &AVContext{
|
av := &AVContext{
|
||||||
reader: reader,
|
reader: reader,
|
||||||
|
|
@ -77,6 +80,8 @@ func LoadAVContext(reader io.Reader, size int64) (*AVContext, error) {
|
||||||
return av, createDecoder(av)
|
return av, createDecoder(av)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ProcessFrames triggers frame processing
|
||||||
|
// limit under max num of frames if maxFrames > 0
|
||||||
func (av *AVContext) ProcessFrames(maxFrames int) (err error) {
|
func (av *AVContext) ProcessFrames(maxFrames int) (err error) {
|
||||||
if av.formatContext == nil || av.codecContext == nil {
|
if av.formatContext == nil || av.codecContext == nil {
|
||||||
return ErrDecoderNotFound
|
return ErrDecoderNotFound
|
||||||
|
|
@ -87,6 +92,7 @@ func (av *AVContext) ProcessFrames(maxFrames int) (err error) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SelectFrame triggers frame processing and select specific frame index
|
||||||
func (av *AVContext) SelectFrame(n int) (err error) {
|
func (av *AVContext) SelectFrame(n int) (err error) {
|
||||||
nn := C.int(n - 1)
|
nn := C.int(n - 1)
|
||||||
if av.thumbContext != nil && nn > av.availableIndex {
|
if av.thumbContext != nil && nn > av.availableIndex {
|
||||||
|
|
@ -104,6 +110,8 @@ func (av *AVContext) SelectPosition(f float64) (err error) {
|
||||||
return av.SelectDuration(av.positionToDuration(f))
|
return av.SelectDuration(av.positionToDuration(f))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SelectDuration seeks to keyframe before the specified duration
|
||||||
|
// then process frames to find precise duration
|
||||||
func (av *AVContext) SelectDuration(ts time.Duration) (err error) {
|
func (av *AVContext) SelectDuration(ts time.Duration) (err error) {
|
||||||
if ts > 0 {
|
if ts > 0 {
|
||||||
av.selectedDuration = ts
|
av.selectedDuration = ts
|
||||||
|
|
@ -116,14 +124,18 @@ func (av *AVContext) SelectDuration(ts time.Duration) (err error) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SeekPosition seeks to keyframe before specified position percentage between 0 and 1
|
||||||
|
// then process frames to find precise position
|
||||||
func (av *AVContext) SeekPosition(f float64) error {
|
func (av *AVContext) SeekPosition(f float64) error {
|
||||||
return av.SeekDuration(av.positionToDuration(f))
|
return av.SeekDuration(av.positionToDuration(f))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SeekDuration seeks to keyframe before the specified duration
|
||||||
func (av *AVContext) SeekDuration(ts time.Duration) error {
|
func (av *AVContext) SeekDuration(ts time.Duration) error {
|
||||||
return seekDuration(av, ts)
|
return seekDuration(av, ts)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Export frame to RGB or RGBA buffer
|
||||||
func (av *AVContext) Export(bands int) (buf []byte, err error) {
|
func (av *AVContext) Export(bands int) (buf []byte, err error) {
|
||||||
if err = av.ProcessFrames(-1); err != nil {
|
if err = av.ProcessFrames(-1); err != nil {
|
||||||
return
|
return
|
||||||
|
|
@ -137,10 +149,12 @@ func (av *AVContext) Export(bands int) (buf []byte, err error) {
|
||||||
return exportBuffer(av, bands)
|
return exportBuffer(av, bands)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Close AVContext objects
|
||||||
func (av *AVContext) Close() {
|
func (av *AVContext) Close() {
|
||||||
closeAVContext(av)
|
closeAVContext(av)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Metadata AV metadata
|
||||||
func (av *AVContext) Metadata() *Metadata {
|
func (av *AVContext) Metadata() *Metadata {
|
||||||
var fps float64
|
var fps float64
|
||||||
if av.stream != nil {
|
if av.stream != nil {
|
||||||
|
|
|
||||||
|
|
@ -8,7 +8,7 @@ import "sync"
|
||||||
// AVLogLevel defines the ffmpeg threshold for dumping information to stderr.
|
// AVLogLevel defines the ffmpeg threshold for dumping information to stderr.
|
||||||
type AVLogLevel int
|
type AVLogLevel int
|
||||||
|
|
||||||
// Possible values for AVLogLevel.
|
// AVLogLevel enum
|
||||||
const (
|
const (
|
||||||
AVLogQuiet AVLogLevel = (iota - 1) * 8
|
AVLogQuiet AVLogLevel = (iota - 1) * 8
|
||||||
AVLogPanic
|
AVLogPanic
|
||||||
|
|
@ -35,6 +35,7 @@ func SetFFmpegLogLevel(logLevel AVLogLevel) {
|
||||||
|
|
||||||
type LoggingHandlerFunction func(messageLevel AVLogLevel, message string)
|
type LoggingHandlerFunction func(messageLevel AVLogLevel, message string)
|
||||||
|
|
||||||
|
// SetLogging set AV logging handler
|
||||||
func SetLogging(handler LoggingHandlerFunction) {
|
func SetLogging(handler LoggingHandlerFunction) {
|
||||||
onceLogging.Do(func() {
|
onceLogging.Do(func() {
|
||||||
C.goavLogSetup()
|
C.goavLogSetup()
|
||||||
|
|
|
||||||
|
|
@ -2,14 +2,17 @@ package imagorvideo
|
||||||
|
|
||||||
import "go.uber.org/zap"
|
import "go.uber.org/zap"
|
||||||
|
|
||||||
|
// Option imagorvideo option
|
||||||
type Option func(p *Processor)
|
type Option func(p *Processor)
|
||||||
|
|
||||||
|
// WithDebug with debug option
|
||||||
func WithDebug(debug bool) Option {
|
func WithDebug(debug bool) Option {
|
||||||
return func(p *Processor) {
|
return func(p *Processor) {
|
||||||
p.Debug = debug
|
p.Debug = debug
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// WithLogger with logger option
|
||||||
func WithLogger(logger *zap.Logger) Option {
|
func WithLogger(logger *zap.Logger) Option {
|
||||||
return func(p *Processor) {
|
return func(p *Processor) {
|
||||||
if logger != nil {
|
if logger != nil {
|
||||||
|
|
@ -18,6 +21,7 @@ func WithLogger(logger *zap.Logger) Option {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// WithFallbackImage with fallback imagor option on error
|
||||||
func WithFallbackImage(image string) Option {
|
func WithFallbackImage(image string) Option {
|
||||||
return func(p *Processor) {
|
return func(p *Processor) {
|
||||||
p.FallbackImage = image
|
p.FallbackImage = image
|
||||||
|
|
|
||||||
|
|
@ -13,12 +13,14 @@ import (
|
||||||
"time"
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Processor for imagorvideo that implements imagor.Processor interface
|
||||||
type Processor struct {
|
type Processor struct {
|
||||||
Logger *zap.Logger
|
Logger *zap.Logger
|
||||||
Debug bool
|
Debug bool
|
||||||
FallbackImage string
|
FallbackImage string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// NewProcessor creates Processor
|
||||||
func NewProcessor(options ...Option) *Processor {
|
func NewProcessor(options ...Option) *Processor {
|
||||||
p := &Processor{
|
p := &Processor{
|
||||||
Logger: zap.NewNop(),
|
Logger: zap.NewNop(),
|
||||||
|
|
@ -29,6 +31,7 @@ func NewProcessor(options ...Option) *Processor {
|
||||||
return p
|
return p
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Startup implements imagor.Processor interface
|
||||||
func (p *Processor) Startup(_ context.Context) error {
|
func (p *Processor) Startup(_ context.Context) error {
|
||||||
ffmpeg.SetLogging(func(level ffmpeg.AVLogLevel, message string) {
|
ffmpeg.SetLogging(func(level ffmpeg.AVLogLevel, message string) {
|
||||||
message = strings.TrimSuffix(message, "\n")
|
message = strings.TrimSuffix(message, "\n")
|
||||||
|
|
@ -49,10 +52,12 @@ func (p *Processor) Startup(_ context.Context) error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Shutdown implements imagor.Processor interface
|
||||||
func (p *Processor) Shutdown(_ context.Context) error {
|
func (p *Processor) Shutdown(_ context.Context) error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Process implements imagor.Processor interface
|
||||||
func (p *Processor) Process(ctx context.Context, in *imagor.Blob, params imagorpath.Params, load imagor.LoadFunc) (out *imagor.Blob, err error) {
|
func (p *Processor) Process(ctx context.Context, in *imagor.Blob, params imagorpath.Params, load imagor.LoadFunc) (out *imagor.Blob, err error) {
|
||||||
defer func() {
|
defer func() {
|
||||||
if err == nil || out != nil {
|
if err == nil || out != nil {
|
||||||
|
|
@ -179,6 +184,7 @@ func (p *Processor) Process(ctx context.Context, in *imagor.Blob, params imagorp
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Metadata imagorvideo metadata
|
||||||
type Metadata struct {
|
type Metadata struct {
|
||||||
Format string `json:"format"`
|
Format string `json:"format"`
|
||||||
ContentType string `json:"content_type"`
|
ContentType string `json:"content_type"`
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue