isaachwf commited on
Commit
d1e54f6
·
1 Parent(s): 8509a7d

feat: improve custom coordinate text layout (two-line title/subtitle)

Browse files
Files changed (3) hide show
  1. app.py +49 -14
  2. cities_data.py +9 -3
  3. create_map_poster.py +36 -29
app.py CHANGED
@@ -376,7 +376,7 @@ def update_cities(country, province, lang="en"):
376
 
377
  def update_districts(country, province, city, lang="en"):
378
  """Update district dropdown based on city selection."""
379
- if country != "中国":
380
  return gr.update(choices=[], value=None, visible=False)
381
 
382
  lang_code = "en" if lang == "English" else "cn"
@@ -411,6 +411,20 @@ def create_interface():
411
  else []
412
  )
413
  default_city_key = default_cities[0][1] if default_cities else None
 
 
 
 
 
 
 
 
 
 
 
 
 
 
414
  default_theme = theme_choices[0][1] if theme_choices else "feature_based"
415
  default_theme = theme_choices[0][1] if theme_choices else "feature_based"
416
 
@@ -504,16 +518,11 @@ def create_interface():
504
  )
505
 
506
  district_dropdown = gr.Dropdown(
507
- choices=get_districts(
508
- default_country_key,
509
- default_province_key,
510
- default_city_key,
511
- default_lang_code,
512
- ),
513
- value=default_city_key,
514
  label="选择区县",
515
  interactive=True,
516
- visible=(default_country_key == "中国"),
517
  )
518
 
519
  with gr.Group(visible=False) as custom_coords_group:
@@ -528,11 +537,11 @@ def create_interface():
528
  label="经度 (Longitude)", value=None, precision=6
529
  )
530
  custom_city_name = gr.Textbox(
531
- label="显示城市名 (City Name)", placeholder="如: Shanghai"
532
  )
533
  custom_country_name = gr.Textbox(
534
- label="显示国家名 (Country Name)",
535
- placeholder="如: China",
536
  value="",
537
  )
538
 
@@ -629,6 +638,7 @@ def create_interface():
629
  current_country,
630
  current_province,
631
  current_city,
 
632
  current_theme,
633
  current_layers,
634
  ):
@@ -649,6 +659,14 @@ def create_interface():
649
  if current_city
650
  else []
651
  )
 
 
 
 
 
 
 
 
652
 
653
  # Themes
654
  new_theme_choices = get_theme_choices(lang_code)
@@ -691,8 +709,8 @@ def create_interface():
691
  ),
692
  gr.update(
693
  choices=new_districts,
694
- value=current_city if current_city else None,
695
- visible=(current_country == "中国"),
696
  label="Select District" if lang == "English" else "选择区县",
697
  ),
698
  gr.update(
@@ -729,12 +747,26 @@ def create_interface():
729
  if lang == "English"
730
  else "勾选后保留海报边缘背景",
731
  ),
 
 
 
 
 
 
732
  gr.update(
733
  value="🚀 Generate Poster" if lang == "English" else "🚀 生成海报"
734
  ),
735
  gr.update(
736
  label="📥 Download Poster" if lang == "English" else "📥 下载海报"
737
  ),
 
 
 
 
 
 
 
 
738
  )
739
 
740
  lang_radio.change(
@@ -744,6 +776,7 @@ def create_interface():
744
  country_dropdown,
745
  province_dropdown,
746
  city_dropdown,
 
747
  theme_dropdown,
748
  layers_checkbox,
749
  ],
@@ -763,6 +796,8 @@ def create_interface():
763
  show_text_checkbox,
764
  generate_btn,
765
  download_btn,
 
 
766
  ],
767
  )
768
 
 
376
 
377
  def update_districts(country, province, city, lang="en"):
378
  """Update district dropdown based on city selection."""
379
+ if country != "中国" or not city or city.endswith("_WHOLE"):
380
  return gr.update(choices=[], value=None, visible=False)
381
 
382
  lang_code = "en" if lang == "English" else "cn"
 
411
  else []
412
  )
413
  default_city_key = default_cities[0][1] if default_cities else None
414
+
415
+ # Handle district initialization carefully to avoid "Value not in choices" error
416
+ default_districts = (
417
+ get_districts(
418
+ default_country_key,
419
+ default_province_key,
420
+ default_city_key,
421
+ default_lang_code,
422
+ )
423
+ if default_city_key
424
+ else []
425
+ )
426
+ default_district_key = default_districts[0][1] if default_districts else None
427
+
428
  default_theme = theme_choices[0][1] if theme_choices else "feature_based"
