commit 8b7d3b5c2d9eb6996da5f3a355b3430671e18473
parent 4fc7070285c578096a8597b7a4b1dc10d55a2632
Author: Alexander Kojevnikov <alexander@kojevnikov.com>
Date: Sat, 2 Feb 2013 19:06:40 -0800
Use C++ everywhere
Diffstat:
48 files changed, 1354 insertions(+), 1353 deletions(-)
diff --git a/Makefile.am b/Makefile.am
@@ -3,8 +3,7 @@ SUBDIRS = \
lib \
man \
po \
- src \
- tests
+ src
EXTRA_DIST = \
INSTALL.md \
diff --git a/configure.ac b/configure.ac
@@ -4,7 +4,7 @@ AC_CONFIG_HEADERS([config.h])
AM_INIT_AUTOMAKE([1.11.1 foreign no-dist-gzip dist-xz])
AM_SILENT_RULES([yes])
-AC_PROG_CC_C99
+AC_LANG([C++])
AC_PROG_CXX
AC_PROG_RANLIB
AC_PROG_INSTALL
@@ -71,7 +71,6 @@ AC_CONFIG_FILES([
man/spek.1
po/Makefile.in
src/Makefile
- tests/Makefile
web/version
])
AC_OUTPUT
diff --git a/lib/Makefile.am b/lib/Makefile.am
@@ -1,20 +1,20 @@
noinst_LIBRARIES = libspek.a
libspek_a_SOURCES = \
- spek-audio.c \
+ spek-audio.cc \
spek-audio.h \
- spek-fft.c \
+ spek-fft.cc \
spek-fft.h \
- spek-palette.c \
+ spek-palette.cc \
spek-palette.h \
- spek-pipeline.c \
+ spek-pipeline.cc \
spek-pipeline.h \
- spek-utils.c \
+ spek-utils.cc \
spek-utils.h
libspek_a_CPPFLAGS = \
-include config.h \
-pthread
-libspek_a_CFLAGS = \
+libspek_a_CXXFLAGS = \
$(FFMPEG_CFLAGS)
diff --git a/lib/spek-audio.c b/lib/spek-audio.c
@@ -1,223 +0,0 @@
-/* spek-audio.c
- *
- * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <string.h>
-
-#include <libavformat/avformat.h>
-#include <libavcodec/avcodec.h>
-#include <libavutil/mathematics.h>
-
-#include "spek-audio.h"
-
-struct spek_audio_context
-{
- AVFormatContext *format_context;
- int audio_stream;
- AVCodecContext *codec_context;
- AVStream *stream;
- AVCodec *codec;
- int buffer_size;
- AVPacket *packet;
- int offset;
-
- struct spek_audio_properties properties;
-};
-
-
-void spek_audio_init()
-{
- // TODO: register only audio decoders.
- av_register_all();
-}
-
-const struct spek_audio_properties * spek_audio_get_properties(struct spek_audio_context *cx)
-{
- return &cx->properties;
-}
-
-struct spek_audio_context * spek_audio_open(const char *path)
-{
- // TODO: malloc and initialise explicitely
- struct spek_audio_context *cx = calloc(1, sizeof(struct spek_audio_context));
-
- if (avformat_open_input(&cx->format_context, path, NULL, NULL) != 0) {
- cx->properties.error = SPEK_AUDIO_CANNOT_OPEN_FILE;
- return cx;
- }
- if (avformat_find_stream_info(cx->format_context, NULL) < 0) {
- // 24-bit APE returns an error but parses the stream info just fine.
- if (cx->format_context->nb_streams <= 0) {
- cx->properties.error = SPEK_AUDIO_NO_STREAMS;
- return cx;
- }
- }
- cx->audio_stream = -1;
- for (int i = 0; i < cx->format_context->nb_streams; i++) {
- if (cx->format_context->streams[i]->codec->codec_type == AVMEDIA_TYPE_AUDIO) {
- cx->audio_stream = i;
- break;
- }
- }
- if (cx->audio_stream == -1) {
- cx->properties.error = SPEK_AUDIO_NO_AUDIO;
- return cx;
- }
- cx->stream = cx->format_context->streams[cx->audio_stream];
- cx->codec_context = cx->stream->codec;
- cx->codec = avcodec_find_decoder(cx->codec_context->codec_id);
- if (cx->codec == NULL) {
- cx->properties.error = SPEK_AUDIO_NO_DECODER;
- return cx;
- }
- // We can already fill in the stream info even if the codec won't be able to open it.
- cx->properties.codec_name = strdup(cx->codec->long_name);
- cx->properties.bit_rate = cx->codec_context->bit_rate;
- cx->properties.sample_rate = cx->codec_context->sample_rate;
- cx->properties.bits_per_sample = cx->codec_context->bits_per_raw_sample;
- if (!cx->properties.bits_per_sample) {
- // APE uses bpcs, FLAC uses bprs.
- cx->properties.bits_per_sample = cx->codec_context->bits_per_coded_sample;
- }
- cx->properties.channels = cx->codec_context->channels;
- if (cx->stream->duration != AV_NOPTS_VALUE) {
- cx->properties.duration = cx->stream->duration * av_q2d(cx->stream->time_base);
- } else if (cx->format_context->duration != AV_NOPTS_VALUE) {
- cx->properties.duration = cx->format_context->duration / (double) AV_TIME_BASE;
- } else {
- cx->properties.error = SPEK_AUDIO_NO_DURATION;
- return cx;
- }
- if (cx->properties.channels <= 0) {
- cx->properties.error = SPEK_AUDIO_NO_CHANNELS;
- return cx;
- }
- if (avcodec_open2(cx->codec_context, cx->codec, NULL) < 0) {
- cx->properties.error = SPEK_AUDIO_CANNOT_OPEN_DECODER;
- return cx;
- }
- switch (cx->codec_context->sample_fmt) {
- case AV_SAMPLE_FMT_S16:
- cx->properties.width = 16;
- cx->properties.fp = false;
- break;
- case AV_SAMPLE_FMT_S32:
- cx->properties.width = 32;
- cx->properties.fp = false;
- break;
- case AV_SAMPLE_FMT_FLT:
- cx->properties.width = 32;
- cx->properties.fp = true;
- break;
- case AV_SAMPLE_FMT_DBL:
- cx->properties.width = 64;
- cx->properties.fp = true;
- break;
- default:
- cx->properties.error = SPEK_AUDIO_BAD_SAMPLE_FORMAT;
- return cx;
- }
- cx->buffer_size = (AVCODEC_MAX_AUDIO_FRAME_SIZE * 3) / 2;
- cx->properties.buffer = av_malloc(cx->buffer_size);
- cx->packet = av_mallocz(sizeof(AVPacket));
- av_init_packet(cx->packet);
- cx->offset = 0;
- return cx;
-}
-
-void spek_audio_start(struct spek_audio_context *cx, int samples)
-{
- int64_t rate = cx->properties.sample_rate * (int64_t) cx->stream->time_base.num;
- int64_t duration = (int64_t)
- (cx->properties.duration * cx->stream->time_base.den / cx->stream->time_base.num);
- cx->properties.error_base = samples * (int64_t)cx->stream->time_base.den;
- cx->properties.frames_per_interval = av_rescale_rnd(
- duration, rate, cx->properties.error_base, AV_ROUND_DOWN);
- cx->properties.error_per_interval = (duration * rate) % cx->properties.error_base;
-}
-
-int spek_audio_read(struct spek_audio_context *cx) {
- if (cx->properties.error) {
- return -1;
- }
-
- for (;;) {
- while (cx->packet->size > 0) {
- int buffer_size = cx->buffer_size;
- int len = avcodec_decode_audio3(
- cx->codec_context, (int16_t *)cx->properties.buffer, &buffer_size, cx->packet);
- if (len < 0) {
- // Error, skip the frame.
- cx->packet->size = 0;
- break;
- }
- cx->packet->data += len;
- cx->packet->size -= len;
- cx->offset += len;
- if (buffer_size <= 0) {
- // No data yet, get more frames.
- continue;
- }
- // We have data, return it and come back for more later.
- return buffer_size;
- }
- if (cx->packet->data) {
- cx->packet->data -= cx->offset;
- cx->packet->size += cx->offset;
- cx->offset = 0;
- av_free_packet (cx->packet);
- }
-
- int res = 0;
- while ((res = av_read_frame(cx->format_context, cx->packet)) >= 0) {
- if (cx->packet->stream_index == cx->audio_stream) {
- break;
- }
- av_free_packet(cx->packet);
- }
- if (res < 0) {
- // End of file or error.
- return 0;
- }
- }
-}
-
-void spek_audio_close(struct spek_audio_context *cx)
-{
- if (cx->properties.codec_name != NULL) {
- free(cx->properties.codec_name);
- }
- if (cx->properties.buffer) {
- av_free(cx->properties.buffer);
- }
- if (cx->packet) {
- if (cx->packet->data) {
- cx->packet->data -= cx->offset;
- cx->packet->size += cx->offset;
- cx->offset = 0;
- av_free_packet(cx->packet);
- }
- av_free(cx->packet);
- }
- if (cx->codec_context != NULL) {
- avcodec_close(cx->codec_context);
- }
- if (cx->format_context != NULL) {
- av_close_input_file(cx->format_context);
- }
- free(cx);
-}
diff --git a/lib/spek-audio.cc b/lib/spek-audio.cc
@@ -0,0 +1,227 @@
+/* spek-audio.cc
+ *
+ * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <string.h>
+
+#define __STDC_CONSTANT_MACROS
+extern "C" {
+#include <libavformat/avformat.h>
+#include <libavcodec/avcodec.h>
+#include <libavutil/mathematics.h>
+}
+
+#include "spek-audio.h"
+
+struct spek_audio_context
+{
+ AVFormatContext *format_context;
+ int audio_stream;
+ AVCodecContext *codec_context;
+ AVStream *stream;
+ AVCodec *codec;
+ int buffer_size;
+ AVPacket *packet;
+ int offset;
+
+ struct spek_audio_properties properties;
+};
+
+
+void spek_audio_init()
+{
+ // TODO: register only audio decoders.
+ av_register_all();
+}
+
+const struct spek_audio_properties * spek_audio_get_properties(struct spek_audio_context *cx)
+{
+ return &cx->properties;
+}
+
+struct spek_audio_context * spek_audio_open(const char *path)
+{
+ // TODO: malloc and initialise explicitely
+ struct spek_audio_context *cx =
+ (spek_audio_context *)calloc(1, sizeof(struct spek_audio_context));
+
+ if (avformat_open_input(&cx->format_context, path, NULL, NULL) != 0) {
+ cx->properties.error = SPEK_AUDIO_CANNOT_OPEN_FILE;
+ return cx;
+ }
+ if (avformat_find_stream_info(cx->format_context, NULL) < 0) {
+ // 24-bit APE returns an error but parses the stream info just fine.
+ if (cx->format_context->nb_streams <= 0) {
+ cx->properties.error = SPEK_AUDIO_NO_STREAMS;
+ return cx;
+ }
+ }
+ cx->audio_stream = -1;
+ for (int i = 0; i < cx->format_context->nb_streams; i++) {
+ if (cx->format_context->streams[i]->codec->codec_type == AVMEDIA_TYPE_AUDIO) {
+ cx->audio_stream = i;
+ break;
+ }
+ }
+ if (cx->audio_stream == -1) {
+ cx->properties.error = SPEK_AUDIO_NO_AUDIO;
+ return cx;
+ }
+ cx->stream = cx->format_context->streams[cx->audio_stream];
+ cx->codec_context = cx->stream->codec;
+ cx->codec = avcodec_find_decoder(cx->codec_context->codec_id);
+ if (cx->codec == NULL) {
+ cx->properties.error = SPEK_AUDIO_NO_DECODER;
+ return cx;
+ }
+ // We can already fill in the stream info even if the codec won't be able to open it.
+ cx->properties.codec_name = strdup(cx->codec->long_name);
+ cx->properties.bit_rate = cx->codec_context->bit_rate;
+ cx->properties.sample_rate = cx->codec_context->sample_rate;
+ cx->properties.bits_per_sample = cx->codec_context->bits_per_raw_sample;
+ if (!cx->properties.bits_per_sample) {
+ // APE uses bpcs, FLAC uses bprs.
+ cx->properties.bits_per_sample = cx->codec_context->bits_per_coded_sample;
+ }
+ cx->properties.channels = cx->codec_context->channels;
+ if (cx->stream->duration != AV_NOPTS_VALUE) {
+ cx->properties.duration = cx->stream->duration * av_q2d(cx->stream->time_base);
+ } else if (cx->format_context->duration != AV_NOPTS_VALUE) {
+ cx->properties.duration = cx->format_context->duration / (double) AV_TIME_BASE;
+ } else {
+ cx->properties.error = SPEK_AUDIO_NO_DURATION;
+ return cx;
+ }
+ if (cx->properties.channels <= 0) {
+ cx->properties.error = SPEK_AUDIO_NO_CHANNELS;
+ return cx;
+ }
+ if (avcodec_open2(cx->codec_context, cx->codec, NULL) < 0) {
+ cx->properties.error = SPEK_AUDIO_CANNOT_OPEN_DECODER;
+ return cx;
+ }
+ switch (cx->codec_context->sample_fmt) {
+ case AV_SAMPLE_FMT_S16:
+ cx->properties.width = 16;
+ cx->properties.fp = false;
+ break;
+ case AV_SAMPLE_FMT_S32:
+ cx->properties.width = 32;
+ cx->properties.fp = false;
+ break;
+ case AV_SAMPLE_FMT_FLT:
+ cx->properties.width = 32;
+ cx->properties.fp = true;
+ break;
+ case AV_SAMPLE_FMT_DBL:
+ cx->properties.width = 64;
+ cx->properties.fp = true;
+ break;
+ default:
+ cx->properties.error = SPEK_AUDIO_BAD_SAMPLE_FORMAT;
+ return cx;
+ }
+ cx->buffer_size = (AVCODEC_MAX_AUDIO_FRAME_SIZE * 3) / 2;
+ cx->properties.buffer = (uint8_t*)av_malloc(cx->buffer_size);
+ cx->packet = (AVPacket*)av_mallocz(sizeof(AVPacket));
+ av_init_packet(cx->packet);
+ cx->offset = 0;
+ return cx;
+}
+
+void spek_audio_start(struct spek_audio_context *cx, int samples)
+{
+ int64_t rate = cx->properties.sample_rate * (int64_t) cx->stream->time_base.num;
+ int64_t duration = (int64_t)
+ (cx->properties.duration * cx->stream->time_base.den / cx->stream->time_base.num);
+ cx->properties.error_base = samples * (int64_t)cx->stream->time_base.den;
+ cx->properties.frames_per_interval = av_rescale_rnd(
+ duration, rate, cx->properties.error_base, AV_ROUND_DOWN);
+ cx->properties.error_per_interval = (duration * rate) % cx->properties.error_base;
+}
+
+int spek_audio_read(struct spek_audio_context *cx) {
+ if (cx->properties.error) {
+ return -1;
+ }
+
+ for (;;) {
+ while (cx->packet->size > 0) {
+ int buffer_size = cx->buffer_size;
+ int len = avcodec_decode_audio3(
+ cx->codec_context, (int16_t *)cx->properties.buffer, &buffer_size, cx->packet);
+ if (len < 0) {
+ // Error, skip the frame.
+ cx->packet->size = 0;
+ break;
+ }
+ cx->packet->data += len;
+ cx->packet->size -= len;
+ cx->offset += len;
+ if (buffer_size <= 0) {
+ // No data yet, get more frames.
+ continue;
+ }
+ // We have data, return it and come back for more later.
+ return buffer_size;
+ }
+ if (cx->packet->data) {
+ cx->packet->data -= cx->offset;
+ cx->packet->size += cx->offset;
+ cx->offset = 0;
+ av_free_packet (cx->packet);
+ }
+
+ int res = 0;
+ while ((res = av_read_frame(cx->format_context, cx->packet)) >= 0) {
+ if (cx->packet->stream_index == cx->audio_stream) {
+ break;
+ }
+ av_free_packet(cx->packet);
+ }
+ if (res < 0) {
+ // End of file or error.
+ return 0;
+ }
+ }
+}
+
+void spek_audio_close(struct spek_audio_context *cx)
+{
+ if (cx->properties.codec_name != NULL) {
+ free(cx->properties.codec_name);
+ }
+ if (cx->properties.buffer) {
+ av_free(cx->properties.buffer);
+ }
+ if (cx->packet) {
+ if (cx->packet->data) {
+ cx->packet->data -= cx->offset;
+ cx->packet->size += cx->offset;
+ cx->offset = 0;
+ av_free_packet(cx->packet);
+ }
+ av_free(cx->packet);
+ }
+ if (cx->codec_context != NULL) {
+ avcodec_close(cx->codec_context);
+ }
+ if (cx->format_context != NULL) {
+ av_close_input_file(cx->format_context);
+ }
+ free(cx);
+}
diff --git a/lib/spek-fft.c b/lib/spek-fft.c
@@ -1,64 +0,0 @@
-/* spek-fft.c
- *
- * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <math.h>
-#include <libavcodec/avfft.h>
-#include <libavutil/mem.h>
-
-#include "spek-fft.h"
-
-struct spek_fft_plan * spek_fft_plan_new(int n)
-{
- struct spek_fft_plan *p = malloc(sizeof(struct spek_fft_plan));
- p->input = av_mallocz(sizeof(float) * n);
- p->output = av_mallocz(sizeof(float) * (n / 2 + 1));
- int bits = 0;
- while (n) {
- n >>= 1;
- ++bits;
- }
- p->n = 1 << --bits;
- p->cx = av_rdft_init(bits, DFT_R2C);
- return p;
-}
-
-void spek_fft_execute(struct spek_fft_plan *p)
-{
- av_rdft_calc(p->cx, p->input);
-
- // Calculate magnitudes.
- int n = p->n;
- float n2 = n * n;
- p->output[0] = 10.0f * log10f(p->input[0] * p->input[0] / n2);
- p->output[n / 2] = 10.0f * log10f(p->input[1] * p->input[1] / n2);
- for (int i = 1; i < n / 2; i++) {
- float val =
- p->input[i * 2] * p->input[i * 2] +
- p->input[i * 2 + 1] * p->input[i * 2 + 1];
- val /= n2;
- p->output[i] = 10.0f * log10f(val);
- }
-}
-
-void spek_fft_delete(struct spek_fft_plan *p)
-{
- av_rdft_end(p->cx);
- av_free(p->input);
- av_free(p->output);
- free(p);
-}
diff --git a/lib/spek-fft.cc b/lib/spek-fft.cc
@@ -0,0 +1,68 @@
+/* spek-fft.cc
+ *
+ * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <math.h>
+
+#define __STDC_CONSTANT_MACROS
+extern "C" {
+#include <libavcodec/avfft.h>
+#include <libavutil/mem.h>
+}
+
+#include "spek-fft.h"
+
+struct spek_fft_plan * spek_fft_plan_new(int n)
+{
+ struct spek_fft_plan *p = (spek_fft_plan*)malloc(sizeof(struct spek_fft_plan));
+ p->input = (float*)av_mallocz(sizeof(float) * n);
+ p->output = (float*)av_mallocz(sizeof(float) * (n / 2 + 1));
+ int bits = 0;
+ while (n) {
+ n >>= 1;
+ ++bits;
+ }
+ p->n = 1 << --bits;
+ p->cx = av_rdft_init(bits, DFT_R2C);
+ return p;
+}
+
+void spek_fft_execute(struct spek_fft_plan *p)
+{
+ av_rdft_calc(p->cx, p->input);
+
+ // Calculate magnitudes.
+ int n = p->n;
+ float n2 = n * n;
+ p->output[0] = 10.0f * log10f(p->input[0] * p->input[0] / n2);
+ p->output[n / 2] = 10.0f * log10f(p->input[1] * p->input[1] / n2);
+ for (int i = 1; i < n / 2; i++) {
+ float val =
+ p->input[i * 2] * p->input[i * 2] +
+ p->input[i * 2 + 1] * p->input[i * 2 + 1];
+ val /= n2;
+ p->output[i] = 10.0f * log10f(val);
+ }
+}
+
+void spek_fft_delete(struct spek_fft_plan *p)
+{
+ av_rdft_end(p->cx);
+ av_free(p->input);
+ av_free(p->output);
+ free(p);
+}
diff --git a/lib/spek-palette.c b/lib/spek-palette.c
@@ -1,61 +0,0 @@
-/* spek-palette.c
- *
- * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include "spek-palette.h"
-
-// Modified version of Dan Bruton's algorithm:
-// http://www.physics.sfasu.edu/astro/color/spectra.html
-uint32_t spek_palette_spectrum(double level)
-{
- level *= 0.6625;
- double r = 0.0, g = 0.0, b = 0.0;
- if (level >= 0 && level < 0.15) {
- r = (0.15 - level) / (0.15 + 0.075);
- g = 0.0;
- b = 1.0;
- } else if (level >= 0.15 && level < 0.275) {
- r = 0.0;
- g = (level - 0.15) / (0.275 - 0.15);
- b = 1.0;
- } else if (level >= 0.275 && level < 0.325) {
- r = 0.0;
- g = 1.0;
- b = (0.325 - level) / (0.325 - 0.275);
- } else if (level >= 0.325 && level < 0.5) {
- r = (level - 0.325) / (0.5 - 0.325);
- g = 1.0;
- b = 0.0;
- } else if (level >= 0.5 && level < 0.6625) {
- r = 1.0;
- g = (0.6625 - level) / (0.6625 - 0.5f);
- b = 0.0;
- }
-
- // Intensity correction.
- double cf = 1.0;
- if (level >= 0.0 && level < 0.1) {
- cf = level / 0.1;
- }
- cf *= 255.0;
-
- // Pack RGB values into a 32-bit uint.
- uint32_t rr = (uint32_t) (r * cf + 0.5);
- uint32_t gg = (uint32_t) (g * cf + 0.5);
- uint32_t bb = (uint32_t) (b * cf + 0.5);
- return (rr << 16) + (gg << 8) + bb;
-}
diff --git a/lib/spek-palette.cc b/lib/spek-palette.cc
@@ -0,0 +1,61 @@
+/* spek-palette.cc
+ *
+ * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "spek-palette.h"
+
+// Modified version of Dan Bruton's algorithm:
+// http://www.physics.sfasu.edu/astro/color/spectra.html
+uint32_t spek_palette_spectrum(double level)
+{
+ level *= 0.6625;
+ double r = 0.0, g = 0.0, b = 0.0;
+ if (level >= 0 && level < 0.15) {
+ r = (0.15 - level) / (0.15 + 0.075);
+ g = 0.0;
+ b = 1.0;
+ } else if (level >= 0.15 && level < 0.275) {
+ r = 0.0;
+ g = (level - 0.15) / (0.275 - 0.15);
+ b = 1.0;
+ } else if (level >= 0.275 && level < 0.325) {
+ r = 0.0;
+ g = 1.0;
+ b = (0.325 - level) / (0.325 - 0.275);
+ } else if (level >= 0.325 && level < 0.5) {
+ r = (level - 0.325) / (0.5 - 0.325);
+ g = 1.0;
+ b = 0.0;
+ } else if (level >= 0.5 && level < 0.6625) {
+ r = 1.0;
+ g = (0.6625 - level) / (0.6625 - 0.5f);
+ b = 0.0;
+ }
+
+ // Intensity correction.
+ double cf = 1.0;
+ if (level >= 0.0 && level < 0.1) {
+ cf = level / 0.1;
+ }
+ cf *= 255.0;
+
+ // Pack RGB values into a 32-bit uint.
+ uint32_t rr = (uint32_t) (r * cf + 0.5);
+ uint32_t gg = (uint32_t) (g * cf + 0.5);
+ uint32_t bb = (uint32_t) (b * cf + 0.5);
+ return (rr << 16) + (gg << 8) + bb;
+}
diff --git a/lib/spek-palette.h b/lib/spek-palette.h
@@ -16,8 +16,8 @@
* along with Spek. If not, see <http://www.gnu.org/licenses/>.
*/
-#ifndef SPEK_PALETTE_HH_
-#define SPEK_PALETTE_HH_
+#ifndef SPEK_PALETTE_H_
+#define SPEK_PALETTE_H_
#include <stdint.h>
diff --git a/lib/spek-pipeline.c b/lib/spek-pipeline.c
@@ -1,369 +0,0 @@
-/* spek-pipeline.c
- *
- * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- *
- * Conversion of decoded samples into an FFT-happy format is heavily
- * influenced by GstSpectrum which is part of gst-plugins-good.
- * The original code:
- * (c) 1999 Erik Walthinsen <omega@cse.ogi.edu>
- * (c) 2006 Stefan Kost <ensonic@users.sf.net>
- * (c) 2007-2009 Sebastian Dröge <sebastian.droege@collabora.co.uk>
- */
-
-#include <assert.h>
-#include <math.h>
-#include <pthread.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "spek-audio.h"
-#include "spek-fft.h"
-
-#include "spek-pipeline.h"
-
-enum
-{
- NFFT = 64 // Number of FFTs to pre-fetch.
-};
-
-struct spek_pipeline
-{
- struct spek_audio_context *cx;
- const struct spek_audio_properties *properties;
- int bands;
- int samples;
- spek_pipeline_cb cb;
- void *cb_data;
-
- struct spek_fft_plan *fft;
- float *coss; // Pre-computed cos table.
- int nfft; // Size of the FFT transform.
- int input_size;
- int input_pos;
- float *input;
- float *output;
-
- pthread_t reader_thread;
- bool has_reader_thread;
- pthread_mutex_t reader_mutex;
- bool has_reader_mutex;
- pthread_cond_t reader_cond;
- bool has_reader_cond;
- pthread_t worker_thread;
- bool has_worker_thread;
- pthread_mutex_t worker_mutex;
- bool has_worker_mutex;
- pthread_cond_t worker_cond;
- bool has_worker_cond;
- bool worker_done;
- volatile bool quit;
-};
-
-// Forward declarations.
-static void * reader_func(void *);
-static void * worker_func(void *);
-static void reader_sync(struct spek_pipeline *p, int pos);
-static float average_input(const struct spek_pipeline *p, void *buffer);
-
-struct spek_pipeline * spek_pipeline_open(
- const char *path, int bands, int samples, spek_pipeline_cb cb, void *cb_data)
-{
- struct spek_pipeline *p = malloc(sizeof(struct spek_pipeline));
- p->cx = spek_audio_open(path);
- p->properties = spek_audio_get_properties(p->cx);
- p->bands = bands;
- p->samples = samples;
- p->cb = cb;
- p->cb_data = cb_data;
-
- p->coss = NULL;
- p->fft = NULL;
- p->input = NULL;
- p->output = NULL;
- p->has_reader_thread = false;
- p->has_reader_mutex = false;
- p->has_reader_cond = false;
- p->has_worker_thread = false;
- p->has_worker_mutex = false;
- p->has_worker_cond = false;
-
- if (!p->properties->error) {
- p->nfft = 2 * bands - 2;
- p->coss = malloc(p->nfft * sizeof(float));
- float cf = 2.0f * (float)M_PI / p->nfft;
- for (int i = 0; i < p->nfft; ++i) {
- p->coss[i] = cosf(cf * i);
- }
- p->fft = spek_fft_plan_new(p->nfft);
- p->input_size = p->nfft * (NFFT * 2 + 1);
- p->input = malloc(p->input_size * sizeof(float));
- p->output = malloc(bands * sizeof(float));
- spek_audio_start(p->cx, samples);
- }
-
- return p;
-}
-
-const struct spek_audio_properties * spek_pipeline_properties(struct spek_pipeline *pipeline)
-{
- return pipeline->properties;
-}
-
-void spek_pipeline_start(struct spek_pipeline *p)
-{
- if (p->properties->error) return;
-
- p->input_pos = 0;
- p->worker_done = false;
- p->quit = false;
-
- p->has_reader_mutex = !pthread_mutex_init(&p->reader_mutex, NULL);
- p->has_reader_cond = !pthread_cond_init(&p->reader_cond, NULL);
- p->has_worker_mutex = !pthread_mutex_init(&p->worker_mutex, NULL);
- p->has_worker_cond = !pthread_cond_init(&p->worker_cond, NULL);
-
- p->has_reader_thread = !pthread_create(&p->reader_thread, NULL, &reader_func, p);
- if (!p->has_reader_thread) {
- spek_pipeline_close(p);
- }
-}
-
-void spek_pipeline_close(struct spek_pipeline *p)
-{
- if (p->has_reader_thread) {
- p->quit = true;
- pthread_join(p->reader_thread, NULL);
- p->has_reader_thread = false;
- }
- if (p->has_worker_cond) {
- pthread_cond_destroy(&p->worker_cond);
- p->has_worker_cond = false;
- }
- if (p->has_worker_mutex) {
- pthread_mutex_destroy(&p->worker_mutex);
- p->has_worker_mutex = false;
- }
- if (p->has_reader_cond) {
- pthread_cond_destroy(&p->reader_cond);
- p->has_reader_cond = false;
- }
- if (p->has_reader_mutex) {
- pthread_mutex_destroy(&p->reader_mutex);
- p->has_reader_mutex = false;
- }
- if (p->output) {
- free(p->output);
- p->output = NULL;
- }
- if (p->input) {
- free(p->input);
- p->input = NULL;
- }
- if (p->fft) {
- spek_fft_delete(p->fft);
- p->fft = NULL;
- }
- if (p->coss) {
- free(p->coss);
- p->coss = NULL;
- }
- if (p->cx) {
- spek_audio_close(p->cx);
- p->cx = NULL;
- }
- free(p);
-}
-
-static void * reader_func(void *pp)
-{
- struct spek_pipeline *p = pp;
-
- p->has_worker_thread = !pthread_create(&p->worker_thread, NULL, &worker_func, p);
- if (!p->has_worker_thread) {
- return NULL;
- }
-
- int pos = 0, prev_pos = 0;
- int block_size = p->properties->width * p->properties->channels / 8;
- int size;
- while ((size = spek_audio_read(p->cx)) > 0) {
- if (p->quit) break;
-
- uint8_t *buffer = p->properties->buffer;
- while (size >= block_size) {
- p->input[pos] = average_input(p, buffer);
- buffer += block_size;
- size -= block_size;
- pos = (pos + 1) % p->input_size;
-
- // Wake up the worker if we have enough data.
- if ((pos > prev_pos ? pos : pos + p->input_size) - prev_pos == p->nfft * NFFT) {
- reader_sync(p, prev_pos = pos);
- }
- }
- assert(size == 0);
- }
-
- if (pos != prev_pos) {
- // Process the remaining data.
- reader_sync(p, pos);
- }
-
- // Force the worker to quit.
- reader_sync(p, -1);
- pthread_join(p->worker_thread, NULL);
-
- // Notify the client.
- p->cb(-1, NULL, p->cb_data);
- return NULL;
-}
-
-static void reader_sync(struct spek_pipeline *p, int pos)
-{
- pthread_mutex_lock(&p->reader_mutex);
- while (!p->worker_done) {
- pthread_cond_wait(&p->reader_cond, &p->reader_mutex);
- }
- p->worker_done = false;
- pthread_mutex_unlock(&p->reader_mutex);
-
- pthread_mutex_lock(&p->worker_mutex);
- p->input_pos = pos;
- pthread_cond_signal(&p->worker_cond);
- pthread_mutex_unlock(&p->worker_mutex);
-}
-
-static void * worker_func(void *pp)
-{
- struct spek_pipeline *p = pp;
-
- int sample = 0;
- int64_t frames = 0;
- int64_t num_fft = 0;
- int64_t acc_error = 0;
- int head = 0, tail = 0;
- int prev_head = 0;
-
- memset(p->output, 0, sizeof(float) * p->bands);
-
- while (true) {
- pthread_mutex_lock(&p->reader_mutex);
- p->worker_done = true;
- pthread_cond_signal(&p->reader_cond);
- pthread_mutex_unlock(&p->reader_mutex);
-
- pthread_mutex_lock(&p->worker_mutex);
- while (tail == p->input_pos) {
- pthread_cond_wait(&p->worker_cond, &p->worker_mutex);
- }
- tail = p->input_pos;
- pthread_mutex_unlock(&p->worker_mutex);
-
- if (tail == -1) {
- return NULL;
- }
-
- while (true) {
- head = (head + 1) % p->input_size;
- if (head == tail) {
- head = prev_head;
- break;
- }
- frames++;
-
- // If we have enough frames for an FFT or we have
- // all frames required for the interval run and FFT.
- bool int_full =
- acc_error < p->properties->error_base &&
- frames == p->properties->frames_per_interval;
- bool int_over =
- acc_error >= p->properties->error_base &&
- frames == 1 + p->properties->frames_per_interval;
-
- if (frames % p->nfft == 0 || ((int_full || int_over) && num_fft == 0)) {
- prev_head = head;
- for (int i = 0; i < p->nfft; i++) {
- float val = p->input[(p->input_size + head - p->nfft + i) % p->input_size];
- // TODO: allow the user to chose the window function
- // Hamming window.
- // val *= 0.53836f - 0.46164f * coss[i];
- // Hann window.
- val *= 0.5f * (1.0f - p->coss[i]);
- p->fft->input[i] = val;
- }
- spek_fft_execute(p->fft);
- num_fft++;
- for (int i = 0; i < p->bands; i++) {
- p->output[i] += p->fft->output[i];
- }
- }
-
- // Do we have the FFTs for one interval?
- if (int_full || int_over) {
- if (int_over) {
- acc_error -= p->properties->error_base;
- } else {
- acc_error += p->properties->error_per_interval;
- }
-
- for (int i = 0; i < p->bands; i++) {
- p->output[i] /= num_fft;
- }
-
- if (sample == p->samples) break;
- p->cb(sample++, p->output, p->cb_data);
-
- memset(p->output, 0, sizeof(float) * p->bands);
- frames = 0;
- num_fft = 0;
- }
- }
- }
-}
-
-static float average_input(const struct spek_pipeline *p, void *buffer)
-{
- int channels = p->properties->channels;
- float res = 0.0f;
- if (p->properties->fp) {
- if (p->properties->width == 32) {
- float *b = buffer;
- for (int i = 0; i < channels; i++) {
- res += b[i];
- }
- } else {
- assert(p->properties->width == 64);
- double *b = buffer;
- for (int i = 0; i < channels; i++) {
- res += (float) b[i];
- }
- }
- } else {
- if (p->properties->width == 16) {
- int16_t *b = buffer;
- for (int i = 0; i < channels; i++) {
- res += b[i] / (float) INT16_MAX;
- }
- } else {
- assert (p->properties->width == 32);
- int32_t *b = buffer;
- for (int i = 0; i < channels; i++) {
- res += b[i] / (float) INT32_MAX;
- }
- }
- }
- return res / channels;
-}
diff --git a/lib/spek-pipeline.cc b/lib/spek-pipeline.cc
@@ -0,0 +1,372 @@
+/* spek-pipeline.cc
+ *
+ * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * Conversion of decoded samples into an FFT-happy format is heavily
+ * influenced by GstSpectrum which is part of gst-plugins-good.
+ * The original code:
+ * (c) 1999 Erik Walthinsen <omega@cse.ogi.edu>
+ * (c) 2006 Stefan Kost <ensonic@users.sf.net>
+ * (c) 2007-2009 Sebastian Dröge <sebastian.droege@collabora.co.uk>
+ */
+
+#define __STDC_LIMIT_MACROS
+
+#include <assert.h>
+#include <math.h>
+#include <pthread.h>
+#include <stdint.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "spek-audio.h"
+#include "spek-fft.h"
+
+#include "spek-pipeline.h"
+
+enum
+{
+ NFFT = 64 // Number of FFTs to pre-fetch.
+};
+
+struct spek_pipeline
+{
+ struct spek_audio_context *cx;
+ const struct spek_audio_properties *properties;
+ int bands;
+ int samples;
+ spek_pipeline_cb cb;
+ void *cb_data;
+
+ struct spek_fft_plan *fft;
+ float *coss; // Pre-computed cos table.
+ int nfft; // Size of the FFT transform.
+ int input_size;
+ int input_pos;
+ float *input;
+ float *output;
+
+ pthread_t reader_thread;
+ bool has_reader_thread;
+ pthread_mutex_t reader_mutex;
+ bool has_reader_mutex;
+ pthread_cond_t reader_cond;
+ bool has_reader_cond;
+ pthread_t worker_thread;
+ bool has_worker_thread;
+ pthread_mutex_t worker_mutex;
+ bool has_worker_mutex;
+ pthread_cond_t worker_cond;
+ bool has_worker_cond;
+ bool worker_done;
+ volatile bool quit;
+};
+
+// Forward declarations.
+static void * reader_func(void *);
+static void * worker_func(void *);
+static void reader_sync(struct spek_pipeline *p, int pos);
+static float average_input(const struct spek_pipeline *p, void *buffer);
+
+struct spek_pipeline * spek_pipeline_open(
+ const char *path, int bands, int samples, spek_pipeline_cb cb, void *cb_data)
+{
+ struct spek_pipeline *p = (spek_pipeline*)malloc(sizeof(struct spek_pipeline));
+ p->cx = spek_audio_open(path);
+ p->properties = spek_audio_get_properties(p->cx);
+ p->bands = bands;
+ p->samples = samples;
+ p->cb = cb;
+ p->cb_data = cb_data;
+
+ p->coss = NULL;
+ p->fft = NULL;
+ p->input = NULL;
+ p->output = NULL;
+ p->has_reader_thread = false;
+ p->has_reader_mutex = false;
+ p->has_reader_cond = false;
+ p->has_worker_thread = false;
+ p->has_worker_mutex = false;
+ p->has_worker_cond = false;
+
+ if (!p->properties->error) {
+ p->nfft = 2 * bands - 2;
+ p->coss = (float*)malloc(p->nfft * sizeof(float));
+ float cf = 2.0f * (float)M_PI / p->nfft;
+ for (int i = 0; i < p->nfft; ++i) {
+ p->coss[i] = cosf(cf * i);
+ }
+ p->fft = spek_fft_plan_new(p->nfft);
+ p->input_size = p->nfft * (NFFT * 2 + 1);
+ p->input = (float*)malloc(p->input_size * sizeof(float));
+ p->output = (float*)malloc(bands * sizeof(float));
+ spek_audio_start(p->cx, samples);
+ }
+
+ return p;
+}
+
+const struct spek_audio_properties * spek_pipeline_properties(struct spek_pipeline *pipeline)
+{
+ return pipeline->properties;
+}
+
+void spek_pipeline_start(struct spek_pipeline *p)
+{
+ if (p->properties->error) return;
+
+ p->input_pos = 0;
+ p->worker_done = false;
+ p->quit = false;
+
+ p->has_reader_mutex = !pthread_mutex_init(&p->reader_mutex, NULL);
+ p->has_reader_cond = !pthread_cond_init(&p->reader_cond, NULL);
+ p->has_worker_mutex = !pthread_mutex_init(&p->worker_mutex, NULL);
+ p->has_worker_cond = !pthread_cond_init(&p->worker_cond, NULL);
+
+ p->has_reader_thread = !pthread_create(&p->reader_thread, NULL, &reader_func, p);
+ if (!p->has_reader_thread) {
+ spek_pipeline_close(p);
+ }
+}
+
+void spek_pipeline_close(struct spek_pipeline *p)
+{
+ if (p->has_reader_thread) {
+ p->quit = true;
+ pthread_join(p->reader_thread, NULL);
+ p->has_reader_thread = false;
+ }
+ if (p->has_worker_cond) {
+ pthread_cond_destroy(&p->worker_cond);
+ p->has_worker_cond = false;
+ }
+ if (p->has_worker_mutex) {
+ pthread_mutex_destroy(&p->worker_mutex);
+ p->has_worker_mutex = false;
+ }
+ if (p->has_reader_cond) {
+ pthread_cond_destroy(&p->reader_cond);
+ p->has_reader_cond = false;
+ }
+ if (p->has_reader_mutex) {
+ pthread_mutex_destroy(&p->reader_mutex);
+ p->has_reader_mutex = false;
+ }
+ if (p->output) {
+ free(p->output);
+ p->output = NULL;
+ }
+ if (p->input) {
+ free(p->input);
+ p->input = NULL;
+ }
+ if (p->fft) {
+ spek_fft_delete(p->fft);
+ p->fft = NULL;
+ }
+ if (p->coss) {
+ free(p->coss);
+ p->coss = NULL;
+ }
+ if (p->cx) {
+ spek_audio_close(p->cx);
+ p->cx = NULL;
+ }
+ free(p);
+}
+
+static void * reader_func(void *pp)
+{
+ struct spek_pipeline *p = (spek_pipeline*)pp;
+
+ p->has_worker_thread = !pthread_create(&p->worker_thread, NULL, &worker_func, p);
+ if (!p->has_worker_thread) {
+ return NULL;
+ }
+
+ int pos = 0, prev_pos = 0;
+ int block_size = p->properties->width * p->properties->channels / 8;
+ int size;
+ while ((size = spek_audio_read(p->cx)) > 0) {
+ if (p->quit) break;
+
+ uint8_t *buffer = p->properties->buffer;
+ while (size >= block_size) {
+ p->input[pos] = average_input(p, buffer);
+ buffer += block_size;
+ size -= block_size;
+ pos = (pos + 1) % p->input_size;
+
+ // Wake up the worker if we have enough data.
+ if ((pos > prev_pos ? pos : pos + p->input_size) - prev_pos == p->nfft * NFFT) {
+ reader_sync(p, prev_pos = pos);
+ }
+ }
+ assert(size == 0);
+ }
+
+ if (pos != prev_pos) {
+ // Process the remaining data.
+ reader_sync(p, pos);
+ }
+
+ // Force the worker to quit.
+ reader_sync(p, -1);
+ pthread_join(p->worker_thread, NULL);
+
+ // Notify the client.
+ p->cb(-1, NULL, p->cb_data);
+ return NULL;
+}
+
+static void reader_sync(struct spek_pipeline *p, int pos)
+{
+ pthread_mutex_lock(&p->reader_mutex);
+ while (!p->worker_done) {
+ pthread_cond_wait(&p->reader_cond, &p->reader_mutex);
+ }
+ p->worker_done = false;
+ pthread_mutex_unlock(&p->reader_mutex);
+
+ pthread_mutex_lock(&p->worker_mutex);
+ p->input_pos = pos;
+ pthread_cond_signal(&p->worker_cond);
+ pthread_mutex_unlock(&p->worker_mutex);
+}
+
+static void * worker_func(void *pp)
+{
+ struct spek_pipeline *p = (spek_pipeline*)pp;
+
+ int sample = 0;
+ int64_t frames = 0;
+ int64_t num_fft = 0;
+ int64_t acc_error = 0;
+ int head = 0, tail = 0;
+ int prev_head = 0;
+
+ memset(p->output, 0, sizeof(float) * p->bands);
+
+ while (true) {
+ pthread_mutex_lock(&p->reader_mutex);
+ p->worker_done = true;
+ pthread_cond_signal(&p->reader_cond);
+ pthread_mutex_unlock(&p->reader_mutex);
+
+ pthread_mutex_lock(&p->worker_mutex);
+ while (tail == p->input_pos) {
+ pthread_cond_wait(&p->worker_cond, &p->worker_mutex);
+ }
+ tail = p->input_pos;
+ pthread_mutex_unlock(&p->worker_mutex);
+
+ if (tail == -1) {
+ return NULL;
+ }
+
+ while (true) {
+ head = (head + 1) % p->input_size;
+ if (head == tail) {
+ head = prev_head;
+ break;
+ }
+ frames++;
+
+ // If we have enough frames for an FFT or we have
+ // all frames required for the interval run and FFT.
+ bool int_full =
+ acc_error < p->properties->error_base &&
+ frames == p->properties->frames_per_interval;
+ bool int_over =
+ acc_error >= p->properties->error_base &&
+ frames == 1 + p->properties->frames_per_interval;
+
+ if (frames % p->nfft == 0 || ((int_full || int_over) && num_fft == 0)) {
+ prev_head = head;
+ for (int i = 0; i < p->nfft; i++) {
+ float val = p->input[(p->input_size + head - p->nfft + i) % p->input_size];
+ // TODO: allow the user to chose the window function
+ // Hamming window.
+ // val *= 0.53836f - 0.46164f * coss[i];
+ // Hann window.
+ val *= 0.5f * (1.0f - p->coss[i]);
+ p->fft->input[i] = val;
+ }
+ spek_fft_execute(p->fft);
+ num_fft++;
+ for (int i = 0; i < p->bands; i++) {
+ p->output[i] += p->fft->output[i];
+ }
+ }
+
+ // Do we have the FFTs for one interval?
+ if (int_full || int_over) {
+ if (int_over) {
+ acc_error -= p->properties->error_base;
+ } else {
+ acc_error += p->properties->error_per_interval;
+ }
+
+ for (int i = 0; i < p->bands; i++) {
+ p->output[i] /= num_fft;
+ }
+
+ if (sample == p->samples) break;
+ p->cb(sample++, p->output, p->cb_data);
+
+ memset(p->output, 0, sizeof(float) * p->bands);
+ frames = 0;
+ num_fft = 0;
+ }
+ }
+ }
+}
+
+static float average_input(const struct spek_pipeline *p, void *buffer)
+{
+ int channels = p->properties->channels;
+ float res = 0.0f;
+ if (p->properties->fp) {
+ if (p->properties->width == 32) {
+ float *b = (float*)buffer;
+ for (int i = 0; i < channels; i++) {
+ res += b[i];
+ }
+ } else {
+ assert(p->properties->width == 64);
+ double *b = (double*)buffer;
+ for (int i = 0; i < channels; i++) {
+ res += (float) b[i];
+ }
+ }
+ } else {
+ if (p->properties->width == 16) {
+ int16_t *b = (int16_t*)buffer;
+ for (int i = 0; i < channels; i++) {
+ res += b[i] / (float) INT16_MAX;
+ }
+ } else {
+ assert (p->properties->width == 32);
+ int32_t *b = (int32_t*)buffer;
+ for (int i = 0; i < channels; i++) {
+ res += b[i] / (float) INT32_MAX;
+ }
+ }
+ }
+ return res / channels;
+}
diff --git a/lib/spek-utils.c b/lib/spek-utils.c
@@ -1,65 +0,0 @@
-/* spek-utils.c
- *
- * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <assert.h>
-#include <limits.h>
-#include <stdlib.h>
-
-#include "spek-utils.h"
-
-int spek_vercmp(const char *a, const char *b)
-{
- assert(a && b);
-
- if (!*a && !*b) {
- return 0;
- }
- if (!*a) {
- return -1;
- }
- if (!*b) {
- return 1;
- }
-
- char *i, *j;
- while(1) {
- i = j = NULL;
- long x = strtol(a, &i, 10);
- long y = strtol(b, &j, 10);
-
- if (x < y) {
- return -1;
- }
- if (x > y) {
- return 1;
- }
-
- if (!*i && !*j) {
- return 0;
- }
- if (!*i) {
- return -1;
- }
- if (!*j) {
- return 1;
- }
-
- a = i + 1;
- b = j + 1;
- }
-}
diff --git a/lib/spek-utils.cc b/lib/spek-utils.cc
@@ -0,0 +1,65 @@
+/* spek-utils.cc
+ *
+ * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <assert.h>
+#include <limits.h>
+#include <stdlib.h>
+
+#include "spek-utils.h"
+
+int spek_vercmp(const char *a, const char *b)
+{
+ assert(a && b);
+
+ if (!*a && !*b) {
+ return 0;
+ }
+ if (!*a) {
+ return -1;
+ }
+ if (!*b) {
+ return 1;
+ }
+
+ char *i, *j;
+ while(1) {
+ i = j = NULL;
+ long x = strtol(a, &i, 10);
+ long y = strtol(b, &j, 10);
+
+ if (x < y) {
+ return -1;
+ }
+ if (x > y) {
+ return 1;
+ }
+
+ if (!*i && !*j) {
+ return 0;
+ }
+ if (!*i) {
+ return -1;
+ }
+ if (!*j) {
+ return 1;
+ }
+
+ a = i + 1;
+ b = j + 1;
+ }
+}
diff --git a/po/spek.pot b/po/spek.pot
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2012-09-21 19:49-0700\n"
+"POT-Creation-Date: 2013-02-02 19:03-0800\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
@@ -34,179 +34,179 @@ msgstr ""
msgid "View spectrograms of your audio files"
msgstr ""
-#: ../src/spek-audio-desc.cc:38
+#: ../src/spek-audio-desc.cc:36
#, c-format
msgid "%d kbps"
msgstr ""
-#: ../src/spek-audio-desc.cc:41
+#: ../src/spek-audio-desc.cc:39
#, c-format
msgid "%d Hz"
msgstr ""
-#: ../src/spek-audio-desc.cc:46
+#: ../src/spek-audio-desc.cc:44
#, c-format
msgid "%d bit"
msgid_plural "%d bits"
msgstr[0] ""
msgstr[1] ""
-#: ../src/spek-audio-desc.cc:52
+#: ../src/spek-audio-desc.cc:50
#, c-format
msgid "%d channel"
msgid_plural "%d channels"
msgstr[0] ""
msgstr[1] ""
-#: ../src/spek-audio-desc.cc:69
+#: ../src/spek-audio-desc.cc:67
msgid "Cannot open input file"
msgstr ""
-#: ../src/spek-audio-desc.cc:72
+#: ../src/spek-audio-desc.cc:70
msgid "Cannot find stream info"
msgstr ""
-#: ../src/spek-audio-desc.cc:75
+#: ../src/spek-audio-desc.cc:73
msgid "The file contains no audio streams"
msgstr ""
-#: ../src/spek-audio-desc.cc:78
+#: ../src/spek-audio-desc.cc:76
msgid "Cannot find decoder"
msgstr ""
-#: ../src/spek-audio-desc.cc:81
+#: ../src/spek-audio-desc.cc:79
msgid "Unknown duration"
msgstr ""
-#: ../src/spek-audio-desc.cc:84
+#: ../src/spek-audio-desc.cc:82
msgid "No audio channels"
msgstr ""
-#: ../src/spek-audio-desc.cc:87
+#: ../src/spek-audio-desc.cc:85
msgid "Cannot open decoder"
msgstr ""
-#: ../src/spek-audio-desc.cc:90
+#: ../src/spek-audio-desc.cc:88
msgid "Unsupported sample format"
msgstr ""
#. TRANSLATORS: first %s is the error message, second %s is stream description.
-#: ../src/spek-audio-desc.cc:98
+#: ../src/spek-audio-desc.cc:96
#, c-format
msgid "%s: %s"
msgstr ""
-#: ../src/spek-preferences-dialog.cc:58
+#: ../src/spek-preferences-dialog.cc:61
msgid "Preferences"
msgstr ""
-#: ../src/spek-preferences-dialog.cc:63
+#: ../src/spek-preferences-dialog.cc:66
msgid "(system default)"
msgstr ""
#. TRANSLATORS: The name of a section in the Preferences dialog.
-#: ../src/spek-preferences-dialog.cc:70
+#: ../src/spek-preferences-dialog.cc:73
msgid "General"
msgstr ""
-#: ../src/spek-preferences-dialog.cc:79
+#: ../src/spek-preferences-dialog.cc:82
msgid "Language:"
msgstr ""
-#: ../src/spek-preferences-dialog.cc:95
+#: ../src/spek-preferences-dialog.cc:98
msgid "Check for &updates"
msgstr ""
-#: ../src/spek-spectrogram.cc:193
+#: ../src/spek-spectrogram.cc:191
#, c-format
msgid "%d kHz"
msgstr ""
-#: ../src/spek-spectrogram.cc:198
+#: ../src/spek-spectrogram.cc:196
#, c-format
msgid "%d dB"
msgstr ""
#. TRANSLATORS: keep "00" unchanged, it's used to calc the text width
-#: ../src/spek-spectrogram.cc:304
+#: ../src/spek-spectrogram.cc:302
msgid "00 kHz"
msgstr ""
#. TRANSLATORS: keep "-00" unchanged, it's used to calc the text width
-#: ../src/spek-spectrogram.cc:335
+#: ../src/spek-spectrogram.cc:333
msgid "-00 dB"
msgstr ""
-#: ../src/spek-window.cc:77
+#: ../src/spek-window.cc:75
msgid "Spek - Acoustic Spectrum Analyser"
msgstr ""
-#: ../src/spek-window.cc:97
+#: ../src/spek-window.cc:95
msgid "&File"
msgstr ""
-#: ../src/spek-window.cc:103
+#: ../src/spek-window.cc:101
msgid "&Edit"
msgstr ""
-#: ../src/spek-window.cc:107 ../src/spek-window.cc:112
+#: ../src/spek-window.cc:105 ../src/spek-window.cc:110
msgid "&Help"
msgstr ""
-#: ../src/spek-window.cc:135
+#: ../src/spek-window.cc:133
msgid "Help"
msgstr ""
-#: ../src/spek-window.cc:149
+#: ../src/spek-window.cc:147
msgid "A new version of Spek is available, click to download."
msgstr ""
#. TRANSLATORS: window title, %s is replaced with the file name
-#: ../src/spek-window.cc:187
+#: ../src/spek-window.cc:185
#, c-format
msgid "Spek - %s"
msgstr ""
-#: ../src/spek-window.cc:233
+#: ../src/spek-window.cc:231
msgid "All files"
msgstr ""
-#: ../src/spek-window.cc:235
+#: ../src/spek-window.cc:233
msgid "Audio files"
msgstr ""
-#: ../src/spek-window.cc:249
+#: ../src/spek-window.cc:247
msgid "Open File"
msgstr ""
-#: ../src/spek-window.cc:271
+#: ../src/spek-window.cc:269
msgid "PNG images"
msgstr ""
-#: ../src/spek-window.cc:277
+#: ../src/spek-window.cc:275
msgid "Save Spectrogram"
msgstr ""
#. Suggested name is <file_name>.png
-#: ../src/spek-window.cc:285
+#: ../src/spek-window.cc:283
msgid "Untitled"
msgstr ""
#. TRANSLATORS: Add your name here
-#: ../src/spek-window.cc:330
+#: ../src/spek-window.cc:329
msgid "translator-credits"
msgstr ""
-#: ../src/spek-window.cc:336
+#: ../src/spek-window.cc:335
msgid "Copyright (c) 2010-2012 Alexander Kojevnikov and contributors"
msgstr ""
-#: ../src/spek-window.cc:339
+#: ../src/spek-window.cc:338
msgid "Spek Website"
msgstr ""
#. TRANSLATORS: the %s is the package version.
-#: ../src/spek.cc:100
+#: ../src/spek.cc:98
#, c-format
msgid "Spek version %s"
msgstr ""
diff --git a/src/Makefile.am b/src/Makefile.am
@@ -1,24 +1,24 @@
bin_PROGRAMS = spek
spek_SOURCES = \
- spek-artwork.hh \
spek-artwork.cc \
+ spek-artwork.h \
spek-audio-desc.cc \
- spek-audio-desc.hh \
+ spek-audio-desc.h \
spek-events.cc \
- spek-events.hh \
+ spek-events.h \
spek-platform.cc \
- spek-platform.hh \
+ spek-platform.h \
spek-preferences-dialog.cc \
- spek-preferences-dialog.hh \
+ spek-preferences-dialog.h \
spek-preferences.cc \
- spek-preferences.hh \
+ spek-preferences.h \
spek-ruler.cc \
- spek-ruler.hh \
+ spek-ruler.h \
spek-spectrogram.cc \
- spek-spectrogram.hh \
+ spek-spectrogram.h \
spek-window.cc \
- spek-window.hh \
+ spek-window.h \
spek.cc
spek_CPPFLAGS = \
diff --git a/src/spek-artwork.cc b/src/spek-artwork.cc
@@ -19,7 +19,7 @@
#include <wx/artprov.h>
#include <wx/iconbndl.h>
-#include "spek-artwork.hh"
+#include "spek-artwork.h"
class SpekArtProvider : public wxArtProvider
{
diff --git a/src/spek-artwork.h b/src/spek-artwork.h
@@ -0,0 +1,32 @@
+/* spek-artwork.h
+ *
+ * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef SPEK_ARTWORK_H_
+#define SPEK_ARTWORK_H_
+
+#include <wx/string.h>
+
+#define ART_SPEK wxT("art-spek")
+#define ART_OPEN wxT("art-open")
+#define ART_SAVE wxT("art-save")
+#define ART_HELP wxT("art-help")
+#define ART_CLOSE wxT("art-close")
+
+void spek_artwork_init();
+
+#endif
diff --git a/src/spek-artwork.hh b/src/spek-artwork.hh
@@ -1,32 +0,0 @@
-/* spek-artwork.hh
- *
- * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef SPEK_ARTWORK_HH_
-#define SPEK_ARTWORK_HH_
-
-#include <wx/string.h>
-
-#define ART_SPEK wxT("art-spek")
-#define ART_OPEN wxT("art-open")
-#define ART_SAVE wxT("art-save")
-#define ART_HELP wxT("art-help")
-#define ART_CLOSE wxT("art-close")
-
-void spek_artwork_init();
-
-#endif
diff --git a/src/spek-audio-desc.cc b/src/spek-audio-desc.cc
@@ -19,11 +19,9 @@
#include <wx/arrstr.h>
#include <wx/intl.h>
-extern "C" {
#include <spek-audio.h>
-}
-#include "spek-audio-desc.hh"
+#include "spek-audio-desc.h"
#define ngettext wxPLURAL
diff --git a/src/spek-audio-desc.h b/src/spek-audio-desc.h
@@ -0,0 +1,28 @@
+/* spek-audio-desc.h
+ *
+ * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef SPEK_AUDIO_DESC_H_
+#define SPEK_AUDIO_DESC_H_
+
+#include <wx/string.h>
+
+struct spek_audio_properties;
+
+wxString spek_audio_desc(const struct spek_audio_properties *properties);
+
+#endif
diff --git a/src/spek-audio-desc.hh b/src/spek-audio-desc.hh
@@ -1,28 +0,0 @@
-/* spek-audio-desc.hh
- *
- * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef SPEK_AUDIO_DESC_HH_
-#define SPEK_AUDIO_DESC_HH_
-
-#include <wx/string.h>
-
-struct spek_audio_properties;
-
-wxString spek_audio_desc(const struct spek_audio_properties *properties);
-
-#endif
diff --git a/src/spek-events.cc b/src/spek-events.cc
@@ -16,7 +16,7 @@
* along with Spek. If not, see <http://www.gnu.org/licenses/>.
*/
-#include "spek-events.hh"
+#include "spek-events.h"
//IMPLEMENT_DYNAMIC_CLASS(SpekHaveSampleEvent, wxEvent)
DEFINE_EVENT_TYPE(SPEK_HAVE_SAMPLE)
diff --git a/src/spek-events.h b/src/spek-events.h
@@ -0,0 +1,53 @@
+/* spek-events.h
+ *
+ * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef SPEK_EVENTS_H_
+#define SPEK_EVENTS_H_
+
+#include <wx/wx.h>
+
+class SpekHaveSampleEvent: public wxEvent
+{
+public:
+ SpekHaveSampleEvent(int bands, int sample, float *values, bool free_values);
+ SpekHaveSampleEvent(const SpekHaveSampleEvent& other);
+ ~SpekHaveSampleEvent();
+
+ int get_bands() const { return this->bands; }
+ int get_sample() const { return this->sample; }
+ const float *get_values() const { return this->values; }
+
+ wxEvent *Clone() const { return new SpekHaveSampleEvent(*this); }
+// DECLARE_DYNAMIC_CLASS(SpekHaveSampleEvent);
+
+private:
+ int bands;
+ int sample;
+ float *values;
+ bool free_values;
+};
+
+typedef void (wxEvtHandler::*SpekHaveSampleEventFunction)(SpekHaveSampleEvent&);
+
+DECLARE_EVENT_TYPE(SPEK_HAVE_SAMPLE, wxID_ANY)
+
+#define SPEK_EVT_HAVE_SAMPLE(fn) \
+ DECLARE_EVENT_TABLE_ENTRY(SPEK_HAVE_SAMPLE, -1, -1, \
+ (wxObjectEventFunction) (SpekHaveSampleEventFunction) &fn, (wxObject *) NULL ),
+
+#endif
diff --git a/src/spek-events.hh b/src/spek-events.hh
@@ -1,53 +0,0 @@
-/* spek-events.hh
- *
- * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef SPEK_EVENTS_HH_
-#define SPEK_EVENTS_HH_
-
-#include <wx/wx.h>
-
-class SpekHaveSampleEvent: public wxEvent
-{
-public:
- SpekHaveSampleEvent(int bands, int sample, float *values, bool free_values);
- SpekHaveSampleEvent(const SpekHaveSampleEvent& other);
- ~SpekHaveSampleEvent();
-
- int get_bands() const { return this->bands; }
- int get_sample() const { return this->sample; }
- const float *get_values() const { return this->values; }
-
- wxEvent *Clone() const { return new SpekHaveSampleEvent(*this); }
-// DECLARE_DYNAMIC_CLASS(SpekHaveSampleEvent);
-
-private:
- int bands;
- int sample;
- float *values;
- bool free_values;
-};
-
-typedef void (wxEvtHandler::*SpekHaveSampleEventFunction)(SpekHaveSampleEvent&);
-
-DECLARE_EVENT_TYPE(SPEK_HAVE_SAMPLE, wxID_ANY)
-
-#define SPEK_EVT_HAVE_SAMPLE(fn) \
- DECLARE_EVENT_TABLE_ENTRY(SPEK_HAVE_SAMPLE, -1, -1, \
- (wxObjectEventFunction) (SpekHaveSampleEventFunction) &fn, (wxObject *) NULL ),
-
-#endif
diff --git a/src/spek-platform.cc b/src/spek-platform.cc
@@ -26,7 +26,7 @@
#include <wx/stdpaths.h>
#include <wx/utils.h>
-#include "spek-platform.hh"
+#include "spek-platform.h"
void spek_platform_init()
{
diff --git a/src/spek-platform.h b/src/spek-platform.h
@@ -0,0 +1,37 @@
+/* spek-platform.h
+ *
+ * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef SPEK_PLATFORM_H_
+#define SPEK_PLATFORM_H_
+
+#include <wx/string.h>
+
+// Platform-specific initialisation code.
+void spek_platform_init();
+
+// Not quite XDG-compatible, but close enough.
+wxString spek_platform_config_path(const wxString& app_name);
+
+// Setting non-default locale under GTK+ is tricky (see e.g. how FileZilla does it). We will
+// just disable the language setting for GTK+ users and will always use the system locale.
+bool spek_platform_can_change_language();
+
+// Fonts are smaller on OSX.
+double spek_platform_font_scale();
+
+#endif
diff --git a/src/spek-platform.hh b/src/spek-platform.hh
@@ -1,37 +0,0 @@
-/* spek-platform.hh
- *
- * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef SPEK_PLATFORM_HH_
-#define SPEK_PLATFORM_HH_
-
-#include <wx/string.h>
-
-// Platform-specific initialisation code.
-void spek_platform_init();
-
-// Not quite XDG-compatible, but close enough.
-wxString spek_platform_config_path(const wxString& app_name);
-
-// Setting non-default locale under GTK+ is tricky (see e.g. how FileZilla does it). We will
-// just disable the language setting for GTK+ users and will always use the system locale.
-bool spek_platform_can_change_language();
-
-// Fonts are smaller on OSX.
-double spek_platform_font_scale();
-
-#endif
diff --git a/src/spek-preferences-dialog.cc b/src/spek-preferences-dialog.cc
@@ -16,10 +16,10 @@
* along with Spek. If not, see <http://www.gnu.org/licenses/>.
*/
-#include "spek-platform.hh"
-#include "spek-preferences.hh"
+#include "spek-platform.h"
+#include "spek-preferences.h"
-#include "spek-preferences-dialog.hh"
+#include "spek-preferences-dialog.h"
// List all languages with a decent (e.g. 80%) number of translated
// strings. Don't translate language names. Keep the first line intact.
diff --git a/src/spek-preferences-dialog.h b/src/spek-preferences-dialog.h
@@ -0,0 +1,38 @@
+/* spek-preferences-dialog.h
+ *
+ * Copyright (C) 2011-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef SPEK_PREFERENCES_DIALOG_H_
+#define SPEK_PREFERENCES_DIALOG_H_
+
+#include <wx/wx.h>
+
+class SpekPreferencesDialog : public wxDialog
+{
+public:
+ SpekPreferencesDialog(wxWindow *parent);
+
+private:
+ void on_language(wxCommandEvent& event);
+ void on_check(wxCommandEvent& event);
+
+ wxArrayString languages;
+
+ DECLARE_EVENT_TABLE()
+};
+
+#endif
diff --git a/src/spek-preferences-dialog.hh b/src/spek-preferences-dialog.hh
@@ -1,38 +0,0 @@
-/* spek-preferences-dialog.hh
- *
- * Copyright (C) 2011-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef SPEK_PREFERENCES_DIALOG_HH_
-#define SPEK_PREFERENCES_DIALOG_HH_
-
-#include <wx/wx.h>
-
-class SpekPreferencesDialog : public wxDialog
-{
-public:
- SpekPreferencesDialog(wxWindow *parent);
-
-private:
- void on_language(wxCommandEvent& event);
- void on_check(wxCommandEvent& event);
-
- wxArrayString languages;
-
- DECLARE_EVENT_TABLE()
-};
-
-#endif
diff --git a/src/spek-preferences.cc b/src/spek-preferences.cc
@@ -18,9 +18,9 @@
#include <wx/string.h>
-#include "spek-platform.hh"
+#include "spek-platform.h"
-#include "spek-preferences.hh"
+#include "spek-preferences.h"
SpekPreferences& SpekPreferences::get()
{
diff --git a/src/spek-preferences.h b/src/spek-preferences.h
@@ -0,0 +1,47 @@
+/* spek-preferences.h
+ *
+ * Copyright (C) 2011-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef SPEK_PREFERENCES_H_
+#define SPEK_PREFERENCES_H_
+
+#include <wx/fileconf.h>
+#include <wx/intl.h>
+
+class SpekPreferences
+{
+public:
+ static SpekPreferences& get();
+
+ void init();
+ bool get_check_update();
+ void set_check_update(bool value);
+ long get_last_update();
+ void set_last_update(long value);
+ wxString get_language();
+ void set_language(const wxString& value);
+
+private:
+ SpekPreferences();
+ SpekPreferences(const SpekPreferences&);
+ void operator=(const SpekPreferences&);
+
+ wxLocale *locale;
+ wxFileConfig *config;
+};
+
+#endif
diff --git a/src/spek-preferences.hh b/src/spek-preferences.hh
@@ -1,47 +0,0 @@
-/* spek-preferences.hh
- *
- * Copyright (C) 2011-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef SPEK_PREFERENCES_HH_
-#define SPEK_PREFERENCES_HH_
-
-#include <wx/fileconf.h>
-#include <wx/intl.h>
-
-class SpekPreferences
-{
-public:
- static SpekPreferences& get();
-
- void init();
- bool get_check_update();
- void set_check_update(bool value);
- long get_last_update();
- void set_last_update(long value);
- wxString get_language();
- void set_language(const wxString& value);
-
-private:
- SpekPreferences();
- SpekPreferences(const SpekPreferences&);
- void operator=(const SpekPreferences&);
-
- wxLocale *locale;
- wxFileConfig *config;
-};
-
-#endif
diff --git a/src/spek-ruler.cc b/src/spek-ruler.cc
@@ -18,7 +18,7 @@
#include <cmath>
-#include "spek-ruler.hh"
+#include "spek-ruler.h"
SpekRuler::SpekRuler(
int x, int y, Position pos, wxString sample_label,
diff --git a/src/spek-ruler.h b/src/spek-ruler.h
@@ -0,0 +1,62 @@
+/* spek-ruler.h
+ *
+ * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef SPEK_RULER_H_
+#define SPEK_RULER_H_
+
+#include <wx/dc.h>
+#include <wx/string.h>
+
+class SpekRuler
+{
+public:
+ enum Position
+ {
+ TOP,
+ RIGHT,
+ BOTTOM,
+ LEFT
+ };
+
+ typedef wxString (*formatter_cb)(int unit);
+
+ SpekRuler(
+ int x, int y, Position pos, wxString sample_label,
+ int *factors, int min_units, int max_units, double spacing,
+ double scale, double offset, formatter_cb formatter
+ );
+
+ void draw(wxDC& dc);
+
+protected:
+ void draw_tick(wxDC& dc, int tick);
+
+ int x;
+ int y;
+ Position pos;
+ wxString sample_label;
+ int *factors;
+ int min_units;
+ int max_units;
+ double spacing;
+ double scale;
+ double offset;
+ formatter_cb formatter;
+};
+
+#endif
diff --git a/src/spek-ruler.hh b/src/spek-ruler.hh
@@ -1,62 +0,0 @@
-/* spek-ruler.hh
- *
- * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef SPEK_RULER_HH_
-#define SPEK_RULER_HH_
-
-#include <wx/dc.h>
-#include <wx/string.h>
-
-class SpekRuler
-{
-public:
- enum Position
- {
- TOP,
- RIGHT,
- BOTTOM,
- LEFT
- };
-
- typedef wxString (*formatter_cb)(int unit);
-
- SpekRuler(
- int x, int y, Position pos, wxString sample_label,
- int *factors, int min_units, int max_units, double spacing,
- double scale, double offset, formatter_cb formatter
- );
-
- void draw(wxDC& dc);
-
-protected:
- void draw_tick(wxDC& dc, int tick);
-
- int x;
- int y;
- Position pos;
- wxString sample_label;
- int *factors;
- int min_units;
- int max_units;
- double spacing;
- double scale;
- double offset;
- formatter_cb formatter;
-};
-
-#endif
diff --git a/src/spek-spectrogram.cc b/src/spek-spectrogram.cc
@@ -20,19 +20,17 @@
#include <wx/dcbuffer.h>
-extern "C" {
#include <spek-audio.h>
#include <spek-palette.h>
#include <spek-pipeline.h>
#include <spek-utils.h>
-}
-#include "spek-audio-desc.hh"
-#include "spek-events.hh"
-#include "spek-platform.hh"
-#include "spek-ruler.hh"
+#include "spek-audio-desc.h"
+#include "spek-events.h"
+#include "spek-platform.h"
+#include "spek-ruler.h"
-#include "spek-spectrogram.hh"
+#include "spek-spectrogram.h"
BEGIN_EVENT_TABLE(SpekSpectrogram, wxWindow)
EVT_CHAR(SpekSpectrogram::on_char)
diff --git a/src/spek-spectrogram.h b/src/spek-spectrogram.h
@@ -0,0 +1,60 @@
+/* spek-spectrogram.h
+ *
+ * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef SPEK_SPECTROGRAM_H_
+#define SPEK_SPECTROGRAM_H_
+
+#include <wx/wx.h>
+
+class SpekHaveSampleEvent;
+struct spek_audio_properties;
+struct spek_pipeline;
+
+class SpekSpectrogram : public wxWindow
+{
+public:
+ SpekSpectrogram(wxFrame *parent);
+ ~SpekSpectrogram();
+ void open(const wxString& path);
+ void save(const wxString& path);
+
+private:
+ void on_char(wxKeyEvent& evt);
+ void on_paint(wxPaintEvent& evt);
+ void on_size(wxSizeEvent& evt);
+ void on_have_sample(SpekHaveSampleEvent& evt);
+ void render(wxDC& dc);
+
+ void start();
+ void stop();
+
+ spek_pipeline *pipeline;
+ wxString path;
+ wxString desc;
+ double duration;
+ int sample_rate;
+ wxImage palette;
+ wxImage image;
+ int prev_width;
+ int urange;
+ int lrange;
+
+ DECLARE_EVENT_TABLE()
+};
+
+#endif
diff --git a/src/spek-spectrogram.hh b/src/spek-spectrogram.hh
@@ -1,60 +0,0 @@
-/* spek-spectrogram.hh
- *
- * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef SPEK_SPECTROGRAM_HH_
-#define SPEK_SPECTROGRAM_HH_
-
-#include <wx/wx.h>
-
-class SpekHaveSampleEvent;
-struct spek_audio_properties;
-struct spek_pipeline;
-
-class SpekSpectrogram : public wxWindow
-{
-public:
- SpekSpectrogram(wxFrame *parent);
- ~SpekSpectrogram();
- void open(const wxString& path);
- void save(const wxString& path);
-
-private:
- void on_char(wxKeyEvent& evt);
- void on_paint(wxPaintEvent& evt);
- void on_size(wxSizeEvent& evt);
- void on_have_sample(SpekHaveSampleEvent& evt);
- void render(wxDC& dc);
-
- void start();
- void stop();
-
- spek_pipeline *pipeline;
- wxString path;
- wxString desc;
- double duration;
- int sample_rate;
- wxImage palette;
- wxImage image;
- int prev_width;
- int urange;
- int lrange;
-
- DECLARE_EVENT_TABLE()
-};
-
-#endif
diff --git a/src/spek-window.cc b/src/spek-window.cc
@@ -26,16 +26,14 @@
// WX on WIN doesn't like it when pthread.h is included first.
#include <pthread.h>
-extern "C" {
#include <spek-utils.h>
-}
-#include "spek-artwork.hh"
-#include "spek-preferences-dialog.hh"
-#include "spek-preferences.hh"
-#include "spek-spectrogram.hh"
+#include "spek-artwork.h"
+#include "spek-preferences-dialog.h"
+#include "spek-preferences.h"
+#include "spek-spectrogram.h"
-#include "spek-window.hh"
+#include "spek-window.h"
DECLARE_EVENT_TYPE(SPEK_NOTIFY_EVENT, -1)
DEFINE_EVENT_TYPE(SPEK_NOTIFY_EVENT)
diff --git a/src/spek-window.h b/src/spek-window.h
@@ -0,0 +1,51 @@
+/* spek-window.h
+ *
+ * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef SPEK_WINDOW_H_
+#define SPEK_WINDOW_H_
+
+#include <wx/wx.h>
+
+class SpekSpectrogram;
+
+class SpekWindow : public wxFrame
+{
+public:
+ SpekWindow(const wxString& path);
+ void open(const wxString& path);
+
+private:
+ void on_open(wxCommandEvent& event);
+ void on_save(wxCommandEvent& event);
+ void on_exit(wxCommandEvent& event);
+ void on_preferences(wxCommandEvent& event);
+ void on_help(wxCommandEvent& event);
+ void on_about(wxCommandEvent& event);
+ void on_notify(wxCommandEvent& event);
+ void on_visit(wxCommandEvent& event);
+ void on_close(wxCommandEvent& event);
+
+ SpekSpectrogram *spectrogram;
+ wxString path;
+ wxString cur_dir;
+ wxString description;
+
+ DECLARE_EVENT_TABLE()
+};
+
+#endif
diff --git a/src/spek-window.hh b/src/spek-window.hh
@@ -1,51 +0,0 @@
-/* spek-window.hh
- *
- * Copyright (C) 2010-2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef SPEK_WINDOW_HH_
-#define SPEK_WINDOW_HH_
-
-#include <wx/wx.h>
-
-class SpekSpectrogram;
-
-class SpekWindow : public wxFrame
-{
-public:
- SpekWindow(const wxString& path);
- void open(const wxString& path);
-
-private:
- void on_open(wxCommandEvent& event);
- void on_save(wxCommandEvent& event);
- void on_exit(wxCommandEvent& event);
- void on_preferences(wxCommandEvent& event);
- void on_help(wxCommandEvent& event);
- void on_about(wxCommandEvent& event);
- void on_notify(wxCommandEvent& event);
- void on_visit(wxCommandEvent& event);
- void on_close(wxCommandEvent& event);
-
- SpekSpectrogram *spectrogram;
- wxString path;
- wxString cur_dir;
- wxString description;
-
- DECLARE_EVENT_TABLE()
-};
-
-#endif
diff --git a/src/spek.cc b/src/spek.cc
@@ -20,15 +20,13 @@
#include <wx/log.h>
#include <wx/socket.h>
-extern "C" {
#include <spek-audio.h>
-}
-#include "spek-artwork.hh"
-#include "spek-platform.hh"
-#include "spek-preferences.hh"
+#include "spek-artwork.h"
+#include "spek-platform.h"
+#include "spek-preferences.h"
-#include "spek-window.hh"
+#include "spek-window.h"
class Spek: public wxApp
{
diff --git a/tests/test-utils.c b/tests/test-utils.c
@@ -1,44 +0,0 @@
-/* test-utils.c
- *
- * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <spek-utils.h>
-
-#include "test.h"
-
-int main()
-{
- ensure(0 == spek_vercmp("1.2.3", "1.2.3"), "1.2.3 == 1.2.3");
- ensure(1 == spek_vercmp("1.2.3", "1.2.2"), "1.2.3 > 1.2.2");
- ensure(-1 == spek_vercmp("1.2.2", "1.2.3"), "1.2.2 < 1.2.3");
- ensure(1 == spek_vercmp("1.2.3", "1"), "1.2.3 > 1");
- ensure(1 == spek_vercmp("1.2.3", "1."), "1.2.3 > 1.");
- ensure(1 == spek_vercmp("1.2.3", "1.2"), "1.2.3 > 1.2");
- ensure(1 == spek_vercmp("1.2.3", "1.2."), "1.2.3 > 1.2.");
- ensure(1 == spek_vercmp("1.15.3", "1.2"), "1.15.3 > 1.2");
- ensure(1 == spek_vercmp("2", "1.2.2"), "2 > 1.2.2");
- ensure(1 == spek_vercmp("1.2.3", ""), "1.2.3 > ''");
- ensure(0 == spek_vercmp("", ""), "'' == ''");
- ensure(0 == spek_vercmp("123", "123"), "123 == 123");
- ensure(-1 == spek_vercmp("0.2.3", "1"), "0.2.3 < 1");
- ensure(-1 == spek_vercmp("0.9.8", "0.10.1"), "0.9.8 < 0.10.1");
- ensure(-1 == spek_vercmp("1.200", "2.20"), "1.200 < 2.20");
- ensure(-1 == spek_vercmp("1.0.0", "2.0.0"), "1.0.0 < 2.0.0");
- ensure(-1 == spek_vercmp("1.0.0", "1.0.1"), "1.0.0 < 1.0.1");
-
- return 0;
-}
diff --git a/tests/test-utils.cc b/tests/test-utils.cc
@@ -0,0 +1,44 @@
+/* test-utils.cc
+ *
+ * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <spek-utils.h>
+
+#include "test.h"
+
+int main()
+{
+ ensure(0 == spek_vercmp("1.2.3", "1.2.3"), "1.2.3 == 1.2.3");
+ ensure(1 == spek_vercmp("1.2.3", "1.2.2"), "1.2.3 > 1.2.2");
+ ensure(-1 == spek_vercmp("1.2.2", "1.2.3"), "1.2.2 < 1.2.3");
+ ensure(1 == spek_vercmp("1.2.3", "1"), "1.2.3 > 1");
+ ensure(1 == spek_vercmp("1.2.3", "1."), "1.2.3 > 1.");
+ ensure(1 == spek_vercmp("1.2.3", "1.2"), "1.2.3 > 1.2");
+ ensure(1 == spek_vercmp("1.2.3", "1.2."), "1.2.3 > 1.2.");
+ ensure(1 == spek_vercmp("1.15.3", "1.2"), "1.15.3 > 1.2");
+ ensure(1 == spek_vercmp("2", "1.2.2"), "2 > 1.2.2");
+ ensure(1 == spek_vercmp("1.2.3", ""), "1.2.3 > ''");
+ ensure(0 == spek_vercmp("", ""), "'' == ''");
+ ensure(0 == spek_vercmp("123", "123"), "123 == 123");
+ ensure(-1 == spek_vercmp("0.2.3", "1"), "0.2.3 < 1");
+ ensure(-1 == spek_vercmp("0.9.8", "0.10.1"), "0.9.8 < 0.10.1");
+ ensure(-1 == spek_vercmp("1.200", "2.20"), "1.200 < 2.20");
+ ensure(-1 == spek_vercmp("1.0.0", "2.0.0"), "1.0.0 < 2.0.0");
+ ensure(-1 == spek_vercmp("1.0.0", "1.0.1"), "1.0.0 < 1.0.1");
+
+ return 0;
+}
diff --git a/tests/test.c b/tests/test.c
@@ -1,26 +0,0 @@
-/* test.c
- *
- * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
- *
- * Spek is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * Spek is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with Spek. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include "test.h"
-
-int main()
-{
- ensure(2 + 2 == 4, "Hello, tests!");
-
- return 0;
-}
diff --git a/tests/test.cc b/tests/test.cc
@@ -0,0 +1,26 @@
+/* test.cc
+ *
+ * Copyright (C) 2012 Alexander Kojevnikov <alexander@kojevnikov.com>
+ *
+ * Spek is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Spek is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Spek. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "test.h"
+
+int main()
+{
+ ensure(2 + 2 == 4, "Hello, tests!");
+
+ return 0;
+}