import 'package:xml/xml.dart' as xml; import '../../extensions/helpers_extension.dart'; import '../../retry.dart'; import '../youtube_http_client.dart'; /// class ClosedCaptionClient { final xml.XmlDocument root; /// late final Iterable closedCaptions = root.findAllElements('p').map((e) => ClosedCaption._(e)); /// ClosedCaptionClient(this.root); /// // ignore: deprecated_member_use ClosedCaptionClient.parse(String raw) : root = xml.parse(raw); /// static Future get( YoutubeHttpClient httpClient, Uri url) { final formatUrl = url.replaceQueryParameters({'fmt': 'srv3'}); return retry(httpClient, () async { var raw = await httpClient.getString(formatUrl); return ClosedCaptionClient.parse(raw); }); } } /// class ClosedCaption { final xml.XmlElement root; /// String get text => root.text; /// late final Duration offset = Duration(milliseconds: int.parse(root.getAttribute('t') ?? '0')); /// late final Duration duration = Duration(milliseconds: int.parse(root.getAttribute('d') ?? '0')); /// late final Duration end = offset + duration; /// late final List parts = root.findAllElements('s').map((e) => ClosedCaptionPart._(e)).toList(); ClosedCaption._(this.root); } /// class ClosedCaptionPart { final xml.XmlElement root; /// String get text => root.text; /// late final Duration offset = Duration(milliseconds: int.parse(root.getAttribute('t') ?? '0')); ClosedCaptionPart._(this.root); }