public static Id3v2Frame CreateFrame(ByteVector data, uint version) { Id3v2FrameHeader header = new Id3v2FrameHeader(data, version); ByteVector frameId = header.FrameId; // A quick sanity check -- make sure that the frameId is 4 uppercase // Latin1 characters. Also make sure that there is data in the frame. if (frameId == null || frameId.Count != (version < 3 ? 3 : 4) || header.FrameSize < 0) return null; foreach (byte b in frameId) { char c = (char)b; if ((c < 'A' || c > 'Z') && (c < '1' || c > '9')) return null; } // Windows Media Player may create zero byte frames. Just send them // off as unknown. if (header.FrameSize == 0) return new Id3v2UnknownFrame(data, header); // TagLib doesn'type mess with encrypted frames, so just treat them // as unknown frames. if (header.Compression) { TagLibDebugger.Debug("Compressed frames are currently not supported."); return new Id3v2UnknownFrame(data, header); } if (header.Encryption) { TagLibDebugger.Debug("Encrypted frames are currently not supported."); return new Id3v2UnknownFrame(data, header); } if (!UpdateFrame(header)) { header.TagAlterPreservation = true; return new Id3v2UnknownFrame(data, header); } foreach (FrameCreator creator in frameCreators) { Id3v2Frame frame = creator(data, header); if (frame != null) return frame; } // UpdateFrame() might have updated the frame ID. frameId = header.FrameId; // This is where things get necissarily nasty. Here we determine which // Frame subclass (or if none is found simply an Frame) based // on the frame ID. Since there are a lot of possibilities, that means // a lot of if blocks. // Text Identification (frames 4.2) if (frameId.StartsWith("T")) { Id3v2TextIdentificationFrame frame = frameId != "TXXX" ? new Id3v2TextIdentificationFrame(data, header) : new Id3v2UserTextIdentificationFrame(data, header); if (useDefaultEncoding) frame.TextEncoding = defaultEncoding; return frame; } // Comments (frames 4.10) if (frameId == "COMM") { Id3v2CommentsFrame frame = new Id3v2CommentsFrame(data, header); if (useDefaultEncoding) frame.TextEncoding = defaultEncoding; return frame; } // Attached Picture (frames 4.14) if (frameId == "APIC") { Id3v2AttachedPictureFrame f = new Id3v2AttachedPictureFrame(data, header); if (useDefaultEncoding) f.TextEncoding = defaultEncoding; return f; } // Relative Volume Adjustment (frames 4.11) if (frameId == "RVA2") return new Id3v2RelativeVolumeFrame(data, header); // Unique File Identifier (frames 4.1) if (frameId == "UFID") return new Id3v2UniqueFileIdentifierFrame(data, header); // Private (frames 4.27) if (frameId == "PRIV") return new Id3v2PrivateFrame(data, header); return new Id3v2UnknownFrame(data, header); }
public static Id3v2Frame CreateFrame(ByteVector data, uint version) { Id3v2FrameHeader header = new Id3v2FrameHeader(data, version); ByteVector frameId = header.FrameId; // A quick sanity check -- make sure that the frameId is 4 uppercase // Latin1 characters. Also make sure that there is data in the frame. if (frameId == null || frameId.Count != (version < 3 ? 3 : 4) || header.FrameSize < 0) { return(null); } foreach (byte b in frameId) { char c = (char)b; if ((c < 'A' || c > 'Z') && (c < '1' || c > '9')) { return(null); } } // Windows Media Player may create zero byte frames. Just send them // off as unknown. if (header.FrameSize == 0) { return(new Id3v2UnknownFrame(data, header)); } // TagLib doesn'type mess with encrypted frames, so just treat them // as unknown frames. if (header.Compression) { TagLibDebugger.Debug("Compressed frames are currently not supported."); return(new Id3v2UnknownFrame(data, header)); } if (header.Encryption) { TagLibDebugger.Debug("Encrypted frames are currently not supported."); return(new Id3v2UnknownFrame(data, header)); } if (!UpdateFrame(header)) { header.TagAlterPreservation = true; return(new Id3v2UnknownFrame(data, header)); } foreach (FrameCreator creator in frameCreators) { Id3v2Frame frame = creator(data, header); if (frame != null) { return(frame); } } // UpdateFrame() might have updated the frame ID. frameId = header.FrameId; // This is where things get necissarily nasty. Here we determine which // Frame subclass (or if none is found simply an Frame) based // on the frame ID. Since there are a lot of possibilities, that means // a lot of if blocks. // Text Identification (frames 4.2) if (frameId.StartsWith("T")) { Id3v2TextIdentificationFrame frame = frameId != "TXXX" ? new Id3v2TextIdentificationFrame(data, header) : new Id3v2UserTextIdentificationFrame(data, header); if (useDefaultEncoding) { frame.TextEncoding = defaultEncoding; } return(frame); } // Comments (frames 4.10) if (frameId == "COMM") { Id3v2CommentsFrame frame = new Id3v2CommentsFrame(data, header); if (useDefaultEncoding) { frame.TextEncoding = defaultEncoding; } return(frame); } // Attached Picture (frames 4.14) if (frameId == "APIC") { Id3v2AttachedPictureFrame f = new Id3v2AttachedPictureFrame(data, header); if (useDefaultEncoding) { f.TextEncoding = defaultEncoding; } return(f); } // Relative Volume Adjustment (frames 4.11) if (frameId == "RVA2") { return(new Id3v2RelativeVolumeFrame(data, header)); } // Unique File Identifier (frames 4.1) if (frameId == "UFID") { return(new Id3v2UniqueFileIdentifierFrame(data, header)); } // Private (frames 4.27) if (frameId == "PRIV") { return(new Id3v2PrivateFrame(data, header)); } return(new Id3v2UnknownFrame(data, header)); }