Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

v1 #12

Open
wants to merge 29 commits into
base: master
Choose a base branch
from
Open

v1 #12

Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
902449e
Fix CI auth
nabijaczleweli Dec 26, 2017
d4b9a02
Replace RawGit links with GitHack
nabijaczleweli Oct 6, 2018
958feb0
Bump ffmpeg to n4.2.1
nabijaczleweli Oct 19, 2019
b7a31b0
Bump pb-cpp to v0.1.3. Bump Catch2 to v2.10.1
nabijaczleweli Oct 19, 2019
c541af0
Final pass over README et al.
nabijaczleweli Oct 20, 2019
22261c3
modern libav can understand gifs, and much faster
nabijaczleweli Mar 22, 2024
3986543
Normal parsing, no TCLAP
nabijaczleweli Mar 22, 2024
904b0b7
Delete progressbar (and pb-cpp). Delete ffmpeg dep and port to modern…
nabijaczleweli Mar 22, 2024
c4e2493
C++17 to replace nonstd
nabijaczleweli Mar 22, 2024
49728e4
C++17 quickscope_wrapper
nabijaczleweli Mar 22, 2024
85a7053
Port tests to doctest2
nabijaczleweli Mar 22, 2024
c22d932
{file,directory}_exists() not used
nabijaczleweli Mar 22, 2024
7d2c27d
read_file() not used
nabijaczleweli Mar 22, 2024
9f19c88
const_cast to const instead of two identical implementations
nabijaczleweli Mar 22, 2024
44bd384
-MD deps
nabijaczleweli Mar 22, 2024
5818899
Add to frames on threads [22FPS -> 45FPS]
nabijaczleweli Mar 22, 2024
5a20b42
Index in inlineable [45 -> 49FPS]
nabijaczleweli Mar 22, 2024
1a9503c
Re-add rudimentary progress bar
nabijaczleweli Mar 22, 2024
1cd1ea3
Flip once at the end [47.5 -> 88.9FPS]
nabijaczleweli Mar 22, 2024
4c31669
Ignore AVERROR_INVALIDDATA and disable the log callback (kinda like f…
nabijaczleweli Mar 23, 2024
53f6217
Dump input format like ffmpeg
nabijaczleweli Mar 23, 2024
1fe7fcb
No need to do the additional links
nabijaczleweli Mar 23, 2024
faddb62
Actually you do need gif-specific processing
nabijaczleweli Mar 23, 2024
4a56efa
templated operator[]
nabijaczleweli Mar 23, 2024
3f651ea
Progress for GIF too
nabijaczleweli Mar 23, 2024
6571926
README cleanup
nabijaczleweli Mar 23, 2024
7b83aa6
README cleanup
nabijaczleweli Mar 23, 2024
16d33e3
Makefile detritus
nabijaczleweli Mar 23, 2024
dd57674
av_log_set_callback() takes NULL to mean no-log as well
nabijaczleweli Mar 23, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -16,4 +16,4 @@
!gh_rsa.enc
!README.md
!pictura-mediocritas.rc
!pictura-mediocritas.md
!pictura-mediocritas.1
15 changes: 0 additions & 15 deletions .gitmodules

This file was deleted.

4 changes: 3 additions & 1 deletion .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,8 @@ matrix:
- env: LANGUAGE=Ruby DEPLOY=true DEPLOY_FILE="$TRAVIS_BUILD_DIR/../pictura-mediocritas-man-$TRAVIS_TAG.tbz2"
language: ruby
rvm: "2.2"
allow_failures:
- env: LANGUAGE=C++ CXX="clang++-5.0 -stdlib=libc++" CC=clang-5.0

before_install:
- if [ "$TRAVIS_SECURE_ENV_VARS" == "true" ]; then
Expand Down Expand Up @@ -167,7 +169,7 @@ after_success:
deploy:
provider: releases
api-key:
secure: stxnyBJJBRCIL5CdzwQeCGwrZ9Bh1Z8jZA4ojKZ/1RzXyAV/h1g2tQnbbW7cUA7QT4AvITwRDN5CW6KzZfUAqUr2Kz0XoMuE7+zuyFUihVt6Vmilr//ZUpkTbektfJDUvfYA4P4kna9S2zUfE1sW3wGheq5lbi70UVN39Zc1d8aE2dO25DP4Hcqf2HH/sHRA+U7uyMtD75qPlGgcl4YPQaPVyuVfIthMaXYYr2Pt21qIOoMib2oMIKJWLc9ftkBQaIvs9Zt0sECMTmQhaO0li8N4ZpaxiUJsSyGxt/ZkydRjDoReJVkQQO+/p4Ed7jQp8TcaBlSmFivNyd18/L06CX2h0BiawftbtEIDC9U1Xi+7VqVWfk2kIK6MqjnY0AtdsAJmQvTq60e7O1lnHkDZTu3tvXR8v+6HQdofeUM6oU75CRXgmO+MTtxQkyB1v1tDqh7REfYHCO4Q6HKaPVGpJP5XOuY0qN9vragTP5UlVgVDYi0+jzX8zrL+gE0SKm55lYkYrfNqheCvTref1No4K92Lt5fjQbT2LSjp3b/NESvcLHiL42S7KrkhI3qFqJwEYPVXl/3eGyRp/EpGUaNdFh9eZECTBOAaGLVtHQlVgfUpoST+9fBiFuRHmSexlV19Ke3NPa2h229kuIBshFWxq3Dlk9ZJMpWXKzJII36/TAA=
secure: jKKJHvnWlVzfHVn67OcSbtJTiDSHpAu7bMRs0Of64q2fqb6EAjL0l8+9ckgY1TnLU9AIXZrFJzkrt45t7qbWPb2ZsAUxd/O7n6cZuh+TDYkYj3SUsfNx9CAV8Gxb86GVogg1mXDuqYS+FKCK1lsfSV0y50bMkLz5oVtLP6Iq8/JkCugCO/XQluXCoE6tDH/lCVl3yLsgtG66Trv7bufLS05D9bnEAg/UvI4W4oxucnxRpwd0rSRCHi+rmaSjDVRFIvGTj8RzLtGm8SJTeedulT5CWXr7pvXxo19cnWSyXeRhjjrnV2aM3JEtDYerqeIW0e1TyRSs2q9oUmMFs1fQ2ZGwm5fLjeYSB2jVU637mdUnh/SmrvXQ5mv+IZTI/RejUm16qLqH4/IFlxkGmAwyhLtj0A+thula+PuZ2RMd2FfymVGvEklC7/hyWTjE3kJESc2uv0xph9iceJrLaQI4qXI++uJPVJntto7hoBEJWTLcc0nVvigjMLkCfmfifzb/KwItYyImHHjCs8dCYc771Oup3jEqHDprmiJtizp+mAi3cNIr3mCtspcll7cxELg9RBR9AUIhyql0FtfH1qatFQYB8KYyUMeLdmJRzkz023dCMznenkgIm/Pg7KzQjGxsRePJMA4qR4FxMOGnnvZMwziHh7DWQu6y7bpfMh8NVAw=
file: "$DEPLOY_FILE"
skip_cleanup: true
on:
Expand Down
50 changes: 23 additions & 27 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -23,18 +23,21 @@
include configMakefile


# If ffmpeg autodetects something for your system, you can put it here to link to
FFMPEG_PREREQUESITE_LD_LIBS := bz2 lzma z
LDAR := $(PIC) $(LNCXXAR) $(foreach l,ffmpeg/lib pb-cpp,-L$(BLDDIR)$(l)) $(foreach l,pb-cpp swscale avformat avcodec avutil freeimage $(FFMPEG_PREREQUESITE_LD_LIBS) $(OS_LD_LIBS),-l$(l))
VERAR := $(foreach l,PICTURA_MEDIOCRITAS CATCH2 PB_CPP TCLAP,-D$(l)_VERSION='$($(l)_VERSION)')
INCAR := $(foreach l,$(foreach l,$(foreach l,pb-cpp pb-cpp/ext/optional-lite TCLAP,$(l)/include) Catch2/single_include,ext/$(l)) $(foreach l,ffmpeg,$(BLDDIR)$(l)/include),-isystem$(l))
LDAR := $(PIC) $(LNCXXAR) $(foreach l,swscale avformat avcodec avutil freeimage $(OS_LD_LIBS),-l$(l))
VERAR := $(foreach l,PICTURA_MEDIOCRITAS,-D$(l)_VERSION='$($(l)_VERSION)')
TEST_SOURCES := $(sort $(wildcard tests/*.cpp tests/**/*.cpp tests/**/**/*.cpp tests/**/**/**/*.cpp))
BUILD_TEST_SOURCES := $(sort $(wildcard build-tests/*.cpp build-tests/**/*.cpp build-tests/**/**/*.cpp build-tests/**/**/**/*.cpp))
SOURCES := $(sort $(wildcard src/*.cpp src/**/*.cpp src/**/**/*.cpp src/**/**/**/*.cpp))
PREFIX ?= /usr/local

.PHONY : all clean ffmpeg pb-cpp exe tests no-build-tests run-tests
.PHONY : all clean exe tests no-build-tests run-tests

all : ffmpeg pb-cpp exe tests no-build-tests run-tests
all : exe tests no-build-tests run-tests

install : exe
mkdir -p $(DESTDIR)/$(PREFIX)/bin $(DESTDIR)/$(PREFIX)/share/man/man1
cp $(OUTDIR)pictura-mediocritas$(EXE) $(DESTDIR)/$(PREFIX)/bin/
gzip -9 < pictura-mediocritas.1 > $(DESTDIR)/$(PREFIX)/share/man/man1/pictura-mediocritas.1.gz

clean :
rm -rf $(OUTDIR)
Expand All @@ -44,36 +47,29 @@ run-tests : $(OUTDIR)pictura-mediocritas-tests$(EXE)

exe : $(OUTDIR)pictura-mediocritas$(EXE)
tests : $(OUTDIR)pictura-mediocritas-tests$(EXE)
no-build-tests : $(subst build-tests/,$(BLDDIR)build_test_obj/,$(subst .cpp,$(OBJ),$(BUILD_TEST_SOURCES)))
ffmpeg : $(BLDDIR)ffmpeg/lib/libavcodec$(ARCH)
pb-cpp : $(BLDDIR)pb-cpp/libpb-cpp$(ARCH)
no-build-tests : $(subst build-tests/,$(BLDDIR)build_test_obj/,$(subst .cpp,.o,$(BUILD_TEST_SOURCES)))


$(OUTDIR)pictura-mediocritas$(EXE) : $(subst $(SRCDIR),$(OBJDIR),$(subst .cpp,$(OBJ),$(SOURCES)))
$(OUTDIR)pictura-mediocritas$(EXE) : $(subst $(SRCDIR),$(OBJDIR),$(subst .cpp,.o,$(SOURCES)))
$(CXX) $(CXXAR) -o$@ $^ $(PIC) $(LDAR)

$(OUTDIR)pictura-mediocritas-tests$(EXE) : $(subst tests/,$(BLDDIR)test_obj/,$(subst .cpp,$(OBJ),$(TEST_SOURCES))) $(subst $(SRCDIR),$(OBJDIR),$(subst .cpp,$(OBJ),$(filter-out src/main.cpp,$(SOURCES))))
$(OUTDIR)pictura-mediocritas-tests$(EXE) : $(subst tests/,$(BLDDIR)test_obj/,$(subst .cpp,.o,$(TEST_SOURCES))) $(subst $(SRCDIR),$(OBJDIR),$(subst .cpp,.o,$(filter-out src/main.cpp,$(SOURCES))))
$(CXX) $(CXXAR) -o$@ $^ $(PIC) $(LDAR)

$(BLDDIR)ffmpeg/lib/libavcodec$(ARCH) : ext/ffmpeg/configure
@mkdir -p $(abspath $(dir $@)..)
cd $(abspath $(dir $@)..) && $(abspath $^) --enable-static $(foreach l,shared programs doc avdevice swresample postproc avfilter iconv jack alsa appkit coreimage sndio schannel securetransport avfoundation encoders filters muxers libxcb libxcb-shm libxcb-xfixes libxcb-shape audiotoolbox encoders filters muxers,--disable-$(l)) --prefix="$(abspath $(dir $@)..)" && $(MAKE) install

$(BLDDIR)pb-cpp/libpb-cpp$(ARCH) : ext/pb-cpp/Makefile
@mkdir -p $(abspath $(dir $@)..)
cd $(dir $^) && $(MAKE) OUTDIR="$(abspath $(dir $@))/" static


$(OBJDIR)%$(OBJ) : $(SRCDIR)%.cpp
$(OBJDIR)%.o : $(SRCDIR)%.cpp
@mkdir -p $(dir $@)
$(CXX) $(CXXAR) $(INCAR) $(VERAR) -c -o$@ $^
$(CXX) $(CXXAR) $(VERAR) -c -o$@ $<

$(BLDDIR)test_obj/%$(OBJ) : tests/%.cpp
$(BLDDIR)test_obj/%.o : tests/%.cpp
@mkdir -p $(dir $@)
$(CXX) $(CXXAR) $(INCAR) -Isrc -c -o$@ $^
$(CXX) $(CXXAR) -Isrc -c -o$@ $<

$(BLDDIR)build_test_obj/%$(OBJ) : build-tests/%.cpp
$(BLDDIR)build_test_obj/%.o : build-tests/%.cpp
@mkdir -p $(dir $@)
! $(CXX) $(CXXAR) $(INCAR) -Isrc -c -o$@ $^ 2>$(subst $(OBJ),.err_out,$@)
grep -q "$(shell grep ERROR_MUST_CONTAIN $^ | sed -e 's/#define ERROR_MUST_CONTAIN "//' -e 's/"$$//')" $(subst $(OBJ),.err_out,$@)
! $(CXX) $(CXXAR) -Isrc -c -o$@ $< 2>$(subst .o,.err_out,$@)
grep -q "$(shell grep ERROR_MUST_CONTAIN $^ | sed -e 's/#define ERROR_MUST_CONTAIN "//' -e 's/"$$//')" $(subst .o,.err_out,$@)
touch $@


include $(wildcard $(OBJDIR)*/*.d $(OBJDIR)*.d)
4 changes: 0 additions & 4 deletions PicturaMediocritas.sublime-project
Original file line number Diff line number Diff line change
Expand Up @@ -26,10 +26,6 @@
"name": "Build tests",
"path": "build-tests"
},
{
"name": "External code",
"path": "ext"
},
{
"file_include_patterns":
[
Expand Down
36 changes: 12 additions & 24 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,38 +3,26 @@ Like aurea mediocritas, but with frames in a video instead.

Or, you know, get an average frame from a video.

## [Manpage](https://cdn.rawgit.com/LoungeCPP/PicturaMediocritas/man/pictura-mediocritas.1.html)
## Usage

## Examples
```
usage: pictura-mediocritas in-video [out-image]
```

```sh
# TODO: concretify
$ pictura-mediocritas "video.mp4"
```
# Averaged frame in "video.png"

For details, see the [manpage](https://cdn.rawgit.com/LoungeCPP/PicturaMediocritas/man/pictura-mediocritas.1.html).
$ pictura-mediocritas "video.mp4" "video-average.jpg"
```

## Installation

Either acquire a binary release from [the releases page](https://github.com/LoungeCPP/PicturaMediocritas/releases),
or build it yourself:

```sh
# You need FreeImage to be includable and linkable

$ git clone --recursive https://github.com/LoungeCPP/PicturaMediocritas
# apt install libfreeimage-dev libavcodec-dev libavformat-dev libavutil-dev libswscale-dev doctest-dev
# or pacman -S mingw-w64-x86_64-ffmpeg mingw-w64-x86_64-doctest mingw-w64-x86_64-freeimage
$ git clone https://github.com/LoungeCPP/PicturaMediocritas
$ cd PicturaMediocritas
$ make
$ install out/pictura-mediocritas $(wherever)
$ make -j
$ make install
```

## Contributing

Imperative commit messages, format your code with clang-format, you know the drill.

Branch names *should* be in the format `{issue}-{name}-{desc}`, where
`issue` is the issue # this branch closes,
`name` is your name (or a shorthand, like "nab" for "nabijaczleweli"), and
`desc` is a few-word description of the changes in the branch (like "rework-dir-listing", "second-time").

Non-FF PRs (ergo, merge commits) are illegal.
4 changes: 3 additions & 1 deletion appveyor.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ install:
- bash -lc "pacman --needed --noconfirm -Sy pacman-mirrors"
- bash -lc "pacman --noconfirm -Syyu"
- bash -lc "pacman --noconfirm -Su mingw-w64-x86_64-freeimage mingw-w64-x86_64-nasm"
-
- sed -i "s/FFMPEG_PREREQUESITE_LD_LIBS :=/\0 bcrypt/" Makefile

build: off
build_script:
Expand All @@ -31,7 +33,7 @@ deploy:
provider: GitHub
artifact: pictura-mediocritas-v0.1.0.exe
auth_token:
secure: /6TsIkMcI5dtUAvr8RJZxjUMR9uDgFLLZDyNbm5HqNCD0zbuj4TUY2JPIte4F+E7
secure: ulV16u9GQNsy21XpNcP46K2SSbTHTv68LK0UGobzLbTEswEPEg0hso5XTpmuwa7Y
on:
appveyor_repo_tag: true

Expand Down
19 changes: 3 additions & 16 deletions configMakefile
Original file line number Diff line number Diff line change
Expand Up @@ -23,13 +23,11 @@
ifeq "$(OS)" "Windows_NT"
EXE := .exe
PIC :=
ECHO := /usr/bin/echo
OS_LD_LIBS := ncurses ole32 ws2_32
OS_LD_LIBS :=
else
EXE :=
PIC := -fPIC
ECHO := echo
OS_LD_LIBS := ncurses dl pthread
OS_LD_LIBS := pthread
endif

ifneq "$(ADDITIONAL_INCLUDE_DIR)" ""
Expand All @@ -44,18 +42,7 @@ else
LNCXXAR :=
endif

# TODO: uncomment when there's a first tag
# PICTURA_MEDIOCRITAS_VERSION := "$(patsubst v%,%,$(shell git describe --tags --abbrev=0))"
PICTURA_MEDIOCRITAS_VERSION := "0.1.0"
CATCH2_VERSION := "$(patsubst v%,%,$(shell git -C ext/Catch2 describe --tags --abbrev=0))"
PB_CPP_VERSION := "$(patsubst v%,%,$(shell git -C ext/pb-cpp describe --tags --abbrev=0))"
TCLAP_VERSION := "$(shell cat ext/TCLAP/configure.in | grep AM_INIT_AUTOMAKE | sed "s/.*(tclap,\(.*\))/\1/")"

OBJ := .o
ARCH := .a
AR := ar
CXXAR := -O3 -fomit-frame-pointer -std=c++14 -pedantic -Wall -Wextra -pipe $(INCCXXAR) $(PIC)
CCAR := -O3 -fomit-frame-pointer -std=c11 -pipe $(PIC)
CXXAR := -g -MD -O3 -fomit-frame-pointer -march=native -std=c++20 -pedantic -Wall -Wextra -Wno-missing-field-initializers -pipe $(INCCXXAR) $(PIC)

OUTDIR := out/
BLDDIR := out/build/
Expand Down
1 change: 0 additions & 1 deletion ext/Catch2
Submodule Catch2 deleted from 19ab21
1 change: 0 additions & 1 deletion ext/TCLAP
Submodule TCLAP deleted from 3d02fe
1 change: 0 additions & 1 deletion ext/ffmpeg
Submodule ffmpeg deleted from 01e291
1 change: 0 additions & 1 deletion ext/pb-cpp
Submodule pb-cpp deleted from 35c52a
34 changes: 34 additions & 0 deletions pictura-mediocritas.1
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
.\" SPDX-License-Identifier: 0BSD
.\"
.Dd March 23, 2024
.Dt PICTŪRA-MEDIOCRITAS 1
.Os
.
.Sh NAME
.Nm pictura-mediocritas
.Nd average video frames into single image
.Sh SYNOPSIS
.Nm
.Ar video
.Op Ar image
.
.Sh DESCRIPTION
Like aurea mediocritas, but with frames in a video instead:
averages
.Ar video
.Pq which may be in GIF, or any Xr ffmpeg 1 Ns -understood, format
into
.Ar image
(which defaults to
.Ar video
but with the "extension" replaced with
.Pa .png ) .
.
.Sh AUTHORS
.An наб Aq Mt [email protected]
.
.Sh REPORTING BUGS
.Lk https://github.com/LoungeCPP/PicturaMediocritas/issues
.
.Sh SEE ALSO
.Lk https://github.com/LoungeCPP/PicturaMediocritas
38 changes: 0 additions & 38 deletions pictura-mediocritas.md

This file was deleted.

19 changes: 13 additions & 6 deletions src/average_frame.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@

#include <array>
#include <cstddef>
#include <cstdint>
#include <utility>
#include <vector>

Expand Down Expand Up @@ -79,15 +80,18 @@ namespace pictura_mediocritas {

/// Get a frame from the specified source.
///
/// The `frame` argument must be indexable by a `std::size_t` in [0; width * height * Channels) ∩ ℤ.
template <class FrameT>
void process_frame(const FrameT & frame);
/// The `frame` argument must be indexable by a `{std::size_t, Additional...}` where the size_t is in [0; width * height * Channels) ∩ ℤ.
template <class FrameT, class... Additional>
void process_frame(const FrameT & frame, Additional &&... frame_ctr);

/// Get a frame from the specified source.
///
/// The `frame` argument must be indexable by a `std::size_t` in [0; width * height * Channels) ∩ ℤ.
template <class FrameT>
void process_frame(FrameT & frame);
/// The `frame` argument must be indexable by a `{std::size_t, frame_ctr}` where the size_t is in [0; width * height * Channels) ∩ ℤ.
template <class FrameT, class... Additional>
void process_frame(FrameT & frame, Additional &&... frame_ctr);

/// Add the values from a partial frame to this one.
average_frame & operator+=(const average_frame & partial);

/// Get the average channel at the given index.
///
Expand All @@ -104,6 +108,9 @@ namespace pictura_mediocritas {
///
/// The behaviour is undefined if `idx` ∉ [0; width * height) ∩ ℤ.
std::array<AccT, Channels> pixel(std::size_t idx) const;

/// Swap pixels at the given coordinates, both within [0; width * height * Channels) ∩ ℤ.
void swap(std::size_t idx1, std::size_t idx2);
};


Expand Down
Loading