429
  default_theme = theme_choices[0][1] if theme_choices else "feature_based"
430
 
 
518
  )
519
 
520
  district_dropdown = gr.Dropdown(
521
+ choices=default_districts,
522
+ value=default_district_key,
 
 
 
 
 
523
  label="选择区县",
524
  interactive=True,
525
+ visible=(default_country_key == "中国" and default_district_key is not None),
526
  )
527
 
528
  with gr.Group(visible=False) as custom_coords_group:
 
537
  label="经度 (Longitude)", value=None, precision=6
538
  )
539
  custom_city_name = gr.Textbox(
540
+ label="主标题 (Main Title)", placeholder="如: Shanghai 或 '我们的家'"
541
  )
542
  custom_country_name = gr.Textbox(
543
+ label="副标题 (Subtitle)",
544
+ placeholder="如: China 或 '2024.10.20'",
545
  value="",
546
  )
547
 
 
638
  current_country,
639
  current_province,
640
  current_city,
641
+ current_district,
642
  current_theme,
643
  current_layers,
644
  ):
 
659
  if current_city
660
  else []
661
  )
662
+
663
+ # Ensure district value is valid for new choices
664
+ valid_district = None
665
+ if new_districts:
666
+ if any(v == current_district for d, v in new_districts):
667
+ valid_district = current_district
668
+ else:
669
+ valid_district = new_districts[0][1]
670
 
671
  # Themes
672
  new_theme_choices = get_theme_choices(lang_code)
 
709
  ),
710
  gr.update(
711
  choices=new_districts,
712
+ value=valid_district,
713
+ visible=(current_country == "中国" and valid_district is not None),
714
  label="Select District" if lang == "English" else "选择区县",
715
  ),
716
  gr.update(
 
747
  if lang == "English"
748
  else "勾选后保留海报边缘背景",
749
  ),
750
+ gr.update(
751
+ label="Show Text" if lang == "English" else "显示文字",
752
+ info="Show city name and coordinates on poster"
753
+ if lang == "English"
754
+ else "在海报上显示城市名和经纬度",
755
+ ),
756
  gr.update(
757
  value="🚀 Generate Poster" if lang == "English" else "🚀 生成海报"
758
  ),
759
  gr.update(
760
  label="📥 Download Poster" if lang == "English" else "📥 下载海报"
761
  ),
762
+ gr.update(
763
+ label="Main Title" if lang == "English" else "主标题 (Main Title)",
764
+ placeholder="e.g. Shanghai or 'Our Home'" if lang == "English" else "如: Shanghai 或 '我们的家'"
765
+ ),
766
+ gr.update(
767
+ label="Subtitle" if lang == "English" else "副标题 (Subtitle)",
768
+ placeholder="e.g. China or '2024.10.20'" if lang == "English" else "如: China 或 '2024.10.20'"
769
+ )
770
  )
771
 
772
  lang_radio.change(
 
776
  country_dropdown,
777
  province_dropdown,
778
  city_dropdown,
779
+ district_dropdown,
780
  theme_dropdown,
781
  layers_checkbox,
782
  ],
 
796
  show_text_checkbox,
797
  generate_btn,
798
  download_btn,
799
+ custom_city_name,
800
+ custom_country_name,
801
  ],
802
  )
803
 
cities_data.py CHANGED
@@ -1044,19 +1044,25 @@ def get_manual_coordinates(name, parent_adcode=None):
1044
 
1045
  def get_china_adcode(name, parent_adcode=None):
1046
  """Search for adcode by name in local China data."""
 
 
 
 
 
 
1047
  info = _load_china_info()
1048
  if not parent_adcode:
1049
  # Check provinces
1050
  china_entry = info.get("100000")
1051
  if china_entry:
1052
  for p in china_entry.get("children", []):
1053
- if p["name"] == name or p["name"].rstrip("省").rstrip("市") == name:
1054
  return p["adcode"]
1055
  else:
1056
  parent_entry = info.get(str(parent_adcode))
1057
  if parent_entry:
1058
  for child in parent_entry.get("children", []):
1059
- if child["name"] == name:
1060
  return child["adcode"]
1061
  return None
1062
 
@@ -1209,7 +1215,7 @@ def get_cities(country_name, province_name, lang="en"):
1209
  def get_districts(country_name, province_name, city_name, lang="en"):
