Reputation: 694
I'm currently using python-telegram-bot and basically what I want to achieve with it is to send telegram messages like this:
So the message consists of 2+ photos/videos with text message underneath.
What I've already tried:
sending message with send_message method, and including photo URLs, but it only shows 1 picture which is under the text
sending media group using send_media_group, but this method has no caption
parameter as send_photo.
Upvotes: 22
Views: 40424
Reputation: 2945
Here is a vanilla Python implementation using requests
:
SEND_MEDIA_GROUP = f'https://api.telegram.org/bot{token}/sendMediaGroup'
def send_media_group(chat_id, images, caption=None, reply_to_message_id=None):
"""
Use this method to send an album of photos. On success, an array of Messages that were sent is returned.
:param chat_id: chat id
:param images: list of PIL images to send
:param caption: caption of image
:param reply_to_message_id: If the message is a reply, ID of the original message
:return: response with the sent message
"""
files = {}
media = []
for i, img in enumerate(images):
with BytesIO() as output:
img.save(output, format='PNG')
output.seek(0)
name = f'photo{i}'
files[name] = output.read()
# a list of InputMediaPhoto. attach refers to the name of the file in the files dict
media.append(dict(type='photo', media=f'attach://{name}'))
media[0]['caption'] = caption
return requests.post(SEND_MEDIA_GROUP, data={'chat_id': chat_id, 'media': json.dumps(media), 'reply_to_message_id': reply_to_message_id }, files=files)
Upvotes: 2
Reputation: 3547
send_media_group
works but the caption has to be added when creating the media_group
and to the first image only. Let's say we have three images img0.png
, img1.png
and img2.png
, we add them to the media_group
using InputMediaPhoto
with the parameter caption
equal to the text we want to send only for the first image, otherwise we set caption
equal to ''
.
import telegram
from telegram import InputMediaPhoto
TOKEN = '' # token to access the HTTP API of your bot created with @BotFather
CHANNEL_ID = '' # id of your channel, for example @durov
bot = telegram.Bot(token = TOKEN)
media_group = []
text = 'some caption for album'
for num in range(3):
media_group.append(InputMediaPhoto(open('img%d.png' % num, 'rb'),
caption = text if num == 0 else ''))
bot.send_media_group(chat_id = CHANNEL_ID, media = media_group)
Upvotes: 10
Reputation: 1281
You should use sendMediaGroup, where you can specify media
field with an array of photo/video objects but the trick is to set caption
property only for the first element of an array. In this case telegram will show that caption below the media content.
If you'll specify captions for more than one element telegram will show them only when you click on photo preview for each photo separately.
Upvotes: 53