2
0
Эх сурвалжийг харах

finhsing CSpot integration

Philippe G 3 жил өмнө
parent
commit
7f894f1635

+ 7 - 6
components/spotify/Shim.cpp

@@ -110,7 +110,6 @@ static void cspotTask(void *pvParameters) {
         if (token.size() > 0 && cspot.cHandler(CSPOT_SETUP, 44100)) {
 			auto audioSink = std::make_shared<ShimAudioSink>();
 
-            // @TODO Actually store this token somewhere
             mercuryManager = std::make_shared<MercuryManager>(std::move(session));
             mercuryManager->startTask();
 
@@ -120,7 +119,7 @@ static void cspotTask(void *pvParameters) {
             switch (event.eventType) {
             case CSpotEventType::TRACK_INFO: {
                 TrackInfo track = std::get<TrackInfo>(event.data);
-				cspot.cHandler(CSPOT_TRACK, 44100, track.artist.c_str(), track.album.c_str(), track.name.c_str());
+				cspot.cHandler(CSPOT_TRACK, 44100, track.duration, track.artist.c_str(), track.album.c_str(), track.name.c_str());
                 break;
             }
             case CSpotEventType::PLAY_PAUSE: {
@@ -129,6 +128,9 @@ static void cspotTask(void *pvParameters) {
 				else cspot.cHandler(CSPOT_PLAY);
                 break;
             }
+			case CSpotEventType::LOAD:
+				cspot.cHandler(CSPOT_LOAD, std::get<int>(event.data), -1);
+				break;
 			case CSpotEventType::SEEK:
 				cspot.cHandler(CSPOT_SEEK, std::get<int>(event.data));
 				break;
@@ -165,12 +167,11 @@ static void cspotTask(void *pvParameters) {
 			spircController.reset();
 		}
 
-		// release auth blob
+		// release auth blob and flush files
 		cspot.blob.reset();
-
-		// flush files
 		file->flush();
-ESP_LOGW(TAG, "THIS SESSION IS FINISHED %ld %ld %ld", mercuryManager.use_count(), spircController.use_count(), cspot.blob.use_count());
+		
+		ESP_LOGI(TAG, "Shutting down CSpot player");
 	}
 
 	// we should not be here

+ 1 - 0
components/spotify/cspot/include/SpircController.h

@@ -24,6 +24,7 @@ enum class CSpotEventType {
     NEXT,
     PREV,
     SEEK,
+	LOAD,
 };
 
 struct CSpotEvent {

+ 1 - 0
components/spotify/cspot/include/SpotifyTrack.h

@@ -20,6 +20,7 @@ struct TrackInfo {
     std::string album;
     std::string artist;
     std::string imageUrl;
+    int duration;
 };
 
 typedef std::function<void(TrackInfo&)> trackChangedCallback;

+ 1 - 1
components/spotify/cspot/protocol/metadata.proto

@@ -34,7 +34,7 @@ message Track {
     optional string name = 2;
     optional Album album = 0x3;
     repeated Artist artist = 0x4;
-    optional sint32 duration = 7;
+    optional sint32 duration = 0x7;
     repeated Restriction restriction = 0xb;
     repeated AudioFile file = 0xc;
     repeated Track alternative = 0xd;

+ 19 - 19
components/spotify/cspot/protos/ReflectTypeInfo.cpp

@@ -9,18 +9,18 @@ ReflectType::ofEnum(/* mine id */ ReflectTypeID::EnumReflectTypeID, /* name */ "
    ReflectEnumValue("EnumReflectTypeKind", 4),
    ReflectEnumValue("VectorOfClassReflectField", 5),
    ReflectEnumValue("VectorOfClassReflectEnumValue", 6),
-   ReflectEnumValue("Double", 7),
-   ReflectEnumValue("Uint32", 8),
-   ReflectEnumValue("Char", 9),
-   ReflectEnumValue("UnsignedChar", 10),
-   ReflectEnumValue("Float", 11),
-   ReflectEnumValue("Bool", 12),
-   ReflectEnumValue("String", 13),
-   ReflectEnumValue("Int32", 14),
-   ReflectEnumValue("Int64", 15),
-   ReflectEnumValue("Int", 16),
-   ReflectEnumValue("Uint8", 17),
-   ReflectEnumValue("Uint64", 18),
+   ReflectEnumValue("Int32", 7),
+   ReflectEnumValue("Int64", 8),
+   ReflectEnumValue("Uint32", 9),
+   ReflectEnumValue("Uint8", 10),
+   ReflectEnumValue("Int", 11),
+   ReflectEnumValue("UnsignedChar", 12),
+   ReflectEnumValue("Float", 13),
+   ReflectEnumValue("String", 14),
+   ReflectEnumValue("Uint64", 15),
+   ReflectEnumValue("Char", 16),
+   ReflectEnumValue("Double", 17),
+   ReflectEnumValue("Bool", 18),
    ReflectEnumValue("VectorOfUint8", 19),
    ReflectEnumValue("EnumCpuFamily", 20),
    ReflectEnumValue("EnumOs", 21),
@@ -174,18 +174,18 @@ ReflectType::ofEnum(/* mine id */ ReflectTypeID::EnumReflectTypeKind, /* name */
 	
 	
 	,
-ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Double, /* name */ "double", /* size */ sizeof(double)),
+ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Int32, /* name */ "int32_t", /* size */ sizeof(int32_t)),
+ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Int64, /* name */ "int64_t", /* size */ sizeof(int64_t)),
 ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Uint32, /* name */ "uint32_t", /* size */ sizeof(uint32_t)),
-ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Char, /* name */ "char", /* size */ sizeof(char)),
+ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Uint8, /* name */ "uint8_t", /* size */ sizeof(uint8_t)),
+ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Int, /* name */ "int", /* size */ sizeof(int)),
 ReflectType::ofPrimitive(/* type id */ ReflectTypeID::UnsignedChar, /* name */ "unsigned char", /* size */ sizeof(unsigned char)),
 ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Float, /* name */ "float", /* size */ sizeof(float)),
-ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Bool, /* name */ "bool", /* size */ sizeof(bool)),
 ReflectType::ofPrimitive(/* type id */ ReflectTypeID::String, /* name */ "std::string", /* size */ sizeof(std::string)),
-ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Int32, /* name */ "int32_t", /* size */ sizeof(int32_t)),
-ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Int64, /* name */ "int64_t", /* size */ sizeof(int64_t)),
-ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Int, /* name */ "int", /* size */ sizeof(int)),
-ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Uint8, /* name */ "uint8_t", /* size */ sizeof(uint8_t)),
 ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Uint64, /* name */ "uint64_t", /* size */ sizeof(uint64_t)),
+ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Char, /* name */ "char", /* size */ sizeof(char)),
+ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Double, /* name */ "double", /* size */ sizeof(double)),
+ReflectType::ofPrimitive(/* type id */ ReflectTypeID::Bool, /* name */ "bool", /* size */ sizeof(bool)),
 
 	ReflectType::ofVector(
 		/* mine typeId */ ReflectTypeID::VectorOfUint8,

+ 12 - 12
components/spotify/cspot/protos/ReflectionInternal.h

@@ -11,18 +11,18 @@ ClassReflectType = 3,
 EnumReflectTypeKind = 4,
 VectorOfClassReflectField = 5,
 VectorOfClassReflectEnumValue = 6,
-Double = 7,
-Uint32 = 8,
-Char = 9,
-UnsignedChar = 10,
-Float = 11,
-Bool = 12,
-String = 13,
-Int32 = 14,
-Int64 = 15,
-Int = 16,
-Uint8 = 17,
-Uint64 = 18,
+Int32 = 7,
+Int64 = 8,
+Uint32 = 9,
+Uint8 = 10,
+Int = 11,
+UnsignedChar = 12,
+Float = 13,
+String = 14,
+Uint64 = 15,
+Char = 16,
+Double = 17,
+Bool = 18,
 VectorOfUint8 = 19,
 EnumCpuFamily = 20,
 EnumOs = 21,

+ 43 - 43
components/spotify/cspot/protos/protobuf.h

@@ -113,14 +113,20 @@ class Frame;
 					if constexpr(std::is_same<T, std::vector<ReflectEnumValue>>::value) {
 						return ReflectTypeID::VectorOfClassReflectEnumValue == this->typeID;
 					} else 
-					if constexpr(std::is_same<T, double>::value) {
-						return ReflectTypeID::Double == this->typeID;
+					if constexpr(std::is_same<T, int32_t>::value) {
+						return ReflectTypeID::Int32 == this->typeID;
+					} else 
+					if constexpr(std::is_same<T, int64_t>::value) {
+						return ReflectTypeID::Int64 == this->typeID;
 					} else 
 					if constexpr(std::is_same<T, uint32_t>::value) {
 						return ReflectTypeID::Uint32 == this->typeID;
 					} else 
-					if constexpr(std::is_same<T, char>::value) {
-						return ReflectTypeID::Char == this->typeID;
+					if constexpr(std::is_same<T, uint8_t>::value) {
+						return ReflectTypeID::Uint8 == this->typeID;
+					} else 
+					if constexpr(std::is_same<T, int>::value) {
+						return ReflectTypeID::Int == this->typeID;
 					} else 
 					if constexpr(std::is_same<T, unsigned char>::value) {
 						return ReflectTypeID::UnsignedChar == this->typeID;
@@ -128,26 +134,20 @@ class Frame;
 					if constexpr(std::is_same<T, float>::value) {
 						return ReflectTypeID::Float == this->typeID;
 					} else 
-					if constexpr(std::is_same<T, bool>::value) {
-						return ReflectTypeID::Bool == this->typeID;
-					} else 
 					if constexpr(std::is_same<T, std::string>::value) {
 						return ReflectTypeID::String == this->typeID;
 					} else 
-					if constexpr(std::is_same<T, int32_t>::value) {
-						return ReflectTypeID::Int32 == this->typeID;
-					} else 
-					if constexpr(std::is_same<T, int64_t>::value) {
-						return ReflectTypeID::Int64 == this->typeID;
+					if constexpr(std::is_same<T, uint64_t>::value) {
+						return ReflectTypeID::Uint64 == this->typeID;
 					} else 
-					if constexpr(std::is_same<T, int>::value) {
-						return ReflectTypeID::Int == this->typeID;
+					if constexpr(std::is_same<T, char>::value) {
+						return ReflectTypeID::Char == this->typeID;
 					} else 
-					if constexpr(std::is_same<T, uint8_t>::value) {
-						return ReflectTypeID::Uint8 == this->typeID;
+					if constexpr(std::is_same<T, double>::value) {
+						return ReflectTypeID::Double == this->typeID;
 					} else 
-					if constexpr(std::is_same<T, uint64_t>::value) {
-						return ReflectTypeID::Uint64 == this->typeID;
+					if constexpr(std::is_same<T, bool>::value) {
+						return ReflectTypeID::Bool == this->typeID;
 					} else 
 					if constexpr(std::is_same<T, std::vector<uint8_t>>::value) {
 						return ReflectTypeID::VectorOfUint8 == this->typeID;
@@ -296,14 +296,20 @@ class Frame;
 					if constexpr(std::is_same<T, std::vector<ReflectEnumValue>>::value) {
 						typeID = ReflectTypeID::VectorOfClassReflectEnumValue;
 					} else 
-					if constexpr(std::is_same<T, double>::value) {
-						typeID = ReflectTypeID::Double;
+					if constexpr(std::is_same<T, int32_t>::value) {
+						typeID = ReflectTypeID::Int32;
+					} else 
+					if constexpr(std::is_same<T, int64_t>::value) {
+						typeID = ReflectTypeID::Int64;
 					} else 
 					if constexpr(std::is_same<T, uint32_t>::value) {
 						typeID = ReflectTypeID::Uint32;
 					} else 
-					if constexpr(std::is_same<T, char>::value) {
-						typeID = ReflectTypeID::Char;
+					if constexpr(std::is_same<T, uint8_t>::value) {
+						typeID = ReflectTypeID::Uint8;
+					} else 
+					if constexpr(std::is_same<T, int>::value) {
+						typeID = ReflectTypeID::Int;
 					} else 
 					if constexpr(std::is_same<T, unsigned char>::value) {
 						typeID = ReflectTypeID::UnsignedChar;
@@ -311,26 +317,20 @@ class Frame;
 					if constexpr(std::is_same<T, float>::value) {
 						typeID = ReflectTypeID::Float;
 					} else 
-					if constexpr(std::is_same<T, bool>::value) {
-						typeID = ReflectTypeID::Bool;
-					} else 
 					if constexpr(std::is_same<T, std::string>::value) {
 						typeID = ReflectTypeID::String;
 					} else 
-					if constexpr(std::is_same<T, int32_t>::value) {
-						typeID = ReflectTypeID::Int32;
-					} else 
-					if constexpr(std::is_same<T, int64_t>::value) {
-						typeID = ReflectTypeID::Int64;
+					if constexpr(std::is_same<T, uint64_t>::value) {
+						typeID = ReflectTypeID::Uint64;
 					} else 
-					if constexpr(std::is_same<T, int>::value) {
-						typeID = ReflectTypeID::Int;
+					if constexpr(std::is_same<T, char>::value) {
+						typeID = ReflectTypeID::Char;
 					} else 
-					if constexpr(std::is_same<T, uint8_t>::value) {
-						typeID = ReflectTypeID::Uint8;
+					if constexpr(std::is_same<T, double>::value) {
+						typeID = ReflectTypeID::Double;
 					} else 
-					if constexpr(std::is_same<T, uint64_t>::value) {
-						typeID = ReflectTypeID::Uint64;
+					if constexpr(std::is_same<T, bool>::value) {
+						typeID = ReflectTypeID::Bool;
 					} else 
 					if constexpr(std::is_same<T, std::vector<uint8_t>>::value) {
 						typeID = ReflectTypeID::VectorOfUint8;
@@ -473,18 +473,18 @@ class Frame;
 					ReflectTypeKind *u_EnumReflectTypeKind;
 					std::vector<ReflectField> *u_VectorOfClassReflectField;
 					std::vector<ReflectEnumValue> *u_VectorOfClassReflectEnumValue;
-					double *u_Double;
+					int32_t *u_Int32;
+					int64_t *u_Int64;
 					uint32_t *u_Uint32;
-					char *u_Char;
+					uint8_t *u_Uint8;
+					int *u_Int;
 					unsigned char *u_UnsignedChar;
 					float *u_Float;
-					bool *u_Bool;
 					std::string *u_String;
-					int32_t *u_Int32;
-					int64_t *u_Int64;
-					int *u_Int;
-					uint8_t *u_Uint8;
 					uint64_t *u_Uint64;
+					char *u_Char;
+					double *u_Double;
+					bool *u_Bool;
 					std::vector<uint8_t> *u_VectorOfUint8;
 					CpuFamily *u_EnumCpuFamily;
 					Os *u_EnumOs;

+ 2 - 0
components/spotify/cspot/src/SpircController.cpp

@@ -182,6 +182,7 @@ void SpircController::handleFrame(std::vector<uint8_t> &data) {
 }
 
 void SpircController::loadTrack(uint32_t position_ms, bool isPaused) {
+	sendEvent(CSpotEventType::LOAD, (int) position_ms);
     state->setPlaybackState(PlaybackState::Loading);
     std::function<void()> loadedLambda = [=]() {
         // Loading finished, notify that playback started
@@ -216,6 +217,7 @@ void SpircController::setEventHandler(cspotEventHandler callback) {
             info.artist = track.artist;
             info.imageUrl = track.imageUrl;
             info.name = track.name;
+			info.duration = track.duration;
 
 			this->sendEvent(CSpotEventType::TRACK_INFO, info);
     });

+ 3 - 2
components/spotify/cspot/src/SpotifyTrack.cpp

@@ -99,12 +99,13 @@ void SpotifyTrack::trackInformationCallback(std::unique_ptr<MercuryResponse> res
 
     if (trackInfoReceived != nullptr)
     {
-        CSPOT_LOG(info, "Calling %d", trackInfo.album.value().cover_group.value().image.size());
         TrackInfo simpleTrackInfo = {
             .name = trackInfo.name.value(),
             .album = trackInfo.album.value().name.value(),
             .artist = trackInfo.artist[0].name.value(),
-            .imageUrl = "https://i.scdn.co/image/" + bytesToHexString(trackInfo.album.value().cover_group.value().image[0].file_id.value())
+            .imageUrl = "https://i.scdn.co/image/" + bytesToHexString(trackInfo.album.value().cover_group.value().image[0].file_id.value()),
+            .duration = trackInfo.duration.value(),
+
         };
 
         trackInfoReceived(simpleTrackInfo);

+ 8 - 1
components/spotify/cspot_sink.c

@@ -90,6 +90,7 @@ const static actrls_t controls = {
  */
 static bool cmd_handler(cspot_event_t event, ...) {
 	va_list args;	
+	static bool loaded = false;
 	
 	va_start(args, event);
 	
@@ -115,14 +116,20 @@ static bool cmd_handler(cspot_event_t event, ...) {
 		actrls_unset();
 		displayer_control(DISPLAYER_SUSPEND);
 		break;
+	case CSPOT_LOAD:
+		// this message only appears if we load in the middle of a track
+		loaded = true;
+		__attribute__ ((fallthrough));
 	case CSPOT_SEEK:
 		displayer_timer(DISPLAYER_ELAPSED, va_arg(args, int), -1);
 		break;
 	case CSPOT_TRACK: {
 		uint32_t sample_rate = va_arg(args, uint32_t);
+		int duration = va_arg(args, int);
 		char *artist = va_arg(args, char*), *album = va_arg(args, char*), *title = va_arg(args, char*);
 		displayer_metadata(artist, album, title);
-		displayer_timer(DISPLAYER_ELAPSED, 0, -1);
+		displayer_timer(DISPLAYER_ELAPSED, loaded ? -1 : 0, duration);
+		loaded = false;
 		break;
 	}	
 	// nothing to do on CSPOT_FLUSH

+ 1 - 1
components/spotify/cspot_sink.h

@@ -16,7 +16,7 @@ extern "C"
 #endif
 
 // STOP means remove playlist, FLUSH means flush audio buffer, DISC means bye-bye
-typedef enum { 	CSPOT_SETUP, CSPOT_DISC, CSPOT_FLUSH, CSPOT_STOP, CSPOT_PLAY, CSPOT_PAUSE, CSPOT_SEEK, CSPOT_TRACK, 
+typedef enum { 	CSPOT_SETUP, CSPOT_DISC, CSPOT_FLUSH, CSPOT_STOP, CSPOT_PLAY, CSPOT_PAUSE, CSPOT_SEEK, CSPOT_TRACK, CSPOT_LOAD, 
 				CSPOT_VOLUME, CSPOT_VOLUME_UP, CSPOT_VOLUME_DOWN, CSPOT_NEXT, CSPOT_PREV, CSPOT_TOGGLE, 
 } cspot_event_t;