【问题标题】:How do I send a GIF to a Discord channel using a Python Discord Bot如何使用 Python Discord Bot 将 GIF 发送到 Discord 频道
【发布时间】:2021-07-20 06:47:34
【问题描述】:

当用户输入命令“!gif”(他们想要的 gif 在哪里)时,我希望机器人返回该名称的 gif。

我正在尝试的代码基于 Tenor 的 API,但我也不介意使用任何其他网站来获取 gif。我目前的代码不起作用,我对如何去做这件事有点不知所措。

注意:我将其作为个人项目进行。我不介意你给我答案,但如果可以的话,请解释你为什么要这么做。

到目前为止,这是我的代码:

import discord
import requests
import json

from constants import (TenorToken, DiscordToken)

client = discord.Client()
embedColour = 0xff0000

#Retrieves GIF from site
def getGIF(searchTerm):
    response = requests.get("https://g.tenor.com/v1/search?q=%s&key=%s&limit=1" %(searchTerm, TenorToken))
    gif = json.loads(response.content)
    print(gif)

@client.event
async def on_ready():
    print(f"{client.user}"[:-5] + " is now Online!")

@client.event
async def on_message(message):
    if (message.author == client.user):
        return

    if (message.content.lower().startswith(f"{CommandKey}gif")):
        getGIF(message.content.lower()[5:]) #Collects word after !gif

client.run(DiscordToken)

感谢您的帮助!

【问题讨论】:

  • 您打印(gif),但您没有发送此 GIF - 您应该查看文档如何发送/嵌入文件。我不确定,但在发送之前可能需要将文件保存在磁盘上。最终它可能需要使用io.BytesIO 在内存中创建假文件。
  • 哦,我希望我不需要先将 GIF 保存在我的电脑上,但我想我最终可能不得不这样做。
  • 首先您应该搜索如何发送图像的信息 - 即。 send(file=filename) - 稍后您可以尝试使用io.BytesIO()(类似文件的对象)而不是filename。一些函数(在不同的模块中)可以使用类似文件的对象而不是filename
  • 使用谷歌我发现了一些例子,它从磁盘上的文件发送图像,它使用处理程序打开文件,这意味着你可以使用io.BytesIO()而不是处理程序。
  • 哦,好的,谢谢@furas

标签: python python-3.x discord.py gif


【解决方案1】:

我检查了你的代码,Tensor 不发送 GIF 数据,而只发送图片的网址。

这段代码在第一个结果中给了我url for gif`

def get_gif(searchTerm):  # PEP8: lower_case_names for functions

    response = requests.get("https://g.tenor.com/v1/search?q={}&key={}&limit=1".format(searchTerm, TenorToken))

    data = response.json()  # `requests` doesn't need `json.loads()`
         
    return data['results'][0]['media'][0]['gif']['url']

我通过手动挖掘 JSON 并创建此代码得到它

# see urls for all GIFs

for result in data['results']:
    print('- result -')
    #print(result)
    
    for media in result['media']:
        print('- media -')
        #print(media)
        #print(media['gif'])
        print('url:', media['gif']['url'])

当我收到url 时,我可以使用Embed 发送url,discord 会下载并显示 - 我不必下载。

if (message.content.lower().startswith(f"{CommandKey}gif")):

    gif_url = get_gif(message.content.lower()[5:]) #Collects word after !gif
    
    embed = discord.Embed()
    embed.set_image(url=gif_url)

    await message.channel.send(embed=embed)

完整的工作代码

import discord
import requests

from constants import (TenorToken, DiscordToken)

#import os
#DiscordToken = os.getenv('DISCORD_TOKEN')
#TenorToken = os.getenv('TENOR_TOKEN')

client = discord.Client()

embedColour = 0xff0000
CommandKey = '!'

# --- functions ---

#Retrieves GIF from site
def get_gif(searchTerm):  # PEP8: lower_case_names for functions
    response = requests.get("https://g.tenor.com/v1/search?q={}&key={}&limit=1".format(searchTerm, TenorToken))
    data = response.json()
    
    ''' 
    # see urls for all GIFs
    
    for result in data['results']:
        print('- result -')
        #print(result)
        
        for media in result['media']:
            print('- media -')
            print(media)
            print(media['gif'])
            print('url:', media['gif']['url'])
    '''
         
    return data['results'][0]['media'][0]['gif']['url']
    

@client.event
async def on_ready():
    print(f"{client.user}"[:-5] + " is now Online!")

@client.event
async def on_message(message):
    if message.author == client.user:  # `if/else` doesn't need `()`
        return

    if message.content.lower().startswith(f"{CommandKey}gif"):
        gif_url = get_gif(message.content.lower()[5:]) #Collects word after !gif
        
        embed = discord.Embed()
        embed.set_image(url=gif_url)
        await message.channel.send(embed=embed)

# --- main ---

client.run(DiscordToken)

编辑:

与将gif 下载到本地计算机内存(使用io.BytesIO)并作为普通文件发送相同。

import io

@client.event
async def on_message(message):
    if (message.author == client.user):
        return

    if (message.content.lower().startswith(f"{CommandKey}gif")):
        gif_url = get_gif(message.content.lower()[5:]) #Collects word after !gif
        # download image from url
        response = requests.get(gif_url) 
        
        # put it in file-like object in memory
        file_like_object = io.BytesIO(response.content)

        #file_name = 'image.gif'
        file_name = gif_url.split('/')[-1]
        
        # send it as normal file
        # it needs filename with extension `.gif` to display it as GIF image
        await message.channel.send(file=discord.File(file_like_object, filename=file_name))

它需要更长的时间才能显示,因为它必须将其发送到本地计算机然后将其发送到互联网。

它可用于使用pillowwandgizeh 编辑图像(即添加文本、更改颜色、绘制图形),使用opencv 检测人脸/人物/对象,使用@ 生成视频987654324@等


顺便说一句:

在回答How to make a canvas profile card in discord python bot? 问题时,我使用pillow 向图像添加元素。但它是静态图像,而不是需要更多工作的动画 GIF(每帧分开)

【讨论】:

    猜你喜欢
    • 2018-11-24
    • 2021-01-10
    • 1970-01-01
    • 2019-05-11
    • 2020-12-08
    • 2023-03-07
    • 2018-11-24
    • 2020-07-13
    • 1970-01-01
    相关资源
    最近更新 更多