main.cpp 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  1. #include <iostream>
  2. #include <iomanip>
  3. #include <memory>
  4. #include <stdio.h>
  5. #include <taglib/id3v2tag.h>
  6. #include <taglib/mpegfile.h>
  7. #include <taglib/flacfile.h>
  8. #include <taglib/vorbisfile.h>
  9. #include <taglib/id3v2frame.h>
  10. #include <taglib/id3v2header.h>
  11. #include <taglib/attachedpictureframe.h>
  12. using namespace std;
  13. using namespace TagLib;
  14. void usage(string message) {
  15. cerr << "usage: id3-extract-cover MP3|FLAC|OGG" << "\n";
  16. cerr << message << "\n";
  17. exit(EXIT_FAILURE);
  18. }
  19. int main(int argc, char **argv) {
  20. if (argc < 2)
  21. usage("error: filename required");
  22. string str(argv[1]);
  23. /* string conversion */
  24. transform(str.begin(), str.end(), str.begin(),
  25. [](unsigned char c){ return tolower(c); });
  26. vector<shared_ptr<File>> files;
  27. shared_ptr<File> mpeg_file(new MPEG::File(argv[1]));
  28. shared_ptr<File> flac_file(new FLAC::File(argv[1]));
  29. shared_ptr<File> oggv_file(new Ogg::Vorbis::File(argv[1]));
  30. files.push_back(move(mpeg_file));
  31. files.push_back(move(flac_file));
  32. files.push_back(move(oggv_file));
  33. for (vector<shared_ptr<File>>::iterator files_it = std::begin(files); files_it != std::end(files); ++files_it) {
  34. /* try to cast file into mpeg */
  35. if (std::shared_ptr<MPEG::File> mpeg_p = std::dynamic_pointer_cast<MPEG::File>(*files_it)) {
  36. ID3v2::Tag *id3v2tag = (*mpeg_p).ID3v2Tag();
  37. if (!id3v2tag)
  38. usage("file does not contain an id3v2 tag");
  39. ID3v2::FrameList frame = id3v2tag->frameList();
  40. for (ID3v2::FrameList::ConstIterator it = frame.begin(); it != frame.end(); ++it) {
  41. /* try to cast picture into picture frame */
  42. if (ID3v2::AttachedPictureFrame* pic_frame = dynamic_cast<ID3v2::AttachedPictureFrame*>(*it)) {
  43. auto picture_bytes = pic_frame->picture();
  44. cout << picture_bytes;
  45. return EXIT_SUCCESS;
  46. }
  47. }
  48. }
  49. /* try to cast file into flac */
  50. if (std::shared_ptr<FLAC::File> flac_p = std::dynamic_pointer_cast<FLAC::File>(*files_it)) {
  51. /* id3v2 route */
  52. if (flac_p->hasID3v2Tag()) {
  53. ID3v2::Tag *id3v2tag = (*flac_p).ID3v2Tag();
  54. ID3v2::FrameList frame = id3v2tag->frameList();
  55. for (ID3v2::FrameList::ConstIterator it = frame.begin(); it != frame.end(); ++it) {
  56. /* try to cast picture into picture frame */
  57. if (ID3v2::AttachedPictureFrame* pic_frame = dynamic_cast<ID3v2::AttachedPictureFrame*>(*it)) {
  58. auto picture_bytes = pic_frame->picture();
  59. cout << picture_bytes;
  60. return EXIT_SUCCESS;
  61. }
  62. }
  63. /* ogg::xiphcomment route */
  64. } else {
  65. if (!flac_p->tag())
  66. usage("file does not contain a xiph tag");
  67. if (flac_p->pictureList().front()) {
  68. auto picture_bytes = flac_p->pictureList().front()->data();
  69. cout << picture_bytes;
  70. return EXIT_SUCCESS;
  71. }
  72. }
  73. }
  74. /* try to cast file into ogg vorbis */
  75. if (std::shared_ptr<Ogg::Vorbis::File> oggv_p = std::dynamic_pointer_cast<Ogg::Vorbis::File>(*files_it)) {
  76. if (!oggv_p->tag())
  77. usage("file does not contain a xiph tag");
  78. if (oggv_p->tag()->pictureList().front()) {
  79. auto picture_bytes = oggv_p->tag()->pictureList().front()->data();
  80. cout << picture_bytes;
  81. return EXIT_SUCCESS;
  82. }
  83. }
  84. }
  85. return EXIT_SUCCESS;
  86. }