Give the Material pack every icon TeamSpeak's packs have
The rest of default_colored_2014's keys get Material counterparts: talk power, whisper, recording, text formatting, identities, add-ons, permissions and the like. Ping levels are drawn as signal bars, since Material's own tell their levels apart by a hairline, and the default group icons as lettered badges. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -18,6 +18,8 @@ TALKING = "#2E9BF0"
|
||||
MUTED = "#D9443A"
|
||||
AWAY = "#9E8A2E"
|
||||
IDLE = "#888888"
|
||||
YELLOW = "#C9A227"
|
||||
GREEN = "#3A9D4A"
|
||||
UNSUBSCRIBED = 0.5
|
||||
|
||||
# key: (icon, style, colour, opacity); style "o" is Material's outlined variant.
|
||||
@@ -109,14 +111,175 @@ ICONS = {
|
||||
"FILETRANSFER": ("swap_vert",),
|
||||
"UPLOAD": ("upload",),
|
||||
"DOWNLOAD": ("download",),
|
||||
|
||||
# Everything else TeamSpeak's own packs draw, so the pack is as complete as theirs.
|
||||
"CHANNEL_YELLOW": ("chat", "o", YELLOW, UNSUBSCRIBED),
|
||||
"CHANNEL_YELLOW_SUBSCRIBED": ("chat", "o", YELLOW),
|
||||
"CHANNEL_COLLAPSE_ALL": ("unfold_less",),
|
||||
"CHANNEL_COLLAPSE_SUB": ("unfold_less",),
|
||||
"CHANNEL_EXPAND_ALL": ("unfold_more",),
|
||||
"CHANNEL_EXPAND_SUB": ("unfold_more",),
|
||||
"MAKE_CURRENT_CHANNEL_DEFAULT": ("push_pin",),
|
||||
"MODERATED": ("shield", "o"),
|
||||
"SUBSCRIBE_MODE": ("visibility", "o"),
|
||||
"UNSUBSCRIBE_MODE": ("visibility_off", "o"),
|
||||
"CLIENT_SHOW": ("preview",),
|
||||
"CLIENT_HIDE": ("hide_source",),
|
||||
"IS_TALKER": ("record_voice_over", "o"),
|
||||
"TALK_POWER_REQUEST": ("back_hand",),
|
||||
"TALK_POWER_CANCEL_REQUEST": ("do_not_touch",),
|
||||
"TALK_POWER_GRANT": ("record_voice_over", "", GREEN),
|
||||
"TALK_POWER_GRANT_NEXT": ("record_voice_over", "o", GREEN),
|
||||
"TALK_POWER_REVOKE": ("voice_over_off", "", MUTED),
|
||||
"TALK_POWER_REVOKE_ALL_GRANT_NEXT": ("voice_over_off", "o", MUTED),
|
||||
|
||||
"WHISPER": ("hearing",),
|
||||
"ON_WHISPERLIST": ("hearing", "", TALKING),
|
||||
"PLAYER_WHISPER": ("hearing", "", MUTED),
|
||||
"WHISPERHISTORY": ("history",),
|
||||
"WHISPERLISTS": ("list_alt",),
|
||||
"TOGGLE_BLOCK_INCOMING_WHISPERS": ("hearing_disabled",),
|
||||
"TOGGLE_SERVER_QUERY_CLIENTS": ("terminal", "o"),
|
||||
"3D_SOUND": ("surround_sound",),
|
||||
"3D_SOUND_ME": ("person_pin_circle",),
|
||||
"3D_SOUND_OTHER": ("person_pin",),
|
||||
"MUSIC": ("music_note",),
|
||||
"PLAY": ("play_arrow",),
|
||||
"STOP": ("stop",),
|
||||
"RECORDING_START": ("fiber_manual_record", "", MUTED),
|
||||
"RECORDING_STOP": ("stop_circle",),
|
||||
|
||||
"PING_CALCULATING": ("network_check",),
|
||||
"PING_DISCONNECTED": ("wifi_off", "", IDLE),
|
||||
|
||||
"MESSAGES": ("forum",),
|
||||
"MESSAGE_INCOMING": ("call_received",),
|
||||
"MESSAGE_OUTGOING": ("call_made",),
|
||||
"MESSAGE_INFO": ("info", "", TALKING),
|
||||
"OFFLINE_MESSAGES": ("mail", "o"),
|
||||
"NOTIFICATIONS": ("notifications",),
|
||||
"EMOTICON": ("emoji_emotions", "o"),
|
||||
"TEXTFORMAT": ("text_format",),
|
||||
"TEXTFORMAT_BOLD": ("format_bold",),
|
||||
"TEXTFORMAT_ITALIC": ("format_italic",),
|
||||
"TEXTFORMAT_UNDERLINE": ("format_underlined",),
|
||||
"TEXTFORMAT_FOREGROUND": ("format_color_text",),
|
||||
"COPY_URL": ("link",),
|
||||
"URLCATCHER": ("add_link",),
|
||||
"WEBLIST": ("public",),
|
||||
"WARNING_EXTERNAL_LINK": ("open_in_new",),
|
||||
"SERVER_LOG": ("receipt_long",),
|
||||
"COMPLAINT_LIST": ("report", "o"),
|
||||
"SEND_COMPLAINT": ("flag",),
|
||||
"INVITE_BUDDY": ("group_add",),
|
||||
"PHONETICSNICKNAME": ("spellcheck",),
|
||||
"RENAME": ("edit", "o"),
|
||||
|
||||
"CONNECT_NEW_TAB": ("tab",),
|
||||
"DISCONNECT_ALL": ("link_off",),
|
||||
"HOSTER_BUTTON": ("storage",),
|
||||
"VIRTUALSERVER_EDIT": ("settings_applications",),
|
||||
"TEMP_SERVER_PASSWORD": ("password",),
|
||||
"TEMP_SERVER_PASSWORD_ADD": ("enhanced_encryption",),
|
||||
"TOKEN": ("vpn_key",),
|
||||
"TOKEN_USE": ("key",),
|
||||
"SECURITY": ("security",),
|
||||
"PERMISSION_OVERVIEW": ("policy",),
|
||||
"PERMISSIONS_CLIENTS": ("manage_accounts",),
|
||||
"PERMISSIONS_CHANNELS": ("rule",),
|
||||
"PERMISSIONS_CHANNEL_CLIENT": ("switch_account",),
|
||||
|
||||
"IDENTITY_ADD": ("person_add_alt",),
|
||||
"IDENTITY_REMOVE": ("person_remove_alt_1",),
|
||||
"IDENTITY_DEFAULT": ("how_to_reg",),
|
||||
"IDENTITY_IMPORT": ("file_download",),
|
||||
"IDENTITY_EXPORT": ("file_upload",),
|
||||
"DELETE_AVATAR_OTHER": ("no_photography",),
|
||||
"BOOKMARK_ADD_FOLDER": ("create_new_folder", "o"),
|
||||
"BOOKMARK_DUPLICATE": ("bookmarks",),
|
||||
"BOOKMARK_SET_FOR_ALL": ("bookmark_added",),
|
||||
"MYTS_ACCOUNT": ("account_circle",),
|
||||
"MYTS_ACCOUNT_ONLINE": ("cloud_done",),
|
||||
"MYTS_ACCOUNT_OFFLINE": ("cloud_off", "", IDLE),
|
||||
"MYTS_ACCOUNT_ERROR": ("sync_problem", "", MUTED),
|
||||
"SYNC": ("sync",),
|
||||
"SYNC_ENABLE": ("cloud_sync",),
|
||||
"SYNC_DISABLE": ("cloud_off",),
|
||||
"REGISTER": ("app_registration",),
|
||||
|
||||
"ADDON": ("extension",),
|
||||
"ADDON_BROWSER": ("travel_explore",),
|
||||
"ADDON_COLLECTION": ("library_add",),
|
||||
"ADDON_ICONPACK": ("category",),
|
||||
"ADDON_SOUNDPACK": ("library_music",),
|
||||
"ADDON_THEME": ("palette",),
|
||||
"ADDON_TRANSLATION": ("translate",),
|
||||
"PLUGINS": ("electrical_services",),
|
||||
"SOUNDPACK": ("library_music",),
|
||||
"HOTKEYS": ("keyboard",),
|
||||
"GUISETUP": ("tune",),
|
||||
"SWITCH_ADVANCED": ("build",),
|
||||
"SWITCH_STANDARD": ("build", "o"),
|
||||
"CHANGELOG": ("article",),
|
||||
"CHECK_UPDATE": ("update",),
|
||||
"PRESENT": ("redeem",),
|
||||
|
||||
"APPLY": ("check",),
|
||||
"RELOAD": ("replay",),
|
||||
"FIND": ("search",),
|
||||
"SEARCH": ("search",),
|
||||
"SEARCH_CLEAR": ("close",),
|
||||
"SEARCH_HIDE": ("close",),
|
||||
"FILTER_CLEAR": ("filter_alt_off",),
|
||||
"SORT_BY_NAME": ("sort_by_alpha",),
|
||||
"UP": ("arrow_drop_up",),
|
||||
"UP_ARROW": ("arrow_drop_up",),
|
||||
"DOWN": ("arrow_drop_down",),
|
||||
"DOWN_ARROW": ("arrow_drop_down",),
|
||||
"FILE_HOME": ("home",),
|
||||
"SELECTFOLDER": ("folder_open",),
|
||||
"LISTVIEW": ("view_list",),
|
||||
"ICONSVIEW": ("grid_view",),
|
||||
"ICONVIEWER": ("photo_library",),
|
||||
"BROKEN_IMAGE": ("broken_image",),
|
||||
"LOADING_IMAGE": ("hourglass_empty",),
|
||||
}
|
||||
|
||||
# TeamSpeak's default server and channel groups, lettered as its own packs letter them.
|
||||
GROUP_BADGES = {
|
||||
"GROUP_100": ("C", "#D9443A"),
|
||||
"GROUP_200": ("O", "#E0782E"),
|
||||
"GROUP_300": ("S", "#B02E6E"),
|
||||
"GROUP_500": ("Q", "#6E4CB0"),
|
||||
"GROUP_600": ("V", "#2E7DB0"),
|
||||
}
|
||||
|
||||
# Material's own signal icons tell their levels apart by an outline too thin for 16 px.
|
||||
PING_LEVELS = {"PING_1": 1, "PING_2": 2, "PING_3": 3, "PING_4": 4}
|
||||
|
||||
|
||||
def ping_bars(level):
|
||||
bars = "".join(
|
||||
f'<rect x="{3 + i * 5}" y="{17 - i * 4}" width="3.5" height="{4 + i * 4}" rx="1"'
|
||||
+ ("" if i < level else ' fill-opacity="0.3"') + "/>"
|
||||
for i in range(4))
|
||||
return ('<svg fill="currentColor" xmlns="http://www.w3.org/2000/svg" width="24" height="24" '
|
||||
f'viewBox="0 0 24 24">{bars}</svg>')
|
||||
|
||||
|
||||
BADGE = (
|
||||
'<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24">'
|
||||
'<rect x="2" y="2" width="20" height="20" rx="5" fill="{colour}"/>'
|
||||
'<text x="12" y="17.5" text-anchor="middle" font-family="sans-serif" font-weight="bold" '
|
||||
'font-size="15" fill="#FFFFFF">{letter}</text></svg>'
|
||||
)
|
||||
|
||||
INI_HEAD = """\
|
||||
[info]
|
||||
name = Material
|
||||
|
||||
[options]
|
||||
# Complete for what the client draws; the rest stays with the client's own icons.
|
||||
# Covers every icon TeamSpeak's own packs do.
|
||||
FALLBACK=false
|
||||
|
||||
[gfxfiles]
|
||||
@@ -158,6 +321,14 @@ def main():
|
||||
if not path.exists():
|
||||
path.write_text(paint(fetch(icon, style), colour, opacity) + "\n")
|
||||
lines.append(f"{key.ljust(width)} = {name}")
|
||||
for key, level in PING_LEVELS.items():
|
||||
name = f"ping-{level}.svg"
|
||||
(OUT / name).write_text(ping_bars(level) + "\n")
|
||||
lines.append(f"{key.ljust(width)} = {name}")
|
||||
for key, (letter, colour) in GROUP_BADGES.items():
|
||||
name = f"group-{letter.lower()}.svg"
|
||||
(OUT / name).write_text(BADGE.format(letter=letter, colour=colour) + "\n")
|
||||
lines.append(f"{key.ljust(width)} = {name}")
|
||||
(OUT / "settings.ini").write_text(INI_HEAD + "\n".join(lines) + "\n")
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user