1210
  """Return list of (Display, Key) tuples for districts."""
1211
  country_key = get_country_key(country_name)
1212
- if country_key != "中国":
1213
  return []
1214
 
1215
  p_adcode = get_china_adcode(province_name)
 
1044
 
1045
  def get_china_adcode(name, parent_adcode=None):
1046
  """Search for adcode by name in local China data."""
1047
+ if not name:
1048
+ return None
1049
+
1050
+ # Strip convention-based suffixes
1051
+ search_name = name.replace("_WHOLE", "")
1052
+
1053
  info = _load_china_info()
1054
  if not parent_adcode:
1055
  # Check provinces
1056
  china_entry = info.get("100000")
1057
  if china_entry:
1058
  for p in china_entry.get("children", []):
1059
+ if p["name"] == search_name or p["name"].rstrip("省").rstrip("市") == search_name:
1060
  return p["adcode"]
1061
  else:
1062
  parent_entry = info.get(str(parent_adcode))
1063
  if parent_entry:
1064
  for child in parent_entry.get("children", []):
1065
+ if child["name"] == search_name:
1066
  return child["adcode"]
1067
  return None
1068
 
 
1215
  def get_districts(country_name, province_name, city_name, lang="en"):
1216
  """Return list of (Display, Key) tuples for districts."""
1217
  country_key = get_country_key(country_name)
1218
+ if country_key != "中国" or not city_name or city_name.endswith("_WHOLE"):
1219
  return []
1220
 
1221
  p_adcode = get_china_adcode(province_name)
create_map_poster.py CHANGED
@@ -552,28 +552,44 @@ def create_poster(
552
 
553
  # --- BOTTOM TEXT ---
554
  if show_text:
555
- ax.text(
556
- 0.5,
557
- 0.14,
558
- display_city,
559
- transform=ax.transAxes,
560
- color=THEME["text"],
561
- ha="center",
562
- fontproperties=font_main,
563
- zorder=11,
564
- )
 
 
565
 
566
- ax.text(
567
- 0.5,
568
- 0.10,
569
- display_country,
570
- transform=ax.transAxes,
571
- color=THEME["text"],
572
- ha="center",
573
- fontproperties=font_sub,
574
- zorder=11,
575
- )
 
 
 
 
 
 
 
 
 
 
 
 
 
576
 
 
577
  lat, lon = point
578
  coords_text = (
579
  f"{lat:.4f}° N / {lon:.4f}° E"
@@ -595,15 +611,6 @@ def create_poster(
595
  zorder=11,
596
  )
597
 
598
- ax.plot(
599
- [0.4, 0.6],
600
- [0.125, 0.125],
601
- transform=ax.transAxes,
602
- color=THEME["text"],
603
- linewidth=1,
604
- zorder=11,
605
- )
606
-
607
  # --- ATTRIBUTION (bottom right) ---
608
  attr_font = font_sub_base.copy()
609
  attr_font.set_size(8)
 
552
 
553
  # --- BOTTOM TEXT ---
554
  if show_text:
555
+ # Title
556
+ if display_city:
557
+ ax.text(
558
+ 0.5,
559
+ 0.14,
560
+ display_city,
561
+ transform=ax.transAxes,
562
+ color=THEME["text"],
563
+ ha="center",
564
+ fontproperties=font_main,
565
+ zorder=11,
566
+ )
567
 
568
+ # Subtitle
569
+ if display_country:
570
+ ax.text(
571
+ 0.5,
572
+ 0.10,
573
+ display_country,
574
+ transform=ax.transAxes,
575
+ color=THEME["text"],
576
+ ha="center",
577
+ fontproperties=font_sub,
578
+ zorder=11,
579
+ )
580
+
581
+ # Decorative separator line (only show if both exist)
582
+ if display_city and display_country:
583
+ ax.plot(
584
+ [0.4, 0.6],
585
+ [0.125, 0.125],
586
+ transform=ax.transAxes,
587
+ color=THEME["text"],
588
+ linewidth=1,
589
+ zorder=11,
590
+ )
591
 
592
+ # Coordinates (Third line, smaller)
593
  lat, lon = point
594
  coords_text = (
595
  f"{lat:.4f}° N / {lon:.4f}° E"
 
611
  zorder=11,
612
  )
613
 
 
 
 
 
 
 
 
 
 
614
  # --- ATTRIBUTION (bottom right) ---
615
  attr_font = font_sub_base.copy()
616
  attr_font.set_size(8)