🐛 Fix sticker cannot capture pictures, support batch addition (#78)

🐛 修复 sticker 无法截取图片、支持批量添加 (#78)
This commit is contained in:
lowking 2021-05-28 20:28:03 +08:00 committed by GitHub
parent 165dd661a6
commit 69c6fa26ad
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 217 additions and 39 deletions

View File

@ -391,6 +391,12 @@ us_static_uploading: Uploading pictures...
us_static_rounding: Rounding in progress...
us_change_rounding_true: Automatic conversion of rounded corners for stickers has been turned on.
us_change_rounding_false: Automatic conversion of rounded corners for stickers has been turned off.
## merge
merge_command_error: Command parameter error!
merge_processing_left: Processing the 【
merge_processing_right: 】st message.
merge_total_processed_left: A total of 【
merge_total_processed_right: 】 stickers were processed.
# system
# sh

View File

@ -409,6 +409,12 @@ us_static_uploading: 上传图片中 . . .
us_static_rounding: 图片圆角处理中 . . .
us_change_rounding_true: 已开启贴纸自动转换圆角功能
us_change_rounding_false: 已关闭贴纸自动转换圆角功能
## merge
merge_command_error: 命令参数错误!
merge_processing_left: 正在处理第【
merge_processing_right: 】条消息。
merge_total_processed_left: 共处理了【
merge_total_processed_right: 】张贴纸。
# system
## sh

View File

@ -391,6 +391,12 @@ us_static_uploading: 上傳圖片中…
us_static_rounding: 圖片圓角處理中…
us_change_rounding_true: 已開啟貼紙自動轉換圓角功能
us_change_rounding_false: 已關閉貼紙自動轉換圓角功能
## merge
merge_command_error: 命令參數錯誤!
merge_processing_left: 正在處理第【
merge_processing_right: 】條消息。
merge_total_processed_left: 共處理了【
merge_total_processed_right: 】張貼紙。
# system
# sh

View File

@ -13,6 +13,7 @@ from math import floor
from pagermaid import bot, redis, redis_status
from pagermaid.listener import listener
from pagermaid.utils import lang
from pagermaid import log
@listener(is_plugin=False, outgoing=True, command="s",
@ -21,33 +22,142 @@ from pagermaid.utils import lang
async def sticker(context):
""" Fetches images/stickers and add them to your pack. """
pic_round = False
is_batch = False
package_name = ""
if redis_status():
if redis.get("sticker.round"):
pic_round = True
if len(context.parameter) == 1:
if context.parameter[0] == "set_round":
if pic_round:
redis.delete("sticker.round")
if len(context.parameter) >= 1:
# s merge
await log(f"{context.parameter}")
if context.parameter[0] == "merge" or context.parameter[0] == "m":
is_batch = True
# s merge png <package_name> <number>
try:
if context.parameter[3].isnumeric():
if "png" in context.parameter[1]:
pic_round = False
else:
pic_round = True
package_name = context.parameter[2]
except:
# 异常,多半是数组越界,不处理,继续参数校验
pass
try:
# s merge <package_name> <number>
if context.parameter[2].isnumeric():
if "png" in context.parameter[1]:
pic_round = False
package_name = context.parameter[2]
else:
package_name = context.parameter[1]
# s merge png <package_name>
elif "png" in context.parameter[1]:
pic_round = False
package_name = context.parameter[2]
# s merge <package_name> <number>
else:
package_name = context.parameter[1]
except:
# 异常,多半是数组越界
# s merge <package_name>
try:
await context.edit(lang('us_change_rounding_false'))
if "png" in context.parameter[1]:
raise Exception()
package_name = context.parameter[1]
except:
pass
# 命令错误
try:
await context.edit(lang('merge_command_error'))
except:
pass
return
# s <png | number> | error
else:
if context.parameter[0] == "set_round":
if pic_round:
redis.delete("sticker.round")
try:
await context.edit(lang('us_change_rounding_false'))
except:
pass
else:
redis.set("sticker.round", "true")
try:
await context.edit(lang('us_change_rounding_true'))
except:
pass
return
elif "png" in context.parameter[0]:
pic_round = False
# s <number>
elif context.parameter[0].isnumeric():
pass
elif isEmoji(context.parameter[0]) or len(context.parameter[0]) == 1:
await log(f"emoji{context.parameter[0]}")
pass
else:
redis.set("sticker.round", "true")
try:
await context.edit(lang('us_change_rounding_true'))
await context.edit(lang('merge_command_error'))
except:
pass
return
elif "png" in context.parameter[0]:
pic_round = False
return
user = await bot.get_me()
if not user.username:
user.username = user.first_name
message = await context.get_reply_message()
custom_emoji = False
animated = False
emoji = ""
if is_batch:
# 多张
""" merge every single sticker after the message you replied to. """
if not context.reply_to_msg_id:
await context.edit(lang('not_reply'))
return
input_chat = await context.get_input_chat()
count = 0
scount = 0
result = ""
if context.parameter[0] == "m":
message = await context.get_reply_message()
await single_sticker(animated, context, custom_emoji, emoji, message, pic_round, user,
package_name)
else:
async for message in context.client.iter_messages(input_chat, min_id=context.reply_to_msg_id):
count += 1
if message and message.media:
scount += 1
try:
await log(f"{lang('merge_processing_left')}{count}{lang('merge_processing_right')}")
await context.edit(f"{lang('merge_processing_left')}{count}{lang('merge_processing_right')}")
except:
pass
result = await single_sticker(animated, context, custom_emoji, emoji, message, pic_round, user,
package_name)
await sleep(.5)
try:
await context.edit(f"{result}\n"
f"{lang('merge_total_processed_left')}{scount}{lang('merge_total_processed_right')}", parse_mode='md')
except:
pass
await sleep(5)
try:
await context.delete()
except:
pass
else:
# 单张收集图片
message = await context.get_reply_message()
await single_sticker(animated, context, custom_emoji, emoji, message, pic_round, user, "")
async def single_sticker(animated, context, custom_emoji, emoji, message, pic_round, user, package_name):
try:
await context.edit(lang('sticker_processing'))
except:
@ -99,19 +209,38 @@ async def sticker(context):
emoji = "👀"
pack = 1
sticker_already = False
if len(split_strings) == 3:
pack = split_strings[2]
if split_strings[1].replace("png", "") != "":
emoji = split_strings[1].replace("png", "")
elif len(split_strings) == 2:
if split_strings[1].isnumeric():
pack = int(split_strings[1])
else:
if package_name:
# 批量处理贴纸无法指定emoji只获取第几个pack
# s merge png <package_name> <number>
if len(split_strings) == 5:
pack = split_strings[4]
# s merge <package_name> <number>
elif len(split_strings) == 4:
pack = split_strings[3]
else:
if len(split_strings) == 3:
# s png <number|emoji>
pack = split_strings[2]
if split_strings[1].replace("png", "") != "":
emoji = split_strings[1].replace("png", "")
elif len(split_strings) == 2:
# s <number|emoji>
if split_strings[1].isnumeric():
pack = int(split_strings[1])
else:
if split_strings[1].replace("png", "") != "":
emoji = split_strings[1].replace("png", "")
pack_name = f"{user.username}_{pack}"
pack_title = f"@{user.username} {lang('sticker_pack_title')} ({pack})"
if not isinstance(pack, int):
pack = 1
if package_name:
# merge指定package_name
pack_name = f"{user.username}_{package_name}_{pack}"
pack_title = f"@{user.username} {lang('sticker_pack_title')} ({package_name}) ({pack})"
else:
pack_name = f"{user.username}_{pack}"
pack_title = f"@{user.username} {lang('sticker_pack_title')} ({pack})"
command = '/newpack'
file = BytesIO()
@ -126,7 +255,7 @@ async def sticker(context):
await context.edit(lang('us_static_rounding'))
except:
pass
image = await rounded_image(photo)
image = await rounded_image(image)
file.name = "sticker.png"
image.save(file, "PNG")
else:
@ -136,13 +265,15 @@ async def sticker(context):
try:
response = request.urlopen(
request.Request(f'http://t.me/addstickers/{pack_name}'), context=ssl.create_default_context(cafile=certifi.where()))
request.Request(f'http://t.me/addstickers/{pack_name}'),
context=ssl.create_default_context(cafile=certifi.where()))
except UnicodeEncodeError:
pack_name = 's' + hex(context.sender.id)[2:]
if animated:
pack_name = 's' + hex(context.sender.id)[2:] + '_animated'
response = request.urlopen(
request.Request(f'http://t.me/addstickers/{pack_name}'), context=ssl.create_default_context(cafile=certifi.where()))
request.Request(f'http://t.me/addstickers/{pack_name}'),
context=ssl.create_default_context(cafile=certifi.where()))
if not response.status == 200:
try:
await context.edit(lang('sticker_telegram_server_error'))
@ -153,7 +284,7 @@ async def sticker(context):
if " A <strong>Telegram</strong> user has created the <strong>Sticker&nbsp;Set</strong>." not in \
http_response:
for _ in range(20): # 最多重试20次
for _ in range(20): # 最多重试20次
try:
async with bot.conversation('Stickers') as conversation:
await conversation.send_message('/addsticker')
@ -164,17 +295,29 @@ async def sticker(context):
while chat_response.text == "Whoa! That's probably enough stickers for one pack, give it a break. \
A pack can't have more than 120 stickers at the moment.":
pack += 1
pack_name = f"{user.username}_{pack}"
pack_title = f"@{user.username} {lang('sticker_pack_title')} ({pack})"
if package_name:
# merge指定package_name
pack_name = f"{user.username}_{package_name}_{pack}"
pack_title = f"@{user.username} {lang('sticker_pack_title')} ({package_name}) ({pack})"
else:
pack_name = f"{user.username}_{pack}"
pack_title = f"@{user.username} {lang('sticker_pack_title')} ({pack})"
try:
await context.edit(lang('sticker_change_pack_to') + str(pack) + lang('sticker_last_is_full'))
if package_name:
await context.edit(
lang('sticker_change_pack_to') + str(package_name) + str(pack) + lang(
'sticker_last_is_full'))
else:
await context.edit(
lang('sticker_change_pack_to') + str(pack) + lang('sticker_last_is_full'))
except:
pass
await conversation.send_message(pack_name)
chat_response = await conversation.get_response()
if chat_response.text == "Invalid pack selected.":
await add_sticker(conversation, command, pack_title, pack_name, animated, message,
context, file, emoji)
context, file, emoji)
try:
await context.edit(
f"{lang('sticker_has_been_added')} [{lang('sticker_this')}](t.me/addstickers/{pack_name}) {lang('sticker_pack')}",
@ -218,11 +361,14 @@ A pack can't have more than 120 stickers at the moment.":
parse_mode='md')
except:
pass
await sleep(5)
try:
await context.delete()
except:
pass
if package_name:
return f"{lang('sticker_has_been_added')} [{lang('sticker_this')}](t.me/addstickers/{pack_name}) {lang('sticker_pack')}"
else:
await sleep(5)
try:
await context.delete()
except:
pass
async def add_sticker(conversation, command, pack_title, pack_name, animated, message, context, file, emoji):
@ -292,8 +438,8 @@ async def resize_image(photo):
return image
async def rounded_image(photo):
image = Image.open(photo)
async def rounded_image(image):
w = image.width
h = image.height
resize_size = 0
@ -302,7 +448,7 @@ async def rounded_image(photo):
resize_size = h
else:
resize_size = w
half_size = floor(resize_size/2)
half_size = floor(resize_size / 2)
# 获取圆角模版切割成4个角
tl = (0, 0, 256, 256)
@ -321,7 +467,6 @@ async def rounded_image(photo):
blp = blp.resize((half_size, half_size))
brp = brp.resize((half_size, half_size))
# 扩展四个角大小到目标图大小
# tlp = ImageOps.expand(tlp, (0, 0, w - tlp.width, h - tlp.height))
# trp = ImageOps.expand(trp, (w - trp.width, 0, 0, h - trp.height))
@ -339,3 +484,18 @@ async def rounded_image(photo):
image.putalpha(ImageOps.invert(ni))
return image
def isEmoji(content):
if not content:
return False
if u"\U0001F600" <= content <= u"\U0001F64F":
return True
elif u"\U0001F300" <= content <= u"\U0001F5FF":
return True
elif u"\U0001F680" <= content <= u"\U0001F6FF":
return True
elif u"\U0001F1E0" <= content <= u"\U0001F1FF":
return True
else:
return False