async def query_pixiv(self, send_handler, msg, receiver_id, enable_r18=False): res = re.search(r'^看看(.*)?图$', msg.strip()) if res: mmap = { '帅': 'female', '妹子': 'male', '露佬': 'kyaru', } if enable_r18: mmap['色'] = 'daily_r18' file_path, meta = PixivCursor.get_one({'mode': mmap.get(res.group(1), 'daily')}, receiver_id) global COMPRESS_IMAGE msg = [] if isinstance(file_path, list): if file_path: for file in file_path[:3]: if COMPRESS_IMAGE: f = ImageProcesser.compress(os.path.join('/root/pixiv/', file), isabs=True) msg.append(ImageMsg({'file': f})) elif file_path: if COMPRESS_IMAGE: file_path = ImageProcesser.compress(os.path.join('/root/pixiv/', file_path), isabs=True) msg.append(ImageMsg({'file': file_path})) if msg: msg.insert(0, StringMsg(f'id: {meta["id"]}\nauthor: {meta["user"]["id"]}, {meta["user"]["name"]}\n')) await send_handler(receiver_id, MultiMsg(msg)) else: await send_handler(receiver_id, MultiMsg([StringMsg('kkr找不到'), ImageMsg({'file': f'kkr/tuxie'})])) return True else: return False
async def query(self, send_handler, msg, receiver_id): res = re.search(r'^活动(\d+)(\s+(日服|国际服|台服|国服|韩服))?$', msg.strip()) if res: detail = self._detail_ver2(int(res.group(1)), self._server[res.group(3) or '国服']) if detail is not None: await send_handler(receiver_id, MultiMsg(detail)) else: await send_handler( receiver_id, MultiMsg([ StringMsg('没有这个活动'), ImageMsg({ 'file': f'kkr/{random.choice(["hanpi1", "hanpi2", "hanpi3"])}' }) ])) return True constraints = self._parse_query_command(msg.strip()) if constraints is not None: results = self.event_table.select('id', 'eventType', 'eventName', 'bannerAssetBundleName', **constraints) if results: images = [[ ImageProcesser.open_nontransparent( os.path.join(const.asset_event_path, 'jp', f'{r[3]}.png')) or ImageProcesser.white_padding(420, 140), ] for r in results] texts = [f'{r[0]}: {r[2]}' for r in results] MAX_NUM = 32 file_names = [ ImageProcesser.thumbnail( images=images[i * MAX_NUM:min((i + 1) * MAX_NUM, len(images))], labels=texts[i * MAX_NUM:min((i + 1) * MAX_NUM, len(images))], label_style={ 'font_size': 20, 'font_type': 'default_font.ttf' }, col_space=20, row_space=20) for i in range((len(images) - 1) // MAX_NUM + 1) ] [ await send_handler(receiver_id, ImageMsg({'file': f})) for f in file_names ] else: await send_handler( receiver_id, MultiMsg([ StringMsg('kkr找不到'), ImageMsg({'file': f'kkr/tuxie'}) ])) return True return False
async def fixed_roomcode_reply(self, send_handler, msg, receiver_id, sender_id, submit_permission=False, logger=None): if msg == 'ycm' or msg == '有车吗': rl = self._query_room_number() if rl is None: await send_handler(receiver_id, StringMsg('查车失败,芽佬快看看怎么啦 QAQ')) elif rl: await send_handler(receiver_id, StringMsg('\n\n'.join(rl))) else: await send_handler(receiver_id, MultiMsg([ImageMsg({'file': f'kkr/{random.choice(self.preset_keywords["憨批"])}'}), StringMsg('哈哈,没车')])) return True else: if submit_permission or user_profile[str(sender_id)].get('authority') == 'admin': res = re.search(r'^([0-9]{5,6})(\s+.+)*(\s+[Qq][0-4])(\s+.+)*$', msg.strip()) if res: room_code = res.group(1) flag, msg = self._submit_room_number(room_code, sender_id, msg) if flag: await send_handler(receiver_id, MultiMsg([ImageMsg({'file': f'kkr/nb'}), StringMsg('上传车牌啦!')])) else: await send_handler(receiver_id, StringMsg(f'kkr坏了,芽佬快看看QAQ {msg}')) return True return False
async def query_gacha(self, send_handler, msg, receiver_id): res = re.search(r'^卡池(\d+)(\s+(日服|国际服|台服|国服|韩服))?$', msg.strip()) if res: detail = gacha._detail(int(res.group(1)), gacha._server[res.group(3) or '国服']) if detail is not None: await send_handler(receiver_id, MultiMsg(detail)) else: await send_handler(receiver_id, MultiMsg([StringMsg('没有这个卡池'), ImageMsg({'file': f'kkr/{random.choice(self.preset_keywords["憨批"])}'})])) return True constraints = gacha._parse_query_command(msg.strip()) if constraints is not None: if constraints == {}: results = gacha.gacha_table.select_or('id', 'type', 'gachaName', 'bannerAssetBundleName', 'resourceName', type=['permanent', 'limited'], fixed4star=[1]) else: results = gacha.gacha_table.select('id', 'type', 'gachaName', 'bannerAssetBundleName', 'resourceName', **constraints) if results: images = [[ ImageProcesser.open_nontransparent(os.path.join(const.asset_gacha_path, 'jp', f'{r[3]}.png')) or ImageProcesser.open_nontransparent(os.path.join(const.asset_gacha_path, r[4], 'jp', 'logo.png')) or ImageProcesser.white_padding(420, 140), ] for r in results] texts = [f'{r[0]}: {r[2]} ({gacha._type[r[1]]})' for r in results] MAX_NUM = 32 file_names = [ImageProcesser.thumbnail(images=images[i * MAX_NUM: min((i + 1) * MAX_NUM, len(images))], image_style={'height': 140}, labels=texts[i * MAX_NUM: min((i + 1) * MAX_NUM, len(images))], label_style={'font_size': 20, 'font_type': 'default_font.ttf'}, col_space=20, row_space=20 ) for i in range((len(images) - 1) // MAX_NUM + 1)] [await send_handler(receiver_id, ImageMsg({'file': f})) for f in file_names] else: await send_handler(receiver_id, MultiMsg([StringMsg('kkr找不到'), ImageMsg({'file': f'kkr/tuxie'})])) return True return False
async def fixed_reply(self, send_handler, msg, receiver_id, logger=None): be_at = False if '[CQ:at,qq=2807901929]' in msg: be_at = True if msg == '使用说明': await send_handler(receiver_id, ImageMsg({'file': ImageProcesser.manual()})) return True if msg == '底图目录': file_name = ImageProcesser.get_back_pics() await send_handler(receiver_id, ImageMsg({'file': file_name})) return True if be_at: m = re.compile(r'^(我){0,1}.*?([日草操]|cao|ri).*?([你]|kkr|kokoro){0,1}(.*)$').findall(msg.strip().lower()) self.logger.info('be_at %s', m) if m: m = m[0] verb = m[1] obj = m[2] subj = m[0] obj2 = m[3] if not subj: subj = 'kkr也' if obj in ['kkr', 'kokoro']: subj = obj obj = '你' final_s = f'{subj}{verb}{obj}{obj2}' fn = ImageProcesser.image_merge(47, final_s) await send_handler(receiver_id, ImageMsg({'file': fn})) return True else: file_path, meta = PixivCursor.get_one({'mode': 'kkr'}, receiver_id) global COMPRESS_IMAGE if isinstance(file_path, list): if file_path: for file in file_path[:3]: if COMPRESS_IMAGE: f = ImageProcesser.compress(os.path.join('/root/pixiv/', file), isabs=True) await send_handler(receiver_id, ImageMsg({'file': f})) return True else: if file_path is None: await send_handler(receiver_id, MultiMsg([StringMsg('kkr被看光了'), ImageMsg({'file': f'kkr/tuxie'})])) else: if COMPRESS_IMAGE: file_path = ImageProcesser.compress(os.path.join('/root/pixiv/', file_path), isabs=True) await send_handler(receiver_id, ImageMsg({'file': file_path})) return True return False
async def _on_stage_0(self, context): msg = context['raw_message'] uid = str(context['sender']['user_id']) if msg == '开始': if len(self.players) < 3: await self._send_g(StringMsg('人数不足无法开始游戏,需要至少3人')) else: await self.start() elif msg == '加入': if uid in self.players: await self._send_g(StringMsg('请勿重复加入')) else: self.players[uid] = 'default' await self._send_g(StringMsg(f'{uid} 加入成功 现在有{len(self.players)}个玩家')) elif msg == '退出': if uid not in self.players: await self._send_g(MultiMsg([StringMsg('没加入退个锤子'), ImageMsg({'file': f'kkr/worinima'})])) else: self.players.pop(uid) await self._send_g(StringMsg(f'{uid} 退出成功 现在有{len(self.players)}个玩家'))
async def query_card(self, send_handler, msg, receiver_id): # send_handler: Bot send handler res = re.search(r'^无框(\d+)(\s+(特训前|特训后))?$', msg.strip()) if res: result = self.card_table.select_by_single_value('resourceSetName', id=int( res.group(1))) if result: resource_set_name = result[0][0] if res.group(3) == '特训前': if os.access( os.path.join( const.asset_card_path, f'{resource_set_name}_card_normal.png'), os.R_OK): file_path = f'assets/cards/{resource_set_name}_card_normal.png' elif res.group(3) == '特训后': if os.access( os.path.join( const.asset_card_path, f'{resource_set_name}_card_after_training.png' ), os.R_OK): file_path = f'assets/cards/{resource_set_name}_card_after_training.png' else: file_path = f'assets/cards/{resource_set_name}_card_normal.png' \ if os.access(os.path.join(const.asset_card_path, f'{resource_set_name}_card_normal.png'), os.R_OK) \ else f'assets/cards/{resource_set_name}_card_after_training.png' \ if os.access(os.path.join(const.asset_card_path, f'{resource_set_name}_card_after_training.png'), os.R_OK) \ else '' if file_path: await send_handler(receiver_id, ImageMsg({'file': file_path})) else: await send_handler( receiver_id, MultiMsg([ StringMsg('没有这张卡'), ImageMsg({ 'file': f'kkr/{random.choice(["hanpi1", "hanpi2", "hanpi3"])}' }) ])) return True res = re.search(r'^查卡(\d+)(\s+(特训前|特训后))?$', msg.strip()) if res: description, resource_set_name, rarity, attribute, band_id = self._detail( cid=int(res.group(1))) if resource_set_name: if res.group(3) == '特训前': file_path = ImageProcesser.merge_image(resource_set_name, rarity, attribute, band_id, thumbnail=False, trained=False) elif res.group(3) == '特训后': file_path = ImageProcesser.merge_image(resource_set_name, rarity, attribute, band_id, thumbnail=False, trained=True) else: file_path = ImageProcesser.merge_image(resource_set_name, rarity, attribute, band_id, thumbnail=False, trained=False) \ or ImageProcesser.merge_image(resource_set_name, rarity, attribute, band_id, thumbnail=False, trained=True) if file_path: await send_handler( receiver_id, MultiMsg([ ImageMsg({'file': file_path}), StringMsg(description) ])) else: await send_handler( receiver_id, MultiMsg([ StringMsg('没有这张卡'), ImageMsg({ 'file': f'kkr/{random.choice(["hanpi1", "hanpi2", "hanpi3"])}' }) ])) return True constraints = self._parse_query_command(msg.strip()) if constraints: if constraints == '露佬': await send_handler( receiver_id, MultiMsg([ StringMsg('再查露佬头都给你锤爆\n'), ImageMsg({'file': 'kkr/lulao'}) ])) return True results = self.card_table.select('id', 'resourceSetName', 'rarity', 'attribute', 'bandId', 'skillId', 'type', **constraints) if results: images = [[ ImageProcesser.merge_image(r[1], r[2], r[3], r[4]) or ImageProcesser.white_padding(180, 180), ImageProcesser.merge_image( r[1], r[2], r[3], r[4], trained=True) or ImageProcesser.white_padding(180, 180) ] for r in results] # images = [ImageProcesser.merge_image(r[1], r[2], r[3], r[4]) or ImageProcesser.white_padding(180, 180) for r in results] texts = [ str(r[0]) + f'({self._skill_types.get(r[5], "未知")}, {self._types.get(r[6], "未知")})' for r in results ] # fragment MAX_NUM = 32 file_names = [ ImageProcesser.thumbnail( images=images[i * MAX_NUM:min((i + 1) * MAX_NUM, len(images))], labels=texts[i * MAX_NUM:min((i + 1) * MAX_NUM, len(images))], label_style={'font_size': 20}, col_space=20, row_space=20, ) for i in range((len(images) - 1) // MAX_NUM + 1) ] [ await send_handler(receiver_id, ImageMsg({'file': f})) for f in file_names ] else: await send_handler( receiver_id, MultiMsg([ StringMsg('kkr找不到'), ImageMsg({'file': f'kkr/tuxie'}) ])) return True return False
async def query_user_gacha(self, send_handler, msg, receiver_id, logger=None): if msg == '更新抽卡数据': l = self.bilibili_drawcard_spider.fetch_once() if not l is None: await send_handler(receiver_id, MultiMsg([ImageMsg({'file': f'kkr/nb'}), StringMsg(f'又有新的{l}个出货记录了!')])) else: await send_handler(receiver_id, StringMsg('更新失败,芽佬快看看怎么啦 QAQ')) return True else: res = re.search(r'^查抽卡名字 (.*?)$', msg) self.logger.info(f'{msg}, {res}') ret = [] query = False if res: self.logger.info(f'query gacha user {res.group(1)}') query = True ret = self.bilibili_drawcard_spider.get_data_by_username(res.group(1)) else: res = re.search(r'^查抽卡id (.*?)$', msg) if res: uid = int(res.group(1)) self.logger.info(f'query gacha user {uid}') query = True ret = self.bilibili_drawcard_spider.get_data_by_uid(uid) if not query: return False if not ret: await send_handler(receiver_id, MultiMsg([ImageMsg({'file': f'kkr/{random.choice(self.preset_keywords["憨批"])}'}), StringMsg('没出货查什么查')])) return True images = [] texts = [] stringmsg = [] # self.logger.info(f'gacha result {ret}') too_large = False if len(ret) > 50: ret = ret[:50] too_large = True for (i, d) in enumerate(ret): card_id = d.situation_id r = card.card_table.select_by_single_value('id', 'resourceSetName', 'rarity', 'attribute', 'bandId', 'skillId', 'type', id=card_id)[0] if r: images.append(ImageProcesser.merge_image(r[1], r[2], r[3], r[4]) or ImageProcesser.white_padding(180, 180)) t = time.strftime('%Y/%m/%d %H:%M:%S', time.localtime(d.gacha_at // 1000)) s = f'{t}' texts.append(s) stringmsg.append(f'{t}: {d.user_name}({d.user_id}) ==< {d.gacha_name}') if (i+1) % 10 == 0: file_name = ImageProcesser.thumbnail(images=images, labels=texts, col_space=40) await send_handler(receiver_id, MultiMsg([ImageMsg({'file': file_name}), StringMsg('\n'.join(stringmsg))])) images = [] texts = [] stringmsg = [] if images: file_name = ImageProcesser.thumbnail(images=images, labels=texts, col_space=40) await send_handler(receiver_id, MultiMsg([ImageMsg({'file': file_name}), StringMsg('\n'.join(stringmsg))])) if too_large: await send_handler(receiver_id, MultiMsg([ImageMsg({'file': f'kkr/nb'}), StringMsg('出货的也太多了,kkr好累!下次再查吧!')])) return True
async def on_stage_2_enter(self): await self._send_g(MultiMsg([StringMsg('所有人行动完毕,天亮了。现在是自由讨论时间,讨论完毕后,输入"查看结果"以查看游戏结果'), ImageMsg({'file': f'kkr/want'})]))