bauiv1lib.store.item
UI functionality related to UI items.
1# Released under the MIT License. See LICENSE for details. 2# 3"""UI functionality related to UI items.""" 4from __future__ import annotations 5 6from typing import TYPE_CHECKING 7 8import bascenev1 as bs 9import bauiv1 as bui 10 11if TYPE_CHECKING: 12 from typing import Any 13 14 15def instantiate_store_item_display( 16 item_name: str, 17 item: dict[str, Any], 18 parent_widget: bui.Widget, 19 b_pos: tuple[float, float], 20 b_width: float, 21 b_height: float, 22 *, 23 boffs_h: float = 0.0, 24 boffs_h2: float = 0.0, 25 boffs_v2: float = 0, 26 delay: float = 0.0, 27 button: bool = True, 28) -> None: 29 """(internal)""" 30 # pylint: disable=too-many-positional-arguments 31 # pylint: disable=too-many-statements 32 # pylint: disable=too-many-branches 33 # pylint: disable=too-many-locals 34 assert bui.app.classic is not None 35 store = bui.app.classic.store 36 37 plus = bui.app.plus 38 assert plus is not None 39 40 del boffs_h # unused arg 41 del boffs_h2 # unused arg 42 del boffs_v2 # unused arg 43 item_info = store.get_store_item(item_name) 44 title_v = 0.24 45 price_v = 0.145 46 base_text_scale = 1.0 47 48 item['name'] = title = store.get_store_item_name_translated(item_name) 49 50 btn: bui.Widget | None 51 52 # Hack; showbuffer stuff isn't working well when we're showing merch. 53 showbuffer = 10 if item_name in {'merch', 'pro', 'pro_sale'} else 76.0 54 55 if button: 56 item['button'] = btn = bui.buttonwidget( 57 parent=parent_widget, 58 position=b_pos, 59 transition_delay=delay, 60 show_buffer_top=showbuffer, 61 enable_sound=False, 62 button_type='square', 63 size=(b_width, b_height), 64 autoselect=True, 65 label='', 66 ) 67 bui.widget(edit=btn, show_buffer_bottom=showbuffer) 68 else: 69 btn = None 70 71 b_offs_x = -0.015 * b_width 72 check_pos = 0.76 73 74 icon_tex = None 75 tint_tex = None 76 tint_color = None 77 tint2_color = None 78 tex_name: str | None = None 79 desc: bui.Lstr | None = None 80 modes: bui.Lstr | None = None 81 82 if item_name.startswith('characters.'): 83 assert bui.app.classic is not None 84 character = bui.app.classic.spaz_appearances[item_info['character']] 85 tint_color = ( 86 item_info['color'] 87 if 'color' in item_info 88 else ( 89 character.default_color 90 if character.default_color is not None 91 else (1, 1, 1) 92 ) 93 ) 94 tint2_color = ( 95 item_info['highlight'] 96 if 'highlight' in item_info 97 else ( 98 character.default_highlight 99 if character.default_highlight is not None 100 else (1, 1, 1) 101 ) 102 ) 103 icon_tex = character.icon_texture 104 tint_tex = character.icon_mask_texture 105 title_v = 0.255 106 price_v = 0.145 107 elif item_name == 'merch': 108 base_text_scale = 0.6 109 title_v = 0.85 110 price_v = 0.15 111 elif item_name in ['upgrades.pro', 'pro']: 112 base_text_scale = 0.6 113 title_v = 0.85 114 price_v = 0.15 115 elif item_name.startswith('maps.'): 116 map_type = item_info['map_type'] 117 tex_name = map_type.get_preview_texture_name() 118 title_v = 0.312 119 price_v = 0.17 120 121 elif item_name.startswith('games.'): 122 gametype = item_info['gametype'] 123 modes_l = [] 124 if gametype.supports_session_type(bs.CoopSession): 125 modes_l.append(bui.Lstr(resource='playModes.coopText')) 126 if gametype.supports_session_type(bs.DualTeamSession): 127 modes_l.append(bui.Lstr(resource='playModes.teamsText')) 128 if gametype.supports_session_type(bs.FreeForAllSession): 129 modes_l.append(bui.Lstr(resource='playModes.freeForAllText')) 130 131 if len(modes_l) == 3: 132 modes = bui.Lstr( 133 value='${A}, ${B}, ${C}', 134 subs=[ 135 ('${A}', modes_l[0]), 136 ('${B}', modes_l[1]), 137 ('${C}', modes_l[2]), 138 ], 139 ) 140 elif len(modes_l) == 2: 141 modes = bui.Lstr( 142 value='${A}, ${B}', 143 subs=[('${A}', modes_l[0]), ('${B}', modes_l[1])], 144 ) 145 elif len(modes_l) == 1: 146 modes = modes_l[0] 147 else: 148 raise RuntimeError() 149 desc = gametype.get_description_display_string(bs.CoopSession) 150 tex_name = item_info['previewTex'] 151 base_text_scale = 0.8 152 title_v = 0.48 153 price_v = 0.17 154 elif item_name == 'upgrades.infinite_runaround': 155 base_text_scale = 0.8 156 desc = bui.Lstr( 157 translate=( 158 'gameDescriptions', 159 'Prevent enemies from reaching the exit.', 160 ) 161 ) 162 modes = bui.Lstr(resource='playModes.coopText') 163 tex_name = 'towerDPreview' 164 title_v = 0.48 165 price_v = 0.17 166 elif item_name == 'upgrades.infinite_onslaught': 167 base_text_scale = 0.8 168 desc = bui.Lstr( 169 translate=( 170 'gameDescriptions', 171 'Defeat all enemies.', 172 ) 173 ) 174 modes = bui.Lstr(resource='playModes.coopText') 175 tex_name = 'doomShroomPreview' 176 title_v = 0.48 177 price_v = 0.17 178 179 elif item_name.startswith('icons.'): 180 base_text_scale = 1.5 181 price_v = 0.2 182 check_pos = 0.6 183 184 if item_name.startswith('characters.'): 185 frame_size = b_width * 0.7 186 im_dim = frame_size * (100.0 / 113.0) 187 im_pos = ( 188 b_pos[0] + b_width * 0.5 - im_dim * 0.5 + b_offs_x, 189 b_pos[1] + b_height * 0.57 - im_dim * 0.5, 190 ) 191 mask_texture = bui.gettexture('characterIconMask') 192 assert icon_tex is not None 193 assert tint_tex is not None 194 bui.imagewidget( 195 parent=parent_widget, 196 position=im_pos, 197 size=(im_dim, im_dim), 198 color=(1, 1, 1), 199 transition_delay=delay, 200 mask_texture=mask_texture, 201 draw_controller=btn, 202 texture=bui.gettexture(icon_tex), 203 tint_texture=bui.gettexture(tint_tex), 204 tint_color=tint_color, 205 tint2_color=tint2_color, 206 ) 207 208 if item_name == 'merch': 209 frame_size = b_width * 0.65 210 im_dim = frame_size * (100.0 / 113.0) 211 im_pos = ( 212 b_pos[0] + b_width * 0.5 - im_dim * 0.5 + b_offs_x, 213 b_pos[1] + b_height * 0.47 - im_dim * 0.5, 214 ) 215 bui.imagewidget( 216 parent=parent_widget, 217 position=im_pos, 218 size=(im_dim, im_dim), 219 transition_delay=delay, 220 draw_controller=btn, 221 opacity=1.0, 222 texture=bui.gettexture('merch'), 223 ) 224 225 if item_name in ['pro', 'upgrades.pro']: 226 frame_size = b_width * 0.5 227 im_dim = frame_size * (100.0 / 113.0) 228 im_pos = ( 229 b_pos[0] + b_width * 0.5 - im_dim * 0.5 + b_offs_x, 230 b_pos[1] + b_height * 0.5 - im_dim * 0.5, 231 ) 232 bui.imagewidget( 233 parent=parent_widget, 234 position=im_pos, 235 size=(im_dim, im_dim), 236 transition_delay=delay, 237 draw_controller=btn, 238 color=(0.3, 0.0, 0.3), 239 opacity=0.3, 240 texture=bui.gettexture('logo'), 241 ) 242 txt = bui.Lstr(resource='store.bombSquadProNewDescriptionText') 243 244 item['descriptionText'] = bui.textwidget( 245 parent=parent_widget, 246 text=txt, 247 position=(b_pos[0] + b_width * 0.5, b_pos[1] + b_height * 0.69), 248 transition_delay=delay, 249 scale=b_width * (1.0 / 230.0) * base_text_scale * 0.75, 250 maxwidth=b_width * 0.75, 251 max_height=b_height * 0.2, 252 size=(0, 0), 253 h_align='center', 254 v_align='center', 255 draw_controller=btn, 256 color=(0.3, 1, 0.3), 257 ) 258 259 extra_backings = item['extra_backings'] = [] 260 extra_images = item['extra_images'] = [] 261 extra_texts = item['extra_texts'] = [] 262 extra_texts_2 = item['extra_texts_2'] = [] 263 264 backing_color = (0.5, 0.8, 0.3) if button else (0.6, 0.5, 0.65) 265 b_square_texture = bui.gettexture('buttonSquare') 266 char_mask_texture = bui.gettexture('characterIconMask') 267 268 pos = (0.17, 0.43) 269 tile_size = (b_width * 0.16 * 1.2, b_width * 0.2 * 1.2) 270 tile_pos = (b_pos[0] + b_width * pos[0], b_pos[1] + b_height * pos[1]) 271 extra_backings.append( 272 bui.imagewidget( 273 parent=parent_widget, 274 position=( 275 tile_pos[0] - tile_size[0] * 0.5, 276 tile_pos[1] - tile_size[1] * 0.5, 277 ), 278 size=tile_size, 279 transition_delay=delay, 280 draw_controller=btn, 281 color=backing_color, 282 texture=b_square_texture, 283 ) 284 ) 285 im_size = tile_size[0] * 0.8 286 extra_images.append( 287 bui.imagewidget( 288 parent=parent_widget, 289 position=( 290 tile_pos[0] - im_size * 0.5, 291 tile_pos[1] - im_size * 0.4, 292 ), 293 size=(im_size, im_size), 294 transition_delay=delay, 295 draw_controller=btn, 296 color=(1, 1, 1), 297 texture=bui.gettexture('ticketsMore'), 298 ) 299 ) 300 bonus_tickets = str( 301 plus.get_v1_account_misc_read_val('proBonusTickets', 100) 302 ) 303 extra_texts.append( 304 bui.textwidget( 305 parent=parent_widget, 306 draw_controller=btn, 307 position=( 308 tile_pos[0] - tile_size[0] * 0.03, 309 tile_pos[1] - tile_size[1] * 0.25, 310 ), 311 size=(0, 0), 312 color=(0.6, 1, 0.6), 313 transition_delay=delay, 314 h_align='center', 315 v_align='center', 316 maxwidth=tile_size[0] * 0.7, 317 scale=0.55, 318 text=bui.Lstr( 319 resource='getTicketsWindow.ticketsText', 320 subs=[('${COUNT}', bonus_tickets)], 321 ), 322 flatness=1.0, 323 shadow=0.0, 324 ) 325 ) 326 327 for charname, pos in [ 328 ('Kronk', (0.32, 0.45)), 329 ('Zoe', (0.425, 0.4)), 330 ('Jack Morgan', (0.555, 0.45)), 331 ('Mel', (0.645, 0.4)), 332 ]: 333 tile_size = (b_width * 0.16 * 0.9, b_width * 0.2 * 0.9) 334 tile_pos = ( 335 b_pos[0] + b_width * pos[0], 336 b_pos[1] + b_height * pos[1], 337 ) 338 assert bui.app.classic is not None 339 character = bui.app.classic.spaz_appearances[charname] 340 extra_backings.append( 341 bui.imagewidget( 342 parent=parent_widget, 343 position=( 344 tile_pos[0] - tile_size[0] * 0.5, 345 tile_pos[1] - tile_size[1] * 0.5, 346 ), 347 size=tile_size, 348 transition_delay=delay, 349 draw_controller=btn, 350 color=backing_color, 351 texture=b_square_texture, 352 ) 353 ) 354 im_size = tile_size[0] * 0.7 355 extra_images.append( 356 bui.imagewidget( 357 parent=parent_widget, 358 position=( 359 tile_pos[0] - im_size * 0.53, 360 tile_pos[1] - im_size * 0.35, 361 ), 362 size=(im_size, im_size), 363 transition_delay=delay, 364 draw_controller=btn, 365 color=(1, 1, 1), 366 texture=bui.gettexture(character.icon_texture), 367 tint_texture=bui.gettexture(character.icon_mask_texture), 368 tint_color=character.default_color, 369 tint2_color=character.default_highlight, 370 mask_texture=char_mask_texture, 371 ) 372 ) 373 extra_texts.append( 374 bui.textwidget( 375 parent=parent_widget, 376 draw_controller=btn, 377 position=( 378 tile_pos[0] - im_size * 0.03, 379 tile_pos[1] - im_size * 0.51, 380 ), 381 size=(0, 0), 382 color=(0.6, 1, 0.6), 383 transition_delay=delay, 384 h_align='center', 385 v_align='center', 386 maxwidth=tile_size[0] * 0.7, 387 scale=0.55, 388 text=bui.Lstr(translate=('characterNames', charname)), 389 flatness=1.0, 390 shadow=0.0, 391 ) 392 ) 393 394 # If we have a 'total-worth' item-id for this id, show that price so 395 # the user knows how much this is worth. 396 total_worth_item = plus.get_v1_account_misc_read_val('twrths', {}).get( 397 item_name 398 ) 399 total_worth_price: str | None 400 if total_worth_item is not None: 401 price = plus.get_price(total_worth_item) 402 total_worth_price = ( 403 store.get_clean_price(price) if price is not None else '??' 404 ) 405 else: 406 total_worth_price = None 407 408 if total_worth_price is not None: 409 total_worth_text = bui.Lstr( 410 resource='store.totalWorthText', 411 subs=[('${TOTAL_WORTH}', total_worth_price)], 412 ) 413 extra_texts_2.append( 414 bui.textwidget( 415 parent=parent_widget, 416 text=total_worth_text, 417 position=( 418 b_pos[0] + b_width * 0.5 + b_offs_x, 419 b_pos[1] + b_height * 0.25, 420 ), 421 transition_delay=delay, 422 scale=b_width * (1.0 / 230.0) * base_text_scale * 0.45, 423 maxwidth=b_width * 0.5, 424 size=(0, 0), 425 h_align='center', 426 v_align='center', 427 shadow=1.0, 428 flatness=1.0, 429 draw_controller=btn, 430 color=(0.3, 1, 1), 431 ) 432 ) 433 434 mesh_opaque = bui.getmesh('level_select_button_opaque') 435 mesh_transparent = bui.getmesh('level_select_button_transparent') 436 mask_tex = bui.gettexture('mapPreviewMask') 437 for levelname, preview_tex_name, pos in [ 438 ('Infinite Onslaught', 'doomShroomPreview', (0.80, 0.48)), 439 ('Infinite Runaround', 'towerDPreview', (0.80, 0.32)), 440 ]: 441 tile_size = (b_width * 0.2, b_width * 0.13) 442 tile_pos = ( 443 b_pos[0] + b_width * pos[0], 444 b_pos[1] + b_height * pos[1], 445 ) 446 im_size = tile_size[0] * 0.8 447 extra_backings.append( 448 bui.imagewidget( 449 parent=parent_widget, 450 position=( 451 tile_pos[0] - tile_size[0] * 0.5, 452 tile_pos[1] - tile_size[1] * 0.5, 453 ), 454 size=tile_size, 455 transition_delay=delay, 456 draw_controller=btn, 457 color=backing_color, 458 texture=b_square_texture, 459 ) 460 ) 461 462 # Hack - gotta draw two transparent versions to avoid z issues. 463 for mod in mesh_opaque, mesh_transparent: 464 extra_images.append( 465 bui.imagewidget( 466 parent=parent_widget, 467 position=( 468 tile_pos[0] - im_size * 0.52, 469 tile_pos[1] - im_size * 0.2, 470 ), 471 size=(im_size, im_size * 0.5), 472 transition_delay=delay, 473 mesh_transparent=mod, 474 mask_texture=mask_tex, 475 draw_controller=btn, 476 texture=bui.gettexture(preview_tex_name), 477 ) 478 ) 479 480 extra_texts.append( 481 bui.textwidget( 482 parent=parent_widget, 483 draw_controller=btn, 484 position=( 485 tile_pos[0] - im_size * 0.03, 486 tile_pos[1] - im_size * 0.2, 487 ), 488 size=(0, 0), 489 color=(0.6, 1, 0.6), 490 transition_delay=delay, 491 h_align='center', 492 v_align='center', 493 maxwidth=tile_size[0] * 0.7, 494 scale=0.55, 495 text=bui.Lstr(translate=('coopLevelNames', levelname)), 496 flatness=1.0, 497 shadow=0.0, 498 ) 499 ) 500 501 if item_name.startswith('icons.'): 502 item['icon_text'] = bui.textwidget( 503 parent=parent_widget, 504 text=item_info['icon'], 505 position=(b_pos[0] + b_width * 0.5, b_pos[1] + b_height * 0.5), 506 transition_delay=delay, 507 scale=b_width * (1.0 / 230.0) * base_text_scale * 2.0, 508 maxwidth=b_width * 0.9, 509 max_height=b_height * 0.9, 510 size=(0, 0), 511 h_align='center', 512 v_align='center', 513 draw_controller=btn, 514 ) 515 516 if item_name.startswith('maps.'): 517 frame_size = b_width * 0.9 518 im_dim = frame_size * (100.0 / 113.0) 519 im_pos = ( 520 b_pos[0] + b_width * 0.5 - im_dim * 0.5 + b_offs_x, 521 b_pos[1] + b_height * 0.62 - im_dim * 0.25, 522 ) 523 mesh_opaque = bui.getmesh('level_select_button_opaque') 524 mesh_transparent = bui.getmesh('level_select_button_transparent') 525 mask_tex = bui.gettexture('mapPreviewMask') 526 assert tex_name is not None 527 bui.imagewidget( 528 parent=parent_widget, 529 position=im_pos, 530 size=(im_dim, im_dim * 0.5), 531 transition_delay=delay, 532 mesh_opaque=mesh_opaque, 533 mesh_transparent=mesh_transparent, 534 mask_texture=mask_tex, 535 draw_controller=btn, 536 texture=bui.gettexture(tex_name), 537 ) 538 539 if item_name.startswith('games.') or item_name in ( 540 'upgrades.infinite_runaround', 541 'upgrades.infinite_onslaught', 542 ): 543 frame_size = b_width * 0.8 544 im_dim = frame_size * (100.0 / 113.0) 545 im_pos = ( 546 b_pos[0] + b_width * 0.5 - im_dim * 0.5 + b_offs_x, 547 b_pos[1] + b_height * 0.72 - im_dim * 0.25, 548 ) 549 mesh_opaque = bui.getmesh('level_select_button_opaque') 550 mesh_transparent = bui.getmesh('level_select_button_transparent') 551 mask_tex = bui.gettexture('mapPreviewMask') 552 assert tex_name is not None 553 bui.imagewidget( 554 parent=parent_widget, 555 position=im_pos, 556 size=(im_dim, im_dim * 0.5), 557 transition_delay=delay, 558 mesh_opaque=mesh_opaque, 559 mesh_transparent=mesh_transparent, 560 mask_texture=mask_tex, 561 draw_controller=btn, 562 texture=bui.gettexture(tex_name), 563 ) 564 item['descriptionText'] = bui.textwidget( 565 parent=parent_widget, 566 text=desc, 567 position=(b_pos[0] + b_width * 0.5, b_pos[1] + b_height * 0.36), 568 transition_delay=delay, 569 scale=b_width * (1.0 / 230.0) * base_text_scale * 0.78, 570 maxwidth=b_width * 0.8, 571 max_height=b_height * 0.14, 572 size=(0, 0), 573 h_align='center', 574 v_align='center', 575 draw_controller=btn, 576 flatness=1.0, 577 shadow=0.0, 578 color=(0.6, 1, 0.6), 579 ) 580 item['gameModesText'] = bui.textwidget( 581 parent=parent_widget, 582 text=modes, 583 position=(b_pos[0] + b_width * 0.5, b_pos[1] + b_height * 0.26), 584 transition_delay=delay, 585 scale=b_width * (1.0 / 230.0) * base_text_scale * 0.65, 586 maxwidth=b_width * 0.8, 587 size=(0, 0), 588 h_align='center', 589 v_align='center', 590 draw_controller=btn, 591 shadow=0, 592 flatness=1.0, 593 color=(0.6, 0.8, 0.6), 594 ) 595 596 if not item_name.startswith('icons.'): 597 item['title_text'] = bui.textwidget( 598 parent=parent_widget, 599 text=title, 600 position=( 601 b_pos[0] + b_width * 0.5 + b_offs_x, 602 b_pos[1] + b_height * title_v, 603 ), 604 transition_delay=delay, 605 scale=b_width * (1.0 / 230.0) * base_text_scale, 606 maxwidth=b_width * 0.8, 607 size=(0, 0), 608 h_align='center', 609 v_align='center', 610 draw_controller=btn, 611 color=(0.7, 0.9, 0.7, 1.0), 612 ) 613 614 item['purchase_check'] = bui.imagewidget( 615 parent=parent_widget, 616 position=(b_pos[0] + b_width * check_pos, b_pos[1] + b_height * 0.05), 617 transition_delay=delay, 618 mesh_transparent=bui.getmesh('checkTransparent'), 619 opacity=0.0, 620 size=(60, 60), 621 color=(0.6, 0.5, 0.8), 622 draw_controller=btn, 623 texture=bui.gettexture('uiAtlas'), 624 ) 625 item['price_widget'] = bui.textwidget( 626 parent=parent_widget, 627 text='', 628 position=( 629 b_pos[0] + b_width * 0.5 + b_offs_x, 630 b_pos[1] + b_height * price_v, 631 ), 632 transition_delay=delay, 633 scale=b_width * (1.0 / 300.0) * base_text_scale, 634 maxwidth=b_width * 0.9, 635 size=(0, 0), 636 h_align='center', 637 v_align='center', 638 draw_controller=btn, 639 color=(0.2, 1, 0.2, 1.0), 640 ) 641 item['price_widget_left'] = bui.textwidget( 642 parent=parent_widget, 643 text='', 644 position=( 645 b_pos[0] + b_width * 0.33 + b_offs_x, 646 b_pos[1] + b_height * price_v, 647 ), 648 transition_delay=delay, 649 scale=b_width * (1.0 / 300.0) * base_text_scale, 650 maxwidth=b_width * 0.3, 651 size=(0, 0), 652 h_align='center', 653 v_align='center', 654 draw_controller=btn, 655 color=(0.2, 1, 0.2, 0.5), 656 ) 657 item['price_widget_right'] = bui.textwidget( 658 parent=parent_widget, 659 text='', 660 position=( 661 b_pos[0] + b_width * 0.66 + b_offs_x, 662 b_pos[1] + b_height * price_v, 663 ), 664 transition_delay=delay, 665 scale=1.1 * b_width * (1.0 / 300.0) * base_text_scale, 666 maxwidth=b_width * 0.3, 667 size=(0, 0), 668 h_align='center', 669 v_align='center', 670 draw_controller=btn, 671 color=(0.2, 1, 0.2, 1.0), 672 ) 673 item['price_slash_widget'] = bui.imagewidget( 674 parent=parent_widget, 675 position=( 676 b_pos[0] + b_width * 0.33 + b_offs_x - 36, 677 b_pos[1] + b_height * price_v - 35, 678 ), 679 transition_delay=delay, 680 texture=bui.gettexture('slash'), 681 opacity=0.0, 682 size=(70, 70), 683 draw_controller=btn, 684 color=(1, 0, 0), 685 ) 686 badge_rad = 44 687 badge_center = ( 688 b_pos[0] + b_width * 0.1 + b_offs_x, 689 b_pos[1] + b_height * 0.87, 690 ) 691 item['sale_bg_widget'] = bui.imagewidget( 692 parent=parent_widget, 693 position=(badge_center[0] - badge_rad, badge_center[1] - badge_rad), 694 opacity=0.0, 695 transition_delay=delay, 696 texture=bui.gettexture('circleZigZag'), 697 draw_controller=btn, 698 size=(badge_rad * 2, badge_rad * 2), 699 color=(0.5, 0, 1), 700 ) 701 item['sale_title_widget'] = bui.textwidget( 702 parent=parent_widget, 703 position=(badge_center[0], badge_center[1] + 12), 704 transition_delay=delay, 705 scale=1.0, 706 maxwidth=badge_rad * 1.6, 707 size=(0, 0), 708 h_align='center', 709 v_align='center', 710 draw_controller=btn, 711 shadow=0.0, 712 flatness=1.0, 713 color=(0, 1, 0), 714 ) 715 item['sale_time_widget'] = bui.textwidget( 716 parent=parent_widget, 717 position=(badge_center[0], badge_center[1] - 12), 718 transition_delay=delay, 719 scale=0.7, 720 maxwidth=badge_rad * 1.6, 721 size=(0, 0), 722 h_align='center', 723 v_align='center', 724 draw_controller=btn, 725 shadow=0.0, 726 flatness=1.0, 727 color=(0.0, 1, 0.0, 1), 728 )