feat(task): 培育支持指定P偶像
|
@ -16,6 +16,7 @@ from typing import (
|
||||||
Concatenate,
|
Concatenate,
|
||||||
Generic,
|
Generic,
|
||||||
Type,
|
Type,
|
||||||
|
Sequence,
|
||||||
)
|
)
|
||||||
from typing_extensions import deprecated
|
from typing_extensions import deprecated
|
||||||
|
|
||||||
|
@ -279,14 +280,15 @@ class ContextOcr:
|
||||||
|
|
||||||
def find_all(
|
def find_all(
|
||||||
self,
|
self,
|
||||||
patterns: list[str | re.Pattern | StringMatchFunction],
|
patterns: Sequence[str | re.Pattern | StringMatchFunction],
|
||||||
*,
|
*,
|
||||||
hint: HintBox | None = None,
|
hint: HintBox | None = None,
|
||||||
rect: Rect | None = None,
|
rect: Rect | None = None,
|
||||||
|
|
||||||
) -> list[OcrResult | None]:
|
) -> list[OcrResult | None]:
|
||||||
return self.__engine.find_all(
|
return self.__engine.find_all(
|
||||||
ContextStackVars.ensure_current().screenshot,
|
ContextStackVars.ensure_current().screenshot,
|
||||||
patterns,
|
list(patterns),
|
||||||
hint=hint,
|
hint=hint,
|
||||||
rect=rect,
|
rect=rect,
|
||||||
)
|
)
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
from enum import IntEnum, Enum
|
|
||||||
from typing import Literal
|
from typing import Literal
|
||||||
|
from enum import IntEnum, Enum
|
||||||
|
|
||||||
from pydantic import BaseModel
|
from pydantic import BaseModel
|
||||||
|
|
||||||
|
@ -22,10 +22,88 @@ class APShopItems(IntEnum):
|
||||||
"""回忆再生成券"""
|
"""回忆再生成券"""
|
||||||
|
|
||||||
|
|
||||||
class PIdols(Enum):
|
class PIdol(Enum):
|
||||||
pass
|
"""P偶像"""
|
||||||
|
倉本千奈_Campusmode = ["倉本千奈", "Campus mode!!"]
|
||||||
|
倉本千奈_WonderScale = ["倉本千奈", "Wonder Scale"]
|
||||||
|
倉本千奈_ようこそ初星温泉 = ["倉本千奈", "ようこそ初星温泉"]
|
||||||
|
倉本千奈_仮装狂騒曲 = ["倉本千奈", "仮装狂騒曲"]
|
||||||
|
倉本千奈_初心 = ["倉本千奈", "初心"]
|
||||||
|
倉本千奈_学園生活 = ["倉本千奈", "学園生活"]
|
||||||
|
倉本千奈_日々_発見的ステップ = ["倉本千奈", "日々、発見的ステップ!"]
|
||||||
|
倉本千奈_胸を張って一歩ずつ = ["倉本千奈", "胸を張って一歩ずつ"]
|
||||||
|
十王星南_Campusmode = ["十王星南", "Campus mode!!"]
|
||||||
|
十王星南_一番星 = ["十王星南", "一番星"]
|
||||||
|
十王星南_学園生活 = ["十王星南", "学園生活"]
|
||||||
|
十王星南_小さな野望 = ["十王星南", "小さな野望"]
|
||||||
|
姫崎莉波_clumsytrick = ["姫崎莉波", "clumsy trick"]
|
||||||
|
姫崎莉波_私らしさのはじまり = ["姫崎莉波", "『私らしさ』のはじまり"]
|
||||||
|
姫崎莉波_キミとセミブルー = ["姫崎莉波", "キミとセミブルー"]
|
||||||
|
姫崎莉波_Campusmode = ["姫崎莉波", "Campus mode!!"]
|
||||||
|
姫崎莉波_LUV = ["姫崎莉波", "L.U.V"]
|
||||||
|
姫崎莉波_ようこそ初星温泉 = ["姫崎莉波", "ようこそ初星温泉"]
|
||||||
|
姫崎莉波_ハッピーミルフィーユ = ["姫崎莉波", "ハッピーミルフィーユ"]
|
||||||
|
姫崎莉波_初心 = ["姫崎莉波", "初心"]
|
||||||
|
姫崎莉波_学園生活 = ["姫崎莉波", "学園生活"]
|
||||||
|
月村手毬_Lunasaymaybe = ["月村手毬", "Luna say maybe"]
|
||||||
|
月村手毬_一匹狼 = ["月村手毬", "一匹狼"]
|
||||||
|
月村手毬_Campusmode = ["月村手毬", "Campus mode!!"]
|
||||||
|
月村手毬_アイヴイ = ["月村手毬", "アイヴイ"]
|
||||||
|
月村手毬_初声 = ["月村手毬", "初声"]
|
||||||
|
月村手毬_学園生活 = ["月村手毬", "学園生活"]
|
||||||
|
月村手毬_仮装狂騒曲 = ["月村手毬", "仮装狂騒曲"]
|
||||||
|
有村麻央_Fluorite = ["有村麻央", "Fluorite"]
|
||||||
|
有村麻央_はじまりはカッコよく = ["有村麻央", "はじまりはカッコよく"]
|
||||||
|
有村麻央_Campusmode = ["有村麻央", "Campus mode!!"]
|
||||||
|
有村麻央_FeelJewelDream = ["有村麻央", "Feel Jewel Dream"]
|
||||||
|
有村麻央_キミとセミブルー = ["有村麻央", "キミとセミブルー"]
|
||||||
|
有村麻央_初恋 = ["有村麻央", "初恋"]
|
||||||
|
有村麻央_学園生活 = ["有村麻央", "学園生活"]
|
||||||
|
篠泽广_コントラスト = ["篠泽广", "コントラスト"]
|
||||||
|
篠泽广_一番向いていないこと = ["篠泽广", "一番向いていないこと"]
|
||||||
|
篠泽广_光景 = ["篠泽广", "光景"]
|
||||||
|
篠泽广_Campusmode = ["篠泽广", "Campus mode!!"]
|
||||||
|
篠泽广_仮装狂騒曲 = ["篠泽广", "仮装狂騒曲"]
|
||||||
|
篠泽广_ハッピーミルフィーユ = ["篠泽广", "ハッピーミルフィーユ"]
|
||||||
|
篠泽广_初恋 = ["篠泽广", "初恋"]
|
||||||
|
篠泽广_学園生活 = ["篠泽广", "学園生活"]
|
||||||
|
紫云清夏_TameLieOneStep = ["紫云清夏", "Tame-Lie-One-Step"]
|
||||||
|
紫云清夏_カクシタワタシ = ["紫云清夏", "カクシタワタシ"]
|
||||||
|
紫云清夏_夢へのリスタート = ["紫云清夏", "夢へのリスタート"]
|
||||||
|
紫云清夏_Campusmode = ["紫云清夏", "Campus mode!!"]
|
||||||
|
紫云清夏_キミとセミブルー = ["紫云清夏", "キミとセミブルー"]
|
||||||
|
紫云清夏_初恋 = ["紫云清夏", "初恋"]
|
||||||
|
紫云清夏_学園生活 = ["紫云清夏", "学園生活"]
|
||||||
|
花海佑芽_WhiteNightWhiteWish = ["花海佑芽", "White Night! White Wish!"]
|
||||||
|
花海佑芽_学園生活 = ["花海佑芽", "学園生活"]
|
||||||
|
花海佑芽_Campusmode = ["花海佑芽", "Campus mode!!"]
|
||||||
|
花海佑芽_TheRollingRiceball = ["花海佑芽", "The Rolling Riceball"]
|
||||||
|
花海佑芽_アイドル_はじめっ = ["花海佑芽", "アイドル、はじめっ!"]
|
||||||
|
花海咲季_BoomBoomPow = ["花海咲季", "Boom Boom Pow"]
|
||||||
|
花海咲季_Campusmode = ["花海咲季", "Campus mode!!"]
|
||||||
|
花海咲季_FightingMyWay = ["花海咲季", "Fighting My Way"]
|
||||||
|
花海咲季_わたしが一番 = ["花海咲季", "わたしが一番!"]
|
||||||
|
花海咲季_冠菊 = ["花海咲季", "冠菊"]
|
||||||
|
花海咲季_初声 = ["花海咲季", "初声"]
|
||||||
|
花海咲季_古今東西ちょちょいのちょい = ["花海咲季", "古今東西ちょちょいのちょい"]
|
||||||
|
花海咲季_学園生活 = ["花海咲季", "学園生活"]
|
||||||
|
葛城リーリヤ_一つ踏み出した先に = ["葛城リーリヤ", "一つ踏み出した先に"]
|
||||||
|
葛城リーリヤ_白線 = ["葛城リーリヤ", "白線"]
|
||||||
|
葛城リーリヤ_Campusmode = ["葛城リーリヤ", "Campus mode!!"]
|
||||||
|
葛城リーリヤ_WhiteNightWhiteWish = ["葛城リーリヤ", "White Night! White Wish!"]
|
||||||
|
葛城リーリヤ_冠菊 = ["葛城リーリヤ", "冠菊"]
|
||||||
|
葛城リーリヤ_初心 = ["葛城リーリヤ", "初心"]
|
||||||
|
葛城リーリヤ_学園生活 = ["葛城リーリヤ", "学園生活"]
|
||||||
|
藤田ことね_カワイイ_はじめました = ["藤田ことね", "カワイイ", "はじめました"]
|
||||||
|
藤田ことね_世界一可愛い私 = ["藤田ことね", "世界一可愛い私"]
|
||||||
|
藤田ことね_Campusmode = ["藤田ことね", "Campus mode!!"]
|
||||||
|
藤田ことね_YellowBigBang = ["藤田ことね", "Yellow Big Bang!"]
|
||||||
|
藤田ことね_WhiteNightWhiteWish = ["藤田ことね", "White Night! White Wish!"]
|
||||||
|
藤田ことね_冠菊 = ["藤田ことね", "冠菊"]
|
||||||
|
藤田ことね_初声 = ["藤田ことね", "初声"]
|
||||||
|
藤田ことね_学園生活 = ["藤田ことね", "学園生活"]
|
||||||
|
|
||||||
|
|
||||||
class PurchaseConfig(BaseModel):
|
class PurchaseConfig(BaseModel):
|
||||||
enabled: bool = False
|
enabled: bool = False
|
||||||
"""是否启用商店购买"""
|
"""是否启用商店购买"""
|
||||||
|
@ -74,11 +152,12 @@ class ProduceConfig(BaseModel):
|
||||||
"""培育模式。"""
|
"""培育模式。"""
|
||||||
produce_count: int = 1
|
produce_count: int = 1
|
||||||
"""培育的次数。"""
|
"""培育的次数。"""
|
||||||
idols: list[str] = []
|
idols: list[PIdol] = []
|
||||||
"""要培育的偶像。将会按顺序循环选择培育。"""
|
"""要培育的偶像。将会按顺序循环选择培育。"""
|
||||||
memory_sets: list[int] = []
|
memory_sets: list[int] = []
|
||||||
"""要使用的回忆编成编号,从 1 开始。将会按顺序循环选择使用。"""
|
"""要使用的回忆编成编号,从 1 开始。将会按顺序循环选择使用。"""
|
||||||
support_card_sets: list[int] = []
|
support_card_sets: list[int] = []
|
||||||
|
|
||||||
"""要使用的支援卡编成编号,从 1 开始。将会按顺序循环选择使用。"""
|
"""要使用的支援卡编成编号,从 1 开始。将会按顺序循环选择使用。"""
|
||||||
auto_set_memory: bool = False
|
auto_set_memory: bool = False
|
||||||
"""是否自动编成回忆。此选项优先级高于回忆编成编号。"""
|
"""是否自动编成回忆。此选项优先级高于回忆编成编号。"""
|
||||||
|
|
|
@ -1,10 +1,10 @@
|
||||||
import logging
|
import logging
|
||||||
|
|
||||||
from . import R
|
from . import R
|
||||||
from .common import conf
|
from .common import conf, PIdol
|
||||||
from .actions.loading import wait_loading_end
|
from .actions.loading import wait_loading_end
|
||||||
from .actions.in_purodyuusu import hajime_regular
|
from .actions.in_purodyuusu import hajime_regular
|
||||||
from kotonebot import device, image, ocr, task, action, sleep
|
from kotonebot import device, image, ocr, task, action, sleep, contains
|
||||||
from .actions.scenes import loading, at_home, goto_home
|
from .actions.scenes import loading, at_home, goto_home
|
||||||
|
|
||||||
logger = logging.getLogger(__name__)
|
logger = logging.getLogger(__name__)
|
||||||
|
@ -14,9 +14,90 @@ def format_time(seconds):
|
||||||
seconds = int(seconds % 60)
|
seconds = int(seconds % 60)
|
||||||
return f"{minutes}m {seconds}s"
|
return f"{minutes}m {seconds}s"
|
||||||
|
|
||||||
|
def unify(arr: list[int]):
|
||||||
|
# 先对数组进行排序
|
||||||
|
arr.sort()
|
||||||
|
result = []
|
||||||
|
i = 0
|
||||||
|
while i < len(arr):
|
||||||
|
# 将当前元素加入结果
|
||||||
|
result.append(arr[i])
|
||||||
|
# 跳过所有与当前元素相似的元素
|
||||||
|
j = i + 1
|
||||||
|
while j < len(arr) and abs(arr[j] - arr[i]) <= 10:
|
||||||
|
j += 1
|
||||||
|
i = j
|
||||||
|
return result
|
||||||
|
|
||||||
|
@action('选择P偶像')
|
||||||
|
def select_idol(target_titles: list[str] | PIdol):
|
||||||
|
"""
|
||||||
|
选择目标P偶像
|
||||||
|
|
||||||
|
前置条件:培育-偶像选择页面 1.アイドル選択\n
|
||||||
|
结束状态:培育-偶像选择页面 1.アイドル選択\n
|
||||||
|
|
||||||
|
:param target_titles: 目标偶像的名称关键字。选择时只会选择所有关键字都出现的偶像。
|
||||||
|
"""
|
||||||
|
# 前置条件:[res/sprites/jp/produce/produce_preparation1.png]
|
||||||
|
# 结束状态:[res/sprites/jp/produce/produce_preparation1.png]
|
||||||
|
|
||||||
|
# 进入总览
|
||||||
|
device.update_screenshot()
|
||||||
|
device.click(image.expect(R.Produce.ButtonPIdolOverview))
|
||||||
|
while not image.find(R.Common.ButtonConfirmNoIcon):
|
||||||
|
device.update_screenshot()
|
||||||
|
|
||||||
|
if isinstance(target_titles, PIdol):
|
||||||
|
target_titles = target_titles.value
|
||||||
|
_target_titles = [contains(t) for t in target_titles]
|
||||||
|
device.update_screenshot()
|
||||||
|
# 定位滑动基准
|
||||||
|
results = image.find_all(R.Produce.IconPIdolLevel)
|
||||||
|
results.sort(key=lambda r: tuple(r.position))
|
||||||
|
ys = unify([r.position[1] for r in results])
|
||||||
|
|
||||||
|
min_y = ys[0]
|
||||||
|
max_y = ys[1]
|
||||||
|
|
||||||
|
found = False
|
||||||
|
max_tries = 5
|
||||||
|
tries = 0
|
||||||
|
# TODO: 加入 ScrollBar 类,判断滚动条进度
|
||||||
|
# 找到目标偶像
|
||||||
|
while not found:
|
||||||
|
# 首先检查当前选中的是不是已经是目标
|
||||||
|
if all(ocr.find_all(_target_titles, rect=R.Produce.KbIdolOverviewName)):
|
||||||
|
found = True
|
||||||
|
break
|
||||||
|
# 如果不是,就挨个选中,判断名称
|
||||||
|
for r in results:
|
||||||
|
device.click(r)
|
||||||
|
device.update_screenshot()
|
||||||
|
if all(ocr.find_all(_target_titles, rect=R.Produce.KbIdolOverviewName)):
|
||||||
|
found = True
|
||||||
|
break
|
||||||
|
if not found:
|
||||||
|
tries += 1
|
||||||
|
if tries > max_tries:
|
||||||
|
break
|
||||||
|
# 翻页
|
||||||
|
device.swipe(x1=100, x2=100, y1=max_y, y2=min_y)
|
||||||
|
sleep(2)
|
||||||
|
device.update_screenshot()
|
||||||
|
results = image.find_all(R.Produce.IconPIdolLevel)
|
||||||
|
results.sort(key=lambda r: tuple(r.position))
|
||||||
|
|
||||||
|
device.click(image.expect(R.Common.ButtonConfirmNoIcon))
|
||||||
|
return found
|
||||||
|
|
||||||
@action('单次培育')
|
@action('单次培育')
|
||||||
def do_produce():
|
def do_produce(idol: PIdol | None = None):
|
||||||
"""进行培育流程"""
|
"""
|
||||||
|
进行培育流程
|
||||||
|
|
||||||
|
:param idol: 要培育的偶像。如果为 None,则使用配置文件中的偶像。
|
||||||
|
"""
|
||||||
if not conf().produce.enabled:
|
if not conf().produce.enabled:
|
||||||
logger.info('Produce is disabled.')
|
logger.info('Produce is disabled.')
|
||||||
return
|
return
|
||||||
|
@ -34,7 +115,14 @@ def do_produce():
|
||||||
sleep(0.3)
|
sleep(0.3)
|
||||||
wait_loading_end()
|
wait_loading_end()
|
||||||
# 选择 PIdol [screenshots/produce/select_p_idol.png]
|
# 选择 PIdol [screenshots/produce/select_p_idol.png]
|
||||||
|
if idol:
|
||||||
|
select_idol(idol.value)
|
||||||
|
elif conf().produce.idols:
|
||||||
|
select_idol(conf().produce.idols[0].value) # TODO: 支持多次培育
|
||||||
|
else:
|
||||||
|
logger.warning('No PIdol specified. Using default idol.')
|
||||||
device.click(image.expect_wait(R.Common.ButtonNextNoIcon))
|
device.click(image.expect_wait(R.Common.ButtonNextNoIcon))
|
||||||
|
|
||||||
sleep(0.1)
|
sleep(0.1)
|
||||||
# 选择支援卡 自动编成 [screenshots/produce/select_support_card.png]
|
# 选择支援卡 自动编成 [screenshots/produce/select_support_card.png]
|
||||||
device.click(image.expect_wait(R.Produce.ButtonAutoSet))
|
device.click(image.expect_wait(R.Produce.ButtonAutoSet))
|
||||||
|
@ -89,5 +177,4 @@ if __name__ == '__main__':
|
||||||
logging.getLogger('kotonebot').setLevel(logging.DEBUG)
|
logging.getLogger('kotonebot').setLevel(logging.DEBUG)
|
||||||
logger.setLevel(logging.DEBUG)
|
logger.setLevel(logging.DEBUG)
|
||||||
produce_task()
|
produce_task()
|
||||||
|
# select_idol(PIdol.藤田ことね_学園生活)
|
||||||
|
|
|
@ -10,7 +10,7 @@ from kotonebot.config.manager import load_config, save_config
|
||||||
from kotonebot.tasks.common import (
|
from kotonebot.tasks.common import (
|
||||||
BaseConfig, APShopItems, PurchaseConfig, ActivityFundsConfig,
|
BaseConfig, APShopItems, PurchaseConfig, ActivityFundsConfig,
|
||||||
PresentsConfig, AssignmentConfig, ContestConfig, ProduceConfig,
|
PresentsConfig, AssignmentConfig, ContestConfig, ProduceConfig,
|
||||||
MissionRewardConfig
|
MissionRewardConfig, PIdol
|
||||||
)
|
)
|
||||||
from kotonebot.config.base_config import UserConfig, BackendConfig
|
from kotonebot.config.base_config import UserConfig, BackendConfig
|
||||||
|
|
||||||
|
@ -115,6 +115,7 @@ class KotoneBotUI:
|
||||||
produce_enabled: bool,
|
produce_enabled: bool,
|
||||||
produce_mode: Literal["regular"],
|
produce_mode: Literal["regular"],
|
||||||
produce_count: int,
|
produce_count: int,
|
||||||
|
produce_idols: List[str],
|
||||||
auto_set_memory: bool,
|
auto_set_memory: bool,
|
||||||
auto_set_support: bool,
|
auto_set_support: bool,
|
||||||
use_pt_boost: bool,
|
use_pt_boost: bool,
|
||||||
|
@ -163,6 +164,7 @@ class KotoneBotUI:
|
||||||
enabled=produce_enabled,
|
enabled=produce_enabled,
|
||||||
mode=produce_mode,
|
mode=produce_mode,
|
||||||
produce_count=produce_count,
|
produce_count=produce_count,
|
||||||
|
idols=[PIdol[idol] for idol in produce_idols],
|
||||||
auto_set_memory=auto_set_memory,
|
auto_set_memory=auto_set_memory,
|
||||||
auto_set_support_card=auto_set_support,
|
auto_set_support_card=auto_set_support,
|
||||||
use_pt_boost=use_pt_boost,
|
use_pt_boost=use_pt_boost,
|
||||||
|
@ -298,7 +300,7 @@ class KotoneBotUI:
|
||||||
)
|
)
|
||||||
return assignment_enabled, mini_live_reassign, mini_live_duration, online_live_reassign, online_live_duration
|
return assignment_enabled, mini_live_reassign, mini_live_duration, online_live_reassign, online_live_duration
|
||||||
|
|
||||||
def _create_produce_settings(self) -> Tuple[gr.Checkbox, gr.Dropdown, gr.Number, gr.Checkbox, gr.Checkbox, gr.Checkbox, gr.Checkbox, gr.Checkbox]:
|
def _create_produce_settings(self) -> Tuple[gr.Checkbox, gr.Dropdown, gr.Number, gr.Dropdown, gr.Checkbox, gr.Checkbox, gr.Checkbox, gr.Checkbox, gr.Checkbox]:
|
||||||
with gr.Column():
|
with gr.Column():
|
||||||
gr.Markdown("### 培育设置")
|
gr.Markdown("### 培育设置")
|
||||||
produce_enabled = gr.Checkbox(
|
produce_enabled = gr.Checkbox(
|
||||||
|
@ -317,6 +319,16 @@ class KotoneBotUI:
|
||||||
label="培育次数",
|
label="培育次数",
|
||||||
interactive=True
|
interactive=True
|
||||||
)
|
)
|
||||||
|
# 添加偶像选择
|
||||||
|
idol_choices = [idol.name for idol in PIdol]
|
||||||
|
selected_idols = [idol.name for idol in self.current_config.options.produce.idols]
|
||||||
|
produce_idols = gr.Dropdown(
|
||||||
|
choices=idol_choices,
|
||||||
|
value=selected_idols,
|
||||||
|
label="选择要培育的偶像",
|
||||||
|
multiselect=True,
|
||||||
|
interactive=True
|
||||||
|
)
|
||||||
auto_set_memory = gr.Checkbox(
|
auto_set_memory = gr.Checkbox(
|
||||||
label="自动编成回忆",
|
label="自动编成回忆",
|
||||||
value=self.current_config.options.produce.auto_set_memory
|
value=self.current_config.options.produce.auto_set_memory
|
||||||
|
@ -343,7 +355,7 @@ class KotoneBotUI:
|
||||||
inputs=[produce_enabled],
|
inputs=[produce_enabled],
|
||||||
outputs=[produce_group]
|
outputs=[produce_group]
|
||||||
)
|
)
|
||||||
return produce_enabled, produce_mode, produce_count, auto_set_memory, auto_set_support, use_pt_boost, use_note_boost, follow_producer
|
return produce_enabled, produce_mode, produce_count, produce_idols, auto_set_memory, auto_set_support, use_pt_boost, use_note_boost, follow_producer
|
||||||
|
|
||||||
def _create_settings_tab(self) -> None:
|
def _create_settings_tab(self) -> None:
|
||||||
with gr.Tab("设置"):
|
with gr.Tab("设置"):
|
||||||
|
|
|
@ -1,24 +1 @@
|
||||||
{
|
{"definitions":{"30a6f399-6999-4f04-bb77-651e0214112f":{"name":"Produce.IconPIdolLevel","displayName":"P偶像卡上的等级图标","type":"template","annotationId":"30a6f399-6999-4f04-bb77-651e0214112f","useHintRect":false},"b71165dd-7285-45a7-bb8c-d4fccee2b0ba":{"name":"Produce.KbIdolOverviewName","displayName":"P偶像总览界面偶像名称","type":"hint-box","annotationId":"b71165dd-7285-45a7-bb8c-d4fccee2b0ba","useHintRect":false}},"annotations":[{"id":"30a6f399-6999-4f04-bb77-651e0214112f","type":"rect","data":{"x1":238,"y1":742,"x2":248,"y2":753}},{"id":"b71165dd-7285-45a7-bb8c-d4fccee2b0ba","type":"rect","data":{"x1":140,"y1":16,"x2":615,"y2":97}}]}
|
||||||
"definitions": {
|
|
||||||
"30a6f399-6999-4f04-bb77-651e0214112f": {
|
|
||||||
"name": "Produce.IconPIdolLevel",
|
|
||||||
"displayName": "P偶像卡上的等级图标",
|
|
||||||
"type": "template",
|
|
||||||
"annotationId": "30a6f399-6999-4f04-bb77-651e0214112f",
|
|
||||||
"useHintRect": false
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"annotations": [
|
|
||||||
{
|
|
||||||
"id": "30a6f399-6999-4f04-bb77-651e0214112f",
|
|
||||||
"type": "rect",
|
|
||||||
"data": {
|
|
||||||
"x1": 238,
|
|
||||||
"y1": 742,
|
|
||||||
"x2": 248,
|
|
||||||
"y2": 753
|
|
||||||
},
|
|
||||||
"_tip": "P偶像卡上的等级图标"
|
|
||||||
}
|
|
||||||
]
|
|
||||||
}
|
|
After Width: | Height: | Size: 110 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 113 KiB |
After Width: | Height: | Size: 111 KiB |
After Width: | Height: | Size: 98 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 113 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 110 KiB |
After Width: | Height: | Size: 93 KiB |
After Width: | Height: | Size: 98 KiB |
After Width: | Height: | Size: 113 KiB |
After Width: | Height: | Size: 124 KiB |
After Width: | Height: | Size: 115 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 122 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 129 KiB |
After Width: | Height: | Size: 114 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 128 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 122 KiB |
After Width: | Height: | Size: 104 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 115 KiB |
After Width: | Height: | Size: 118 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 103 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 111 KiB |
After Width: | Height: | Size: 102 KiB |
After Width: | Height: | Size: 102 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 117 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 99 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 118 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 120 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 99 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 117 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 120 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 118 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 111 KiB |
After Width: | Height: | Size: 113 KiB |
After Width: | Height: | Size: 113 KiB |
After Width: | Height: | Size: 160 KiB |
After Width: | Height: | Size: 122 KiB |
After Width: | Height: | Size: 118 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 103 KiB |
After Width: | Height: | Size: 94 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 126 KiB |
After Width: | Height: | Size: 128 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 212 KiB |
After Width: | Height: | Size: 118 KiB |
After Width: | Height: | Size: 103 KiB |
After Width: | Height: | Size: 212 KiB |