addon.py 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166
  1. # Flexlay - A Generic 2D Game Editor
  2. # Copyright (C) 2014 Ingo Ruhnke <grumbel@gmail.com>
  3. #
  4. # This program is free software: you can redistribute it and/or modify
  5. # it under the terms of the GNU General Public License as published by
  6. # the Free Software Foundation, either version 3 of the License, or
  7. # (at your option) any later version.
  8. #
  9. # This program is distributed in the hope that it will be useful,
  10. # but WITHOUT ANY WARRANTY without even the implied warranty of
  11. # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. # GNU General Public License for more details.
  13. #
  14. # You should have received a copy of the GNU General Public License
  15. # along with this program. If not, see <http://www.gnu.org/licenses/>.
  16. from typing import Any, IO, Optional, TYPE_CHECKING
  17. import os
  18. from flexlay.util.sexpr_reader import get_value_from_tree
  19. from flexlay.util.sexpr_writer import SExprWriter
  20. from supertux.util import load_lisp
  21. if TYPE_CHECKING:
  22. from supertux.level import Level
  23. class Addon:
  24. @staticmethod
  25. def from_file(filename: str) -> 'Addon':
  26. addon = Addon()
  27. # if filename.endswith(".stwm"):
  28. # level.is_worldmap = True
  29. # else:
  30. # level.is_worldmap = False
  31. # level.filename = filename
  32. assert addon.filename is not None
  33. tree: Any = load_lisp(addon.filename, "supertux-addoninfo")
  34. data = tree[1:]
  35. addon.id = get_value_from_tree(["id", "_"], data, "")
  36. addon.version = get_value_from_tree(["version", "_"], data, "")
  37. addon.type = get_value_from_tree(["type", "_"], data, "")
  38. addon.title = get_value_from_tree(["title", "_"], data, "")
  39. addon.author = get_value_from_tree(["author", "_"], data, "")
  40. addon.license = get_value_from_tree(["license", "_"], data, "")
  41. # print("VERSION:", level.filename, " ", level.version)
  42. # if level.version == 1:
  43. # raise Exception("version 1 levels not supported at the moment")
  44. # else:
  45. # level.parse_v2(data)
  46. return addon
  47. def __init__(self) -> None:
  48. self.id = "no-id"
  49. self.version: int = 1
  50. self.type: str = "levelset"
  51. self.title: str = "No Title"
  52. self.author: str = "No Author"
  53. self.license: str = "GPL 2+ / CC-by-sa 3.0"
  54. self.filename: Optional[str] = None
  55. # Arrays containing data that we can use in a SuperTux level:
  56. self.images: list[str] = []
  57. self.levels: list[Level] = []
  58. self.music: list[str] = []
  59. self.scripts: list[str] = []
  60. self.sounds: list[str] = []
  61. # Directory path of add-on:
  62. self.project_dir: Optional[str] = None
  63. def parse_v2(self, data: Any) -> None:
  64. self.id = get_value_from_tree(["id", "_"], data, "")
  65. self.version = get_value_from_tree(["version", "_"], data, "")
  66. self.type = get_value_from_tree(["type", "_"], data, "")
  67. self.title = get_value_from_tree(["title", "_"], data, "")
  68. self.author = get_value_from_tree(["author", "_"], data, "")
  69. self.license = get_value_from_tree(["license", "_"], data, "")
  70. def save(self, dirname: str) -> None:
  71. # Save project dir
  72. self.project_dir = dirname
  73. # Create directory, if it doesn't exist:
  74. if not os.path.exists(dirname):
  75. os.makedirs(dirname)
  76. with open(os.path.join(dirname, self.id + ".nfo"), "w") as f:
  77. self.save_io(f)
  78. # Create directory structure:
  79. self.subdirs = ["images",
  80. os.path.join("levels", self.id),
  81. "music",
  82. "scripts",
  83. "sounds"]
  84. for subdir in self.subdirs:
  85. path = os.path.join(dirname, subdir)
  86. if not os.path.exists(path):
  87. os.makedirs(path)
  88. # Save SuperTux sub-world info file:
  89. info_file_path = os.path.join(dirname, "levels", self.id, "info")
  90. with open(info_file_path, "w") as f:
  91. self.save_info_file(f)
  92. # TODO: Save levels and other things (assets) here:
  93. print("TODO: Save levels in add-on directory")
  94. for level in self.levels:
  95. print(level.name)
  96. for image in self.images:
  97. pass # TODO: Save images
  98. for music_file in self.music:
  99. pass # TODO: Save music
  100. for script in self.scripts:
  101. pass # TODO: Save scripts
  102. for sound in self.sounds:
  103. pass # TODO: Save sounds
  104. def save_io(self, f: IO[str]) -> None:
  105. writer = SExprWriter(f)
  106. writer.write_comment("Generated by Flexlay Level Editor (Development Version)")
  107. writer.begin_list("supertux-addoninfo")
  108. writer.write_string("id", self.id)
  109. writer.write_int("version", self.version)
  110. writer.write_string("type", self.type)
  111. writer.write_string("title", self.title)
  112. writer.write_string("author", self.author)
  113. if self.license:
  114. writer.write_string("license", self.license)
  115. writer.end_list()
  116. def save_info_file(self, f: IO[str]) -> None:
  117. writer = SExprWriter(f)
  118. writer.write_comment("Generated by Flexlay Level Editor (Development Version)")
  119. writer.begin_list("supertux-world")
  120. writer.write_string("title", self.title)
  121. writer.write_string("description", "Example add-on")
  122. writer.write_bool("hide-from-contribs", False)
  123. writer.write_bool("levelset", False)
  124. writer.end_list()
  125. def get_project_dir(self) -> Optional[str]:
  126. return self.project_dir
  127. def set_project_dir(self, project_dir: str) -> None:
  128. self.project_dir = project_dir
  129. # EOF #