diff --git a/compiler/docs/compiler.py b/compiler/docs/compiler.py index 3d4d3a49..02a30458 100644 --- a/compiler/docs/compiler.py +++ b/compiler/docs/compiler.py @@ -514,6 +514,8 @@ def pyrogram_api(): ReactionType MessageReactionUpdated MessageReactionCountUpdated + ExtendedMediaPreview + PaidMedia """, stories=""" Stories diff --git a/pyrogram/enums/message_media_type.py b/pyrogram/enums/message_media_type.py index 10b11cc7..c9e3fa44 100644 --- a/pyrogram/enums/message_media_type.py +++ b/pyrogram/enums/message_media_type.py @@ -81,3 +81,6 @@ class MessageMediaType(AutoName): INVOICE = auto() "Invoice media" + + PAID_MEDIA = auto() + "Paid media" diff --git a/pyrogram/types/messages_and_media/__init__.py b/pyrogram/types/messages_and_media/__init__.py index 5736b8ab..85a67a98 100644 --- a/pyrogram/types/messages_and_media/__init__.py +++ b/pyrogram/types/messages_and_media/__init__.py @@ -23,6 +23,7 @@ from .available_effect import AvailableEffect from .contact import Contact from .dice import Dice from .document import Document +from .extended_media_preview import ExtendedMediaPreview from .game import Game from .gifted_premium import GiftedPremium from .giveaway import Giveaway @@ -35,6 +36,7 @@ from .media_area_channel_post import MediaAreaChannelPost from .media_area_coordinates import MediaAreaCoordinates from .message import Message from .message_entity import MessageEntity +from .paid_media import PaidMedia from .photo import Photo from .poll import Poll from .poll_option import PollOption @@ -67,7 +69,7 @@ from .story_views import StoryViews from .exported_story_link import ExportedStoryLink __all__ = [ - "Animation", "Audio", "AvailableEffect", "Contact", "Document", "Game", "GiftedPremium", "Giveaway", "GiveawayLaunched", "GiveawayResult", "LabeledPrice", "Location", "MediaArea", "MediaAreaChannelPost", "MediaAreaCoordinates", "Message", "MessageEntity", "Photo", "Thumbnail", + "Animation", "Audio", "AvailableEffect", "Contact", "Document", "ExtendedMediaPreview", "Game", "GiftedPremium", "Giveaway", "GiveawayLaunched", "GiveawayResult", "LabeledPrice", "Location", "MediaArea", "MediaAreaChannelPost", "MediaAreaCoordinates", "Message", "MessageEntity", "PaidMedia", "Photo", "Thumbnail", "StrippedThumbnail", "Poll", "PollOption", "Sticker", "StickerSet", "Venue", "Video", "VideoNote", "Voice", "WebPage", "WebPageEmpty", "WebPagePreview", "Dice", "Reaction", "WebAppData", "MessageInvoice", "MessageReactions", "ReactionCount", "ReactionType", "MessageReactionUpdated", "MessageReactionCountUpdated", "MessageStory", "Story", "StoryDeleted", "StorySkipped", "StoryViews", "StoryForwardHeader", "StoriesPrivacyRules", "ExportedStoryLink" ] diff --git a/pyrogram/types/messages_and_media/extended_media_preview.py b/pyrogram/types/messages_and_media/extended_media_preview.py new file mode 100644 index 00000000..201e90a5 --- /dev/null +++ b/pyrogram/types/messages_and_media/extended_media_preview.py @@ -0,0 +1,66 @@ +# Pyrofork - Telegram MTProto API Client Library for Python +# Copyright (C) 2022-present Mayuri-Chan +# +# This file is part of Pyrofork. +# +# Pyrofork is free software: you can redistribute it and/or modify +# it under the terms of the GNU Lesser General Public License as published +# by the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# Pyrofork is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License +# along with Pyrofork. If not, see . + +from pyrogram import raw +from pyrogram import types +from ..object import Object + + +class ExtendedMediaPreview(Object): + """A ExtendedMediaPreview. + + Parameters: + width (``int``, *optional*): + Media Width. + + height (``int``, *optional*): + Media Height. + + thumb (:obj:`~pyrogram.types.Thumbnail`, *optional*): + Media Thumbnail. + + video_duration (``int``, *optional*): + Video duration. + """ + def __init__( + self, + *, + width: int = None, + height: int = None, + thumb: "types.Thumbnail" = None, + video_duration: int = None + ): + super().__init__() + + self.width = width + self.height = height + self.thumb = thumb + self.video_duration = video_duration + + @staticmethod + async def _parse(client, media: "raw.types.MessageExtendedMediaPreview") -> "ExtendedMediaPreview": + thumb = None + if media.thumb: + thumb = await types.Thumbnail._parse(client, media.thumb) + + return ExtendedMediaPreview( + width=media.w, + height=media.h, + thumb=thumb, + video_duration=media.video_duration + ) diff --git a/pyrogram/types/messages_and_media/message.py b/pyrogram/types/messages_and_media/message.py index 12978db9..9605a3ac 100644 --- a/pyrogram/types/messages_and_media/message.py +++ b/pyrogram/types/messages_and_media/message.py @@ -208,6 +208,9 @@ class Message(Object, Update): photo (:obj:`~pyrogram.types.Photo`, *optional*): Message is a photo, information about the photo. + paid_media (:obj:`~pyrogram.types.PaidMedia`, *optional*): + Message is a paid media, information about the paid media. + sticker (:obj:`~pyrogram.types.Sticker`, *optional*): Message is a sticker, information about the sticker. @@ -472,6 +475,7 @@ class Message(Object, Update): audio: "types.Audio" = None, document: "types.Document" = None, photo: "types.Photo" = None, + paid_media: "types.PaidMedia" = None, sticker: "types.Sticker" = None, animation: "types.Animation" = None, game: "types.Game" = None, @@ -582,6 +586,7 @@ class Message(Object, Update): self.audio = audio self.document = document self.photo = photo + self.paid_media = paid_media self.sticker = sticker self.animation = animation self.game = game @@ -971,6 +976,7 @@ class Message(Object, Update): forward_sender_name = forward_header.from_name photo = None + paid_media = None location = None contact = None venue = None @@ -1077,6 +1083,9 @@ class Message(Object, Update): elif isinstance(media, raw.types.MessageMediaInvoice): invoice = types.MessageInvoice._parse(media) media = enums.MessageMediaType.INVOICE + elif isinstance(media, raw.types.MessageMediaPaidMedia): + paid_media = types.PaidMedia._parse(client, media) + media_type = enums.MessageMediaType.PAID_MEDIA else: media = None @@ -1151,6 +1160,7 @@ class Message(Object, Update): media_group_id=message.grouped_id, invert_media=message.invert_media, photo=photo, + paid_media=paid_media, location=location, contact=contact, venue=venue, diff --git a/pyrogram/types/messages_and_media/paid_media.py b/pyrogram/types/messages_and_media/paid_media.py new file mode 100644 index 00000000..b5dabb2a --- /dev/null +++ b/pyrogram/types/messages_and_media/paid_media.py @@ -0,0 +1,78 @@ +# Pyrofork - Telegram MTProto API Client Library for Python +# Copyright (C) 2022-present Mayuri-Chan +# +# This file is part of Pyrofork. +# +# Pyrofork is free software: you can redistribute it and/or modify +# it under the terms of the GNU Lesser General Public License as published +# by the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# Pyrofork is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License +# along with Pyrofork. If not, see . + +from typing import List, Union + +from pyrogram import raw +from pyrogram import types +from ..object import Object + + +class PaidMedia(Object): + """A PaidMedia. + + Parameters: + stars_amount (``int``): + Amount of stars. + + extended_media (List of :obj:`~pyrogram.types.Animation` | :obj:`~pyrogram.types.ExtendedMediaPreview` | :obj:`~pyrogram.types.Photo` | :obj:`~pyrogram.types.Video`, *optional*): + Extended media. + """ + def __init__( + self, + *, + stars_amount: int, + extended_media: List[ + Union[ + "types.Animation", + "types.ExtendedMediaPreview", + "types.Photo", + "types.Video" + ] + ] = None + ): + super().__init__() + + self.stars_amount = stars_amount + self.extended_media = extended_media + + @staticmethod + def _parse(client, media: "raw.types.MessageMediaPaidMedia") -> "PaidMedia": + extended_media = [] + for m in media.extended_media: + if isinstance(m.media, raw.types.MessageMediaPhoto): + extended_media.append(types.Photo._parse(client, m.media.photo, m.media.ttl_seconds)) + elif isinstance(m.media, raw.types.MessageMediaDocument): + attributes = {type(i): i for i in m.media.document.attributes} + file_name = getattr( + attributes.get( + raw.types.DocumentAttributeFilename, None + ), "file_name", None + ) + if raw.types.DocumentAttributeAnimated in attributes: + video_attributes = attributes.get(raw.types.DocumentAttributeVideo, None) + extended_media.append(types.Animation._parse(client, m.media.document, video_attributes, file_name)) + else: + video_attributes = attributes[raw.types.DocumentAttributeVideo] + extended_media.append(types.Video._parse(client, m.media.document, video_attributes, file_name, m.media.ttl_seconds)) + elif isinstance(m, raw.types.MessageExtendedMediaPreview): + extended_media.append(types.ExtendedMediaPreview._parse(client, m)) + return PaidMedia( + stars_amount=media.stars_amount, + extended_media=extended_media + )