mirror of
https://github.com/clangen/musikcube.git
synced 2024-11-19 11:10:52 +00:00
Added a new IDebug
interface to the SDK -- plugins can opt-in to get an instance to one of these and write debug information to the standard location, just like the rest of the app.
This commit is contained in:
parent
1b4b9127c4
commit
cc134775ef
@ -10,6 +10,7 @@ musikcube:
|
|||||||
* added the ability to customize the key used to quit the app. it is currently
|
* added the ability to customize the key used to quit the app. it is currently
|
||||||
not exposed in the ui, but it can be changed by editing
|
not exposed in the ui, but it can be changed by editing
|
||||||
`~/.musikcube/settings.json` and updating the `AppQuitKey`.
|
`~/.musikcube/settings.json` and updating the `AppQuitKey`.
|
||||||
|
* scrapped and re-implemented the debug log viewer, accessible via `ctrl+~`
|
||||||
* added feodra 29 support (dvdmuckle)
|
* added feodra 29 support (dvdmuckle)
|
||||||
* fixed configuration script bugs that were causing breakage in FreeBSD
|
* fixed configuration script bugs that were causing breakage in FreeBSD
|
||||||
* migrated to non-bundled `taglib` for macOS and most Linux distributions
|
* migrated to non-bundled `taglib` for macOS and most Linux distributions
|
||||||
@ -19,6 +20,10 @@ musikcube:
|
|||||||
musikdroid:
|
musikdroid:
|
||||||
* updated to compile against the latest tooling
|
* updated to compile against the latest tooling
|
||||||
|
|
||||||
|
sdk:
|
||||||
|
* added a new `IDebug` interface plugins can request via `SetDebug` to write
|
||||||
|
log information to the standard location, just like the rest of the app.
|
||||||
|
|
||||||
--------------------------------------------------------------------------------
|
--------------------------------------------------------------------------------
|
||||||
|
|
||||||
0.51.0
|
0.51.0
|
||||||
|
@ -99,11 +99,8 @@ void GaplessTransport::PrepareNextTrack(const std::string& uri, Gain gain) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void GaplessTransport::Start(const std::string& uri, Gain gain, StartMode mode) {
|
void GaplessTransport::Start(const std::string& uri, Gain gain, StartMode mode) {
|
||||||
musik::debug::info(TAG, "we were asked to start the track at " + uri);
|
musik::debug::info(TAG, "starting track at " + uri);
|
||||||
|
|
||||||
Player* newPlayer = Player::Create(uri, this->output, Player::NoDrain, this, gain);
|
Player* newPlayer = Player::Create(uri, this->output, Player::NoDrain, this, gain);
|
||||||
musik::debug::info(TAG, "Player created successfully");
|
|
||||||
|
|
||||||
this->StartWithPlayer(newPlayer, mode);
|
this->StartWithPlayer(newPlayer, mode);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -118,7 +118,7 @@ namespace musik { namespace core { namespace audio {
|
|||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
musik::debug::info(TAG, "about ready to play: " + uri);
|
musik::debug::info(TAG, "found a decoder for " + uri);
|
||||||
|
|
||||||
return decoder;
|
return decoder;
|
||||||
}
|
}
|
||||||
|
@ -92,7 +92,6 @@ bool LocalFileStream::Open(const char *filename, unsigned int options) {
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (this->file.load()) {
|
if (this->file.load()) {
|
||||||
debug::info(TAG, "opened successfully");
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -39,6 +39,7 @@
|
|||||||
#include <core/support/Common.h>
|
#include <core/support/Common.h>
|
||||||
#include <core/support/Preferences.h>
|
#include <core/support/Preferences.h>
|
||||||
|
|
||||||
|
#include <core/debug.h>
|
||||||
#include <core/io/DataStreamFactory.h>
|
#include <core/io/DataStreamFactory.h>
|
||||||
#include <core/audio/Buffer.h>
|
#include <core/audio/Buffer.h>
|
||||||
#include <core/audio/Streams.h>
|
#include <core/audio/Streams.h>
|
||||||
@ -49,6 +50,7 @@
|
|||||||
#include <core/runtime/Message.h>
|
#include <core/runtime/Message.h>
|
||||||
#include <core/support/Messages.h>
|
#include <core/support/Messages.h>
|
||||||
|
|
||||||
|
#include <core/sdk/IDebug.h>
|
||||||
#include <core/sdk/IIndexerNotifier.h>
|
#include <core/sdk/IIndexerNotifier.h>
|
||||||
#include <core/sdk/IEnvironment.h>
|
#include <core/sdk/IEnvironment.h>
|
||||||
|
|
||||||
@ -60,6 +62,7 @@ using namespace musik::core::runtime;
|
|||||||
using namespace musik::core::sdk;
|
using namespace musik::core::sdk;
|
||||||
|
|
||||||
typedef void(*SetEnvironment)(IEnvironment*);
|
typedef void(*SetEnvironment)(IEnvironment*);
|
||||||
|
typedef void(*SetDebug)(IDebug*);
|
||||||
typedef void(*SetSimpleDataProvider)(ISimpleDataProvider*);
|
typedef void(*SetSimpleDataProvider)(ISimpleDataProvider*);
|
||||||
typedef void(*SetIndexerNotifier)(IIndexerNotifier*);
|
typedef void(*SetIndexerNotifier)(IIndexerNotifier*);
|
||||||
|
|
||||||
@ -79,7 +82,26 @@ static void saveEnvironment() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static class Environment : public IEnvironment {
|
static class Debug: public IDebug {
|
||||||
|
public:
|
||||||
|
virtual void Verbose(const char* tag, const char* message) override {
|
||||||
|
musik::debug::verbose(tag, message);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void Info(const char* tag, const char* message) override {
|
||||||
|
musik::debug::info(tag, message);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void Warning(const char* tag, const char* message) override {
|
||||||
|
musik::debug::warning(tag, message);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void Error(const char* tag, const char* message) override {
|
||||||
|
musik::debug::error(tag, message);
|
||||||
|
}
|
||||||
|
} debugger;
|
||||||
|
|
||||||
|
static class Environment: public IEnvironment {
|
||||||
public:
|
public:
|
||||||
virtual size_t GetPath(PathType type, char* dst, int size) override {
|
virtual size_t GetPath(PathType type, char* dst, int size) override {
|
||||||
std::string path;
|
std::string path;
|
||||||
@ -110,6 +132,10 @@ static class Environment : public IEnvironment {
|
|||||||
return streams::GetEncoderForType(type);
|
return streams::GetEncoderForType(type);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
virtual IDebug* GetDebug() override {
|
||||||
|
return &debugger;
|
||||||
|
}
|
||||||
|
|
||||||
virtual IPreferences* GetPreferences(const char* name) override {
|
virtual IPreferences* GetPreferences(const char* name) override {
|
||||||
return Preferences::Unmanaged(name ? name : std::string());
|
return Preferences::Unmanaged(name ? name : std::string());
|
||||||
}
|
}
|
||||||
@ -266,6 +292,13 @@ namespace musik { namespace core { namespace plugin {
|
|||||||
[](musik::core::sdk::IPlugin* plugin, SetEnvironment func) {
|
[](musik::core::sdk::IPlugin* plugin, SetEnvironment func) {
|
||||||
func(&environment);
|
func(&environment);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
/* debug */
|
||||||
|
PluginFactory::Instance().QueryFunction<SetDebug>(
|
||||||
|
"SetDebug",
|
||||||
|
[](musik::core::sdk::IPlugin* plugin, SetDebug func) {
|
||||||
|
func(&debugger);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
void UninstallDependencies() {
|
void UninstallDependencies() {
|
||||||
@ -299,6 +332,13 @@ namespace musik { namespace core { namespace plugin {
|
|||||||
[](musik::core::sdk::IPlugin* plugin, SetEnvironment func) {
|
[](musik::core::sdk::IPlugin* plugin, SetEnvironment func) {
|
||||||
func(nullptr);
|
func(nullptr);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
/* debug */
|
||||||
|
PluginFactory::Instance().QueryFunction<SetDebug>(
|
||||||
|
"SetDebug",
|
||||||
|
[](musik::core::sdk::IPlugin* plugin, SetDebug func) {
|
||||||
|
func(nullptr);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
} } }
|
} } }
|
||||||
|
47
src/core/sdk/IDebug.h
Normal file
47
src/core/sdk/IDebug.h
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// Copyright (c) 2007-2017 musikcube team
|
||||||
|
//
|
||||||
|
// All rights reserved.
|
||||||
|
//
|
||||||
|
// Redistribution and use in source and binary forms, with or without
|
||||||
|
// modification, are permitted provided that the following conditions are met:
|
||||||
|
//
|
||||||
|
// * Redistributions of source code must retain the above copyright notice,
|
||||||
|
// this list of conditions and the following disclaimer.
|
||||||
|
//
|
||||||
|
// * Redistributions in binary form must reproduce the above copyright
|
||||||
|
// notice, this list of conditions and the following disclaimer in the
|
||||||
|
// documentation and/or other materials provided with the distribution.
|
||||||
|
//
|
||||||
|
// * Neither the name of the author nor the names of other contributors may
|
||||||
|
// be used to endorse or promote products derived from this software
|
||||||
|
// without specific prior written permission.
|
||||||
|
//
|
||||||
|
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||||
|
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||||
|
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||||
|
// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||||
|
// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||||
|
// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||||
|
// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||||
|
// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||||
|
// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||||
|
// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||||
|
// POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
//
|
||||||
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
namespace musik { namespace core { namespace sdk {
|
||||||
|
|
||||||
|
class IDebug {
|
||||||
|
public:
|
||||||
|
virtual void Verbose(const char* tag, const char* message) = 0;
|
||||||
|
virtual void Info(const char* tag, const char* message) = 0;
|
||||||
|
virtual void Warning(const char* tag, const char* message) = 0;
|
||||||
|
virtual void Error(const char* tag, const char* message) = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
} } }
|
@ -41,6 +41,7 @@
|
|||||||
#include "IPreferences.h"
|
#include "IPreferences.h"
|
||||||
#include "IOutput.h"
|
#include "IOutput.h"
|
||||||
#include "ITrackList.h"
|
#include "ITrackList.h"
|
||||||
|
#include "IDebug.h"
|
||||||
|
|
||||||
namespace musik { namespace core { namespace sdk {
|
namespace musik { namespace core { namespace sdk {
|
||||||
|
|
||||||
@ -52,6 +53,7 @@ namespace musik { namespace core { namespace sdk {
|
|||||||
virtual IEncoder* GetEncoder(const char* type) = 0;
|
virtual IEncoder* GetEncoder(const char* type) = 0;
|
||||||
virtual IBuffer* GetBuffer(size_t samples, size_t rate = 44100, size_t channels = 2) = 0;
|
virtual IBuffer* GetBuffer(size_t samples, size_t rate = 44100, size_t channels = 2) = 0;
|
||||||
virtual IPreferences* GetPreferences(const char* name) = 0;
|
virtual IPreferences* GetPreferences(const char* name) = 0;
|
||||||
|
virtual IDebug* GetDebug() = 0;
|
||||||
virtual size_t GetOutputCount() = 0;
|
virtual size_t GetOutputCount() = 0;
|
||||||
virtual IOutput* GetOutputAtIndex(size_t index) = 0;
|
virtual IOutput* GetOutputAtIndex(size_t index) = 0;
|
||||||
virtual IOutput* GetOutputWithName(const char* name) = 0;
|
virtual IOutput* GetOutputWithName(const char* name) = 0;
|
||||||
|
@ -6,6 +6,7 @@
|
|||||||
#include <cursespp/ToastOverlay.h>
|
#include <cursespp/ToastOverlay.h>
|
||||||
#include <app/util/Hotkeys.h>
|
#include <app/util/Hotkeys.h>
|
||||||
#include <app/util/Messages.h>
|
#include <app/util/Messages.h>
|
||||||
|
#include <app/version.h>
|
||||||
|
|
||||||
using namespace musik::cube;
|
using namespace musik::cube;
|
||||||
using namespace musik::core;
|
using namespace musik::core;
|
||||||
@ -55,6 +56,18 @@ void ConsoleLayout::OnItemActivated(cursespp::ListWindow* window, size_t index)
|
|||||||
ToastOverlay::Show(this->logger->Adapter()->StringAt(index), -1);
|
ToastOverlay::Show(this->logger->Adapter()->StringAt(index), -1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool ConsoleLayout::KeyPress(const std::string& kn) {
|
||||||
|
if (kn == "^_") { /* ctrl+/ */
|
||||||
|
ToastOverlay::Show(u8fmt(_TSTR("console_version"), VERSION), -1);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else if (kn == "x") {
|
||||||
|
this->adapter->Clear();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return LayoutBase::KeyPress(kn);
|
||||||
|
}
|
||||||
|
|
||||||
void ConsoleLayout::SetShortcutsWindow(ShortcutsWindow* shortcuts) {
|
void ConsoleLayout::SetShortcutsWindow(ShortcutsWindow* shortcuts) {
|
||||||
if (shortcuts) {
|
if (shortcuts) {
|
||||||
shortcuts->AddShortcut(Hotkeys::Get(Hotkeys::NavigateConsole), _TSTR("shortcuts_console"));
|
shortcuts->AddShortcut(Hotkeys::Get(Hotkeys::NavigateConsole), _TSTR("shortcuts_console"));
|
||||||
|
@ -17,6 +17,7 @@ namespace musik { namespace cube {
|
|||||||
|
|
||||||
virtual void OnLayout() override;
|
virtual void OnLayout() override;
|
||||||
virtual void SetShortcutsWindow(cursespp::ShortcutsWindow* w) override;
|
virtual void SetShortcutsWindow(cursespp::ShortcutsWindow* w) override;
|
||||||
|
virtual bool KeyPress(const std::string& kn) override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void OnVisibilityChanged(bool visible) override;
|
void OnVisibilityChanged(bool visible) override;
|
||||||
|
@ -36,6 +36,7 @@
|
|||||||
"browse_no_subdirectories_toast": "there are no more sub-directories.\n\npress '%s' to play the selection.",
|
"browse_no_subdirectories_toast": "there are no more sub-directories.\n\npress '%s' to play the selection.",
|
||||||
|
|
||||||
"console_list_title": "debug logs",
|
"console_list_title": "debug logs",
|
||||||
|
"console_version": "musikcube version %s",
|
||||||
|
|
||||||
"hotkeys_title": "key bindings",
|
"hotkeys_title": "key bindings",
|
||||||
"hotkeys_reset_defaults": "reset all",
|
"hotkeys_reset_defaults": "reset all",
|
||||||
|
@ -33,13 +33,27 @@
|
|||||||
//////////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#include "FfmpegDecoder.h"
|
#include "FfmpegDecoder.h"
|
||||||
|
#include <core/sdk/IDebug.h>
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
|
|
||||||
|
#ifdef WIN32
|
||||||
|
#define DLLEXPORT __declspec(dllexport)
|
||||||
|
#else
|
||||||
|
#define DLLEXPORT
|
||||||
|
#endif
|
||||||
|
|
||||||
#define BUFFER_SIZE 4096
|
#define BUFFER_SIZE 4096
|
||||||
#define PROBE_SIZE 32768
|
#define PROBE_SIZE 32768
|
||||||
|
|
||||||
using namespace musik::core::sdk;
|
using namespace musik::core::sdk;
|
||||||
|
|
||||||
|
static const char* TAG = "ffmpegdecoder";
|
||||||
|
static IDebug* debug = nullptr;
|
||||||
|
|
||||||
|
extern "C" DLLEXPORT void SetDebug(IDebug* debug) {
|
||||||
|
::debug = debug;
|
||||||
|
}
|
||||||
|
|
||||||
static int readCallback(void* opaque, uint8_t* buffer, int bufferSize) {
|
static int readCallback(void* opaque, uint8_t* buffer, int bufferSize) {
|
||||||
FfmpegDecoder* decoder = static_cast<FfmpegDecoder*>(opaque);
|
FfmpegDecoder* decoder = static_cast<FfmpegDecoder*>(opaque);
|
||||||
if (decoder && decoder->Stream()) {
|
if (decoder && decoder->Stream()) {
|
||||||
@ -182,6 +196,9 @@ bool FfmpegDecoder::GetBuffer(IBuffer *buffer) {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
::debug->Warning(TAG, "finished decoding.");
|
||||||
|
this->exhausted = true;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -214,6 +231,8 @@ void FfmpegDecoder::Reset() {
|
|||||||
|
|
||||||
bool FfmpegDecoder::Open(musik::core::sdk::IDataStream *stream) {
|
bool FfmpegDecoder::Open(musik::core::sdk::IDataStream *stream) {
|
||||||
if (stream->Seekable() && this->ioContext == nullptr) {
|
if (stream->Seekable() && this->ioContext == nullptr) {
|
||||||
|
::debug->Info(TAG, "parsing data stream...");
|
||||||
|
|
||||||
this->stream = stream;
|
this->stream = stream;
|
||||||
|
|
||||||
this->ioContext = avio_alloc_context(
|
this->ioContext = avio_alloc_context(
|
||||||
@ -254,6 +273,7 @@ bool FfmpegDecoder::Open(musik::core::sdk::IDataStream *stream) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (this->streamId != -1) {
|
if (this->streamId != -1) {
|
||||||
|
::debug->Info(TAG, "found audio!");
|
||||||
this->codecContext = this->formatContext->streams[this->streamId]->codec;
|
this->codecContext = this->formatContext->streams[this->streamId]->codec;
|
||||||
if (codecContext) {
|
if (codecContext) {
|
||||||
this->codecContext->request_sample_fmt = AV_SAMPLE_FMT_FLT;
|
this->codecContext->request_sample_fmt = AV_SAMPLE_FMT_FLT;
|
||||||
@ -262,8 +282,10 @@ bool FfmpegDecoder::Open(musik::core::sdk::IDataStream *stream) {
|
|||||||
if (avcodec_open2(codecContext, codec, nullptr) < 0) {
|
if (avcodec_open2(codecContext, codec, nullptr) < 0) {
|
||||||
goto reset_and_fail;
|
goto reset_and_fail;
|
||||||
}
|
}
|
||||||
|
::debug->Info(TAG, "resolved a codec!");
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
::debug->Error(TAG, "couldn't find a codec.");
|
||||||
goto reset_and_fail;
|
goto reset_and_fail;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -274,16 +296,20 @@ bool FfmpegDecoder::Open(musik::core::sdk::IDataStream *stream) {
|
|||||||
this->duration = (double) this->formatContext->duration / (double) AV_TIME_BASE;
|
this->duration = (double) this->formatContext->duration / (double) AV_TIME_BASE;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
else {
|
||||||
|
::debug->Error(TAG, "audio stream not found in input data.");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
reset_and_fail:
|
reset_and_fail:
|
||||||
|
::debug->Error(TAG, "failed to find compatible audio stream");
|
||||||
this->Reset();
|
this->Reset();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FfmpegDecoder::Exhausted() {
|
bool FfmpegDecoder::Exhausted() {
|
||||||
return false;
|
return this->exhausted;
|
||||||
}
|
}
|
@ -80,4 +80,5 @@ class FfmpegDecoder: public musik::core::sdk::IDecoder {
|
|||||||
size_t rate, channels;
|
size_t rate, channels;
|
||||||
int streamId;
|
int streamId;
|
||||||
double duration;
|
double duration;
|
||||||
|
bool exhausted{false};
|
||||||
};
|
};
|
||||||
|
Loading…
Reference in New Issue
Block a user