天气系统完成
@@ -184,8 +184,8 @@ theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 5
|
||||
theme_override_constants/shadow_offset_y = 5
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_constants/outline_size = 20
|
||||
theme_override_constants/shadow_outline_size = 20
|
||||
theme_override_font_sizes/font_size = 45
|
||||
text = "关于"
|
||||
horizontal_alignment = 1
|
||||
|
||||
51
GameManager/WeatherSystem.gd
Normal file
@@ -0,0 +1,51 @@
|
||||
extends Node2D
|
||||
|
||||
@onready var cherry_blossom_rain: Node2D = $CherryBlossomRain #栀子花雨
|
||||
@onready var gardenia_rain: Node2D = $GardeniaRain #樱花雨
|
||||
@onready var willow_leaf_rain: Node2D = $WillowLeafRain #柳叶雨
|
||||
@onready var rain: GPUParticles2D = $Rain #下雨
|
||||
@onready var snow: GPUParticles2D = $Snow #下雪
|
||||
|
||||
# 天气系统
|
||||
# 要显示哪种天气直接调用相应天气的show()然后一并隐藏其他天气hide()
|
||||
|
||||
# 设置天气的统一方法
|
||||
func set_weather(weather_type: String):
|
||||
# 先隐藏所有天气效果
|
||||
hide_all_weather()
|
||||
|
||||
# 根据天气类型显示对应效果
|
||||
match weather_type:
|
||||
"clear", "stop":
|
||||
# 晴天或停止天气 - 所有天气效果都隐藏
|
||||
pass
|
||||
"rain":
|
||||
if rain:
|
||||
rain.show()
|
||||
"snow":
|
||||
if snow:
|
||||
snow.show()
|
||||
"cherry":
|
||||
if cherry_blossom_rain:
|
||||
cherry_blossom_rain.show()
|
||||
"gardenia":
|
||||
if gardenia_rain:
|
||||
gardenia_rain.show()
|
||||
"willow":
|
||||
if willow_leaf_rain:
|
||||
willow_leaf_rain.show()
|
||||
_:
|
||||
print("未知的天气类型: ", weather_type)
|
||||
|
||||
# 隐藏所有天气效果
|
||||
func hide_all_weather():
|
||||
if cherry_blossom_rain:
|
||||
cherry_blossom_rain.hide()
|
||||
if gardenia_rain:
|
||||
gardenia_rain.hide()
|
||||
if willow_leaf_rain:
|
||||
willow_leaf_rain.hide()
|
||||
if rain:
|
||||
rain.hide()
|
||||
if snow:
|
||||
snow.hide()
|
||||
1
GameManager/WeatherSystem.gd.uid
Normal file
@@ -0,0 +1 @@
|
||||
uid://o4mcuqoivqri
|
||||
481
MainGame.gd
@@ -11,7 +11,7 @@ extends Node
|
||||
@onready var show_level : Label = $UI/GUI/GameInfoHBox1/level # 显示当前玩家的等级
|
||||
@onready var show_tip : Label = $UI/GUI/GameInfoHBox3/tip # 显示小提示
|
||||
@onready var show_like: Label = $UI/GUI/GameInfoHBox1/like # 显示别人给自己点赞的总赞数
|
||||
@onready var show_onlineplayer: Label = $UI/GUI/GameInfoHBox2/onlineplayer # 显示服务器在线人数
|
||||
@onready var show_onlineplayer: Label = $UI/GUI/GameInfoHBox3/onlineplayer # 显示服务器在线人数
|
||||
@onready var show_player_name : Label = $UI/GUI/GameInfoHBox2/player_name # 显示玩家昵称
|
||||
@onready var show_farm_name : Label = $UI/GUI/GameInfoHBox2/farm_name # 显示农场名称
|
||||
@onready var show_status_label : Label = $UI/GUI/GameInfoHBox2/StatusLabel # 显示与服务器连接状态
|
||||
@@ -67,6 +67,7 @@ extends Node
|
||||
@onready var pet_store_panel: Panel = $UI/BigPanel/PetStorePanel #宠物商店面板
|
||||
@onready var pet_fight_panel: Panel = $UI/BigPanel/PetFightPanel #宠物战斗面板
|
||||
@onready var pet_inform_panel: Panel = $UI/SmallPanel/PetInformPanel #宠物信息面板
|
||||
@onready var player_store_panel: Panel = $UI/BigPanel/PlayerStorePanel #玩家小卖部面板
|
||||
|
||||
|
||||
#小面板
|
||||
@@ -92,6 +93,9 @@ extends Node
|
||||
@onready var tree_status: Label = $Decoration/WisdomTree/TreeStatus #智慧树状态 只显示 等级和高度
|
||||
@onready var anonymous_talk: RichTextLabel = $Decoration/WisdomTree/BackgroundPanel/AnonymousTalk #给智慧树听音乐100%会刷新 施肥浇水
|
||||
|
||||
#天气系统
|
||||
@onready var weather_system: Node2D = $WeatherSystem #天气系统节点
|
||||
|
||||
|
||||
#各种弹窗
|
||||
@onready var accept_dialog: AcceptDialog = $UI/DiaLog/AcceptDialog
|
||||
@@ -200,10 +204,6 @@ func _ready():
|
||||
|
||||
# 初始化调试面板(默认隐藏)
|
||||
debug_panel.hide()
|
||||
debug_panel_script = debug_panel
|
||||
|
||||
# 在加载进度面板上添加调试按钮
|
||||
_add_debug_button_to_loading_panel()
|
||||
|
||||
#未登录时隐藏所有UI
|
||||
game_info_h_box_1.hide()
|
||||
@@ -1158,16 +1158,17 @@ func _handle_item_config_response(response_data):
|
||||
|
||||
|
||||
#===============================================作物图片缓存系统===============================================
|
||||
|
||||
## 优化的作物图片缓存和管理系统
|
||||
class CropTextureManager:
|
||||
|
||||
# 缓存字典
|
||||
var texture_cache: Dictionary = {} # 序列帧缓存 {crop_name: [Texture2D]}
|
||||
var mature_texture_cache: Dictionary = {} # 成熟图片缓存 {crop_name: Texture2D}
|
||||
var frame_counts: Dictionary = {} # 帧数记录 {crop_name: int}
|
||||
# 缓存字典 - 改为三阶段图片缓存
|
||||
var texture_cache: Dictionary = {} # 阶段图片缓存 {crop_name: {"幼苗": Texture2D, "未成熟": Texture2D, "成熟": Texture2D}}
|
||||
var default_textures: Dictionary = {} # 默认图片缓存 {"幼苗": Texture2D, "未成熟": Texture2D, "成熟": Texture2D}
|
||||
var failed_resources: Array = [] # 记录加载失败的资源路径
|
||||
|
||||
# 三个生长阶段
|
||||
const GROWTH_STAGES = ["幼苗", "未成熟", "成熟"]
|
||||
|
||||
# 加载状态
|
||||
var is_loading: bool = false
|
||||
var load_progress: float = 0.0
|
||||
@@ -1183,9 +1184,6 @@ class CropTextureManager:
|
||||
var results_mutex: Mutex
|
||||
var completed_results: Array = []
|
||||
|
||||
# 调试面板引用
|
||||
var debug_panel_ref = null
|
||||
|
||||
# 内存管理
|
||||
var max_cache_size: int = 300 # 最大缓存图片数量
|
||||
var cache_access_order: Array = [] # LRU缓存访问顺序
|
||||
@@ -1196,8 +1194,6 @@ class CropTextureManager:
|
||||
results_mutex = Mutex.new()
|
||||
# 根据设备性能动态调整线程数
|
||||
_adjust_thread_count()
|
||||
# 尝试获取调试面板引用
|
||||
_connect_debug_panel()
|
||||
|
||||
## 根据设备性能调整线程数
|
||||
func _adjust_thread_count():
|
||||
@@ -1216,28 +1212,8 @@ class CropTextureManager:
|
||||
|
||||
print("[CropTextureManager] 设备: %s, CPU核心: %d, 使用线程数: %d" % [platform, processor_count, max_threads])
|
||||
|
||||
## 连接调试面板
|
||||
func _connect_debug_panel():
|
||||
# 延迟获取调试面板引用,因为初始化时可能还未创建
|
||||
call_deferred("_try_get_debug_panel")
|
||||
|
||||
## 尝试获取调试面板引用
|
||||
func _try_get_debug_panel():
|
||||
var main_node = Engine.get_main_loop().current_scene
|
||||
if main_node:
|
||||
debug_panel_ref = main_node.get_node_or_null("UI/SmallPanel/DebugPanel")
|
||||
if debug_panel_ref:
|
||||
print("[CropTextureManager] 已连接到调试面板")
|
||||
|
||||
## 向调试面板发送消息
|
||||
func _send_debug_message(message: String, color: Color = Color.WHITE):
|
||||
if debug_panel_ref and debug_panel_ref.has_method("add_debug_message"):
|
||||
debug_panel_ref.add_debug_message(message, color)
|
||||
|
||||
## 设置当前加载项目
|
||||
func _set_current_loading_item(item_name: String):
|
||||
if debug_panel_ref and debug_panel_ref.has_method("set_current_loading_item"):
|
||||
debug_panel_ref.set_current_loading_item(item_name)
|
||||
|
||||
|
||||
|
||||
## 异步预加载所有作物图片 - 主要入口函数
|
||||
func preload_all_textures_async(crop_data: Dictionary, progress_callback: Callable) -> void:
|
||||
@@ -1254,23 +1230,18 @@ class CropTextureManager:
|
||||
completed_results.clear()
|
||||
|
||||
print("[CropTextureManager] 开始预加载 %d 种作物图片" % total_crops)
|
||||
_send_debug_message("开始预加载 %d 种作物图片" % total_crops, Color.CYAN)
|
||||
|
||||
# 阶段1:加载默认图片 (0-10%)
|
||||
progress_callback.call(0, "正在加载默认图片...")
|
||||
_send_debug_message("阶段1: 加载默认图片", Color.YELLOW)
|
||||
await _load_default_textures_async()
|
||||
progress_callback.call(10, "默认图片加载完成")
|
||||
_send_debug_message("默认图片加载完成", Color.GREEN)
|
||||
|
||||
# 阶段2:多线程批量加载作物图片 (10-90%)
|
||||
_send_debug_message("阶段2: 多线程加载作物图片", Color.YELLOW)
|
||||
await _load_crops_multithreaded_async(crop_data, progress_callback)
|
||||
|
||||
# 阶段3:完成 (90-100%)
|
||||
progress_callback.call(100, "所有作物图片加载完成!")
|
||||
_print_cache_stats()
|
||||
_send_debug_message("所有作物图片加载完成!", Color.GREEN)
|
||||
|
||||
# 清理线程
|
||||
await _cleanup_threads()
|
||||
@@ -1278,28 +1249,23 @@ class CropTextureManager:
|
||||
is_loading = false
|
||||
var success_message = "预加载完成,成功: %d, 失败: %d" % [loaded_crops, failed_crops]
|
||||
print("[CropTextureManager] " + success_message)
|
||||
_send_debug_message(success_message, Color.CYAN)
|
||||
|
||||
## 多线程批量异步加载作物图片
|
||||
func _load_crops_multithreaded_async(crop_data: Dictionary, progress_callback: Callable) -> void:
|
||||
var crop_names = crop_data.keys()
|
||||
|
||||
# 准备加载队列
|
||||
# 准备加载队列 - 为每个作物的每个阶段创建任务
|
||||
loading_mutex.lock()
|
||||
loading_queue.clear()
|
||||
for crop_name in crop_names:
|
||||
loading_queue.append({
|
||||
"crop_name": crop_name,
|
||||
"type": "sequence"
|
||||
})
|
||||
loading_queue.append({
|
||||
"crop_name": crop_name,
|
||||
"type": "mature"
|
||||
})
|
||||
for stage in GROWTH_STAGES:
|
||||
loading_queue.append({
|
||||
"crop_name": crop_name,
|
||||
"stage": stage
|
||||
})
|
||||
loading_mutex.unlock()
|
||||
|
||||
# 启动工作线程
|
||||
_send_debug_message("启动 %d 个工作线程" % max_threads, Color.CYAN)
|
||||
for i in range(max_threads):
|
||||
var thread = Thread.new()
|
||||
worker_threads.append(thread)
|
||||
@@ -1363,66 +1329,42 @@ class CropTextureManager:
|
||||
## 执行单个纹理加载任务
|
||||
func _load_texture_task(task: Dictionary) -> Dictionary:
|
||||
var crop_name = task["crop_name"]
|
||||
var task_type = task["type"]
|
||||
var stage = task["stage"]
|
||||
var result = {
|
||||
"crop_name": crop_name,
|
||||
"type": task_type,
|
||||
"stage": stage,
|
||||
"success": false,
|
||||
"textures": [],
|
||||
"texture": null,
|
||||
"error": ""
|
||||
}
|
||||
|
||||
if task_type == "sequence":
|
||||
result["textures"] = _load_crop_textures_threadsafe(crop_name)
|
||||
result["success"] = result["textures"].size() > 0
|
||||
elif task_type == "mature":
|
||||
result["texture"] = _load_mature_texture_threadsafe(crop_name)
|
||||
result["success"] = result["texture"] != null
|
||||
result["texture"] = _load_stage_texture_threadsafe(crop_name, stage)
|
||||
result["success"] = result["texture"] != null
|
||||
|
||||
# 检查加载是否成功
|
||||
if not result["success"]:
|
||||
result["error"] = "加载失败: " + crop_name
|
||||
failed_resources.append(crop_name)
|
||||
result["error"] = "加载失败: %s - %s" % [crop_name, stage]
|
||||
failed_resources.append(crop_name + "/" + stage)
|
||||
|
||||
return result
|
||||
|
||||
## 线程安全的作物序列帧加载
|
||||
func _load_crop_textures_threadsafe(crop_name: String) -> Array:
|
||||
var textures = []
|
||||
## 线程安全的阶段图片加载
|
||||
func _load_stage_texture_threadsafe(crop_name: String, stage: String) -> Texture2D:
|
||||
var crop_path = "res://assets/作物/" + crop_name + "/"
|
||||
var texture_path = crop_path + stage + ".webp"
|
||||
|
||||
# 检查作物文件夹是否存在
|
||||
if not DirAccess.dir_exists_absolute(crop_path):
|
||||
return []
|
||||
|
||||
# 使用ResourceLoader.load_threaded_request进行异步加载
|
||||
var frame_index = 0
|
||||
var max_frames = 20 # 限制最大帧数,避免无限循环
|
||||
|
||||
while frame_index < max_frames:
|
||||
var texture_path = crop_path + str(frame_index) + ".webp"
|
||||
|
||||
if not ResourceLoader.exists(texture_path):
|
||||
break
|
||||
|
||||
# 使用线程安全的资源加载
|
||||
# 首先尝试加载作物特定的阶段图片
|
||||
if ResourceLoader.exists(texture_path):
|
||||
var texture = _load_resource_safe(texture_path)
|
||||
if texture:
|
||||
textures.append(texture)
|
||||
frame_index += 1
|
||||
else:
|
||||
break
|
||||
return texture
|
||||
|
||||
return textures
|
||||
|
||||
## 线程安全的成熟图片加载
|
||||
func _load_mature_texture_threadsafe(crop_name: String) -> Texture2D:
|
||||
var crop_path = "res://assets/作物/" + crop_name + "/"
|
||||
var mature_path = crop_path + "成熟.webp"
|
||||
|
||||
if ResourceLoader.exists(mature_path):
|
||||
return _load_resource_safe(mature_path)
|
||||
# 如果没有找到,尝试使用默认图片
|
||||
var default_path = "res://assets/作物/默认/" + stage + ".webp"
|
||||
if ResourceLoader.exists(default_path):
|
||||
var default_texture = _load_resource_safe(default_path)
|
||||
if default_texture:
|
||||
return default_texture
|
||||
|
||||
return null
|
||||
|
||||
@@ -1448,76 +1390,41 @@ class CropTextureManager:
|
||||
## 应用加载结果到缓存
|
||||
func _apply_loading_result(result: Dictionary):
|
||||
var crop_name = result["crop_name"]
|
||||
var task_type = result["type"]
|
||||
var stage = result["stage"]
|
||||
var success = result["success"]
|
||||
|
||||
if not success:
|
||||
var error_msg = "加载失败: %s (%s)" % [crop_name, task_type]
|
||||
_send_debug_message(error_msg, Color.RED)
|
||||
return
|
||||
|
||||
if task_type == "sequence":
|
||||
var textures = result["textures"]
|
||||
if textures.size() > 0:
|
||||
texture_cache[crop_name] = textures
|
||||
frame_counts[crop_name] = textures.size()
|
||||
_update_cache_access(crop_name)
|
||||
_send_debug_message("✓ %s: %d帧" % [crop_name, textures.size()], Color.GREEN)
|
||||
elif task_type == "mature":
|
||||
var texture = result["texture"]
|
||||
if texture:
|
||||
mature_texture_cache[crop_name] = texture
|
||||
_update_cache_access(crop_name + "_mature")
|
||||
_send_debug_message("✓ %s: 成熟图片" % crop_name, Color.GREEN)
|
||||
var texture = result["texture"]
|
||||
if texture:
|
||||
# 确保作物有缓存字典
|
||||
if not texture_cache.has(crop_name):
|
||||
texture_cache[crop_name] = {}
|
||||
|
||||
# 缓存阶段图片
|
||||
texture_cache[crop_name][stage] = texture
|
||||
_update_cache_access(crop_name + "_" + stage)
|
||||
|
||||
# 检查缓存大小,必要时清理
|
||||
_check_and_cleanup_cache()
|
||||
|
||||
## 立即加载默认图片(同步,但优化)
|
||||
func _load_default_textures_async() -> void:
|
||||
const DEFAULT_CROP = "默认"
|
||||
const DEFAULT_PATH = "res://assets/作物/默认/"
|
||||
|
||||
if texture_cache.has(DEFAULT_CROP):
|
||||
if default_textures.size() > 0:
|
||||
return
|
||||
|
||||
var textures = []
|
||||
var frame_index = 0
|
||||
|
||||
# 限制默认图片帧数
|
||||
while frame_index < 10:
|
||||
var texture_path = DEFAULT_PATH + str(frame_index) + ".webp"
|
||||
# 加载三个阶段的默认图片
|
||||
for stage in GROWTH_STAGES:
|
||||
var texture_path = DEFAULT_PATH + stage + ".webp"
|
||||
if ResourceLoader.exists(texture_path):
|
||||
var texture = _load_resource_safe(texture_path)
|
||||
if texture:
|
||||
textures.append(texture)
|
||||
frame_index += 1
|
||||
else:
|
||||
break
|
||||
else:
|
||||
break
|
||||
default_textures[stage] = texture
|
||||
|
||||
# 如果没有序列帧,尝试加载单个图片
|
||||
if textures.size() == 0:
|
||||
var single_path = DEFAULT_PATH + "0.webp"
|
||||
if ResourceLoader.exists(single_path):
|
||||
var texture = _load_resource_safe(single_path)
|
||||
if texture:
|
||||
textures.append(texture)
|
||||
|
||||
# 缓存结果
|
||||
if textures.size() > 0:
|
||||
texture_cache[DEFAULT_CROP] = textures
|
||||
frame_counts[DEFAULT_CROP] = textures.size()
|
||||
|
||||
# 加载默认成熟图片
|
||||
var mature_path = DEFAULT_PATH + "成熟.webp"
|
||||
if ResourceLoader.exists(mature_path):
|
||||
var mature_texture = _load_resource_safe(mature_path)
|
||||
if mature_texture:
|
||||
mature_texture_cache[DEFAULT_CROP] = mature_texture
|
||||
|
||||
print("[CropTextureManager] 默认图片加载完成:%d 帧" % textures.size())
|
||||
print("[CropTextureManager] 默认图片加载完成:%d 个阶段" % default_textures.size())
|
||||
|
||||
# 让出一帧
|
||||
await Engine.get_main_loop().process_frame
|
||||
@@ -1530,62 +1437,81 @@ class CropTextureManager:
|
||||
|
||||
## 检查并清理缓存
|
||||
func _check_and_cleanup_cache():
|
||||
var total_cached = texture_cache.size() + mature_texture_cache.size()
|
||||
var total_cached = 0
|
||||
for crop_name in texture_cache.keys():
|
||||
total_cached += texture_cache[crop_name].size()
|
||||
|
||||
if total_cached > max_cache_size:
|
||||
var to_remove = total_cached - max_cache_size + 10 # 多清理一些
|
||||
_send_debug_message("⚠ 缓存超限,开始清理 %d 个项目" % to_remove, Color.ORANGE)
|
||||
|
||||
for i in range(min(to_remove, cache_access_order.size())):
|
||||
var key = cache_access_order[i]
|
||||
|
||||
# 不清理默认图片
|
||||
# 不清理默认图片相关的键
|
||||
if key.begins_with("默认"):
|
||||
continue
|
||||
|
||||
if key.ends_with("_mature"):
|
||||
var crop_name = key.replace("_mature", "")
|
||||
mature_texture_cache.erase(crop_name)
|
||||
else:
|
||||
texture_cache.erase(key)
|
||||
frame_counts.erase(key)
|
||||
# 解析键:crop_name_stage
|
||||
var parts = key.split("_")
|
||||
if parts.size() >= 2:
|
||||
var stage = parts[-1]
|
||||
var crop_name = "_".join(parts.slice(0, -1))
|
||||
|
||||
if texture_cache.has(crop_name) and texture_cache[crop_name].has(stage):
|
||||
texture_cache[crop_name].erase(stage)
|
||||
|
||||
# 如果作物的所有阶段都被清理,删除作物条目
|
||||
if texture_cache[crop_name].is_empty():
|
||||
texture_cache.erase(crop_name)
|
||||
|
||||
# 更新访问顺序
|
||||
cache_access_order = cache_access_order.slice(to_remove)
|
||||
|
||||
var current_size = texture_cache.size() + mature_texture_cache.size()
|
||||
var current_size = 0
|
||||
for crop_name in texture_cache.keys():
|
||||
current_size += texture_cache[crop_name].size()
|
||||
var cleanup_msg = "缓存清理完成,当前缓存: %d" % current_size
|
||||
print("[CropTextureManager] " + cleanup_msg)
|
||||
_send_debug_message(cleanup_msg, Color.YELLOW)
|
||||
|
||||
## 根据生长进度获取作物图片(带缓存优化)
|
||||
func get_texture_by_progress(crop_name: String, progress: float) -> Texture2D:
|
||||
# 根据进度确定阶段
|
||||
var stage = ""
|
||||
if progress < 0.33:
|
||||
stage = "幼苗"
|
||||
elif progress < 0.85:
|
||||
stage = "未成熟"
|
||||
else:
|
||||
stage = "成熟"
|
||||
|
||||
# 更新访问记录
|
||||
_update_cache_access(crop_name)
|
||||
var access_key = crop_name + "_" + stage
|
||||
_update_cache_access(access_key)
|
||||
|
||||
# 100%成熟时优先使用成熟图片
|
||||
if progress >= 1.0:
|
||||
var mature_texture = mature_texture_cache.get(crop_name, null)
|
||||
if mature_texture:
|
||||
_update_cache_access(crop_name + "_mature")
|
||||
return mature_texture
|
||||
# 尝试获取作物特定的阶段图片
|
||||
if texture_cache.has(crop_name) and texture_cache[crop_name].has(stage):
|
||||
var texture = texture_cache[crop_name][stage]
|
||||
if texture:
|
||||
return texture
|
||||
|
||||
# 使用序列帧图片
|
||||
var textures = texture_cache.get(crop_name, [])
|
||||
if textures.size() == 0:
|
||||
# 如果没有缓存,尝试使用默认图片
|
||||
textures = texture_cache.get("默认", [])
|
||||
if textures.size() == 0:
|
||||
return null
|
||||
# 如果没有缓存,尝试直接从文件夹加载
|
||||
var direct_texture = _load_stage_texture_threadsafe(crop_name, stage)
|
||||
if direct_texture:
|
||||
# 将直接加载的图片加入缓存,避免下次再次加载
|
||||
if not texture_cache.has(crop_name):
|
||||
texture_cache[crop_name] = {}
|
||||
texture_cache[crop_name][stage] = direct_texture
|
||||
_update_cache_access(crop_name + "_" + stage)
|
||||
return direct_texture
|
||||
|
||||
if textures.size() == 1:
|
||||
return textures[0]
|
||||
# 最后才回退到默认图片
|
||||
if default_textures.has(stage):
|
||||
var default_texture = default_textures[stage]
|
||||
if default_texture:
|
||||
return default_texture
|
||||
|
||||
# 根据进度计算帧索引
|
||||
var frame_index = int(progress * (textures.size() - 1))
|
||||
frame_index = clamp(frame_index, 0, textures.size() - 1)
|
||||
|
||||
return textures[frame_index]
|
||||
# 如果都没有,返回null
|
||||
return null
|
||||
|
||||
## 清理线程
|
||||
func _cleanup_threads() -> void:
|
||||
@@ -1599,8 +1525,7 @@ class CropTextureManager:
|
||||
func clear_cache() -> void:
|
||||
await _cleanup_threads()
|
||||
texture_cache.clear()
|
||||
mature_texture_cache.clear()
|
||||
frame_counts.clear()
|
||||
default_textures.clear()
|
||||
cache_access_order.clear()
|
||||
failed_resources.clear()
|
||||
print("[CropTextureManager] 缓存已清理")
|
||||
@@ -1608,13 +1533,13 @@ class CropTextureManager:
|
||||
## 打印缓存统计信息
|
||||
func _print_cache_stats() -> void:
|
||||
print("[CropTextureManager] 缓存统计:")
|
||||
print(" - 序列帧缓存: %d 种作物" % texture_cache.size())
|
||||
print(" - 成熟图片缓存: %d 种作物" % mature_texture_cache.size())
|
||||
print(" - 阶段图片缓存: %d 种作物" % texture_cache.size())
|
||||
print(" - 默认图片缓存: %d 个阶段" % default_textures.size())
|
||||
print(" - 加载失败: %d 个资源" % failed_resources.size())
|
||||
var total_frames = 0
|
||||
for count in frame_counts.values():
|
||||
total_frames += count
|
||||
print(" - 总图片帧数: %d 帧" % total_frames)
|
||||
var total_stages = 0
|
||||
for crop_name in texture_cache.keys():
|
||||
total_stages += texture_cache[crop_name].size()
|
||||
print(" - 总阶段图片数: %d 个" % total_stages)
|
||||
|
||||
if failed_resources.size() > 0:
|
||||
print(" - 失败的资源:")
|
||||
@@ -1625,13 +1550,15 @@ class CropTextureManager:
|
||||
func get_cache_info() -> String:
|
||||
var info = "作物图片缓存详情:\n"
|
||||
for crop_name in texture_cache.keys():
|
||||
var frame_count = frame_counts.get(crop_name, 0)
|
||||
var has_mature = mature_texture_cache.has(crop_name)
|
||||
info += " - %s: %d帧" % [crop_name, frame_count]
|
||||
if has_mature:
|
||||
info += " (含成熟图片)"
|
||||
var stages = texture_cache[crop_name].keys()
|
||||
info += " - %s: %s" % [crop_name, "/".join(stages)]
|
||||
info += "\n"
|
||||
|
||||
if default_textures.size() > 0:
|
||||
info += "\n默认图片:\n"
|
||||
for stage in default_textures.keys():
|
||||
info += " - " + stage + "\n"
|
||||
|
||||
if failed_resources.size() > 0:
|
||||
info += "\n加载失败的资源:\n"
|
||||
for failed in failed_resources:
|
||||
@@ -1645,25 +1572,19 @@ class CropTextureManager:
|
||||
for crop_name in common_crops:
|
||||
# 确保常用作物在缓存中
|
||||
if not texture_cache.has(crop_name):
|
||||
var textures = _load_crop_textures_threadsafe(crop_name)
|
||||
if textures.size() > 0:
|
||||
texture_cache[crop_name] = textures
|
||||
frame_counts[crop_name] = textures.size()
|
||||
|
||||
if not mature_texture_cache.has(crop_name):
|
||||
var mature = _load_mature_texture_threadsafe(crop_name)
|
||||
if mature:
|
||||
mature_texture_cache[crop_name] = mature
|
||||
texture_cache[crop_name] = {}
|
||||
|
||||
# 加载各个阶段的图片
|
||||
for stage in GROWTH_STAGES:
|
||||
var texture = _load_stage_texture_threadsafe(crop_name, stage)
|
||||
if texture:
|
||||
texture_cache[crop_name][stage] = texture
|
||||
|
||||
|
||||
|
||||
# 全局作物图片管理器实例
|
||||
var crop_texture_manager: CropTextureManager
|
||||
|
||||
# 资源加载调试器(可选,用于调试)
|
||||
var resource_debugger = null
|
||||
|
||||
# 调试面板脚本引用
|
||||
var debug_panel_script = null
|
||||
|
||||
#===============================================作物图片缓存系统===============================================
|
||||
|
||||
|
||||
@@ -1724,11 +1645,7 @@ func _update_load_progress(progress: int, message: String = "") -> void:
|
||||
if message_label and message != "":
|
||||
message_label.text = message
|
||||
|
||||
# 向调试面板发送进度信息
|
||||
if debug_panel_script and debug_panel_script.has_method("add_debug_message"):
|
||||
if message != "":
|
||||
#debug_panel_script.add_debug_message("进度 %d%%: %s" % [progress, message], Color.CYAN)
|
||||
pass
|
||||
|
||||
# 检测卡顿
|
||||
_check_loading_stuck(progress)
|
||||
|
||||
@@ -1748,8 +1665,7 @@ func _check_loading_stuck(progress: int):
|
||||
if progress == last_progress_value:
|
||||
var stuck_time = current_time - last_progress_time
|
||||
if stuck_time > 5.0: # 5秒没有进度变化
|
||||
if debug_panel_script and debug_panel_script.has_method("add_debug_message"):
|
||||
debug_panel_script.add_debug_message("⚠ 加载卡顿检测: 在 %d%% 停留了 %.1f 秒" % [progress, stuck_time], Color.ORANGE)
|
||||
print("⚠ 加载卡顿检测: 在 %d%% 停留了 %.1f 秒" % [progress, stuck_time])
|
||||
else:
|
||||
# 进度有变化,更新记录
|
||||
last_progress_value = progress
|
||||
@@ -1797,95 +1713,7 @@ func _wait_for_crop_data() -> void:
|
||||
|
||||
#===============================================调试和维护工具===============================================
|
||||
|
||||
## 调试:打印缓存信息
|
||||
func _debug_print_crop_cache() -> void:
|
||||
if crop_texture_manager:
|
||||
print(crop_texture_manager.get_cache_info())
|
||||
else:
|
||||
print("[调试] 作物图片管理器未初始化")
|
||||
|
||||
## 调试:强制刷新所有图片
|
||||
func _debug_refresh_all_crop_sprites() -> void:
|
||||
print("[调试] 强制刷新所有地块图片...")
|
||||
_refresh_all_crop_sprites()
|
||||
print("[调试] 图片刷新完成")
|
||||
|
||||
## 调试:清理图片缓存
|
||||
func _debug_clear_crop_cache() -> void:
|
||||
if crop_texture_manager:
|
||||
crop_texture_manager.clear_cache()
|
||||
print("[调试] 图片缓存已清理")
|
||||
|
||||
## 调试:启用资源加载调试器
|
||||
func _debug_enable_resource_debugger() -> void:
|
||||
if not resource_debugger:
|
||||
resource_debugger = preload("res://GlobalScript/ResourceLoadingDebugger.gd").new()
|
||||
add_child(resource_debugger)
|
||||
print("[调试] 资源加载调试器已启用")
|
||||
else:
|
||||
print("[调试] 资源加载调试器已经在运行")
|
||||
|
||||
## 调试:生成资源加载报告
|
||||
func _debug_generate_loading_report() -> void:
|
||||
if resource_debugger:
|
||||
var report = resource_debugger.generate_loading_report()
|
||||
print(report)
|
||||
resource_debugger.export_debug_data_to_file()
|
||||
else:
|
||||
print("[调试] 资源加载调试器未启用,请先调用 _debug_enable_resource_debugger()")
|
||||
|
||||
## 调试:检测设备能力
|
||||
func _debug_detect_device_capabilities() -> void:
|
||||
if resource_debugger:
|
||||
var capabilities = resource_debugger.detect_device_capabilities()
|
||||
print("[调试] 设备能力检测结果:")
|
||||
for key in capabilities:
|
||||
print(" %s: %s" % [key, str(capabilities[key])])
|
||||
else:
|
||||
print("[调试] 资源加载调试器未启用")
|
||||
|
||||
## 调试:强制触发低内存模式
|
||||
func _debug_trigger_low_memory_mode() -> void:
|
||||
if crop_texture_manager:
|
||||
# 临时降低缓存大小来模拟低内存环境
|
||||
crop_texture_manager.max_cache_size = 50
|
||||
crop_texture_manager._check_and_cleanup_cache()
|
||||
print("[调试] 已触发低内存模式,缓存大小限制为50")
|
||||
|
||||
## 调试:恢复正常内存模式
|
||||
func _debug_restore_normal_memory_mode() -> void:
|
||||
if crop_texture_manager:
|
||||
crop_texture_manager.max_cache_size = 200
|
||||
print("[调试] 已恢复正常内存模式,缓存大小限制为200")
|
||||
|
||||
## 在加载进度面板上添加调试按钮
|
||||
func _add_debug_button_to_loading_panel():
|
||||
# 创建调试按钮
|
||||
var debug_button = Button.new()
|
||||
debug_button.text = "调试信息"
|
||||
debug_button.size_flags_horizontal = Control.SIZE_SHRINK_CENTER
|
||||
debug_button.position = Vector2(10, 500) # 左下角位置
|
||||
debug_button.size = Vector2(120, 40)
|
||||
|
||||
# 设置按钮样式
|
||||
debug_button.modulate = Color(0.8, 0.8, 1.0, 0.9) # 半透明蓝色
|
||||
|
||||
# 连接点击信号
|
||||
debug_button.pressed.connect(_on_debug_button_pressed)
|
||||
|
||||
# 添加到加载进度面板
|
||||
load_progress_panel.add_child(debug_button)
|
||||
|
||||
print("[MainGame] 调试按钮已添加到加载进度面板")
|
||||
|
||||
## 调试按钮点击处理
|
||||
func _on_debug_button_pressed():
|
||||
if debug_panel.visible:
|
||||
debug_panel.hide()
|
||||
else:
|
||||
debug_panel.show()
|
||||
debug_panel.move_to_front()
|
||||
print("[MainGame] 调试面板切换显示状态")
|
||||
|
||||
#===============================================调试和维护工具===============================================
|
||||
|
||||
@@ -1894,8 +1722,14 @@ func _on_debug_button_pressed():
|
||||
#===============================================向后兼容性===============================================
|
||||
# 为了保持向后兼容,保留一些原来的函数名
|
||||
func _load_crop_textures(crop_name: String) -> Array:
|
||||
if crop_texture_manager:
|
||||
return crop_texture_manager._load_crop_textures_threadsafe(crop_name)
|
||||
# 返回所有阶段的图片
|
||||
if crop_texture_manager and crop_texture_manager.texture_cache.has(crop_name):
|
||||
var stages = crop_texture_manager.texture_cache[crop_name]
|
||||
var textures = []
|
||||
for stage in crop_texture_manager.GROWTH_STAGES:
|
||||
if stages.has(stage):
|
||||
textures.append(stages[stage])
|
||||
return textures
|
||||
return []
|
||||
|
||||
func _get_crop_texture_by_progress(crop_name: String, progress: float) -> Texture2D:
|
||||
@@ -2398,12 +2232,11 @@ func _handle_broadcast_history_response(data: Dictionary):
|
||||
# 更新主界面大喇叭显示为最新消息
|
||||
if global_server_broadcast:
|
||||
var latest_message = global_server_broadcast_panel.get_latest_message()
|
||||
if latest_message != "暂无消息":
|
||||
if latest_message != "全服大喇叭":
|
||||
global_server_broadcast.text = latest_message
|
||||
print("主界面大喇叭已更新为: ", latest_message)
|
||||
else:
|
||||
global_server_broadcast.text = ""
|
||||
print("没有消息,清空主界面大喇叭显示")
|
||||
global_server_broadcast.text = "全服大喇叭"
|
||||
|
||||
|
||||
# 初始化大喇叭显示
|
||||
@@ -3479,3 +3312,39 @@ func _handle_wisdom_tree_config_response(data):
|
||||
wisdom_tree_panel.wisdom_tree_config = config
|
||||
wisdom_tree_panel.update_ui()
|
||||
# ======================================= 智慧树系统 =========================================
|
||||
|
||||
|
||||
# ======================================= 天气系统 =========================================
|
||||
# 处理天气变更
|
||||
func _handle_weather_change(weather_type: String, weather_name: String):
|
||||
"""处理服务器发送的天气变更消息"""
|
||||
if weather_system and weather_system.has_method("set_weather"):
|
||||
weather_system.set_weather(weather_type)
|
||||
Toast.show("天气已变更为:" + weather_name, Color.CYAN, 3.0)
|
||||
print("天气已切换为:", weather_name)
|
||||
else:
|
||||
print("天气系统不可用")
|
||||
# ======================================= 天气系统 =========================================
|
||||
|
||||
|
||||
#打开小卖部面板
|
||||
func _on_my_store_button_pressed() -> void:
|
||||
player_store_panel.show()
|
||||
pass
|
||||
|
||||
#打开小卖部面板
|
||||
func _on_player_store_pressed() -> void:
|
||||
player_store_panel.show()
|
||||
pass
|
||||
|
||||
func _on_seed_store_pressed() -> void:
|
||||
crop_store_panel.show()
|
||||
pass
|
||||
|
||||
func _on_item_store_pressed() -> void:
|
||||
item_store_panel.show()
|
||||
pass
|
||||
|
||||
func _on_pet_store_pressed() -> void:
|
||||
pet_store_panel.show()
|
||||
pass
|
||||
|
||||
562
MainGame.tscn
@@ -1,8 +1,9 @@
|
||||
[gd_scene load_steps=85 format=3 uid="uid://dgh61dttaas5a"]
|
||||
[gd_scene load_steps=96 format=3 uid="uid://dgh61dttaas5a"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://2pt11sfcaxf7" path="res://MainGame.gd" id="1_v3yaj"]
|
||||
[ext_resource type="Texture2D" uid="uid://du2pyiojliasy" path="res://assets/游戏UI/经验球.webp" id="2_6jgly"]
|
||||
[ext_resource type="PackedScene" uid="uid://bkivlkirrx6u8" path="res://CopyItems/crop_item.tscn" id="3_isiom"]
|
||||
[ext_resource type="FontFile" uid="uid://dl31rnmd4lia" path="res://assets/字体/MapleMono-NF-CN-Bold.ttf" id="3_t4s8j"]
|
||||
[ext_resource type="Texture2D" uid="uid://ftv231igtdoq" path="res://assets/游戏UI/等级.webp" id="3_y1hsh"]
|
||||
[ext_resource type="Texture2D" uid="uid://bqib5y8uwg6hx" path="res://assets/游戏UI/钱币.webp" id="4_ql8k3"]
|
||||
[ext_resource type="Texture2D" uid="uid://waqbwo2r33j3" path="res://assets/游戏UI/小提示.webp" id="5_5b81d"]
|
||||
@@ -31,6 +32,7 @@
|
||||
[ext_resource type="PackedScene" uid="uid://j4ft87o7jk14" path="res://Scene/BigPanel/ItemStorePanel.tscn" id="21_uhubb"]
|
||||
[ext_resource type="PackedScene" uid="uid://cw8am7nnbgca5" path="res://Scene/Pet/PetFightPanel.tscn" id="23_n03md"]
|
||||
[ext_resource type="Script" uid="uid://bdhwvqsmakna2" path="res://Script/BigPanel/PetBagPanel.gd" id="23_uc6q1"]
|
||||
[ext_resource type="Script" uid="uid://bdavskipn547h" path="res://Script/BigPanel/PlayerStorePanel.gd" id="24_dygid"]
|
||||
[ext_resource type="PackedScene" uid="uid://cnjidcwuv4nn4" path="res://Scene/BigPanel/PetStorePanel.tscn" id="24_uc6q1"]
|
||||
[ext_resource type="PackedScene" uid="uid://d3i0l6ysrde6o" path="res://Scene/SmallPanel/AccountSettingPanel.tscn" id="26_uc6q1"]
|
||||
[ext_resource type="PackedScene" uid="uid://d1lu2yg4xl382" path="res://Scene/SmallPanel/LoadProgressPanel.tscn" id="27_vygm6"]
|
||||
@@ -46,31 +48,33 @@
|
||||
[ext_resource type="PackedScene" uid="uid://ibl5wbbw3pwc" path="res://CopyItems/item_button.tscn" id="39_cdkxt"]
|
||||
[ext_resource type="Script" uid="uid://dwf28j01ckg3y" path="res://Script/SmallPanel/WisdomTreePanel.gd" id="39_np7ck"]
|
||||
[ext_resource type="Texture2D" uid="uid://bt1i2yhhlor5e" path="res://assets/地块/土块1.webp" id="41_cdkxt"]
|
||||
[ext_resource type="Script" uid="uid://b185o1hjnlrv5" path="res://Script/SmallPanel/CropInformPanel.gd" id="41_iluto"]
|
||||
[ext_resource type="Texture2D" uid="uid://3ff2lnbc0op7" path="res://assets/稻草人图片/稻草人1.webp" id="43_6rkns"]
|
||||
[ext_resource type="Script" uid="uid://dsmmxivba06ab" path="res://Script/Dialog/BatchSellPopup.gd" id="44_av1bx"]
|
||||
[ext_resource type="Texture2D" uid="uid://cbdm5e6s8bf6l" path="res://assets/智慧树图片/智慧树4.webp" id="45_xvovi"]
|
||||
[ext_resource type="Script" uid="uid://cha0uw4ra1trr" path="res://Script/Dialog/AddProduct2StorePopup.gd" id="46_8d602"]
|
||||
[ext_resource type="Texture2D" uid="uid://dilipbs0lncpd" path="res://assets/草地图片/草地10.webp" id="48_2i8fe"]
|
||||
[ext_resource type="Texture2D" uid="uid://du34yctd8bd8m" path="res://assets/灌木丛图片/灌木丛1.webp" id="49_xjiif"]
|
||||
[ext_resource type="Texture2D" uid="uid://dswjorjhf1i6f" path="res://assets/灌木丛图片/灌木丛2.webp" id="50_sqnmr"]
|
||||
[ext_resource type="Texture2D" uid="uid://go3n3qnpancf" path="res://assets/灌木丛图片/灌木丛3.webp" id="51_2i8fe"]
|
||||
[ext_resource type="Texture2D" uid="uid://dk4yl4ghmxaa2" path="res://assets/天气系统图片/雪花.webp" id="53_4ka7t"]
|
||||
[ext_resource type="PackedScene" uid="uid://cvg38nsrm77jy" path="res://Scene/Particle/WillowLeafRain.tscn" id="53_nf3jg"]
|
||||
[ext_resource type="Texture2D" uid="uid://chcgrmluhfxuk" path="res://assets/天气系统图片/樱花1.webp" id="53_tdq2s"]
|
||||
[ext_resource type="Texture2D" uid="uid://c1qqalp7owgy2" path="res://assets/天气系统图片/栀子花1.webp" id="53_xyeuq"]
|
||||
[ext_resource type="Texture2D" uid="uid://b7g5ut03rm53n" path="res://assets/装饰物图片/小卖部.webp" id="54_06tja"]
|
||||
[ext_resource type="Texture2D" uid="uid://dfkgmj7e0555q" path="res://assets/天气系统图片/樱花2.webp" id="54_dygjy"]
|
||||
[ext_resource type="Texture2D" uid="uid://bfducebx4c4il" path="res://assets/天气系统图片/柳叶3.webp" id="54_jiccn"]
|
||||
[ext_resource type="Texture2D" uid="uid://cd7x78uyi2csh" path="res://assets/天气系统图片/栀子花2.webp" id="54_t4s8j"]
|
||||
[ext_resource type="Texture2D" uid="uid://dl58ie2lneq77" path="res://assets/天气系统图片/柳叶1.webp" id="55_e8wx8"]
|
||||
[ext_resource type="Texture2D" uid="uid://q0difb6wjkgm" path="res://assets/天气系统图片/樱花3.webp" id="55_edvcq"]
|
||||
[ext_resource type="Texture2D" uid="uid://j3h0ocagxf8" path="res://assets/装饰物图片/种子商店.webp" id="55_g4i0f"]
|
||||
[ext_resource type="Texture2D" uid="uid://cqqyc3ddwtvpn" path="res://assets/天气系统图片/栀子花3.webp" id="55_iluto"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_5dq3w"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_nf3jg"]
|
||||
[ext_resource type="Texture2D" uid="uid://d4e54gh5iccul" path="res://assets/装饰物图片/道具商店.webp" id="56_rlmnt"]
|
||||
[ext_resource type="Texture2D" uid="uid://deow5dqdm412v" path="res://assets/装饰物图片/宠物商店.webp" id="57_rlmnt"]
|
||||
[ext_resource type="Script" uid="uid://o4mcuqoivqri" path="res://GameManager/WeatherSystem.gd" id="62_uyv6e"]
|
||||
[ext_resource type="Texture2D" uid="uid://bnv6wb0k443fv" path="res://assets/天气系统图片/柳叶2.webp" id="69_uyv6e"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_adtqp"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_4ka7t"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_n03md"]
|
||||
border_width_left = 5
|
||||
border_width_top = 5
|
||||
@@ -83,6 +87,18 @@ corner_radius_bottom_left = 20
|
||||
corner_detail = 20
|
||||
shadow_size = 20
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_8d602"]
|
||||
border_width_left = 5
|
||||
border_width_top = 5
|
||||
border_width_right = 5
|
||||
border_width_bottom = 5
|
||||
corner_radius_top_left = 20
|
||||
corner_radius_top_right = 20
|
||||
corner_radius_bottom_right = 20
|
||||
corner_radius_bottom_left = 20
|
||||
corner_detail = 20
|
||||
shadow_size = 20
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_5b81d"]
|
||||
border_width_left = 10
|
||||
border_width_top = 10
|
||||
@@ -116,10 +132,22 @@ corner_radius_bottom_left = 20
|
||||
corner_detail = 20
|
||||
shadow_size = 30
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_xyeuq"]
|
||||
border_width_left = 15
|
||||
border_width_top = 15
|
||||
border_width_right = 15
|
||||
border_width_bottom = 15
|
||||
corner_detail = 20
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_t4s8j"]
|
||||
border_width_left = 15
|
||||
border_width_top = 15
|
||||
border_width_right = 15
|
||||
border_width_bottom = 15
|
||||
|
||||
[sub_resource type="Environment" id="Environment_m6fch"]
|
||||
background_mode = 3
|
||||
ambient_light_energy = 0.0
|
||||
glow_enabled = true
|
||||
glow_intensity = 1.0
|
||||
glow_bloom = 0.3
|
||||
glow_blend_mode = 0
|
||||
@@ -164,6 +192,18 @@ turbulence_noise_speed = Vector3(10, 0, 0)
|
||||
turbulence_influence_min = 0.02
|
||||
turbulence_influence_max = 0.07
|
||||
|
||||
[sub_resource type="ParticleProcessMaterial" id="ParticleProcessMaterial_6fhdl"]
|
||||
particle_flag_disable_z = true
|
||||
emission_shape = 3
|
||||
emission_box_extents = Vector3(1000, 1, 1)
|
||||
gravity = Vector3(-30, 80, 0)
|
||||
scale_min = 0.4
|
||||
scale_max = 0.5
|
||||
turbulence_enabled = true
|
||||
turbulence_noise_speed = Vector3(10, 0, 0)
|
||||
turbulence_influence_min = 0.02
|
||||
turbulence_influence_max = 0.07
|
||||
|
||||
[sub_resource type="ParticleProcessMaterial" id="ParticleProcessMaterial_e8wx8"]
|
||||
particle_flag_disable_z = true
|
||||
emission_shape = 3
|
||||
@@ -243,7 +283,7 @@ anchors_preset = 0
|
||||
|
||||
[node name="GameInfoHBox1" type="HBoxContainer" parent="UI/GUI"]
|
||||
layout_mode = 0
|
||||
offset_right = 1400.0
|
||||
offset_right = 1339.0
|
||||
offset_bottom = 35.0
|
||||
|
||||
[node name="experience_image" type="TextureRect" parent="UI/GUI/GameInfoHBox1"]
|
||||
@@ -261,8 +301,10 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "经验:999"
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="level_image" type="TextureRect" parent="UI/GUI/GameInfoHBox1"]
|
||||
layout_mode = 2
|
||||
@@ -278,6 +320,7 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "等级:100"
|
||||
|
||||
@@ -295,6 +338,7 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "钱币:999"
|
||||
|
||||
@@ -312,6 +356,7 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "体力值:20"
|
||||
|
||||
@@ -329,13 +374,14 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "点赞数:0"
|
||||
|
||||
[node name="GameInfoHBox2" type="HBoxContainer" parent="UI/GUI"]
|
||||
layout_mode = 0
|
||||
offset_top = 35.0
|
||||
offset_right = 1400.0
|
||||
offset_right = 1336.0
|
||||
offset_bottom = 70.0
|
||||
|
||||
[node name="player_name_image" type="TextureRect" parent="UI/GUI/GameInfoHBox2"]
|
||||
@@ -352,8 +398,9 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "玩家昵称:树萌芽"
|
||||
text = "玩家昵称:树萌芽"
|
||||
|
||||
[node name="farm_name_image" type="TextureRect" parent="UI/GUI/GameInfoHBox2"]
|
||||
layout_mode = 2
|
||||
@@ -369,6 +416,7 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "农场名称:树萌芽的农场"
|
||||
|
||||
@@ -385,6 +433,7 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "服务器状态:正在检测中"
|
||||
|
||||
@@ -402,31 +451,15 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "FPS:0"
|
||||
|
||||
[node name="onlineplayer_image" type="TextureRect" parent="UI/GUI/GameInfoHBox2"]
|
||||
layout_mode = 2
|
||||
texture = ExtResource("10_vygm6")
|
||||
expand_mode = 2
|
||||
|
||||
[node name="onlineplayer" type="Label" parent="UI/GUI/GameInfoHBox2"]
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_color = Color(0.423529, 1, 0.533333, 1)
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "检测中..."
|
||||
|
||||
[node name="GameInfoHBox3" type="HBoxContainer" parent="UI/GUI"]
|
||||
layout_mode = 0
|
||||
offset_top = 70.0
|
||||
offset_right = 1400.0
|
||||
offset_bottom = 105.0
|
||||
offset_right = 1335.0
|
||||
offset_bottom = 113.0
|
||||
|
||||
[node name="tip_image" type="TextureRect" parent="UI/GUI/GameInfoHBox3"]
|
||||
layout_mode = 2
|
||||
@@ -442,6 +475,7 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "游戏小提示"
|
||||
|
||||
@@ -460,6 +494,7 @@ theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "全服大喇叭"
|
||||
vertical_alignment = 1
|
||||
@@ -473,6 +508,24 @@ theme_override_constants/outline_size = 10
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "查看"
|
||||
|
||||
[node name="onlineplayer_image" type="TextureRect" parent="UI/GUI/GameInfoHBox3"]
|
||||
layout_mode = 2
|
||||
texture = ExtResource("10_vygm6")
|
||||
expand_mode = 2
|
||||
|
||||
[node name="onlineplayer" type="Label" parent="UI/GUI/GameInfoHBox3"]
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_color = Color(0.423529, 1, 0.533333, 1)
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 10
|
||||
theme_override_constants/shadow_outline_size = 10
|
||||
theme_override_fonts/font = ExtResource("3_t4s8j")
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "检测中..."
|
||||
|
||||
[node name="FarmVBox" type="VBoxContainer" parent="UI/GUI"]
|
||||
layout_mode = 0
|
||||
offset_left = 4.0
|
||||
@@ -483,6 +536,7 @@ scale = Vector2(0.8, 0.8)
|
||||
alignment = 2
|
||||
|
||||
[node name="SeedStoreButton" type="Button" parent="UI/GUI/FarmVBox"]
|
||||
visible = false
|
||||
modulate = Color(1, 0.564706, 0.647059, 1)
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 40
|
||||
@@ -501,6 +555,7 @@ theme_override_font_sizes/font_size = 40
|
||||
text = "作物仓库"
|
||||
|
||||
[node name="ItemStoreButton" type="Button" parent="UI/GUI/FarmVBox"]
|
||||
visible = false
|
||||
modulate = Color(0.231373, 0.772549, 1, 1)
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 40
|
||||
@@ -560,6 +615,13 @@ offset_bottom = 408.0
|
||||
scale = Vector2(0.8, 0.8)
|
||||
alignment = 2
|
||||
|
||||
[node name="MyStoreButton" type="Button" parent="UI/GUI/OtherVBox"]
|
||||
visible = false
|
||||
modulate = Color(0.917346, 0.737213, 1, 1)
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 40
|
||||
text = "我的小卖部"
|
||||
|
||||
[node name="AccountSettingButton" type="Button" parent="UI/GUI/OtherVBox"]
|
||||
modulate = Color(0.843137, 0.772549, 1, 1)
|
||||
layout_mode = 2
|
||||
@@ -636,6 +698,7 @@ theme_override_font_sizes/font_size = 40
|
||||
text = "宠物背包"
|
||||
|
||||
[node name="PetStoreButton" type="Button" parent="UI/GUI/OtherVBox"]
|
||||
visible = false
|
||||
modulate = Color(0.992157, 0.482353, 0.870588, 1)
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 40
|
||||
@@ -650,22 +713,6 @@ text = "稻草人"
|
||||
|
||||
[node name="BigPanel" type="CanvasLayer" parent="UI"]
|
||||
|
||||
[node name="LuckyDrawPanel" parent="UI/BigPanel" instance=ExtResource("17_f21le")]
|
||||
visible = false
|
||||
offset_left = 425.0
|
||||
offset_top = 2.0
|
||||
offset_right = 1025.0
|
||||
offset_bottom = 722.0
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_5dq3w")
|
||||
|
||||
[node name="DailyCheckInPanel" parent="UI/BigPanel" instance=ExtResource("18_m6fch")]
|
||||
visible = false
|
||||
offset_left = 442.0
|
||||
offset_top = 3.0
|
||||
offset_right = 1042.0
|
||||
offset_bottom = 723.0
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_nf3jg")
|
||||
|
||||
[node name="TCPNetworkManagerPanel" parent="UI/BigPanel" instance=ExtResource("7_401ut")]
|
||||
visible = false
|
||||
offset_top = 97.0
|
||||
@@ -688,15 +735,6 @@ offset_bottom = 797.0
|
||||
|
||||
[node name="CropWarehousePanel" parent="UI/BigPanel" instance=ExtResource("18_5b81d")]
|
||||
|
||||
[node name="LoginPanel" parent="UI/BigPanel" instance=ExtResource("11_6jgly")]
|
||||
visible = false
|
||||
top_level = true
|
||||
offset_left = 342.0
|
||||
offset_top = 40.0
|
||||
offset_right = 1092.0
|
||||
offset_bottom = 700.0
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_4ka7t")
|
||||
|
||||
[node name="PlayerBagPanel" parent="UI/BigPanel" instance=ExtResource("19_8kysg")]
|
||||
visible = false
|
||||
|
||||
@@ -706,6 +744,88 @@ visible = false
|
||||
[node name="ItemBagPanel" parent="UI/BigPanel" instance=ExtResource("20_n03md")]
|
||||
visible = false
|
||||
|
||||
[node name="PlayerStorePanel" type="Panel" parent="UI/BigPanel"]
|
||||
visible = false
|
||||
offset_left = 69.0
|
||||
offset_top = 56.0
|
||||
offset_right = 1635.0
|
||||
offset_bottom = 836.0
|
||||
scale = Vector2(0.8, 0.8)
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_n03md")
|
||||
script = ExtResource("24_dygid")
|
||||
|
||||
[node name="TMBackGround" type="ColorRect" parent="UI/BigPanel/PlayerStorePanel"]
|
||||
layout_mode = 0
|
||||
offset_left = -90.0
|
||||
offset_top = -71.0
|
||||
offset_right = 1672.0
|
||||
offset_bottom = 831.0
|
||||
color = Color(1, 1, 1, 0)
|
||||
|
||||
[node name="ScrollContainer" type="ScrollContainer" parent="UI/BigPanel/PlayerStorePanel"]
|
||||
layout_mode = 2
|
||||
offset_left = 28.0
|
||||
offset_top = 95.0
|
||||
offset_right = 3805.0
|
||||
offset_bottom = 1723.0
|
||||
scale = Vector2(0.4, 0.4)
|
||||
size_flags_vertical = 3
|
||||
horizontal_scroll_mode = 0
|
||||
|
||||
[node name="Store_Grid" type="GridContainer" parent="UI/BigPanel/PlayerStorePanel/ScrollContainer"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 6
|
||||
size_flags_vertical = 3
|
||||
columns = 8
|
||||
|
||||
[node name="Title" type="Label" parent="UI/BigPanel/PlayerStorePanel"]
|
||||
layout_mode = 2
|
||||
offset_right = 1566.0
|
||||
offset_bottom = 69.0
|
||||
size_flags_horizontal = 3
|
||||
theme_override_colors/font_color = Color(1, 1, 0.807843, 1)
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 4
|
||||
theme_override_constants/shadow_offset_y = 4
|
||||
theme_override_constants/outline_size = 15
|
||||
theme_override_constants/shadow_outline_size = 15
|
||||
theme_override_font_sizes/font_size = 50
|
||||
text = "玩家小卖部"
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="QuitButton" type="Button" parent="UI/BigPanel/PlayerStorePanel"]
|
||||
custom_minimum_size = Vector2(60, 60)
|
||||
layout_mode = 2
|
||||
offset_left = 1478.75
|
||||
offset_top = 20.0
|
||||
offset_right = 1538.75
|
||||
offset_bottom = 83.0
|
||||
theme_override_font_sizes/font_size = 40
|
||||
text = "X"
|
||||
|
||||
[node name="RefreshButton" type="Button" parent="UI/BigPanel/PlayerStorePanel"]
|
||||
custom_minimum_size = Vector2(60, 60)
|
||||
layout_mode = 2
|
||||
offset_left = 27.5
|
||||
offset_top = 16.25
|
||||
offset_right = 115.5
|
||||
offset_bottom = 79.25
|
||||
theme_override_font_sizes/font_size = 40
|
||||
text = "刷新"
|
||||
|
||||
[node name="BuyProductBoothButton" type="Button" parent="UI/BigPanel/PlayerStorePanel"]
|
||||
custom_minimum_size = Vector2(60, 60)
|
||||
layout_mode = 2
|
||||
offset_left = 207.5
|
||||
offset_top = 17.5
|
||||
offset_right = 535.5
|
||||
offset_bottom = 80.5
|
||||
theme_override_font_sizes/font_size = 40
|
||||
text = "购买商品摊位"
|
||||
|
||||
[node name="PetStorePanel" parent="UI/BigPanel" instance=ExtResource("24_uc6q1")]
|
||||
visible = false
|
||||
|
||||
@@ -718,7 +838,7 @@ offset_bottom = 836.0
|
||||
scale = Vector2(0.8, 0.8)
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_n03md")
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_8d602")
|
||||
script = ExtResource("23_uc6q1")
|
||||
|
||||
[node name="TMBackGround" type="ColorRect" parent="UI/BigPanel/PetBagPanel"]
|
||||
@@ -784,6 +904,14 @@ text = "刷新"
|
||||
[node name="PetFightPanel" parent="UI/BigPanel" instance=ExtResource("23_n03md")]
|
||||
visible = false
|
||||
|
||||
[node name="DailyCheckInPanel" parent="UI/BigPanel" instance=ExtResource("18_m6fch")]
|
||||
visible = false
|
||||
|
||||
[node name="LuckyDrawPanel" parent="UI/BigPanel" instance=ExtResource("17_f21le")]
|
||||
visible = false
|
||||
|
||||
[node name="LoginPanel" parent="UI/BigPanel" instance=ExtResource("11_6jgly")]
|
||||
|
||||
[node name="SmallPanel" type="CanvasLayer" parent="UI"]
|
||||
|
||||
[node name="LoadProgressPanel" parent="UI/SmallPanel" instance=ExtResource("27_vygm6")]
|
||||
@@ -1450,6 +1578,101 @@ offset_top = 166.0
|
||||
offset_right = 979.0
|
||||
offset_bottom = 482.0
|
||||
|
||||
[node name="CropInformPanel" type="Panel" parent="UI/SmallPanel"]
|
||||
visible = false
|
||||
offset_left = 330.0
|
||||
offset_right = 958.0
|
||||
offset_bottom = 723.0
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_xyeuq")
|
||||
script = ExtResource("41_iluto")
|
||||
|
||||
[node name="Title" type="Label" parent="UI/SmallPanel/CropInformPanel"]
|
||||
layout_mode = 0
|
||||
offset_top = 17.0
|
||||
offset_right = 628.0
|
||||
offset_bottom = 74.0
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 4
|
||||
theme_override_constants/shadow_offset_y = 4
|
||||
theme_override_constants/outline_size = 20
|
||||
theme_override_constants/shadow_outline_size = 20
|
||||
theme_override_font_sizes/font_size = 35
|
||||
text = "作物信息"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="QuitButton" type="Button" parent="UI/SmallPanel/CropInformPanel"]
|
||||
custom_minimum_size = Vector2(50, 50)
|
||||
layout_mode = 0
|
||||
offset_left = 561.0
|
||||
offset_top = 17.0
|
||||
offset_right = 611.0
|
||||
offset_bottom = 67.0
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "X"
|
||||
|
||||
[node name="VBox" type="VBoxContainer" parent="UI/SmallPanel/CropInformPanel"]
|
||||
layout_mode = 0
|
||||
offset_left = 17.0
|
||||
offset_top = 74.0
|
||||
offset_right = 615.0
|
||||
offset_bottom = 708.0
|
||||
|
||||
[node name="CropImage" type="TextureRect" parent="UI/SmallPanel/CropInformPanel/VBox"]
|
||||
layout_mode = 2
|
||||
texture = ExtResource("31_uc6q1")
|
||||
stretch_mode = 3
|
||||
|
||||
[node name="CropName" type="Label" parent="UI/SmallPanel/CropInformPanel/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "名称:"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="CropDescription" type="Label" parent="UI/SmallPanel/CropInformPanel/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "描述:"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="CropPrice" type="Label" parent="UI/SmallPanel/CropInformPanel/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "收购价:"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="CropQuality" type="Label" parent="UI/SmallPanel/CropInformPanel/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 25
|
||||
text = "品质:"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="HBox" type="HBoxContainer" parent="UI/SmallPanel/CropInformPanel/VBox"]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 10
|
||||
alignment = 1
|
||||
|
||||
[node name="SaleProduct" type="Button" parent="UI/SmallPanel/CropInformPanel/VBox/HBox"]
|
||||
custom_minimum_size = Vector2(120, 70)
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 10
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "直接出售"
|
||||
|
||||
[node name="AddToStore" type="Button" parent="UI/SmallPanel/CropInformPanel/VBox/HBox"]
|
||||
custom_minimum_size = Vector2(120, 70)
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 10
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "放入小卖部"
|
||||
|
||||
[node name="DiaLog" type="CanvasLayer" parent="UI"]
|
||||
|
||||
[node name="AcceptDialog" parent="UI/DiaLog" instance=ExtResource("16_0igvr")]
|
||||
@@ -1461,6 +1684,7 @@ offset_left = 426.0
|
||||
offset_top = 90.0
|
||||
offset_right = 928.0
|
||||
offset_bottom = 556.0
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_t4s8j")
|
||||
script = ExtResource("29_5b81d")
|
||||
|
||||
[node name="VBox" type="VBoxContainer" parent="UI/DiaLog/BatchBuyPopup"]
|
||||
@@ -1499,6 +1723,145 @@ size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "取消"
|
||||
|
||||
[node name="BatchSellPopup" type="PanelContainer" parent="UI/DiaLog"]
|
||||
visible = false
|
||||
offset_left = 391.0
|
||||
offset_top = 95.0
|
||||
offset_right = 893.0
|
||||
offset_bottom = 561.0
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_t4s8j")
|
||||
script = ExtResource("44_av1bx")
|
||||
|
||||
[node name="VBox" type="VBoxContainer" parent="UI/DiaLog/BatchSellPopup"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Title" type="Label" parent="UI/DiaLog/BatchSellPopup/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 20
|
||||
theme_override_constants/shadow_outline_size = 20
|
||||
theme_override_font_sizes/font_size = 40
|
||||
text = "请选择出售数量"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="Contents" type="Label" parent="UI/DiaLog/BatchSellPopup/VBox"]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
theme_override_font_sizes/font_size = 20
|
||||
text = "这是说明内容"
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="SellNumEdit" type="LineEdit" parent="UI/DiaLog/BatchSellPopup/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
|
||||
[node name="HBox" type="HBoxContainer" parent="UI/DiaLog/BatchSellPopup/VBox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="SureButton" type="Button" parent="UI/DiaLog/BatchSellPopup/VBox/HBox"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "确定"
|
||||
|
||||
[node name="CancelButton" type="Button" parent="UI/DiaLog/BatchSellPopup/VBox/HBox"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "取消"
|
||||
|
||||
[node name="AddProductToStorePopup" type="PanelContainer" parent="UI/DiaLog"]
|
||||
visible = false
|
||||
offset_left = 426.0
|
||||
offset_top = 59.0
|
||||
offset_right = 1026.0
|
||||
offset_bottom = 559.0
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_t4s8j")
|
||||
script = ExtResource("46_8d602")
|
||||
|
||||
[node name="VBox" type="VBoxContainer" parent="UI/DiaLog/AddProductToStorePopup"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Title" type="Label" parent="UI/DiaLog/AddProductToStorePopup/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 20
|
||||
theme_override_constants/shadow_outline_size = 20
|
||||
theme_override_font_sizes/font_size = 40
|
||||
text = "弹窗标题"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="Contents" type="Label" parent="UI/DiaLog/AddProductToStorePopup/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_color = Color(0.762404, 0.762404, 0.762404, 1)
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 20
|
||||
theme_override_constants/shadow_outline_size = 20
|
||||
theme_override_font_sizes/font_size = 24
|
||||
text = "弹窗内容"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="SellNum" type="Label" parent="UI/DiaLog/AddProductToStorePopup/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 20
|
||||
theme_override_constants/shadow_outline_size = 20
|
||||
theme_override_font_sizes/font_size = 24
|
||||
text = "请选择售卖的数量"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="SellNumInput" type="LineEdit" parent="UI/DiaLog/AddProductToStorePopup/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
|
||||
[node name="SellPrice" type="Label" parent="UI/DiaLog/AddProductToStorePopup/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 3
|
||||
theme_override_constants/shadow_offset_y = 3
|
||||
theme_override_constants/outline_size = 20
|
||||
theme_override_constants/shadow_outline_size = 20
|
||||
theme_override_font_sizes/font_size = 24
|
||||
text = "请选择售卖的价格"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="SellPriceInput" type="LineEdit" parent="UI/DiaLog/AddProductToStorePopup/VBox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
|
||||
[node name="HBox" type="HBoxContainer" parent="UI/DiaLog/AddProductToStorePopup/VBox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="SureButton" type="Button" parent="UI/DiaLog/AddProductToStorePopup/VBox/HBox"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "确定"
|
||||
|
||||
[node name="CancelButton" type="Button" parent="UI/DiaLog/AddProductToStorePopup/VBox/HBox"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "取消"
|
||||
|
||||
[node name="BackgroundUI" type="CanvasLayer" parent="."]
|
||||
layer = -1
|
||||
|
||||
@@ -2991,7 +3354,7 @@ autowrap_mode = 2
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="Decoration1" type="Button" parent="Decoration"]
|
||||
[node name="PlayerStore" type="Button" parent="Decoration"]
|
||||
self_modulate = Color(1, 1, 1, 0)
|
||||
custom_minimum_size = Vector2(100, 100)
|
||||
offset_left = 122.0
|
||||
@@ -3000,18 +3363,17 @@ offset_right = 386.0
|
||||
offset_bottom = 156.0
|
||||
scale = Vector2(0.4, 0.4)
|
||||
|
||||
[node name="GrassGroundImage" type="Sprite2D" parent="Decoration/Decoration1"]
|
||||
[node name="GrassGroundImage" type="Sprite2D" parent="Decoration/PlayerStore"]
|
||||
position = Vector2(132, 134)
|
||||
scale = Vector2(1.4, 1.4)
|
||||
texture = ExtResource("48_2i8fe")
|
||||
|
||||
[node name="Image" type="Sprite2D" parent="Decoration/Decoration1"]
|
||||
position = Vector2(132, 48)
|
||||
scale = Vector2(1.2, 1.2)
|
||||
texture = ExtResource("49_xjiif")
|
||||
[node name="Image" type="Sprite2D" parent="Decoration/PlayerStore"]
|
||||
position = Vector2(140, 57.5)
|
||||
scale = Vector2(1.5, 1.5)
|
||||
texture = ExtResource("54_06tja")
|
||||
|
||||
[node name="Name" type="RichTextLabel" parent="Decoration/Decoration1"]
|
||||
visible = false
|
||||
[node name="Name" type="RichTextLabel" parent="Decoration/PlayerStore"]
|
||||
layout_mode = 0
|
||||
offset_left = -65.0
|
||||
offset_top = -145.0
|
||||
@@ -3023,11 +3385,11 @@ theme_override_font_sizes/mono_font_size = 40
|
||||
theme_override_font_sizes/normal_font_size = 40
|
||||
theme_override_font_sizes/bold_font_size = 40
|
||||
bbcode_enabled = true
|
||||
text = "稻草人"
|
||||
text = "小卖部"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="Decoration2" type="Button" parent="Decoration"]
|
||||
[node name="SeedStore" type="Button" parent="Decoration"]
|
||||
self_modulate = Color(1, 1, 1, 0)
|
||||
custom_minimum_size = Vector2(100, 100)
|
||||
offset_left = 244.0
|
||||
@@ -3036,18 +3398,17 @@ offset_right = 508.0
|
||||
offset_bottom = 156.0
|
||||
scale = Vector2(0.4, 0.4)
|
||||
|
||||
[node name="GrassGroundImage" type="Sprite2D" parent="Decoration/Decoration2"]
|
||||
[node name="GrassGroundImage" type="Sprite2D" parent="Decoration/SeedStore"]
|
||||
position = Vector2(132, 134)
|
||||
scale = Vector2(1.4, 1.4)
|
||||
texture = ExtResource("48_2i8fe")
|
||||
|
||||
[node name="Image" type="Sprite2D" parent="Decoration/Decoration2"]
|
||||
[node name="Image" type="Sprite2D" parent="Decoration/SeedStore"]
|
||||
position = Vector2(132, 48)
|
||||
scale = Vector2(1.2, 1.2)
|
||||
texture = ExtResource("50_sqnmr")
|
||||
scale = Vector2(1.5, 1.5)
|
||||
texture = ExtResource("55_g4i0f")
|
||||
|
||||
[node name="Name" type="RichTextLabel" parent="Decoration/Decoration2"]
|
||||
visible = false
|
||||
[node name="Name" type="RichTextLabel" parent="Decoration/SeedStore"]
|
||||
layout_mode = 0
|
||||
offset_left = -65.0
|
||||
offset_top = -145.0
|
||||
@@ -3059,11 +3420,11 @@ theme_override_font_sizes/mono_font_size = 40
|
||||
theme_override_font_sizes/normal_font_size = 40
|
||||
theme_override_font_sizes/bold_font_size = 40
|
||||
bbcode_enabled = true
|
||||
text = "稻草人"
|
||||
text = "种子商店"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="Decoration3" type="Button" parent="Decoration"]
|
||||
[node name="ItemStore" type="Button" parent="Decoration"]
|
||||
self_modulate = Color(1, 1, 1, 0)
|
||||
custom_minimum_size = Vector2(100, 100)
|
||||
offset_left = 366.0
|
||||
@@ -3072,18 +3433,17 @@ offset_right = 630.0
|
||||
offset_bottom = 156.0
|
||||
scale = Vector2(0.4, 0.4)
|
||||
|
||||
[node name="GrassGroundImage" type="Sprite2D" parent="Decoration/Decoration3"]
|
||||
[node name="GrassGroundImage" type="Sprite2D" parent="Decoration/ItemStore"]
|
||||
position = Vector2(132, 134)
|
||||
scale = Vector2(1.4, 1.4)
|
||||
texture = ExtResource("48_2i8fe")
|
||||
|
||||
[node name="Image" type="Sprite2D" parent="Decoration/Decoration3"]
|
||||
[node name="Image" type="Sprite2D" parent="Decoration/ItemStore"]
|
||||
position = Vector2(132, 48)
|
||||
scale = Vector2(1.2, 1.2)
|
||||
texture = ExtResource("51_2i8fe")
|
||||
scale = Vector2(1.5, 1.5)
|
||||
texture = ExtResource("56_rlmnt")
|
||||
|
||||
[node name="Name" type="RichTextLabel" parent="Decoration/Decoration3"]
|
||||
visible = false
|
||||
[node name="Name" type="RichTextLabel" parent="Decoration/ItemStore"]
|
||||
layout_mode = 0
|
||||
offset_left = -65.0
|
||||
offset_top = -145.0
|
||||
@@ -3095,11 +3455,11 @@ theme_override_font_sizes/mono_font_size = 40
|
||||
theme_override_font_sizes/normal_font_size = 40
|
||||
theme_override_font_sizes/bold_font_size = 40
|
||||
bbcode_enabled = true
|
||||
text = "稻草人"
|
||||
text = "道具商店"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="Decoration4" type="Button" parent="Decoration"]
|
||||
[node name="PetStore" type="Button" parent="Decoration"]
|
||||
self_modulate = Color(1, 1, 1, 0)
|
||||
custom_minimum_size = Vector2(100, 100)
|
||||
offset_left = 488.0
|
||||
@@ -3108,18 +3468,17 @@ offset_right = 752.0
|
||||
offset_bottom = 156.0
|
||||
scale = Vector2(0.4, 0.4)
|
||||
|
||||
[node name="GrassGroundImage" type="Sprite2D" parent="Decoration/Decoration4"]
|
||||
[node name="GrassGroundImage" type="Sprite2D" parent="Decoration/PetStore"]
|
||||
position = Vector2(132, 134)
|
||||
scale = Vector2(1.4, 1.4)
|
||||
texture = ExtResource("48_2i8fe")
|
||||
|
||||
[node name="Image" type="Sprite2D" parent="Decoration/Decoration4"]
|
||||
[node name="Image" type="Sprite2D" parent="Decoration/PetStore"]
|
||||
position = Vector2(132, 48)
|
||||
scale = Vector2(1.2, 1.2)
|
||||
texture = ExtResource("50_sqnmr")
|
||||
scale = Vector2(1.5, 1.5)
|
||||
texture = ExtResource("57_rlmnt")
|
||||
|
||||
[node name="Name" type="RichTextLabel" parent="Decoration/Decoration4"]
|
||||
visible = false
|
||||
[node name="Name" type="RichTextLabel" parent="Decoration/PetStore"]
|
||||
layout_mode = 0
|
||||
offset_left = -65.0
|
||||
offset_top = -145.0
|
||||
@@ -3131,7 +3490,7 @@ theme_override_font_sizes/mono_font_size = 40
|
||||
theme_override_font_sizes/normal_font_size = 40
|
||||
theme_override_font_sizes/bold_font_size = 40
|
||||
bbcode_enabled = true
|
||||
text = "稻草人"
|
||||
text = "宠物商店"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
@@ -4344,9 +4703,11 @@ horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="WeatherSystem" type="Node2D" parent="."]
|
||||
script = ExtResource("62_uyv6e")
|
||||
|
||||
[node name="CherryBlossomRain" type="Node2D" parent="WeatherSystem"]
|
||||
visible = false
|
||||
z_index = 10
|
||||
position = Vector2(934, -469)
|
||||
|
||||
[node name="CherryBlossomRain1" type="GPUParticles2D" parent="WeatherSystem/CherryBlossomRain"]
|
||||
@@ -4383,6 +4744,8 @@ visibility_rect = Rect2(-900, 0, 2300, 2000)
|
||||
process_material = SubResource("ParticleProcessMaterial_tdq2s")
|
||||
|
||||
[node name="GardeniaRain" type="Node2D" parent="WeatherSystem"]
|
||||
visible = false
|
||||
z_index = 10
|
||||
position = Vector2(759, -370)
|
||||
|
||||
[node name="WillowLeafRain1" type="GPUParticles2D" parent="WeatherSystem/GardeniaRain"]
|
||||
@@ -4417,13 +4780,20 @@ process_material = SubResource("ParticleProcessMaterial_dygjy")
|
||||
|
||||
[node name="WillowLeafRain" type="Node2D" parent="WeatherSystem"]
|
||||
visible = false
|
||||
z_index = 10
|
||||
position = Vector2(882, -469)
|
||||
|
||||
[node name="WillowLeafRain1" parent="WeatherSystem/WillowLeafRain" instance=ExtResource("53_nf3jg")]
|
||||
visible = false
|
||||
[node name="WillowLeafRain1" type="GPUParticles2D" parent="WeatherSystem/WillowLeafRain"]
|
||||
self_modulate = Color(0.7, 0.7, 0.7, 1)
|
||||
z_index = 10
|
||||
amount = 50
|
||||
texture = ExtResource("69_uyv6e")
|
||||
lifetime = 20.0
|
||||
preprocess = 10.0
|
||||
visibility_rect = Rect2(-900, 0, 2300, 2000)
|
||||
process_material = SubResource("ParticleProcessMaterial_6fhdl")
|
||||
|
||||
[node name="WillowLeafRain2" type="GPUParticles2D" parent="WeatherSystem/WillowLeafRain"]
|
||||
visible = false
|
||||
self_modulate = Color(0.7, 0.7, 0.7, 1)
|
||||
z_index = 10
|
||||
amount = 50
|
||||
@@ -4457,6 +4827,7 @@ process_material = SubResource("ParticleProcessMaterial_jiccn")
|
||||
|
||||
[node name="Snow" type="GPUParticles2D" parent="WeatherSystem"]
|
||||
visible = false
|
||||
z_index = 10
|
||||
position = Vector2(16, -520)
|
||||
amount = 300
|
||||
texture = ExtResource("53_4ka7t")
|
||||
@@ -4478,6 +4849,7 @@ process_material = SubResource("ParticleProcessMaterial_nf3jg")
|
||||
[connection signal="pressed" from="UI/GUI/FarmVBox/AddNewGroundButton" to="." method="_on_add_new_ground_button_pressed"]
|
||||
[connection signal="pressed" from="UI/GUI/VisitVBox/LikeButton" to="." method="_on_like_button_pressed"]
|
||||
[connection signal="pressed" from="UI/GUI/VisitVBox/ReturnMyFarmButton" to="." method="_on_return_my_farm_button_pressed"]
|
||||
[connection signal="pressed" from="UI/GUI/OtherVBox/MyStoreButton" to="." method="_on_my_store_button_pressed"]
|
||||
[connection signal="pressed" from="UI/GUI/OtherVBox/AccountSettingButton" to="." method="_on_account_setting_button_pressed"]
|
||||
[connection signal="pressed" from="UI/GUI/OtherVBox/OnlineGiftButton" to="." method="_on_online_gift_button_pressed"]
|
||||
[connection signal="pressed" from="UI/GUI/OtherVBox/NewPlayerGiftButton" to="." method="_on_new_player_gift_button_pressed"]
|
||||
@@ -4494,6 +4866,10 @@ process_material = SubResource("ParticleProcessMaterial_nf3jg")
|
||||
[connection signal="pressed" from="UI/GUI/OtherVBox/ScareCrowButton" to="." method="_on_my_pet_button_pressed"]
|
||||
[connection signal="pressed" from="UI/SmallPanel/DebugPanel/QuitButton" to="UI/SmallPanel/DebugPanel" method="_on_quit_button_pressed"]
|
||||
[connection signal="pressed" from="Decoration/ScareCrow" to="." method="_on_scare_crow_pressed"]
|
||||
[connection signal="pressed" from="Decoration/PlayerStore" to="." method="_on_player_store_pressed"]
|
||||
[connection signal="pressed" from="Decoration/SeedStore" to="." method="_on_seed_store_pressed"]
|
||||
[connection signal="pressed" from="Decoration/ItemStore" to="." method="_on_item_store_pressed"]
|
||||
[connection signal="pressed" from="Decoration/PetStore" to="." method="_on_pet_store_pressed"]
|
||||
[connection signal="pressed" from="Decoration/WisdomTree" to="." method="_on_wisdom_tree_pressed"]
|
||||
[connection signal="pressed" from="Decoration4/ScareCrow" to="." method="_on_scare_crow_pressed"]
|
||||
[connection signal="pressed" from="Decoration4/WisdomTree" to="." method="_on_wisdom_tree_pressed"]
|
||||
|
||||
@@ -239,6 +239,18 @@ func _on_data_received(data):
|
||||
login_panel._on_verification_code_response(success, message)
|
||||
return
|
||||
|
||||
if message_type == "forget_password_verification_code_response":
|
||||
var success = data.get("success", false)
|
||||
var message = data.get("message", "")
|
||||
login_panel._on_verification_code_response(success, message)
|
||||
return
|
||||
|
||||
if message_type == "reset_password_response":
|
||||
var success = data.get("success", false)
|
||||
var message = data.get("message", "")
|
||||
login_panel._on_forget_password_response_received(success, message)
|
||||
return
|
||||
|
||||
if message_type == "verify_code_response":
|
||||
var success = data.get("success", false)
|
||||
var message = data.get("message", "")
|
||||
@@ -428,6 +440,88 @@ func _on_data_received(data):
|
||||
else:
|
||||
Toast.show(message, Color.RED)
|
||||
|
||||
# 出售作物响应
|
||||
elif action_type == "sell_crop":
|
||||
if success:
|
||||
main_game.money = updated_data["money"]
|
||||
main_game.crop_warehouse = updated_data["作物仓库"]
|
||||
main_game.experience = updated_data.get("experience", main_game.experience)
|
||||
main_game.level = updated_data.get("level", main_game.level)
|
||||
main_game._update_ui()
|
||||
main_game.crop_warehouse_panel.update_crop_warehouse_ui()
|
||||
Toast.show(message, Color.GREEN)
|
||||
else:
|
||||
Toast.show(message, Color.RED)
|
||||
|
||||
# 添加商品到小卖部响应
|
||||
elif action_type == "add_product_to_store":
|
||||
if success:
|
||||
main_game.login_data["玩家小卖部"] = updated_data["玩家小卖部"]
|
||||
main_game.crop_warehouse = updated_data["作物仓库"]
|
||||
|
||||
# 更新UI
|
||||
main_game.crop_warehouse_panel.update_crop_warehouse_ui()
|
||||
var player_store_panel = get_node_or_null("/root/main/UI/BigPanel/PlayerStorePanel")
|
||||
if player_store_panel and player_store_panel.has_method("update_player_store_ui"):
|
||||
player_store_panel.update_player_store_ui()
|
||||
|
||||
Toast.show(message, Color.GREEN)
|
||||
else:
|
||||
Toast.show(message, Color.RED)
|
||||
|
||||
# 下架小卖部商品响应
|
||||
elif action_type == "remove_store_product":
|
||||
if success:
|
||||
main_game.login_data["玩家小卖部"] = updated_data["玩家小卖部"]
|
||||
main_game.crop_warehouse = updated_data["作物仓库"]
|
||||
|
||||
# 更新UI
|
||||
main_game.crop_warehouse_panel.update_crop_warehouse_ui()
|
||||
var player_store_panel = get_node_or_null("/root/main/UI/BigPanel/PlayerStorePanel")
|
||||
if player_store_panel and player_store_panel.has_method("update_player_store_ui"):
|
||||
player_store_panel.update_player_store_ui()
|
||||
|
||||
Toast.show(message, Color.GREEN)
|
||||
else:
|
||||
Toast.show(message, Color.RED)
|
||||
|
||||
# 购买小卖部商品响应
|
||||
elif action_type == "buy_store_product":
|
||||
if success:
|
||||
main_game.money = updated_data["money"]
|
||||
main_game.crop_warehouse = updated_data["作物仓库"]
|
||||
|
||||
# 更新UI
|
||||
main_game._update_ui()
|
||||
main_game.crop_warehouse_panel.update_crop_warehouse_ui()
|
||||
|
||||
# 如果在访问模式下,刷新被访问玩家的小卖部(通过重新请求访问)
|
||||
if main_game.is_visiting_mode:
|
||||
var visited_username = main_game.visited_player_data.get("username", "")
|
||||
if visited_username != "":
|
||||
# 重新访问玩家以刷新数据
|
||||
sendVisitPlayer(visited_username)
|
||||
|
||||
Toast.show(message, Color.GREEN)
|
||||
else:
|
||||
Toast.show(message, Color.RED)
|
||||
|
||||
# 购买小卖部格子响应
|
||||
elif action_type == "buy_store_booth":
|
||||
if success:
|
||||
main_game.money = updated_data["money"]
|
||||
main_game.login_data["小卖部格子数"] = updated_data["小卖部格子数"]
|
||||
|
||||
# 更新UI
|
||||
main_game._update_ui()
|
||||
var player_store_panel = get_node_or_null("/root/main/UI/BigPanel/PlayerStorePanel")
|
||||
if player_store_panel and player_store_panel.has_method("update_player_store_ui"):
|
||||
player_store_panel.update_player_store_ui()
|
||||
|
||||
Toast.show(message, Color.GREEN)
|
||||
else:
|
||||
Toast.show(message, Color.RED)
|
||||
|
||||
return
|
||||
|
||||
# 游戏功能响应消息
|
||||
@@ -502,6 +596,12 @@ func _on_data_received(data):
|
||||
|
||||
elif message_type == "wisdom_tree_config_response":
|
||||
main_game._handle_wisdom_tree_config_response(data)
|
||||
|
||||
# 天气变更消息
|
||||
elif message_type == "weather_change":
|
||||
var weather_type = data.get("weather_type", "clear")
|
||||
var weather_name = data.get("weather_name", "晴天")
|
||||
main_game._handle_weather_change(weather_type, weather_name)
|
||||
# ============================= 客户端与服务端通信核心 =====================================
|
||||
|
||||
|
||||
@@ -771,6 +871,32 @@ func sendVerificationCodeRequest(qq_number):
|
||||
})
|
||||
return true
|
||||
|
||||
#发送忘记密码验证码请求
|
||||
func sendForgetPasswordVerificationCode(qq_number):
|
||||
if not client.is_client_connected():
|
||||
return false
|
||||
|
||||
client.send_data({
|
||||
"type": "request_forget_password_verification_code",
|
||||
"qq_number": qq_number,
|
||||
"timestamp": Time.get_unix_time_from_system()
|
||||
})
|
||||
return true
|
||||
|
||||
#发送忘记密码请求
|
||||
func sendForgetPasswordRequest(username, new_password, verification_code):
|
||||
if not client.is_client_connected():
|
||||
return false
|
||||
|
||||
client.send_data({
|
||||
"type": "reset_password",
|
||||
"username": username,
|
||||
"new_password": new_password,
|
||||
"verification_code": verification_code,
|
||||
"timestamp": Time.get_unix_time_from_system()
|
||||
})
|
||||
return true
|
||||
|
||||
#发送验证码验证
|
||||
func sendVerifyCode(qq_number, code):
|
||||
if not client.is_client_connected():
|
||||
|
||||
@@ -1,17 +1,26 @@
|
||||
[gd_scene load_steps=2 format=3 uid="uid://smypui0vyso5"]
|
||||
[gd_scene load_steps=3 format=3 uid="uid://smypui0vyso5"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://c0jfbtkh0mj5b" path="res://Script/BigPanel/DailyCheckInPanel.gd" id="1_fj7a7"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_217t6"]
|
||||
border_width_left = 15
|
||||
border_width_top = 15
|
||||
border_width_right = 15
|
||||
border_width_bottom = 15
|
||||
corner_detail = 20
|
||||
|
||||
[node name="DailyCheckInPanel" type="Panel"]
|
||||
offset_right = 600.0
|
||||
offset_left = 441.0
|
||||
offset_right = 1041.0
|
||||
offset_bottom = 720.0
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_217t6")
|
||||
script = ExtResource("1_fj7a7")
|
||||
|
||||
[node name="Title" type="Label" parent="."]
|
||||
layout_mode = 0
|
||||
offset_top = -1.0
|
||||
offset_top = 20.0
|
||||
offset_right = 600.0
|
||||
offset_bottom = 41.0
|
||||
offset_bottom = 69.0
|
||||
theme_override_colors/font_color = Color(0.624759, 0.8051, 0.828302, 1)
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
@@ -37,10 +46,10 @@ vertical_alignment = 1
|
||||
[node name="QuitButton" type="Button" parent="."]
|
||||
custom_minimum_size = Vector2(57, 57)
|
||||
layout_mode = 0
|
||||
offset_left = 543.0
|
||||
offset_top = 1.0
|
||||
offset_right = 600.0
|
||||
offset_bottom = 58.0
|
||||
offset_left = 520.0
|
||||
offset_top = 22.0
|
||||
offset_right = 577.0
|
||||
offset_bottom = 79.0
|
||||
theme_override_font_sizes/font_size = 35
|
||||
text = "X"
|
||||
|
||||
@@ -48,16 +57,16 @@ text = "X"
|
||||
modulate = Color(1, 1, 0.52549, 1)
|
||||
custom_minimum_size = Vector2(150, 70)
|
||||
layout_mode = 0
|
||||
offset_left = 243.0
|
||||
offset_top = 649.0
|
||||
offset_right = 393.0
|
||||
offset_bottom = 719.0
|
||||
offset_left = 239.0
|
||||
offset_top = 630.0
|
||||
offset_right = 389.0
|
||||
offset_bottom = 700.0
|
||||
theme_override_font_sizes/font_size = 35
|
||||
text = "签到"
|
||||
|
||||
[node name="Scroll" type="ScrollContainer" parent="."]
|
||||
layout_mode = 0
|
||||
offset_top = 58.0
|
||||
offset_top = 77.0
|
||||
offset_right = 600.0
|
||||
offset_bottom = 419.0
|
||||
|
||||
|
||||
@@ -1,18 +1,26 @@
|
||||
[gd_scene load_steps=2 format=3 uid="uid://cbhitturvihqj"]
|
||||
[gd_scene load_steps=3 format=3 uid="uid://cbhitturvihqj"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://cka0r4g8tbf0" path="res://Script/BigPanel/LoginPanel.gd" id="1_xnwaq"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_n8m38"]
|
||||
border_width_left = 15
|
||||
border_width_top = 15
|
||||
border_width_right = 15
|
||||
border_width_bottom = 15
|
||||
|
||||
[node name="LoginPanel" type="PanelContainer"]
|
||||
offset_left = 343.0
|
||||
offset_top = 36.0
|
||||
offset_right = 1071.0
|
||||
offset_bottom = 667.0
|
||||
offset_top = 5.0
|
||||
offset_right = 1093.0
|
||||
offset_bottom = 795.0
|
||||
scale = Vector2(0.9, 0.9)
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_n8m38")
|
||||
script = ExtResource("1_xnwaq")
|
||||
|
||||
[node name="VBox" type="VBoxContainer" parent="."]
|
||||
[node name="LoginVBox" type="VBoxContainer" parent="."]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Title" type="Label" parent="VBox"]
|
||||
[node name="Title" type="Label" parent="LoginVBox"]
|
||||
modulate = Color(1, 1, 0.537255, 1)
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
@@ -22,153 +30,59 @@ theme_override_constants/shadow_offset_y = 5
|
||||
theme_override_constants/outline_size = 15
|
||||
theme_override_constants/shadow_outline_size = 15
|
||||
theme_override_font_sizes/font_size = 40
|
||||
text = "登录/注册面板"
|
||||
text = "登录面板"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="UserName" type="HBoxContainer" parent="VBox"]
|
||||
[node name="UserName" type="HBoxContainer" parent="LoginVBox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="VBox/UserName"]
|
||||
[node name="Label" type="Label" parent="LoginVBox/UserName"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "账号"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="username_input" type="LineEdit" parent="VBox/UserName"]
|
||||
[node name="username_input" type="LineEdit" parent="LoginVBox/UserName"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入QQ号"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="Password1" type="HBoxContainer" parent="VBox"]
|
||||
[node name="Password" type="HBoxContainer" parent="LoginVBox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label2" type="Label" parent="VBox/Password1"]
|
||||
[node name="Label2" type="Label" parent="LoginVBox/Password"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "密码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="password_input" type="LineEdit" parent="VBox/Password1"]
|
||||
[node name="password_input" type="LineEdit" parent="LoginVBox/Password"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入密码"
|
||||
|
||||
[node name="Password2" type="HBoxContainer" parent="VBox"]
|
||||
[node name="LoginButton" type="Button" parent="LoginVBox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label2" type="Label" parent="VBox/Password2"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "确认密码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="password_input2" type="LineEdit" parent="VBox/Password2"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请再次输入密码"
|
||||
|
||||
[node name="VerificationCode" type="HBoxContainer" parent="VBox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="VBox/VerificationCode"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "验证码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="verificationcode_input" type="LineEdit" parent="VBox/VerificationCode"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入您的QQ邮箱收到的验证码"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="SendButton" type="Button" parent="VBox/VerificationCode"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "发送验证码"
|
||||
|
||||
[node name="PlayerName" type="HBoxContainer" parent="VBox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label2" type="Label" parent="VBox/PlayerName"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "玩家昵称"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="playername_input" type="LineEdit" parent="VBox/PlayerName"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入您的玩家昵称"
|
||||
|
||||
[node name="FarmName" type="HBoxContainer" parent="VBox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="VBox/FarmName"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "农场名称"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="farmname_input" type="LineEdit" parent="VBox/FarmName"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入您的农场名称"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="LoginRegister" type="HBoxContainer" parent="VBox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="login_button" type="Button" parent="VBox/LoginRegister"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "登录"
|
||||
|
||||
[node name="register_button" type="Button" parent="VBox/LoginRegister"]
|
||||
[node name="RegisterButton" type="Button" parent="LoginVBox"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "注册"
|
||||
|
||||
[node name="Password3" type="HBoxContainer" parent="VBox"]
|
||||
visible = false
|
||||
[node name="ForgetPasswdButton" type="Button" parent="LoginVBox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "忘记密码"
|
||||
|
||||
[node name="login_button" type="Button" parent="VBox/Password3"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 20
|
||||
text = "发送验证码"
|
||||
|
||||
[node name="Label2" type="Label" parent="VBox/Password3"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 20
|
||||
text = "找回密码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="password_input2" type="LineEdit" parent="VBox/Password3"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 20
|
||||
placeholder_text = "请输入QQ邮箱验证码"
|
||||
|
||||
[node name="Note" type="Label" parent="VBox"]
|
||||
[node name="Note" type="Label" parent="LoginVBox"]
|
||||
modulate = Color(1, 0.552941, 1, 1)
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
@@ -179,7 +93,246 @@ text = "注意:首次游玩游戏需要注册账号,
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="status_label" type="Label" parent="VBox"]
|
||||
[node name="status_label" type="Label" parent="LoginVBox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "连接状态"
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="RegisterVbox" type="VBoxContainer" parent="."]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Title" type="Label" parent="RegisterVbox"]
|
||||
modulate = Color(1, 1, 0.537255, 1)
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 5
|
||||
theme_override_constants/shadow_offset_y = 5
|
||||
theme_override_constants/outline_size = 15
|
||||
theme_override_constants/shadow_outline_size = 15
|
||||
theme_override_font_sizes/font_size = 40
|
||||
text = "注册面板"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="RegisterUserName" type="HBoxContainer" parent="RegisterVbox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="RegisterVbox/RegisterUserName"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "账号"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="username_input" type="LineEdit" parent="RegisterVbox/RegisterUserName"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入QQ号"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="Password1" type="HBoxContainer" parent="RegisterVbox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label2" type="Label" parent="RegisterVbox/Password1"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "密码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="password_input" type="LineEdit" parent="RegisterVbox/Password1"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入密码"
|
||||
|
||||
[node name="Password2" type="HBoxContainer" parent="RegisterVbox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label2" type="Label" parent="RegisterVbox/Password2"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "确认密码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="password_input2" type="LineEdit" parent="RegisterVbox/Password2"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请再次输入密码"
|
||||
|
||||
[node name="PlayerName" type="HBoxContainer" parent="RegisterVbox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label2" type="Label" parent="RegisterVbox/PlayerName"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "玩家昵称"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="playername_input" type="LineEdit" parent="RegisterVbox/PlayerName"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入您的玩家昵称"
|
||||
|
||||
[node name="FarmName" type="HBoxContainer" parent="RegisterVbox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="RegisterVbox/FarmName"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "农场名称"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="farmname_input" type="LineEdit" parent="RegisterVbox/FarmName"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入您的农场名称"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="VerificationCode" type="HBoxContainer" parent="RegisterVbox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="RegisterVbox/VerificationCode"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "验证码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="verificationcode_input" type="LineEdit" parent="RegisterVbox/VerificationCode"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入您的QQ邮箱收到的验证码"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="SendButton" type="Button" parent="RegisterVbox/VerificationCode"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "发送验证码"
|
||||
|
||||
[node name="RegisterButton2" type="Button" parent="RegisterVbox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "注册"
|
||||
|
||||
[node name="Note" type="Label" parent="RegisterVbox"]
|
||||
modulate = Color(1, 0.552941, 1, 1)
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "注意:首次游玩游戏需要注册账号,
|
||||
账号请直接输入您的QQ号,系统会直接向您的QQ
|
||||
邮箱发送一串验证码进行注册验证,密码请设置的复杂一
|
||||
点,以免被暴力破解("
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="status_label2" type="Label" parent="RegisterVbox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "连接状态"
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="ForgetPasswordVbox" type="VBoxContainer" parent="."]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Title" type="Label" parent="ForgetPasswordVbox"]
|
||||
modulate = Color(1, 1, 0.537255, 1)
|
||||
layout_mode = 2
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
theme_override_constants/shadow_offset_x = 5
|
||||
theme_override_constants/shadow_offset_y = 5
|
||||
theme_override_constants/outline_size = 15
|
||||
theme_override_constants/shadow_outline_size = 15
|
||||
theme_override_font_sizes/font_size = 40
|
||||
text = "忘记密码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="ForgetPasswordUserName" type="HBoxContainer" parent="ForgetPasswordVbox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="ForgetPasswordVbox/ForgetPasswordUserName"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "账号"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="username_input" type="LineEdit" parent="ForgetPasswordVbox/ForgetPasswordUserName"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入QQ号"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="NewPassword" type="HBoxContainer" parent="ForgetPasswordVbox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label2" type="Label" parent="ForgetPasswordVbox/NewPassword"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "新密码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="password_input" type="LineEdit" parent="ForgetPasswordVbox/NewPassword"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请设置新的密码"
|
||||
|
||||
[node name="VerificationCode2" type="HBoxContainer" parent="ForgetPasswordVbox"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="ForgetPasswordVbox/VerificationCode2"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "验证码"
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="verificationcode_input" type="LineEdit" parent="ForgetPasswordVbox/VerificationCode2"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
theme_override_font_sizes/font_size = 30
|
||||
placeholder_text = "请输入您的QQ邮箱收到的验证码"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="SendButton" type="Button" parent="ForgetPasswordVbox/VerificationCode2"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "发送验证码"
|
||||
|
||||
[node name="ForgetPasswordButton" type="Button" parent="ForgetPasswordVbox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "确认"
|
||||
|
||||
[node name="Note" type="Label" parent="ForgetPasswordVbox"]
|
||||
modulate = Color(1, 0.552941, 1, 1)
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "注意:首次游玩游戏需要注册账号,
|
||||
账号请直接输入您的QQ号,系统会直接向您的QQ
|
||||
邮箱发送一串验证码进行注册验证,密码请设置的复杂一
|
||||
点,以免被暴力破解("
|
||||
horizontal_alignment = 1
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="status_label3" type="Label" parent="ForgetPasswordVbox"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "连接状态"
|
||||
|
||||
@@ -1,17 +1,27 @@
|
||||
[gd_scene load_steps=2 format=3 uid="uid://bndf1e4sgdjr6"]
|
||||
[gd_scene load_steps=3 format=3 uid="uid://bndf1e4sgdjr6"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://65e0rl31fx0i" path="res://Script/BigPanel/LuckyDrawPanel.gd" id="1_dcmen"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_ynokl"]
|
||||
border_width_left = 15
|
||||
border_width_top = 15
|
||||
border_width_right = 15
|
||||
border_width_bottom = 15
|
||||
corner_detail = 20
|
||||
|
||||
[node name="LuckyDrawPanel" type="Panel"]
|
||||
offset_right = 600.0
|
||||
offset_bottom = 720.0
|
||||
offset_left = 373.0
|
||||
offset_top = 1.0
|
||||
offset_right = 1045.0
|
||||
offset_bottom = 721.0
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_ynokl")
|
||||
script = ExtResource("1_dcmen")
|
||||
|
||||
[node name="Title" type="Label" parent="."]
|
||||
layout_mode = 0
|
||||
offset_top = -1.0
|
||||
offset_right = 600.0
|
||||
offset_bottom = 58.0
|
||||
offset_top = 19.0
|
||||
offset_right = 669.0
|
||||
offset_bottom = 78.0
|
||||
theme_override_colors/font_color = Color(0.624759, 0.8051, 0.828302, 1)
|
||||
theme_override_colors/font_shadow_color = Color(0, 0, 0, 1)
|
||||
theme_override_colors/font_outline_color = Color(0, 0, 0, 1)
|
||||
@@ -28,7 +38,7 @@ vertical_alignment = 1
|
||||
modulate = Color(0.642982, 0.510828, 1, 1)
|
||||
layout_mode = 0
|
||||
offset_top = 419.0
|
||||
offset_right = 600.0
|
||||
offset_right = 671.0
|
||||
offset_bottom = 468.0
|
||||
theme_override_font_sizes/font_size = 30
|
||||
text = "🎉获得奖励🎉"
|
||||
@@ -38,18 +48,19 @@ vertical_alignment = 1
|
||||
[node name="QuitButton" type="Button" parent="."]
|
||||
custom_minimum_size = Vector2(57, 57)
|
||||
layout_mode = 0
|
||||
offset_left = 543.0
|
||||
offset_top = 1.0
|
||||
offset_right = 600.0
|
||||
offset_bottom = 58.0
|
||||
offset_left = 595.0
|
||||
offset_top = 21.0
|
||||
offset_right = 652.0
|
||||
offset_bottom = 78.0
|
||||
theme_override_font_sizes/font_size = 35
|
||||
text = "X"
|
||||
|
||||
[node name="LuckyDrawReward" type="RichTextLabel" parent="."]
|
||||
layout_mode = 0
|
||||
offset_left = 16.0
|
||||
offset_top = 481.0
|
||||
offset_right = 600.0
|
||||
offset_bottom = 649.0
|
||||
offset_right = 671.0
|
||||
offset_bottom = 633.0
|
||||
theme_override_font_sizes/normal_font_size = 20
|
||||
bbcode_enabled = true
|
||||
text = "+500 经验,+400 钱币,+5 普通-番茄种子,+1 传奇-火龙果种子 "
|
||||
@@ -57,14 +68,18 @@ horizontal_alignment = 1
|
||||
|
||||
[node name="Grid" type="GridContainer" parent="."]
|
||||
layout_mode = 0
|
||||
offset_top = 58.0
|
||||
offset_right = 600.0
|
||||
offset_left = 16.0
|
||||
offset_top = 85.0
|
||||
offset_right = 657.0
|
||||
offset_bottom = 419.0
|
||||
columns = 5
|
||||
|
||||
[node name="RewardItem" type="RichTextLabel" parent="Grid"]
|
||||
custom_minimum_size = Vector2(120, 120)
|
||||
layout_mode = 2
|
||||
theme_override_constants/outline_size = 15
|
||||
theme_override_font_sizes/normal_font_size = 17
|
||||
bbcode_enabled = true
|
||||
text = "+50钱币
|
||||
+100经验
|
||||
+4番茄种子
|
||||
@@ -75,9 +90,10 @@ threaded = true
|
||||
|
||||
[node name="HBox" type="HBoxContainer" parent="."]
|
||||
layout_mode = 0
|
||||
offset_top = 649.0
|
||||
offset_right = 600.0
|
||||
offset_bottom = 719.0
|
||||
offset_left = -2.0
|
||||
offset_top = 633.0
|
||||
offset_right = 671.0
|
||||
offset_bottom = 703.0
|
||||
alignment = 1
|
||||
|
||||
[node name="FiveLuckyDrawButton" type="Button" parent="HBox"]
|
||||
|
||||
@@ -320,45 +320,51 @@ func _create_crop_button(crop_name: String, crop_quality: String) -> Button:
|
||||
|
||||
# 正常模式下的成熟物点击处理
|
||||
func _on_crop_selected(crop_name, crop_count):
|
||||
# 显示成熟物信息
|
||||
var info_text = ""
|
||||
|
||||
if main_game.can_planted_crop.has(crop_name):
|
||||
var crop = main_game.can_planted_crop[crop_name]
|
||||
var display_name = crop_name
|
||||
var mature_name = crop.get("成熟物名称")
|
||||
if mature_name != null and mature_name != "":
|
||||
display_name = mature_name
|
||||
else:
|
||||
display_name = crop.get("作物名称", crop_name)
|
||||
var quality = crop.get("品质", "未知")
|
||||
var price = crop.get("花费", 0)
|
||||
var grow_time = crop.get("生长时间", 0)
|
||||
var profit = crop.get("收益", 0)
|
||||
var level_req = crop.get("等级", 1)
|
||||
|
||||
# 将成熟时间转换为可读格式
|
||||
var time_str = ""
|
||||
var total_seconds = int(grow_time)
|
||||
var hours = total_seconds / 3600
|
||||
var minutes = (total_seconds % 3600) / 60
|
||||
var seconds = total_seconds % 60
|
||||
|
||||
if hours > 0:
|
||||
time_str += str(hours) + "小时"
|
||||
if minutes > 0:
|
||||
time_str += str(minutes) + "分钟"
|
||||
if seconds > 0:
|
||||
time_str += str(seconds) + "秒"
|
||||
|
||||
info_text = quality + "-" + display_name + " (数量: " + str(crop_count) + ")\n"
|
||||
info_text += "原价格: " + str(price) + "元, 原收益: " + str(profit) + "元\n"
|
||||
info_text += "成熟时间: " + time_str + ", 需求等级: " + str(level_req) + "\n"
|
||||
info_text += "这是收获的成熟品,可以用于出售或其他用途"
|
||||
# 获取作物信息面板的引用
|
||||
var crop_inform_panel = get_node("/root/main/UI/SmallPanel/CropInformPanel")
|
||||
if crop_inform_panel and crop_inform_panel.has_method("show_crop_info"):
|
||||
# 打开作物信息面板并传递作物数据
|
||||
crop_inform_panel.show_crop_info(crop_name, crop_count)
|
||||
else:
|
||||
info_text = crop_name + " (数量: " + str(crop_count) + ")"
|
||||
|
||||
Toast.show(info_text, Color.GOLD, 3.0, 1.0)
|
||||
# 如果作物信息面板不可用,显示Toast作为后备方案
|
||||
var info_text = ""
|
||||
|
||||
if main_game.can_planted_crop.has(crop_name):
|
||||
var crop = main_game.can_planted_crop[crop_name]
|
||||
var display_name = crop_name
|
||||
var mature_name = crop.get("成熟物名称")
|
||||
if mature_name != null and mature_name != "":
|
||||
display_name = mature_name
|
||||
else:
|
||||
display_name = crop.get("作物名称", crop_name)
|
||||
var quality = crop.get("品质", "未知")
|
||||
var price = crop.get("花费", 0)
|
||||
var grow_time = crop.get("生长时间", 0)
|
||||
var profit = crop.get("收益", 0)
|
||||
var level_req = crop.get("等级", 1)
|
||||
|
||||
# 将成熟时间转换为可读格式
|
||||
var time_str = ""
|
||||
var total_seconds = int(grow_time)
|
||||
var hours = total_seconds / 3600
|
||||
var minutes = (total_seconds % 3600) / 60
|
||||
var seconds = total_seconds % 60
|
||||
|
||||
if hours > 0:
|
||||
time_str += str(hours) + "小时"
|
||||
if minutes > 0:
|
||||
time_str += str(minutes) + "分钟"
|
||||
if seconds > 0:
|
||||
time_str += str(seconds) + "秒"
|
||||
|
||||
info_text = quality + "-" + display_name + " (数量: " + str(crop_count) + ")\n"
|
||||
info_text += "原价格: " + str(price) + "元, 原收益: " + str(profit) + "元\n"
|
||||
info_text += "成熟时间: " + time_str + ", 需求等级: " + str(level_req) + "\n"
|
||||
info_text += "这是收获的成熟品,可以用于出售或其他用途"
|
||||
else:
|
||||
info_text = crop_name + " (数量: " + str(crop_count) + ")"
|
||||
|
||||
Toast.show(info_text, Color.GOLD, 3.0, 1.0)
|
||||
|
||||
# 访问模式下的成熟物点击处理
|
||||
func _on_visit_crop_selected(crop_name, crop_count):
|
||||
|
||||
@@ -1,35 +1,52 @@
|
||||
#玩家登录注册面板
|
||||
extends PanelContainer
|
||||
|
||||
#玩家登录账号,用QQ号代替
|
||||
@onready var username_input : LineEdit = $VBox/UserName/username_input
|
||||
#用户登录密码
|
||||
@onready var password_input : LineEdit = $VBox/Password1/password_input
|
||||
#登录按钮
|
||||
@onready var login_button : Button = $VBox/LoginRegister/login_button
|
||||
#默认显示登录面板(登录面板可以进入注册面板和忘记密码面板)
|
||||
@onready var login_v_box: VBoxContainer = $LoginVBox #显示或隐藏登录面板
|
||||
@onready var user_name: HBoxContainer = $LoginVBox/UserName #玩家账号
|
||||
@onready var password: HBoxContainer = $LoginVBox/Password #玩家密码
|
||||
@onready var login_button: Button = $LoginVBox/LoginButton #登录按钮
|
||||
@onready var register_button: Button = $LoginVBox/RegisterButton #注册按钮,点击后隐藏登录面板显示注册面板
|
||||
@onready var forget_passwd_button: Button = $LoginVBox/ForgetPasswdButton #忘记密码按钮,点击后隐藏登录面板显示忘记密码面板
|
||||
@onready var status_label: Label = $LoginVBox/status_label #登录状态
|
||||
|
||||
#下面是注册相关的
|
||||
#注册按钮
|
||||
@onready var register_button : Button = $VBox/LoginRegister/register_button
|
||||
#注册账号时二次确认密码
|
||||
@onready var password_input_2 : LineEdit = $VBox/Password2/password_input2
|
||||
#农场名称
|
||||
@onready var farmname_input : LineEdit = $VBox/FarmName/farmname_input
|
||||
#玩家昵称
|
||||
@onready var playername_input :LineEdit = $VBox/PlayerName/playername_input
|
||||
#邮箱验证码
|
||||
@onready var verificationcode_input :LineEdit = $VBox/VerificationCode/verificationcode_input
|
||||
#发送验证码按钮
|
||||
@onready var send_button :Button = $VBox/VerificationCode/SendButton
|
||||
#状态提示标签
|
||||
@onready var status_label : Label = $VBox/status_label
|
||||
# 登录面板输入框
|
||||
@onready var username_input: LineEdit = $LoginVBox/UserName/username_input
|
||||
@onready var password_input: LineEdit = $LoginVBox/Password/password_input
|
||||
|
||||
#注册面板,注册成功跳转回登录面板
|
||||
@onready var register_vbox: VBoxContainer = $RegisterVbox #显示或隐藏注册面板
|
||||
@onready var register_user_name: HBoxContainer = $RegisterVbox/RegisterUserName #注册玩家账号
|
||||
@onready var password_1: HBoxContainer = $RegisterVbox/Password1 #注册密码
|
||||
@onready var password_2: HBoxContainer = $RegisterVbox/Password2 #二次确认密码
|
||||
@onready var player_name: HBoxContainer = $RegisterVbox/PlayerName #注册玩家昵称
|
||||
@onready var farm_name: HBoxContainer = $RegisterVbox/FarmName #注册玩家农场名称
|
||||
@onready var verification_code: HBoxContainer = $RegisterVbox/VerificationCode #注册所需验证码
|
||||
@onready var register_button_2: Button = $RegisterVbox/RegisterButton2 #注册按钮
|
||||
@onready var status_label_2: Label = $RegisterVbox/status_label2 #注册状态
|
||||
|
||||
@onready var password_2: HBoxContainer = $VBox/Password2
|
||||
@onready var verification_code: HBoxContainer = $VBox/VerificationCode
|
||||
@onready var player_name: HBoxContainer = $VBox/PlayerName
|
||||
@onready var farm_name: HBoxContainer = $VBox/FarmName
|
||||
# 注册面板输入框
|
||||
@onready var register_username_input: LineEdit = $RegisterVbox/RegisterUserName/username_input
|
||||
@onready var password_input_1: LineEdit = $RegisterVbox/Password1/password_input
|
||||
@onready var password_input_2: LineEdit = $RegisterVbox/Password2/password_input2
|
||||
@onready var playername_input: LineEdit = $RegisterVbox/PlayerName/playername_input
|
||||
@onready var farmname_input: LineEdit = $RegisterVbox/FarmName/farmname_input
|
||||
@onready var verificationcode_input: LineEdit = $RegisterVbox/VerificationCode/verificationcode_input
|
||||
@onready var send_button: Button = $RegisterVbox/VerificationCode/SendButton
|
||||
|
||||
#忘记密码面板,设置新密码成功后同样跳转到登录面板
|
||||
@onready var forget_password_vbox: VBoxContainer = $ForgetPasswordVbox #显示或隐藏忘记密码面板
|
||||
@onready var forget_password_user_name: HBoxContainer = $ForgetPasswordVbox/ForgetPasswordUserName #忘记密码的玩家账号
|
||||
@onready var new_password: HBoxContainer = $ForgetPasswordVbox/NewPassword #设置该账号新的密码
|
||||
@onready var verification_code_2: HBoxContainer = $ForgetPasswordVbox/VerificationCode2 #忘记密码所需验证码
|
||||
@onready var forget_password_button: Button = $ForgetPasswordVbox/ForgetPasswordButton #设置新密码确认按钮
|
||||
@onready var status_label_3: Label = $ForgetPasswordVbox/status_label3 #设置新密码状态
|
||||
|
||||
# 忘记密码面板输入框
|
||||
@onready var forget_username_input: LineEdit = $ForgetPasswordVbox/ForgetPasswordUserName/username_input
|
||||
@onready var new_password_input: LineEdit = $ForgetPasswordVbox/NewPassword/password_input
|
||||
@onready var forget_verificationcode_input: LineEdit = $ForgetPasswordVbox/VerificationCode2/verificationcode_input
|
||||
@onready var forget_send_button: Button = $ForgetPasswordVbox/VerificationCode2/SendButton
|
||||
|
||||
|
||||
# 记住密码选项
|
||||
@@ -53,16 +70,20 @@ var remember_password : bool = true # 默认记住密码
|
||||
# 准备函数
|
||||
func _ready():
|
||||
self.show()
|
||||
#隐藏注册相关UI
|
||||
password_2.hide()
|
||||
verification_code.hide()
|
||||
player_name.hide()
|
||||
farm_name.hide()
|
||||
|
||||
# 初始状态:只显示登录面板,隐藏注册和忘记密码面板
|
||||
login_v_box.show()
|
||||
register_vbox.hide()
|
||||
forget_password_vbox.hide()
|
||||
|
||||
# 连接按钮信号
|
||||
login_button.pressed.connect(self._on_login_button_pressed)
|
||||
register_button.pressed.connect(self._on_register_button_pressed)
|
||||
register_button.pressed.connect(self._on_show_register_panel)
|
||||
forget_passwd_button.pressed.connect(self._on_forget_password_button_pressed)
|
||||
register_button_2.pressed.connect(self._on_register_button_2_pressed)
|
||||
forget_password_button.pressed.connect(self._on_forget_password_confirm_pressed)
|
||||
send_button.pressed.connect(self._on_send_button_pressed)
|
||||
forget_send_button.pressed.connect(self._on_forget_send_button_pressed)
|
||||
|
||||
# 加载保存的登录信息
|
||||
_load_login_info()
|
||||
@@ -70,6 +91,23 @@ func _ready():
|
||||
# 显示客户端版本号
|
||||
_display_version_info()
|
||||
|
||||
# 面板切换函数
|
||||
func _on_show_register_panel():
|
||||
"""切换到注册面板"""
|
||||
login_v_box.hide()
|
||||
register_vbox.show()
|
||||
forget_password_vbox.hide()
|
||||
status_label_2.text = "请填写注册信息"
|
||||
status_label_2.modulate = Color.WHITE
|
||||
|
||||
func _on_forget_password_button_pressed():
|
||||
"""切换到忘记密码面板"""
|
||||
login_v_box.hide()
|
||||
register_vbox.hide()
|
||||
forget_password_vbox.show()
|
||||
status_label_3.text = "请输入账号和新密码"
|
||||
status_label_3.modulate = Color.WHITE
|
||||
|
||||
# 处理登录按钮点击
|
||||
func _on_login_button_pressed():
|
||||
password_2.hide()
|
||||
@@ -129,32 +167,30 @@ func _on_login_button_pressed():
|
||||
|
||||
# 处理验证码发送按钮点击
|
||||
func _on_send_button_pressed():
|
||||
|
||||
|
||||
var user_name = username_input.text.strip_edges()
|
||||
var user_name = register_username_input.text.strip_edges()
|
||||
|
||||
if user_name == "":
|
||||
status_label.text = "请输入QQ号以接收验证码!"
|
||||
status_label.modulate = Color.RED
|
||||
status_label_2.text = "请输入QQ号以接收验证码!"
|
||||
status_label_2.modulate = Color.RED
|
||||
return
|
||||
|
||||
if !is_valid_qq_number(user_name):
|
||||
status_label.text = "请输入正确的QQ号码(5-12位数字)!"
|
||||
status_label.modulate = Color.RED
|
||||
status_label_2.text = "请输入正确的QQ号码(5-12位数字)!"
|
||||
status_label_2.modulate = Color.RED
|
||||
return
|
||||
|
||||
# 检查网络连接状态
|
||||
if !tcp_network_manager_panel.client.is_client_connected():
|
||||
status_label.text = "未连接到服务器,正在尝试连接..."
|
||||
status_label.modulate = Color.YELLOW
|
||||
status_label_2.text = "未连接到服务器,正在尝试连接..."
|
||||
status_label_2.modulate = Color.YELLOW
|
||||
# 尝试自动连接到服务器
|
||||
tcp_network_manager_panel.connect_to_current_server()
|
||||
await get_tree().create_timer(2.0).timeout
|
||||
|
||||
# 再次检查连接状态
|
||||
if !tcp_network_manager_panel.client.is_client_connected():
|
||||
status_label.text = "连接服务器失败,正在尝试其他服务器..."
|
||||
status_label.modulate = Color.YELLOW
|
||||
status_label_2.text = "连接服务器失败,正在尝试其他服务器..."
|
||||
status_label_2.modulate = Color.YELLOW
|
||||
# 等待自动服务器切换完成
|
||||
await get_tree().create_timer(3.0).timeout
|
||||
|
||||
@@ -162,8 +198,8 @@ func _on_send_button_pressed():
|
||||
# 禁用按钮,防止重复点击
|
||||
send_button.disabled = true
|
||||
|
||||
status_label.text = "正在发送验证码,请稍候..."
|
||||
status_label.modulate = Color.YELLOW
|
||||
status_label_2.text = "正在发送验证码,请稍候..."
|
||||
status_label_2.modulate = Color.YELLOW
|
||||
|
||||
# 发送验证码请求
|
||||
tcp_network_manager_panel.sendVerificationCodeRequest(user_name)
|
||||
@@ -179,19 +215,14 @@ func _on_send_button_pressed():
|
||||
send_button.disabled = false
|
||||
send_button.text = "发送验证码"
|
||||
|
||||
if status_label.text == "正在发送验证码,请稍候...":
|
||||
status_label.text = "验证码发送超时,请重试!"
|
||||
status_label.modulate = Color.RED
|
||||
if status_label_2.text == "正在发送验证码,请稍候...":
|
||||
status_label_2.text = "验证码发送超时,请重试!"
|
||||
status_label_2.modulate = Color.RED
|
||||
|
||||
# 处理注册按钮点击
|
||||
func _on_register_button_pressed():
|
||||
password_2.show()
|
||||
verification_code.show()
|
||||
player_name.show()
|
||||
farm_name.show()
|
||||
|
||||
var user_name = username_input.text.strip_edges()
|
||||
var user_password = password_input.text.strip_edges()
|
||||
func _on_register_button_2_pressed():
|
||||
var user_name = register_username_input.text.strip_edges()
|
||||
var user_password = password_input_1.text.strip_edges()
|
||||
var user_password_2 = password_input_2.text.strip_edges()
|
||||
var farmname = farmname_input.text.strip_edges()
|
||||
var player_name = playername_input.text.strip_edges()
|
||||
@@ -199,69 +230,180 @@ func _on_register_button_pressed():
|
||||
|
||||
# 检查密码格式(只允许数字和字母)
|
||||
if not is_valid_password(user_password):
|
||||
status_label.text = "密码只能包含数字和字母!"
|
||||
status_label.modulate = Color.RED
|
||||
status_label_2.text = "密码只能包含数字和字母!"
|
||||
status_label_2.modulate = Color.RED
|
||||
return
|
||||
|
||||
if user_name == "" or user_password == "":
|
||||
status_label.text = "用户名或密码不能为空!"
|
||||
status_label.modulate = Color.RED
|
||||
status_label_2.text = "用户名或密码不能为空!"
|
||||
status_label_2.modulate = Color.RED
|
||||
return
|
||||
if farmname == "":
|
||||
status_label.text = "农场名称不能为空!"
|
||||
status_label.modulate = Color.RED
|
||||
status_label_2.text = "农场名称不能为空!"
|
||||
status_label_2.modulate = Color.RED
|
||||
return
|
||||
if user_password != user_password_2:
|
||||
status_label.text = "两次输入的密码不一致!"
|
||||
status_label.modulate = Color.RED
|
||||
status_label_2.text = "两次输入的密码不一致!"
|
||||
status_label_2.modulate = Color.RED
|
||||
return
|
||||
|
||||
if !is_valid_qq_number(user_name):
|
||||
status_label.text = "请输入正确的QQ号码(5-12位数字)!"
|
||||
status_label.modulate = Color.RED
|
||||
status_label_2.text = "请输入正确的QQ号码(5-12位数字)!"
|
||||
status_label_2.modulate = Color.RED
|
||||
return
|
||||
|
||||
if verification_code == "":
|
||||
status_label.text = "请输入验证码!"
|
||||
status_label.modulate = Color.RED
|
||||
status_label_2.text = "请输入验证码!"
|
||||
status_label_2.modulate = Color.RED
|
||||
return
|
||||
|
||||
# 检查网络连接状态
|
||||
# 检查网络连接状态
|
||||
if !tcp_network_manager_panel.client.is_client_connected():
|
||||
status_label.text = "未连接到服务器,正在尝试连接..."
|
||||
status_label.modulate = Color.YELLOW
|
||||
status_label_2.text = "未连接到服务器,正在尝试连接..."
|
||||
status_label_2.modulate = Color.YELLOW
|
||||
# 尝试自动连接到服务器
|
||||
tcp_network_manager_panel.connect_to_current_server()
|
||||
await get_tree().create_timer(2.0).timeout
|
||||
|
||||
# 再次检查连接状态
|
||||
if !tcp_network_manager_panel.client.is_client_connected():
|
||||
status_label.text = "连接服务器失败,正在尝试其他服务器..."
|
||||
status_label.modulate = Color.YELLOW
|
||||
status_label_2.text = "连接服务器失败,正在尝试其他服务器..."
|
||||
status_label_2.modulate = Color.YELLOW
|
||||
# 等待自动服务器切换完成
|
||||
await get_tree().create_timer(3.0).timeout
|
||||
|
||||
|
||||
# 禁用按钮,防止重复点击
|
||||
register_button.disabled = true
|
||||
register_button_2.disabled = true
|
||||
|
||||
status_label.text = "正在注册,请稍候..."
|
||||
status_label.modulate = Color.YELLOW
|
||||
status_label_2.text = "正在注册,请稍候..."
|
||||
status_label_2.modulate = Color.YELLOW
|
||||
|
||||
# 发送注册请求
|
||||
# 发送注册请求
|
||||
tcp_network_manager_panel.sendRegisterInfo(user_name, user_password, farmname, player_name, verification_code)
|
||||
|
||||
|
||||
# 更新主游戏数据
|
||||
main_game.user_name = user_name
|
||||
main_game.user_password = user_password
|
||||
main_game.farmname = farmname
|
||||
# farmname 直接在注册成功后通过UI更新,这里不需要设置
|
||||
|
||||
# 5秒后重新启用按钮(如果没有收到响应)
|
||||
await get_tree().create_timer(5.0).timeout
|
||||
if register_button.disabled:
|
||||
register_button.disabled = false
|
||||
status_label.text = "注册超时,请重试!"
|
||||
status_label.modulate = Color.RED
|
||||
if register_button_2.disabled:
|
||||
register_button_2.disabled = false
|
||||
status_label_2.text = "注册超时,请重试!"
|
||||
status_label_2.modulate = Color.RED
|
||||
|
||||
# 忘记密码发送验证码按钮处理
|
||||
func _on_forget_send_button_pressed():
|
||||
var user_name = forget_username_input.text.strip_edges()
|
||||
|
||||
if user_name == "":
|
||||
status_label_3.text = "请输入QQ号以接收验证码!"
|
||||
status_label_3.modulate = Color.RED
|
||||
return
|
||||
|
||||
if !is_valid_qq_number(user_name):
|
||||
status_label_3.text = "请输入正确的QQ号码(5-12位数字)!"
|
||||
status_label_3.modulate = Color.RED
|
||||
return
|
||||
|
||||
# 检查网络连接状态
|
||||
if !tcp_network_manager_panel.client.is_client_connected():
|
||||
status_label_3.text = "未连接到服务器,正在尝试连接..."
|
||||
status_label_3.modulate = Color.YELLOW
|
||||
# 尝试自动连接到服务器
|
||||
tcp_network_manager_panel.connect_to_current_server()
|
||||
await get_tree().create_timer(2.0).timeout
|
||||
|
||||
# 再次检查连接状态
|
||||
if !tcp_network_manager_panel.client.is_client_connected():
|
||||
status_label_3.text = "连接服务器失败,正在尝试其他服务器..."
|
||||
status_label_3.modulate = Color.YELLOW
|
||||
# 等待自动服务器切换完成
|
||||
await get_tree().create_timer(3.0).timeout
|
||||
|
||||
# 禁用按钮,防止重复点击
|
||||
forget_send_button.disabled = true
|
||||
|
||||
status_label_3.text = "正在发送验证码,请稍候..."
|
||||
status_label_3.modulate = Color.YELLOW
|
||||
|
||||
# 发送验证码请求(用于忘记密码)
|
||||
tcp_network_manager_panel.sendForgetPasswordVerificationCode(user_name)
|
||||
|
||||
# 60秒后重新启用按钮
|
||||
var timer = 60
|
||||
while timer > 0 and forget_send_button.disabled:
|
||||
forget_send_button.text = "重新发送(%d)" % timer
|
||||
await get_tree().create_timer(1.0).timeout
|
||||
timer -= 1
|
||||
|
||||
if forget_send_button.disabled:
|
||||
forget_send_button.disabled = false
|
||||
forget_send_button.text = "发送验证码"
|
||||
|
||||
if status_label_3.text == "正在发送验证码,请稍候...":
|
||||
status_label_3.text = "验证码发送超时,请重试!"
|
||||
status_label_3.modulate = Color.RED
|
||||
|
||||
# 忘记密码确认按钮处理
|
||||
func _on_forget_password_confirm_pressed():
|
||||
var user_name = forget_username_input.text.strip_edges()
|
||||
var new_password = new_password_input.text.strip_edges()
|
||||
var verification_code = forget_verificationcode_input.text.strip_edges()
|
||||
|
||||
# 检查密码格式(只允许数字和字母)
|
||||
if not is_valid_password(new_password):
|
||||
status_label_3.text = "密码只能包含数字和字母!"
|
||||
status_label_3.modulate = Color.RED
|
||||
return
|
||||
|
||||
if user_name == "" or new_password == "":
|
||||
status_label_3.text = "用户名或新密码不能为空!"
|
||||
status_label_3.modulate = Color.RED
|
||||
return
|
||||
|
||||
if !is_valid_qq_number(user_name):
|
||||
status_label_3.text = "请输入正确的QQ号码(5-12位数字)!"
|
||||
status_label_3.modulate = Color.RED
|
||||
return
|
||||
|
||||
if verification_code == "":
|
||||
status_label_3.text = "请输入验证码!"
|
||||
status_label_3.modulate = Color.RED
|
||||
return
|
||||
|
||||
# 检查网络连接状态
|
||||
if !tcp_network_manager_panel.client.is_client_connected():
|
||||
status_label_3.text = "未连接到服务器,正在尝试连接..."
|
||||
status_label_3.modulate = Color.YELLOW
|
||||
# 尝试自动连接到服务器
|
||||
tcp_network_manager_panel.connect_to_current_server()
|
||||
await get_tree().create_timer(2.0).timeout
|
||||
|
||||
# 再次检查连接状态
|
||||
if !tcp_network_manager_panel.client.is_client_connected():
|
||||
status_label_3.text = "连接服务器失败,正在尝试其他服务器..."
|
||||
status_label_3.modulate = Color.YELLOW
|
||||
# 等待自动服务器切换完成
|
||||
await get_tree().create_timer(3.0).timeout
|
||||
|
||||
# 禁用按钮,防止重复点击
|
||||
forget_password_button.disabled = true
|
||||
|
||||
status_label_3.text = "正在重置密码,请稍候..."
|
||||
status_label_3.modulate = Color.YELLOW
|
||||
|
||||
# 发送忘记密码请求
|
||||
tcp_network_manager_panel.sendForgetPasswordRequest(user_name, new_password, verification_code)
|
||||
|
||||
# 5秒后重新启用按钮(如果没有收到响应)
|
||||
await get_tree().create_timer(5.0).timeout
|
||||
if forget_password_button.disabled:
|
||||
forget_password_button.disabled = false
|
||||
status_label_3.text = "重置密码超时,请重试!"
|
||||
status_label_3.modulate = Color.RED
|
||||
|
||||
# 处理验证码发送响应
|
||||
func _on_verification_code_response(success: bool, message: String):
|
||||
@@ -390,24 +532,67 @@ func _on_login_response_received(success: bool, message: String, user_data: Dict
|
||||
# 处理注册响应
|
||||
func _on_register_response_received(success: bool, message: String):
|
||||
# 启用按钮
|
||||
register_button.disabled = false
|
||||
register_button_2.disabled = false
|
||||
|
||||
if success:
|
||||
status_label.text = "注册成功!请登录游戏"
|
||||
status_label.modulate = Color.GREEN
|
||||
status_label_2.text = "注册成功!请登录游戏"
|
||||
status_label_2.modulate = Color.GREEN
|
||||
|
||||
# 注册成功后,如果启用了记住密码,保存登录信息
|
||||
if remember_password:
|
||||
var user_name = username_input.text.strip_edges()
|
||||
var user_password = password_input.text.strip_edges()
|
||||
var user_name = register_username_input.text.strip_edges()
|
||||
var user_password = password_input_1.text.strip_edges()
|
||||
_save_login_info(user_name, user_password)
|
||||
|
||||
# 清除注册相关的输入框
|
||||
password_input_2.text = ""
|
||||
verificationcode_input.text = ""
|
||||
|
||||
# 切换回登录面板
|
||||
register_vbox.hide()
|
||||
forget_password_vbox.hide()
|
||||
login_v_box.show()
|
||||
|
||||
# 如果记住密码,自动填充登录信息
|
||||
if remember_password:
|
||||
username_input.text = register_username_input.text
|
||||
password_input.text = password_input_1.text
|
||||
else:
|
||||
status_label.text = "注册失败:" + message
|
||||
status_label.modulate = Color.RED
|
||||
status_label_2.text = "注册失败:" + message
|
||||
status_label_2.modulate = Color.RED
|
||||
|
||||
# 处理忘记密码响应
|
||||
func _on_forget_password_response_received(success: bool, message: String):
|
||||
# 启用按钮
|
||||
forget_password_button.disabled = false
|
||||
|
||||
if success:
|
||||
status_label_3.text = "密码重置成功!请使用新密码登录"
|
||||
status_label_3.modulate = Color.GREEN
|
||||
|
||||
# 保存新的登录信息
|
||||
if remember_password:
|
||||
var user_name = forget_username_input.text.strip_edges()
|
||||
var new_password = new_password_input.text.strip_edges()
|
||||
_save_login_info(user_name, new_password)
|
||||
|
||||
# 清除输入框
|
||||
forget_verificationcode_input.text = ""
|
||||
|
||||
# 切换回登录面板并自动填充账号信息
|
||||
forget_password_vbox.hide()
|
||||
register_vbox.hide()
|
||||
login_v_box.show()
|
||||
|
||||
# 自动填充登录信息
|
||||
username_input.text = forget_username_input.text
|
||||
password_input.text = new_password_input.text
|
||||
|
||||
status_label.text = "密码已重置,请登录"
|
||||
status_label.modulate = Color.GREEN
|
||||
else:
|
||||
status_label_3.text = "密码重置失败:" + message
|
||||
status_label_3.modulate = Color.RED
|
||||
|
||||
# 保存登录信息到JSON文件
|
||||
func _save_login_info(user_name: String, password: String):
|
||||
|
||||
374
Script/BigPanel/PlayerStorePanel.gd
Normal file
@@ -0,0 +1,374 @@
|
||||
extends Panel
|
||||
#玩家小卖部(目前可以卖道具,种子,成熟作物)
|
||||
#初始玩家有10个格子
|
||||
#然后玩家额外购买格子需要1000元,多加一个格子加500元,最多40个格子,格子满了不能再放了
|
||||
#玩家自己点击自己的摊位(商品格子)显示弹窗是否要取消放置商品
|
||||
#别人拜访玩家打开小卖部点击被拜访玩家的摊位显示批量购买弹窗
|
||||
@onready var quit_button: Button = $QuitButton #关闭玩家小卖部面板
|
||||
@onready var refresh_button: Button = $RefreshButton #刷新小卖部按钮
|
||||
@onready var store_grid: GridContainer = $ScrollContainer/Store_Grid #小卖部商品格子
|
||||
@onready var buy_product_booth_button: Button = $BuyProductBoothButton #购买格子按钮
|
||||
|
||||
# 获取主游戏引用
|
||||
@onready var main_game = get_node("/root/main")
|
||||
|
||||
# 当前小卖部数据
|
||||
var player_store_data: Array = []
|
||||
var max_store_slots: int = 10 # 默认10个格子
|
||||
|
||||
func _ready():
|
||||
# 连接按钮信号
|
||||
quit_button.pressed.connect(_on_quit_button_pressed)
|
||||
refresh_button.pressed.connect(_on_refresh_button_pressed)
|
||||
buy_product_booth_button.pressed.connect(_on_buy_product_booth_button_pressed)
|
||||
|
||||
# 连接可见性改变信号
|
||||
visibility_changed.connect(_on_visibility_changed)
|
||||
|
||||
# 默认隐藏面板
|
||||
self.hide()
|
||||
|
||||
#面板显示与隐藏切换处理
|
||||
func _on_visibility_changed():
|
||||
if visible:
|
||||
GlobalVariables.isZoomDisabled = true
|
||||
# 面板显示时更新小卖部数据
|
||||
update_player_store_ui()
|
||||
else:
|
||||
GlobalVariables.isZoomDisabled = false
|
||||
|
||||
# 初始化玩家小卖部
|
||||
func init_player_store():
|
||||
update_player_store_ui()
|
||||
|
||||
# 更新小卖部UI
|
||||
func update_player_store_ui():
|
||||
# 清空商品格子
|
||||
for child in store_grid.get_children():
|
||||
child.queue_free()
|
||||
|
||||
# 获取小卖部数据
|
||||
if main_game.is_visiting_mode:
|
||||
# 访问模式:显示被访问玩家的小卖部
|
||||
player_store_data = main_game.visited_player_data.get("玩家小卖部", [])
|
||||
max_store_slots = main_game.visited_player_data.get("小卖部格子数", 10)
|
||||
buy_product_booth_button.hide() # 访问模式下隐藏购买格子按钮
|
||||
else:
|
||||
# 正常模式:显示自己的小卖部
|
||||
player_store_data = main_game.login_data.get("玩家小卖部", [])
|
||||
max_store_slots = main_game.login_data.get("小卖部格子数", 10)
|
||||
buy_product_booth_button.show() # 正常模式下显示购买格子按钮
|
||||
|
||||
# 创建商品按钮
|
||||
_create_store_buttons()
|
||||
|
||||
# 更新购买格子按钮文本
|
||||
_update_buy_booth_button()
|
||||
|
||||
# 创建小卖部商品按钮
|
||||
func _create_store_buttons():
|
||||
# 为每个格子创建按钮
|
||||
for i in range(max_store_slots):
|
||||
var button = _create_store_slot_button(i)
|
||||
store_grid.add_child(button)
|
||||
|
||||
# 创建单个商品格子按钮
|
||||
func _create_store_slot_button(slot_index: int) -> Button:
|
||||
var button = main_game.item_button.duplicate()
|
||||
|
||||
# 确保按钮可见并可点击
|
||||
button.visible = true
|
||||
button.disabled = false
|
||||
button.focus_mode = Control.FOCUS_ALL
|
||||
|
||||
# 检查该格子是否有商品
|
||||
var product_data = null
|
||||
if slot_index < player_store_data.size():
|
||||
product_data = player_store_data[slot_index]
|
||||
|
||||
if product_data:
|
||||
# 有商品的格子
|
||||
var product_name = product_data.get("商品名称", "未知商品")
|
||||
var product_price = product_data.get("商品价格", 0)
|
||||
var product_count = product_data.get("商品数量", 0)
|
||||
var product_type = product_data.get("商品类型", "作物")
|
||||
|
||||
# 设置按钮文本
|
||||
button.text = str(product_name + "\n" + str(product_price) + "元/个\n库存:" + str(product_count))
|
||||
|
||||
# 更新商品图片
|
||||
_update_button_product_image(button, product_name, product_type)
|
||||
|
||||
# 设置工具提示
|
||||
button.tooltip_text = str(
|
||||
"商品: " + product_name + "\n" +
|
||||
"类型: " + product_type + "\n" +
|
||||
"单价: " + str(product_price) + " 元\n" +
|
||||
"库存: " + str(product_count) + " 个"
|
||||
)
|
||||
|
||||
# 连接点击事件
|
||||
if main_game.is_visiting_mode:
|
||||
# 访问模式:显示购买弹窗
|
||||
button.pressed.connect(func(): _on_product_buy_selected(product_data, slot_index))
|
||||
else:
|
||||
# 自己的小卖部:显示移除商品弹窗
|
||||
button.pressed.connect(func(): _on_product_manage_selected(product_data, slot_index))
|
||||
else:
|
||||
# 空格子
|
||||
button.text = "空闲格子\n\n点击添加商品"
|
||||
|
||||
# 设置为灰色样式
|
||||
if button.has_node("Title"):
|
||||
button.get_node("Title").modulate = Color.GRAY
|
||||
|
||||
# 只有在非访问模式下才允许点击空格子
|
||||
if not main_game.is_visiting_mode:
|
||||
button.pressed.connect(func(): _on_empty_slot_selected(slot_index))
|
||||
else:
|
||||
button.disabled = true
|
||||
|
||||
return button
|
||||
|
||||
# 更新商品图片
|
||||
func _update_button_product_image(button: Button, product_name: String, product_type: String):
|
||||
var crop_image = button.get_node_or_null("CropImage")
|
||||
if not crop_image:
|
||||
return
|
||||
|
||||
var texture = null
|
||||
|
||||
if product_type == "作物":
|
||||
# 作物商品:加载收获物图片
|
||||
texture = _get_crop_harvest_texture(product_name)
|
||||
# 未来可以添加其他类型的商品图片加载
|
||||
|
||||
if texture:
|
||||
crop_image.texture = texture
|
||||
crop_image.visible = true
|
||||
else:
|
||||
crop_image.visible = false
|
||||
|
||||
# 获取作物的收获物图片
|
||||
func _get_crop_harvest_texture(crop_name: String) -> Texture2D:
|
||||
var crop_path = "res://assets/作物/" + crop_name + "/"
|
||||
var harvest_texture_path = crop_path + "收获物.webp"
|
||||
|
||||
if ResourceLoader.exists(harvest_texture_path):
|
||||
var texture = load(harvest_texture_path)
|
||||
if texture:
|
||||
return texture
|
||||
|
||||
# 如果没有找到,使用默认的收获物图片
|
||||
var default_harvest_path = "res://assets/作物/默认/收获物.webp"
|
||||
if ResourceLoader.exists(default_harvest_path):
|
||||
var texture = load(default_harvest_path)
|
||||
if texture:
|
||||
return texture
|
||||
|
||||
return null
|
||||
|
||||
# 访问模式:点击商品购买
|
||||
func _on_product_buy_selected(product_data: Dictionary, slot_index: int):
|
||||
var product_name = product_data.get("商品名称", "未知商品")
|
||||
var product_price = product_data.get("商品价格", 0)
|
||||
var product_count = product_data.get("商品数量", 0)
|
||||
var product_type = product_data.get("商品类型", "作物")
|
||||
|
||||
# 检查商品是否还有库存
|
||||
if product_count <= 0:
|
||||
Toast.show("该商品已售罄", Color.RED, 2.0, 1.0)
|
||||
return
|
||||
|
||||
# 获取批量购买弹窗
|
||||
var batch_buy_popup = get_node_or_null("/root/main/UI/DiaLog/BatchBuyPopup")
|
||||
if batch_buy_popup and batch_buy_popup.has_method("show_buy_popup"):
|
||||
# 显示批量购买弹窗
|
||||
batch_buy_popup.show_buy_popup(
|
||||
product_name,
|
||||
product_price,
|
||||
"玩家小卖部商品",
|
||||
"store_product", # 特殊类型标识
|
||||
_on_confirm_buy_store_product,
|
||||
_on_cancel_buy_store_product
|
||||
)
|
||||
|
||||
# 临时保存购买信息
|
||||
batch_buy_popup.set_meta("store_slot_index", slot_index)
|
||||
batch_buy_popup.set_meta("store_product_data", product_data)
|
||||
else:
|
||||
Toast.show("购买功能暂未实现", Color.RED, 2.0, 1.0)
|
||||
|
||||
# 确认购买小卖部商品
|
||||
func _on_confirm_buy_store_product(product_name: String, unit_price: int, quantity: int, buy_type: String):
|
||||
var slot_index = get_node("/root/main/UI/DiaLog/BatchBuyPopup").get_meta("store_slot_index", -1)
|
||||
var product_data = get_node("/root/main/UI/DiaLog/BatchBuyPopup").get_meta("store_product_data", {})
|
||||
|
||||
if slot_index == -1 or product_data.is_empty():
|
||||
Toast.show("购买信息错误", Color.RED, 2.0, 1.0)
|
||||
return
|
||||
|
||||
# 发送购买请求到服务器
|
||||
var tcp_network_manager = get_node_or_null("/root/main/UI/BigPanel/TCPNetworkManagerPanel")
|
||||
if tcp_network_manager and tcp_network_manager.has_method("send_message"):
|
||||
var visited_player_name = main_game.visited_player_data.get("player_name", "")
|
||||
var message = {
|
||||
"type": "buy_store_product",
|
||||
"seller_username": main_game.visited_player_data.get("username", ""),
|
||||
"slot_index": slot_index,
|
||||
"product_name": product_name,
|
||||
"unit_price": unit_price,
|
||||
"quantity": quantity
|
||||
}
|
||||
tcp_network_manager.send_message(message)
|
||||
|
||||
Toast.show("购买请求已发送", Color.YELLOW, 2.0, 1.0)
|
||||
else:
|
||||
Toast.show("网络连接异常,无法购买", Color.RED, 2.0, 1.0)
|
||||
|
||||
# 取消购买小卖部商品
|
||||
func _on_cancel_buy_store_product():
|
||||
# 不需要做任何事情,弹窗会自动关闭
|
||||
pass
|
||||
|
||||
# 自己的小卖部:点击商品管理
|
||||
func _on_product_manage_selected(product_data: Dictionary, slot_index: int):
|
||||
var product_name = product_data.get("商品名称", "未知商品")
|
||||
var product_count = product_data.get("商品数量", 0)
|
||||
|
||||
# 显示管理确认对话框
|
||||
_show_product_manage_dialog(product_name, product_count, slot_index)
|
||||
|
||||
# 显示商品管理对话框
|
||||
func _show_product_manage_dialog(product_name: String, product_count: int, slot_index: int):
|
||||
var confirm_dialog = AcceptDialog.new()
|
||||
confirm_dialog.dialog_text = str(
|
||||
"商品管理\n\n" +
|
||||
"商品:" + product_name + "\n" +
|
||||
"库存:" + str(product_count) + " 个\n\n" +
|
||||
"确认要下架这个商品吗?\n" +
|
||||
"商品将返回到您的仓库中。"
|
||||
)
|
||||
confirm_dialog.title = "商品管理"
|
||||
confirm_dialog.ok_button_text = "下架商品"
|
||||
confirm_dialog.add_cancel_button("取消")
|
||||
|
||||
# 添加到场景
|
||||
add_child(confirm_dialog)
|
||||
|
||||
# 连接信号
|
||||
confirm_dialog.confirmed.connect(_on_confirm_remove_product.bind(slot_index, confirm_dialog))
|
||||
confirm_dialog.canceled.connect(_on_cancel_remove_product.bind(confirm_dialog))
|
||||
|
||||
# 显示对话框
|
||||
confirm_dialog.popup_centered()
|
||||
|
||||
# 确认下架商品
|
||||
func _on_confirm_remove_product(slot_index: int, dialog: AcceptDialog):
|
||||
# 发送下架商品请求到服务器
|
||||
var tcp_network_manager = get_node_or_null("/root/main/UI/BigPanel/TCPNetworkManagerPanel")
|
||||
if tcp_network_manager and tcp_network_manager.has_method("send_message"):
|
||||
var message = {
|
||||
"type": "remove_store_product",
|
||||
"slot_index": slot_index
|
||||
}
|
||||
tcp_network_manager.send_message(message)
|
||||
|
||||
Toast.show("下架请求已发送", Color.YELLOW, 2.0, 1.0)
|
||||
else:
|
||||
Toast.show("网络连接异常,无法下架", Color.RED, 2.0, 1.0)
|
||||
|
||||
dialog.queue_free()
|
||||
|
||||
# 取消下架商品
|
||||
func _on_cancel_remove_product(dialog: AcceptDialog):
|
||||
dialog.queue_free()
|
||||
|
||||
# 点击空格子
|
||||
func _on_empty_slot_selected(slot_index: int):
|
||||
Toast.show("请从作物仓库选择商品添加到小卖部", Color.CYAN, 3.0, 1.0)
|
||||
|
||||
# 更新购买格子按钮
|
||||
func _update_buy_booth_button():
|
||||
if main_game.is_visiting_mode:
|
||||
return
|
||||
|
||||
var next_slot_cost = 1000 + (max_store_slots - 10) * 500
|
||||
if max_store_slots >= 40:
|
||||
buy_product_booth_button.text = "格子已满(40/40)"
|
||||
buy_product_booth_button.disabled = true
|
||||
else:
|
||||
buy_product_booth_button.text = str("购买格子(+" + str(next_slot_cost) + "元)")
|
||||
buy_product_booth_button.disabled = false
|
||||
|
||||
# 购买格子按钮处理
|
||||
func _on_buy_product_booth_button_pressed():
|
||||
if main_game.is_visiting_mode:
|
||||
return
|
||||
|
||||
if max_store_slots >= 40:
|
||||
Toast.show("格子数量已达上限", Color.RED, 2.0, 1.0)
|
||||
return
|
||||
|
||||
var next_slot_cost = 1000 + (max_store_slots - 10) * 500
|
||||
|
||||
if main_game.money < next_slot_cost:
|
||||
Toast.show("金钱不足,需要 " + str(next_slot_cost) + " 元", Color.RED, 2.0, 1.0)
|
||||
return
|
||||
|
||||
# 显示购买确认对话框
|
||||
_show_buy_booth_dialog(next_slot_cost)
|
||||
|
||||
# 显示购买格子确认对话框
|
||||
func _show_buy_booth_dialog(cost: int):
|
||||
var confirm_dialog = AcceptDialog.new()
|
||||
confirm_dialog.dialog_text = str(
|
||||
"购买小卖部格子\n\n" +
|
||||
"费用:" + str(cost) + " 元\n" +
|
||||
"当前格子数:" + str(max_store_slots) + "\n" +
|
||||
"购买后格子数:" + str(max_store_slots + 1) + "\n\n" +
|
||||
"确认购买吗?"
|
||||
)
|
||||
confirm_dialog.title = "购买格子"
|
||||
confirm_dialog.ok_button_text = "确认购买"
|
||||
confirm_dialog.add_cancel_button("取消")
|
||||
|
||||
# 添加到场景
|
||||
add_child(confirm_dialog)
|
||||
|
||||
# 连接信号
|
||||
confirm_dialog.confirmed.connect(_on_confirm_buy_booth.bind(cost, confirm_dialog))
|
||||
confirm_dialog.canceled.connect(_on_cancel_buy_booth.bind(confirm_dialog))
|
||||
|
||||
# 显示对话框
|
||||
confirm_dialog.popup_centered()
|
||||
|
||||
# 确认购买格子
|
||||
func _on_confirm_buy_booth(cost: int, dialog: AcceptDialog):
|
||||
# 发送购买格子请求到服务器
|
||||
var tcp_network_manager = get_node_or_null("/root/main/UI/BigPanel/TCPNetworkManagerPanel")
|
||||
if tcp_network_manager and tcp_network_manager.has_method("send_message"):
|
||||
var message = {
|
||||
"type": "buy_store_booth",
|
||||
"cost": cost
|
||||
}
|
||||
tcp_network_manager.send_message(message)
|
||||
|
||||
Toast.show("购买请求已发送", Color.YELLOW, 2.0, 1.0)
|
||||
else:
|
||||
Toast.show("网络连接异常,无法购买", Color.RED, 2.0, 1.0)
|
||||
|
||||
dialog.queue_free()
|
||||
|
||||
# 取消购买格子
|
||||
func _on_cancel_buy_booth(dialog: AcceptDialog):
|
||||
dialog.queue_free()
|
||||
|
||||
# 关闭面板
|
||||
func _on_quit_button_pressed():
|
||||
self.hide()
|
||||
|
||||
# 刷新小卖部
|
||||
func _on_refresh_button_pressed():
|
||||
update_player_store_ui()
|
||||
Toast.show("小卖部已刷新", Color.GREEN, 2.0, 1.0)
|
||||
1
Script/BigPanel/PlayerStorePanel.gd.uid
Normal file
@@ -0,0 +1 @@
|
||||
uid://bdavskipn547h
|
||||
197
Script/Dialog/AddProduct2StorePopup.gd
Normal file
@@ -0,0 +1,197 @@
|
||||
extends PanelContainer
|
||||
#用于添加商品到玩家小卖部的弹窗
|
||||
@onready var title: Label = $VBox/Title #弹窗标题
|
||||
@onready var contents: Label = $VBox/Contents #这里显示弹窗内容
|
||||
@onready var sell_num_input: LineEdit = $VBox/SellNumInput #这里输入需要放入小卖部的商品数量
|
||||
@onready var sell_price_input: LineEdit = $VBox/SellPriceInput #这里输入每件商品的价格
|
||||
@onready var sure_button: Button = $VBox/HBox/SureButton #确定放入按钮
|
||||
@onready var cancel_button: Button = $VBox/HBox/CancelButton #取消按钮
|
||||
|
||||
# 当前要添加的商品信息
|
||||
var current_product_name: String = ""
|
||||
var current_max_count: int = 0
|
||||
var current_suggested_price: int = 0
|
||||
var current_product_desc: String = ""
|
||||
|
||||
# 回调函数,用于处理确认添加
|
||||
var confirm_callback: Callable
|
||||
var cancel_callback: Callable
|
||||
|
||||
func _ready():
|
||||
# 连接按钮信号
|
||||
sure_button.pressed.connect(_on_sure_button_pressed)
|
||||
cancel_button.pressed.connect(_on_cancel_button_pressed)
|
||||
|
||||
# 设置输入框的默认值和限制
|
||||
sell_num_input.text = "1"
|
||||
sell_num_input.placeholder_text = "请输入数量"
|
||||
sell_price_input.placeholder_text = "请输入单价"
|
||||
|
||||
# 只允许输入数字
|
||||
sell_num_input.text_changed.connect(_on_sell_num_changed)
|
||||
sell_price_input.text_changed.connect(_on_sell_price_changed)
|
||||
|
||||
# 连接可见性改变信号
|
||||
visibility_changed.connect(_on_visibility_changed)
|
||||
|
||||
# 默认隐藏弹窗
|
||||
self.hide()
|
||||
|
||||
#面板显示与隐藏切换处理
|
||||
func _on_visibility_changed():
|
||||
if visible:
|
||||
GlobalVariables.isZoomDisabled = true
|
||||
pass
|
||||
else:
|
||||
GlobalVariables.isZoomDisabled = false
|
||||
pass
|
||||
|
||||
# 显示添加商品弹窗
|
||||
func show_add_product_popup(product_name: String, max_count: int, suggested_price: int, product_desc: String, on_confirm: Callable, on_cancel: Callable = Callable()):
|
||||
current_product_name = product_name
|
||||
current_max_count = max_count
|
||||
current_suggested_price = suggested_price
|
||||
current_product_desc = product_desc
|
||||
confirm_callback = on_confirm
|
||||
cancel_callback = on_cancel
|
||||
|
||||
# 设置弹窗内容
|
||||
title.text = "添加商品到小卖部"
|
||||
|
||||
contents.text = str(
|
||||
"商品名称: " + product_name + "\n" +
|
||||
"可用数量: " + str(max_count) + " 个\n" +
|
||||
"建议价格: " + str(suggested_price) + " 元/个\n" +
|
||||
"描述: " + product_desc + "\n\n" +
|
||||
"请设置出售数量和价格:"
|
||||
)
|
||||
|
||||
# 设置默认值
|
||||
sell_num_input.text = "1"
|
||||
sell_price_input.text = str(suggested_price)
|
||||
|
||||
# 显示弹窗并居中
|
||||
self.show()
|
||||
self.move_to_front()
|
||||
|
||||
# 处理数量输入变化
|
||||
func _on_sell_num_changed(new_text: String):
|
||||
# 只允许输入数字
|
||||
var filtered_text = ""
|
||||
for char in new_text:
|
||||
if char.is_valid_int():
|
||||
filtered_text += char
|
||||
|
||||
if filtered_text != new_text:
|
||||
sell_num_input.text = filtered_text
|
||||
sell_num_input.caret_column = filtered_text.length()
|
||||
|
||||
# 更新预览信息
|
||||
_update_preview_info()
|
||||
|
||||
# 处理价格输入变化
|
||||
func _on_sell_price_changed(new_text: String):
|
||||
# 只允许输入数字
|
||||
var filtered_text = ""
|
||||
for char in new_text:
|
||||
if char.is_valid_int():
|
||||
filtered_text += char
|
||||
|
||||
if filtered_text != new_text:
|
||||
sell_price_input.text = filtered_text
|
||||
sell_price_input.caret_column = filtered_text.length()
|
||||
|
||||
# 更新预览信息
|
||||
_update_preview_info()
|
||||
|
||||
# 更新预览信息
|
||||
func _update_preview_info():
|
||||
var quantity = get_sell_quantity()
|
||||
var unit_price = get_sell_price()
|
||||
var total_value = quantity * unit_price
|
||||
|
||||
# 检查数量是否超过最大可用数量
|
||||
var quantity_status = ""
|
||||
if quantity > current_max_count:
|
||||
quantity_status = " (超出库存!)"
|
||||
|
||||
# 检查价格是否合理
|
||||
var price_status = ""
|
||||
if unit_price <= 0:
|
||||
price_status = " (价格无效!)"
|
||||
elif unit_price < current_suggested_price * 0.5:
|
||||
price_status = " (价格偏低)"
|
||||
elif unit_price > current_suggested_price * 2:
|
||||
price_status = " (价格偏高)"
|
||||
|
||||
var preview_info = "\n上架数量: " + str(quantity) + " 个" + quantity_status + "\n单价: " + str(unit_price) + " 元/个" + price_status + "\n总价值: " + str(total_value) + " 元"
|
||||
|
||||
# 更新内容显示
|
||||
var base_content = str(
|
||||
"商品名称: " + current_product_name + "\n" +
|
||||
"可用数量: " + str(current_max_count) + " 个\n" +
|
||||
"建议价格: " + str(current_suggested_price) + " 元/个\n" +
|
||||
"描述: " + current_product_desc + "\n\n" +
|
||||
"请设置出售数量和价格:"
|
||||
)
|
||||
|
||||
contents.text = base_content + preview_info
|
||||
|
||||
# 获取出售数量
|
||||
func get_sell_quantity() -> int:
|
||||
var text = sell_num_input.text.strip_edges()
|
||||
if text.is_empty():
|
||||
return 1
|
||||
|
||||
var quantity = text.to_int()
|
||||
return max(1, quantity) # 至少出售1个
|
||||
|
||||
# 获取出售价格
|
||||
func get_sell_price() -> int:
|
||||
var text = sell_price_input.text.strip_edges()
|
||||
if text.is_empty():
|
||||
return current_suggested_price
|
||||
|
||||
var price = text.to_int()
|
||||
return max(1, price) # 至少1元
|
||||
|
||||
# 确认添加按钮处理
|
||||
func _on_sure_button_pressed():
|
||||
var quantity = get_sell_quantity()
|
||||
var unit_price = get_sell_price()
|
||||
|
||||
if quantity <= 0:
|
||||
_show_error("数量必须大于0")
|
||||
return
|
||||
|
||||
if quantity > current_max_count:
|
||||
_show_error("数量不能超过库存数量(" + str(current_max_count) + ")")
|
||||
return
|
||||
|
||||
if unit_price <= 0:
|
||||
_show_error("价格必须大于0")
|
||||
return
|
||||
|
||||
# 调用确认回调函数
|
||||
if confirm_callback.is_valid():
|
||||
confirm_callback.call(current_product_name, quantity, unit_price)
|
||||
|
||||
# 隐藏弹窗
|
||||
self.hide()
|
||||
|
||||
# 取消添加按钮处理
|
||||
func _on_cancel_button_pressed():
|
||||
# 调用取消回调函数
|
||||
if cancel_callback.is_valid():
|
||||
cancel_callback.call()
|
||||
|
||||
# 隐藏弹窗
|
||||
self.hide()
|
||||
|
||||
# 显示错误信息
|
||||
func _show_error(message: String):
|
||||
# 显示Toast错误提示
|
||||
if has_node("/root/Toast"):
|
||||
get_node("/root/Toast").show(message, Color.RED, 2.0, 1.0)
|
||||
else:
|
||||
print("添加商品弹窗错误: " + message)
|
||||
1
Script/Dialog/AddProduct2StorePopup.gd.uid
Normal file
@@ -0,0 +1 @@
|
||||
uid://cha0uw4ra1trr
|
||||
154
Script/Dialog/BatchSellPopup.gd
Normal file
@@ -0,0 +1,154 @@
|
||||
extends PanelContainer
|
||||
#用于作物批量出售作物弹窗
|
||||
@onready var title: Label = $VBox/Title #弹窗标题
|
||||
@onready var contents: Label = $VBox/Contents #这里显示弹窗内容
|
||||
@onready var sell_num_edit: LineEdit = $VBox/SellNumEdit #出售作物数量
|
||||
@onready var sure_button: Button = $VBox/HBox/SureButton #确定按钮
|
||||
@onready var cancel_button: Button = $VBox/HBox/CancelButton #取消按钮
|
||||
|
||||
# 当前出售的作物信息
|
||||
var current_crop_name: String = ""
|
||||
var current_max_count: int = 0
|
||||
var current_unit_price: int = 0
|
||||
var current_crop_desc: String = ""
|
||||
|
||||
# 回调函数,用于处理确认出售
|
||||
var confirm_callback: Callable
|
||||
var cancel_callback: Callable
|
||||
|
||||
func _ready():
|
||||
# 连接按钮信号
|
||||
sure_button.pressed.connect(_on_sure_button_pressed)
|
||||
cancel_button.pressed.connect(_on_cancel_button_pressed)
|
||||
|
||||
# 设置数量输入框的默认值和限制
|
||||
sell_num_edit.text = "1"
|
||||
sell_num_edit.placeholder_text = "请输入出售数量"
|
||||
|
||||
# 只允许输入数字
|
||||
sell_num_edit.text_changed.connect(_on_sell_num_changed)
|
||||
|
||||
# 连接可见性改变信号
|
||||
visibility_changed.connect(_on_visibility_changed)
|
||||
|
||||
# 默认隐藏弹窗
|
||||
self.hide()
|
||||
|
||||
#面板显示与隐藏切换处理
|
||||
func _on_visibility_changed():
|
||||
if visible:
|
||||
GlobalVariables.isZoomDisabled = true
|
||||
pass
|
||||
else:
|
||||
GlobalVariables.isZoomDisabled = false
|
||||
pass
|
||||
|
||||
# 显示批量出售弹窗
|
||||
func show_sell_popup(crop_name: String, max_count: int, unit_price: int, crop_desc: String, on_confirm: Callable, on_cancel: Callable = Callable()):
|
||||
current_crop_name = crop_name
|
||||
current_max_count = max_count
|
||||
current_unit_price = unit_price
|
||||
current_crop_desc = crop_desc
|
||||
confirm_callback = on_confirm
|
||||
cancel_callback = on_cancel
|
||||
|
||||
# 设置弹窗内容
|
||||
title.text = "批量出售作物"
|
||||
|
||||
contents.text = str(
|
||||
"作物名称: " + crop_name + "\n" +
|
||||
"单价: " + str(unit_price) + " 元/个\n" +
|
||||
"可出售数量: " + str(max_count) + " 个\n" +
|
||||
"描述: " + crop_desc + "\n\n" +
|
||||
"请输入出售数量:"
|
||||
)
|
||||
|
||||
# 重置出售数量为1
|
||||
sell_num_edit.text = "1"
|
||||
|
||||
# 显示弹窗并居中
|
||||
self.show()
|
||||
self.move_to_front()
|
||||
|
||||
# 处理数量输入变化
|
||||
func _on_sell_num_changed(new_text: String):
|
||||
# 只允许输入数字
|
||||
var filtered_text = ""
|
||||
for char in new_text:
|
||||
if char.is_valid_int():
|
||||
filtered_text += char
|
||||
|
||||
if filtered_text != new_text:
|
||||
sell_num_edit.text = filtered_text
|
||||
sell_num_edit.caret_column = filtered_text.length()
|
||||
|
||||
# 更新总价显示
|
||||
_update_total_income()
|
||||
|
||||
# 更新总收入显示
|
||||
func _update_total_income():
|
||||
var quantity = get_sell_quantity()
|
||||
var total_income = quantity * current_unit_price
|
||||
|
||||
# 检查数量是否超过最大可售数量
|
||||
var quantity_status = ""
|
||||
if quantity > current_max_count:
|
||||
quantity_status = " (超出库存!)"
|
||||
|
||||
var income_info = "\n出售数量: " + str(quantity) + " 个" + quantity_status + "\n总收入: " + str(total_income) + " 元"
|
||||
|
||||
# 更新内容显示
|
||||
var base_content = str(
|
||||
"作物名称: " + current_crop_name + "\n" +
|
||||
"单价: " + str(current_unit_price) + " 元/个\n" +
|
||||
"可出售数量: " + str(current_max_count) + " 个\n" +
|
||||
"描述: " + current_crop_desc + "\n\n" +
|
||||
"请输入出售数量:"
|
||||
)
|
||||
|
||||
contents.text = base_content + income_info
|
||||
|
||||
# 获取出售数量
|
||||
func get_sell_quantity() -> int:
|
||||
var text = sell_num_edit.text.strip_edges()
|
||||
if text.is_empty():
|
||||
return 1
|
||||
|
||||
var quantity = text.to_int()
|
||||
return max(1, quantity) # 至少出售1个
|
||||
|
||||
# 确认出售按钮处理
|
||||
func _on_sure_button_pressed():
|
||||
var quantity = get_sell_quantity()
|
||||
|
||||
if quantity <= 0:
|
||||
_show_error("出售数量必须大于0")
|
||||
return
|
||||
|
||||
if quantity > current_max_count:
|
||||
_show_error("出售数量不能超过库存数量(" + str(current_max_count) + ")")
|
||||
return
|
||||
|
||||
# 调用确认回调函数
|
||||
if confirm_callback.is_valid():
|
||||
confirm_callback.call(current_crop_name, quantity, current_unit_price)
|
||||
|
||||
# 隐藏弹窗
|
||||
self.hide()
|
||||
|
||||
# 取消出售按钮处理
|
||||
func _on_cancel_button_pressed():
|
||||
# 调用取消回调函数
|
||||
if cancel_callback.is_valid():
|
||||
cancel_callback.call()
|
||||
|
||||
# 隐藏弹窗
|
||||
self.hide()
|
||||
|
||||
# 显示错误信息
|
||||
func _show_error(message: String):
|
||||
# 显示Toast错误提示
|
||||
if has_node("/root/Toast"):
|
||||
get_node("/root/Toast").show(message, Color.RED, 2.0, 1.0)
|
||||
else:
|
||||
print("批量出售弹窗错误: " + message)
|
||||
1
Script/Dialog/BatchSellPopup.gd.uid
Normal file
@@ -0,0 +1 @@
|
||||
uid://dsmmxivba06ab
|
||||
216
Script/SmallPanel/CropInformPanel.gd
Normal file
@@ -0,0 +1,216 @@
|
||||
extends Panel
|
||||
|
||||
@onready var quit_button: Button = $QuitButton #关闭作物信息面板
|
||||
@onready var crop_image: TextureRect = $VBox/CropImage #显示作物图片
|
||||
@onready var crop_name: Label = $VBox/CropName #作物名称
|
||||
@onready var crop_description: Label = $VBox/CropDescription #作物介绍
|
||||
@onready var crop_price: Label = $VBox/CropPrice #作物价格
|
||||
@onready var crop_quality: Label = $VBox/CropQuality #作物品质
|
||||
@onready var sale_product: Button = $VBox/HBox/SaleProduct #直接出售
|
||||
@onready var add_to_store: Button = $VBox/HBox/AddToStore #添加到小卖部
|
||||
|
||||
@onready var add_product_to_store_popup: PanelContainer = $'../../DiaLog/AddProductToStorePopup'
|
||||
|
||||
|
||||
|
||||
# 当前显示的作物信息
|
||||
var current_crop_name: String = ""
|
||||
var current_crop_count: int = 0
|
||||
|
||||
# 获取主游戏引用
|
||||
@onready var main_game = get_node("/root/main")
|
||||
|
||||
func _ready():
|
||||
# 连接按钮信号
|
||||
quit_button.pressed.connect(_on_quit_button_pressed)
|
||||
sale_product.pressed.connect(_on_sale_product_pressed)
|
||||
add_to_store.pressed.connect(_on_add_to_store_pressed)
|
||||
|
||||
# 默认隐藏面板
|
||||
self.hide()
|
||||
|
||||
# 显示作物信息
|
||||
func show_crop_info(crop_name: String, crop_count: int):
|
||||
current_crop_name = crop_name
|
||||
current_crop_count = crop_count
|
||||
|
||||
# 更新作物信息显示
|
||||
_update_crop_display()
|
||||
|
||||
# 显示面板
|
||||
self.show()
|
||||
self.move_to_front()
|
||||
|
||||
# 更新作物信息显示
|
||||
func _update_crop_display():
|
||||
if not main_game.can_planted_crop.has(current_crop_name):
|
||||
crop_name.text = "作物名称:" + current_crop_name
|
||||
crop_description.text = "描述:未知作物"
|
||||
crop_price.text = "收购价:未知"
|
||||
crop_quality.text = "品质:未知"
|
||||
return
|
||||
|
||||
var crop_data = main_game.can_planted_crop[current_crop_name]
|
||||
|
||||
# 获取显示名称
|
||||
var display_name = current_crop_name
|
||||
var mature_name = crop_data.get("成熟物名称")
|
||||
if mature_name != null and mature_name != "":
|
||||
display_name = mature_name
|
||||
else:
|
||||
display_name = crop_data.get("作物名称", current_crop_name)
|
||||
|
||||
# 更新文本显示
|
||||
crop_name.text = "作物名称:" + display_name + " (数量: " + str(current_crop_count) + ")"
|
||||
crop_description.text = "描述:" + crop_data.get("描述", "美味的作物")
|
||||
|
||||
# 计算出售价格(基于收益)
|
||||
var sell_price = crop_data.get("收益", 0)
|
||||
crop_price.text = "收购价:" + str(sell_price) + " 元/个"
|
||||
|
||||
var quality = crop_data.get("品质", "普通")
|
||||
crop_quality.text = "品质:" + quality
|
||||
|
||||
# 更新作物图片
|
||||
_update_crop_image()
|
||||
|
||||
# 更新作物图片
|
||||
func _update_crop_image():
|
||||
var texture = _get_crop_harvest_texture(current_crop_name)
|
||||
if texture:
|
||||
crop_image.texture = texture
|
||||
else:
|
||||
# 使用默认图片
|
||||
var default_texture = _get_crop_harvest_texture("默认")
|
||||
if default_texture:
|
||||
crop_image.texture = default_texture
|
||||
|
||||
# 获取作物的收获物图片
|
||||
func _get_crop_harvest_texture(crop_name: String) -> Texture2D:
|
||||
var crop_path = "res://assets/作物/" + crop_name + "/"
|
||||
var harvest_texture_path = crop_path + "收获物.webp"
|
||||
|
||||
if ResourceLoader.exists(harvest_texture_path):
|
||||
var texture = load(harvest_texture_path)
|
||||
if texture:
|
||||
return texture
|
||||
|
||||
# 如果没有找到,使用默认的收获物图片
|
||||
var default_harvest_path = "res://assets/作物/默认/收获物.webp"
|
||||
if ResourceLoader.exists(default_harvest_path):
|
||||
var texture = load(default_harvest_path)
|
||||
if texture:
|
||||
return texture
|
||||
|
||||
return null
|
||||
|
||||
# 关闭面板
|
||||
func _on_quit_button_pressed():
|
||||
self.hide()
|
||||
|
||||
# 直接出售按钮处理
|
||||
func _on_sale_product_pressed():
|
||||
# 检查是否在访问模式
|
||||
if main_game.is_visiting_mode:
|
||||
Toast.show("访问模式下无法出售作物", Color.ORANGE, 2.0, 1.0)
|
||||
return
|
||||
|
||||
# 获取批量出售弹窗
|
||||
var batch_sell_popup = get_node_or_null("/root/main/UI/DiaLog/BatchSellPopup")
|
||||
if batch_sell_popup and batch_sell_popup.has_method("show_sell_popup"):
|
||||
# 获取作物数据以传递给出售弹窗
|
||||
var crop_data = main_game.can_planted_crop.get(current_crop_name, {})
|
||||
var sell_price = crop_data.get("收益", 0)
|
||||
var description = crop_data.get("描述", "美味的作物")
|
||||
|
||||
# 显示批量出售弹窗
|
||||
batch_sell_popup.show_sell_popup(
|
||||
current_crop_name,
|
||||
current_crop_count,
|
||||
sell_price,
|
||||
description,
|
||||
_on_confirm_sell_crop,
|
||||
_on_cancel_sell_crop
|
||||
)
|
||||
else:
|
||||
Toast.show("批量出售功能暂未实现", Color.RED, 2.0, 1.0)
|
||||
print("错误:找不到BatchSellPopup或相关方法")
|
||||
|
||||
# 确认出售作物回调
|
||||
func _on_confirm_sell_crop(crop_name: String, sell_count: int, unit_price: int):
|
||||
# 发送出售请求到服务器
|
||||
var tcp_network_manager = get_node_or_null("/root/main/UI/BigPanel/TCPNetworkManagerPanel")
|
||||
if tcp_network_manager and tcp_network_manager.has_method("send_message"):
|
||||
var message = {
|
||||
"type": "sell_crop",
|
||||
"crop_name": crop_name,
|
||||
"sell_count": sell_count,
|
||||
"unit_price": unit_price
|
||||
}
|
||||
tcp_network_manager.send_message(message)
|
||||
|
||||
# 关闭作物信息面板
|
||||
self.hide()
|
||||
|
||||
Toast.show("出售请求已发送", Color.YELLOW, 2.0, 1.0)
|
||||
else:
|
||||
Toast.show("网络连接异常,无法出售", Color.RED, 2.0, 1.0)
|
||||
|
||||
# 取消出售作物回调
|
||||
func _on_cancel_sell_crop():
|
||||
# 不需要做任何事情,弹窗会自动关闭
|
||||
pass
|
||||
|
||||
# 添加到小卖部按钮处理
|
||||
func _on_add_to_store_pressed():
|
||||
# 检查是否在访问模式
|
||||
if main_game.is_visiting_mode:
|
||||
Toast.show("访问模式下无法操作小卖部", Color.ORANGE, 2.0, 1.0)
|
||||
return
|
||||
|
||||
# 获取添加商品到小卖部的弹窗
|
||||
|
||||
if add_product_to_store_popup and add_product_to_store_popup.has_method("show_add_product_popup"):
|
||||
# 获取作物数据以传递给弹窗
|
||||
var crop_data = main_game.can_planted_crop.get(current_crop_name, {})
|
||||
var sell_price = crop_data.get("收益", 0)
|
||||
var description = crop_data.get("描述", "美味的作物")
|
||||
|
||||
# 显示添加商品弹窗
|
||||
add_product_to_store_popup.show_add_product_popup(
|
||||
current_crop_name,
|
||||
current_crop_count,
|
||||
sell_price,
|
||||
description,
|
||||
_on_confirm_add_to_store,
|
||||
_on_cancel_add_to_store
|
||||
)
|
||||
else:
|
||||
Toast.show("添加商品功能暂未实现", Color.RED, 2.0, 1.0)
|
||||
print("错误:找不到AddProduct2StorePopup或相关方法")
|
||||
|
||||
# 确认添加到小卖部回调
|
||||
func _on_confirm_add_to_store(crop_name: String, add_count: int, unit_price: int):
|
||||
# 发送添加商品到小卖部的请求到服务器
|
||||
var tcp_network_manager = get_node_or_null("/root/main/UI/BigPanel/TCPNetworkManagerPanel")
|
||||
if tcp_network_manager and tcp_network_manager.has_method("send_message"):
|
||||
var message = {
|
||||
"type": "add_product_to_store",
|
||||
"product_type": "作物",
|
||||
"product_name": crop_name,
|
||||
"product_count": add_count,
|
||||
"product_price": unit_price
|
||||
}
|
||||
tcp_network_manager.send_message(message)
|
||||
|
||||
# 关闭作物信息面板
|
||||
self.hide()
|
||||
|
||||
Toast.show("添加商品请求已发送", Color.YELLOW, 2.0, 1.0)
|
||||
else:
|
||||
Toast.show("网络连接异常,无法添加商品", Color.RED, 2.0, 1.0)
|
||||
|
||||
# 取消添加到小卖部回调
|
||||
func _on_cancel_add_to_store():
|
||||
# 不需要做任何事情,弹窗会自动关闭
|
||||
pass
|
||||
1
Script/SmallPanel/CropInformPanel.gd.uid
Normal file
@@ -0,0 +1 @@
|
||||
uid://b185o1hjnlrv5
|
||||
@@ -98,7 +98,12 @@ func _update_performance_data():
|
||||
# 从主游戏获取加载信息
|
||||
if main_game and main_game.crop_texture_manager:
|
||||
var manager = main_game.crop_texture_manager
|
||||
performance_data["loaded_textures"] = manager.texture_cache.size() + manager.mature_texture_cache.size()
|
||||
# 计算所有加载的纹理数量(新的三阶段系统)
|
||||
var total_textures = 0
|
||||
for crop_name in manager.texture_cache.keys():
|
||||
total_textures += manager.texture_cache[crop_name].size()
|
||||
total_textures += manager.default_textures.size()
|
||||
performance_data["loaded_textures"] = total_textures
|
||||
performance_data["failed_textures"] = manager.failed_resources.size()
|
||||
|
||||
# 加载进度
|
||||
|
||||
@@ -131,13 +131,14 @@ class EmailVerification:
|
||||
return ''.join(random.choice(chars) for _ in range(length))
|
||||
|
||||
@staticmethod
|
||||
def send_verification_email(qq_number, verification_code):
|
||||
def send_verification_email(qq_number, verification_code, email_type="register"):
|
||||
"""
|
||||
发送验证码邮件到QQ邮箱
|
||||
|
||||
参数:
|
||||
qq_number (str): 接收者QQ号
|
||||
verification_code (str): 验证码
|
||||
email_type (str): 邮件类型,"register" 或 "reset_password"
|
||||
|
||||
返回:
|
||||
bool: 发送成功返回True,否则返回False
|
||||
@@ -145,15 +146,25 @@ class EmailVerification:
|
||||
"""
|
||||
receiver_email = f"{qq_number}@qq.com"
|
||||
|
||||
# 根据邮件类型设置不同的内容
|
||||
if email_type == "reset_password":
|
||||
email_title = "【萌芽农场】密码重置验证码"
|
||||
email_purpose = "重置萌芽农场游戏账号密码"
|
||||
email_color = "#FF6B35" # 橙红色,表示警告性操作
|
||||
else:
|
||||
email_title = "【萌芽农场】注册验证码"
|
||||
email_purpose = "注册萌芽农场游戏账号"
|
||||
email_color = "#4CAF50" # 绿色,表示正常操作
|
||||
|
||||
# 创建邮件内容
|
||||
message = MIMEText(f'''
|
||||
<html>
|
||||
<body>
|
||||
<div style="font-family: Arial, sans-serif; color: #333;">
|
||||
<h2 style="color: #4CAF50;">萌芽农场 - 邮箱验证码</h2>
|
||||
<h2 style="color: {email_color};">萌芽农场 - 邮箱验证码</h2>
|
||||
<p>亲爱的玩家,您好!</p>
|
||||
<p>您正在注册萌芽农场游戏账号,您的验证码是:</p>
|
||||
<div style="background-color: #f2f2f2; padding: 10px; font-size: 24px; font-weight: bold; color: #4CAF50; text-align: center; margin: 20px 0;">
|
||||
<p>您正在{email_purpose},您的验证码是:</p>
|
||||
<div style="background-color: #f2f2f2; padding: 10px; font-size: 24px; font-weight: bold; color: {email_color}; text-align: center; margin: 20px 0;">
|
||||
{verification_code}
|
||||
</div>
|
||||
<p>该验证码有效期为5分钟,请勿泄露给他人。</p>
|
||||
@@ -169,7 +180,7 @@ class EmailVerification:
|
||||
# 修正From头格式,符合QQ邮箱的要求
|
||||
message['From'] = SENDER_EMAIL
|
||||
message['To'] = receiver_email
|
||||
message['Subject'] = Header('【萌芽农场】注册验证码', 'utf-8')
|
||||
message['Subject'] = Header(email_title, 'utf-8')
|
||||
|
||||
try:
|
||||
# 使用SSL/TLS连接而不是STARTTLS
|
||||
@@ -182,7 +193,7 @@ class EmailVerification:
|
||||
return False, f"发送验证码失败: {str(e)}"
|
||||
|
||||
@staticmethod
|
||||
def save_verification_code(qq_number, verification_code, expiry_time=300):
|
||||
def save_verification_code(qq_number, verification_code, expiry_time=300, code_type="register"):
|
||||
"""
|
||||
保存验证码到缓存文件
|
||||
|
||||
@@ -190,6 +201,7 @@ class EmailVerification:
|
||||
qq_number (str): QQ号
|
||||
verification_code (str): 验证码
|
||||
expiry_time (int): 过期时间(秒),默认5分钟
|
||||
code_type (str): 验证码类型,"register" 或 "reset_password"
|
||||
|
||||
返回:
|
||||
bool: 保存成功返回True,否则返回False
|
||||
@@ -205,33 +217,43 @@ class EmailVerification:
|
||||
try:
|
||||
with open(VERIFICATION_CACHE_FILE, 'r', encoding='utf-8') as file:
|
||||
verification_data = json.load(file)
|
||||
except:
|
||||
except Exception as e:
|
||||
print(f"读取验证码文件失败: {str(e)}")
|
||||
verification_data = {}
|
||||
|
||||
# 添加新的验证码
|
||||
expire_at = time.time() + expiry_time
|
||||
current_time = time.time()
|
||||
|
||||
# 创建验证码记录,包含更多信息用于调试
|
||||
verification_data[qq_number] = {
|
||||
"code": verification_code,
|
||||
"expire_at": expire_at
|
||||
"expire_at": expire_at,
|
||||
"code_type": code_type,
|
||||
"created_at": current_time,
|
||||
"used": False # 新增:标记验证码是否已使用
|
||||
}
|
||||
|
||||
# 保存到文件
|
||||
try:
|
||||
with open(VERIFICATION_CACHE_FILE, 'w', encoding='utf-8') as file:
|
||||
json.dump(verification_data, file, indent=2, ensure_ascii=False)
|
||||
|
||||
print(f"[验证码系统] 为QQ {qq_number} 保存{code_type}验证码: {verification_code}, 过期时间: {expire_at}")
|
||||
return True
|
||||
except Exception as e:
|
||||
print(f"保存验证码失败: {str(e)}")
|
||||
return False
|
||||
|
||||
@staticmethod
|
||||
def verify_code(qq_number, input_code):
|
||||
def verify_code(qq_number, input_code, code_type="register"):
|
||||
"""
|
||||
验证用户输入的验证码
|
||||
|
||||
参数:
|
||||
qq_number (str): QQ号
|
||||
input_code (str): 用户输入的验证码
|
||||
code_type (str): 验证码类型,"register" 或 "reset_password"
|
||||
|
||||
返回:
|
||||
bool: 验证成功返回True,否则返回False
|
||||
@@ -241,23 +263,41 @@ class EmailVerification:
|
||||
|
||||
# 检查缓存文件是否存在
|
||||
if not os.path.exists(VERIFICATION_CACHE_FILE):
|
||||
print(f"[验证码系统] QQ {qq_number} 验证失败: 缓存文件不存在")
|
||||
return False, "验证码不存在或已过期"
|
||||
|
||||
# 读取验证码数据
|
||||
try:
|
||||
with open(VERIFICATION_CACHE_FILE, 'r', encoding='utf-8') as file:
|
||||
verification_data = json.load(file)
|
||||
except:
|
||||
except Exception as e:
|
||||
print(f"[验证码系统] 读取验证码文件失败: {str(e)}")
|
||||
return False, "验证码数据损坏"
|
||||
|
||||
# 检查该QQ号是否有验证码
|
||||
if qq_number not in verification_data:
|
||||
print(f"[验证码系统] QQ {qq_number} 验证失败: 没有找到验证码记录")
|
||||
return False, "验证码不存在,请重新获取"
|
||||
|
||||
# 获取存储的验证码信息
|
||||
code_info = verification_data[qq_number]
|
||||
stored_code = code_info.get("code", "")
|
||||
expire_at = code_info.get("expire_at", 0)
|
||||
stored_code_type = code_info.get("code_type", "register")
|
||||
is_used = code_info.get("used", False)
|
||||
created_at = code_info.get("created_at", 0)
|
||||
|
||||
print(f"[验证码系统] QQ {qq_number} 验证码详情: 存储码={stored_code}, 输入码={input_code}, 类型={stored_code_type}, 已使用={is_used}, 创建时间={created_at}")
|
||||
|
||||
# 检查验证码类型是否匹配
|
||||
if stored_code_type != code_type:
|
||||
print(f"[验证码系统] QQ {qq_number} 验证失败: 验证码类型不匹配,存储类型={stored_code_type}, 请求类型={code_type}")
|
||||
return False, f"验证码类型不匹配,请重新获取{code_type}验证码"
|
||||
|
||||
# 检查验证码是否已被使用
|
||||
if is_used:
|
||||
print(f"[验证码系统] QQ {qq_number} 验证失败: 验证码已被使用")
|
||||
return False, "验证码已被使用,请重新获取"
|
||||
|
||||
# 检查验证码是否过期
|
||||
current_time = time.time()
|
||||
@@ -266,22 +306,31 @@ class EmailVerification:
|
||||
del verification_data[qq_number]
|
||||
with open(VERIFICATION_CACHE_FILE, 'w', encoding='utf-8') as file:
|
||||
json.dump(verification_data, file, indent=2, ensure_ascii=False)
|
||||
print(f"[验证码系统] QQ {qq_number} 验证失败: 验证码已过期")
|
||||
return False, "验证码已过期,请重新获取"
|
||||
|
||||
# 验证码比较(不区分大小写)
|
||||
if input_code.upper() == stored_code.upper():
|
||||
# 验证成功后移除该验证码
|
||||
del verification_data[qq_number]
|
||||
with open(VERIFICATION_CACHE_FILE, 'w', encoding='utf-8') as file:
|
||||
json.dump(verification_data, file, indent=2, ensure_ascii=False)
|
||||
return True, "验证码正确"
|
||||
# 验证成功,标记为已使用而不是删除
|
||||
verification_data[qq_number]["used"] = True
|
||||
verification_data[qq_number]["used_at"] = current_time
|
||||
|
||||
try:
|
||||
with open(VERIFICATION_CACHE_FILE, 'w', encoding='utf-8') as file:
|
||||
json.dump(verification_data, file, indent=2, ensure_ascii=False)
|
||||
print(f"[验证码系统] QQ {qq_number} 验证成功: 验证码已标记为已使用")
|
||||
return True, "验证码正确"
|
||||
except Exception as e:
|
||||
print(f"[验证码系统] 标记验证码已使用时失败: {str(e)}")
|
||||
return True, "验证码正确" # 即使标记失败,验证还是成功的
|
||||
else:
|
||||
print(f"[验证码系统] QQ {qq_number} 验证失败: 验证码不匹配")
|
||||
return False, "验证码错误"
|
||||
|
||||
@staticmethod
|
||||
def clean_expired_codes():
|
||||
"""
|
||||
清理过期的验证码
|
||||
清理过期的验证码和已使用的验证码
|
||||
"""
|
||||
import time
|
||||
|
||||
@@ -295,22 +344,79 @@ class EmailVerification:
|
||||
current_time = time.time()
|
||||
removed_keys = []
|
||||
|
||||
# 找出过期的验证码
|
||||
# 找出过期的验证码和已使用的验证码(超过1小时)
|
||||
for qq_number, code_info in verification_data.items():
|
||||
expire_at = code_info.get("expire_at", 0)
|
||||
is_used = code_info.get("used", False)
|
||||
used_at = code_info.get("used_at", 0)
|
||||
|
||||
should_remove = False
|
||||
|
||||
# 过期的验证码
|
||||
if current_time > expire_at:
|
||||
should_remove = True
|
||||
print(f"[验证码清理] 移除过期验证码: QQ {qq_number}")
|
||||
|
||||
# 已使用超过1小时的验证码
|
||||
elif is_used and used_at > 0 and (current_time - used_at) > 3600:
|
||||
should_remove = True
|
||||
print(f"[验证码清理] 移除已使用的验证码: QQ {qq_number}")
|
||||
|
||||
if should_remove:
|
||||
removed_keys.append(qq_number)
|
||||
|
||||
# 移除过期的验证码
|
||||
# 移除标记的验证码
|
||||
for key in removed_keys:
|
||||
del verification_data[key]
|
||||
|
||||
# 保存更新后的数据
|
||||
with open(VERIFICATION_CACHE_FILE, 'w', encoding='utf-8') as file:
|
||||
json.dump(verification_data, file, indent=2, ensure_ascii=False)
|
||||
if removed_keys:
|
||||
with open(VERIFICATION_CACHE_FILE, 'w', encoding='utf-8') as file:
|
||||
json.dump(verification_data, file, indent=2, ensure_ascii=False)
|
||||
print(f"[验证码清理] 共清理了 {len(removed_keys)} 个验证码")
|
||||
|
||||
except Exception as e:
|
||||
print(f"清理过期验证码失败: {str(e)}")
|
||||
print(f"清理验证码失败: {str(e)}")
|
||||
|
||||
@staticmethod
|
||||
def get_verification_status(qq_number):
|
||||
"""
|
||||
获取验证码状态(用于调试)
|
||||
|
||||
参数:
|
||||
qq_number (str): QQ号
|
||||
|
||||
返回:
|
||||
dict: 验证码状态信息
|
||||
"""
|
||||
import time
|
||||
|
||||
if not os.path.exists(VERIFICATION_CACHE_FILE):
|
||||
return {"status": "no_cache_file"}
|
||||
|
||||
try:
|
||||
with open(VERIFICATION_CACHE_FILE, 'r', encoding='utf-8') as file:
|
||||
verification_data = json.load(file)
|
||||
|
||||
if qq_number not in verification_data:
|
||||
return {"status": "no_code"}
|
||||
|
||||
code_info = verification_data[qq_number]
|
||||
current_time = time.time()
|
||||
|
||||
return {
|
||||
"status": "found",
|
||||
"code": code_info.get("code", ""),
|
||||
"code_type": code_info.get("code_type", "unknown"),
|
||||
"used": code_info.get("used", False),
|
||||
"expired": current_time > code_info.get("expire_at", 0),
|
||||
"created_at": code_info.get("created_at", 0),
|
||||
"expire_at": code_info.get("expire_at", 0),
|
||||
"used_at": code_info.get("used_at", 0)
|
||||
}
|
||||
|
||||
except Exception as e:
|
||||
return {"status": "error", "message": str(e)}
|
||||
|
||||
|
||||
# 测试邮件发送
|
||||
|
||||
@@ -94,6 +94,7 @@ class TCPGameServer(TCPServer):
|
||||
self.start_batch_save_timer()
|
||||
self.start_weed_growth_timer()
|
||||
self.start_wisdom_tree_health_decay_timer()
|
||||
self.start_verification_code_cleanup_timer()
|
||||
|
||||
#初始化性能操作
|
||||
def _init_performance_settings(self):
|
||||
@@ -170,6 +171,20 @@ class TCPGameServer(TCPServer):
|
||||
self.wisdom_tree_decay_timer.daemon = True
|
||||
self.wisdom_tree_decay_timer.start()
|
||||
|
||||
def start_verification_code_cleanup_timer(self):
|
||||
"""启动验证码清理定时器"""
|
||||
try:
|
||||
from QQEmailSend import EmailVerification
|
||||
EmailVerification.clean_expired_codes()
|
||||
self.log('INFO', "验证码清理完成", 'SERVER')
|
||||
except Exception as e:
|
||||
self.log('ERROR', f"验证码清理时出错: {str(e)}", 'SERVER')
|
||||
|
||||
# 创建下一个验证码清理计时器(每30分钟检查一次)
|
||||
self.verification_cleanup_timer = threading.Timer(1800, self.start_verification_code_cleanup_timer) # 每30分钟清理一次
|
||||
self.verification_cleanup_timer.daemon = True
|
||||
self.verification_cleanup_timer.start()
|
||||
|
||||
#获取服务器统计信息
|
||||
def get_server_stats(self):
|
||||
"""获取服务器统计信息"""
|
||||
@@ -203,6 +218,12 @@ class TCPGameServer(TCPServer):
|
||||
self.wisdom_tree_decay_timer = None
|
||||
self.log('INFO', "智慧树生命值衰减计时器已停止", 'SERVER')
|
||||
|
||||
# 停止验证码清理定时器
|
||||
if hasattr(self, 'verification_cleanup_timer') and self.verification_cleanup_timer:
|
||||
self.verification_cleanup_timer.cancel()
|
||||
self.verification_cleanup_timer = None
|
||||
self.log('INFO', "验证码清理定时器已停止", 'SERVER')
|
||||
|
||||
# 强制保存所有缓存数据
|
||||
self.log('INFO', "正在保存所有玩家数据...", 'SERVER')
|
||||
saved_count = self.force_save_all_data()
|
||||
@@ -678,6 +699,10 @@ class TCPGameServer(TCPServer):
|
||||
return self._handle_register(client_id, message)
|
||||
elif message_type == "request_verification_code":#验证码请求
|
||||
return self._handle_verification_code_request(client_id, message)
|
||||
elif message_type == "request_forget_password_verification_code":#忘记密码验证码请求
|
||||
return self._handle_forget_password_verification_code_request(client_id, message)
|
||||
elif message_type == "reset_password":#重置密码
|
||||
return self._handle_reset_password_request(client_id, message)
|
||||
elif message_type == "verify_code":#验证码
|
||||
return self._handle_verify_code(client_id, message)
|
||||
|
||||
@@ -775,6 +800,16 @@ class TCPGameServer(TCPServer):
|
||||
return self._handle_wisdom_tree_message(client_id, message)
|
||||
elif message_type == "get_wisdom_tree_config":#获取智慧树配置
|
||||
return self._handle_get_wisdom_tree_config(client_id, message)
|
||||
elif message_type == "sell_crop":#出售作物
|
||||
return self._handle_sell_crop(client_id, message)
|
||||
elif message_type == "add_product_to_store":#添加商品到小卖部
|
||||
return self._handle_add_product_to_store(client_id, message)
|
||||
elif message_type == "remove_store_product":#下架小卖部商品
|
||||
return self._handle_remove_store_product(client_id, message)
|
||||
elif message_type == "buy_store_product":#购买小卖部商品
|
||||
return self._handle_buy_store_product(client_id, message)
|
||||
elif message_type == "buy_store_booth":#购买小卖部格子
|
||||
return self._handle_buy_store_booth(client_id, message)
|
||||
#---------------------------------------------------------------------------
|
||||
|
||||
elif message_type == "message":#处理聊天消息(暂未实现)
|
||||
@@ -982,9 +1017,12 @@ class TCPGameServer(TCPServer):
|
||||
# 验证验证码
|
||||
if verification_code:
|
||||
from QQEmailSend import EmailVerification
|
||||
success, verify_message = EmailVerification.verify_code(username, verification_code)
|
||||
success, verify_message = EmailVerification.verify_code(username, verification_code, "register")
|
||||
if not success:
|
||||
self.log('WARNING', f"QQ号 {username} 注册验证码验证失败: {verify_message}", 'SERVER')
|
||||
return self._send_register_error(client_id, f"验证码错误: {verify_message}")
|
||||
else:
|
||||
self.log('INFO', f"QQ号 {username} 注册验证码验证成功", 'SERVER')
|
||||
|
||||
# 检查用户是否已存在
|
||||
file_path = os.path.join("game_saves", f"{username}.json")
|
||||
@@ -1114,9 +1152,9 @@ class TCPGameServer(TCPServer):
|
||||
success, send_message = EmailVerification.send_verification_email(qq_number, verification_code)
|
||||
|
||||
if success:
|
||||
# 保存验证码
|
||||
EmailVerification.save_verification_code(qq_number, verification_code)
|
||||
self.log('INFO', f"已向QQ号 {qq_number} 发送验证码", 'SERVER')
|
||||
# 保存验证码(注册类型)
|
||||
EmailVerification.save_verification_code(qq_number, verification_code, 300, "register")
|
||||
self.log('INFO', f"已向QQ号 {qq_number} 发送注册验证码: {verification_code}", 'SERVER')
|
||||
|
||||
return self.send_data(client_id, {
|
||||
"type": "verification_code_response",
|
||||
@@ -1166,6 +1204,127 @@ class TCPGameServer(TCPServer):
|
||||
|
||||
#验证QQ号格式
|
||||
|
||||
#处理忘记密码验证码请求
|
||||
def _handle_forget_password_verification_code_request(self, client_id, message):
|
||||
"""处理忘记密码验证码请求"""
|
||||
from QQEmailSend import EmailVerification
|
||||
|
||||
qq_number = message.get("qq_number", "")
|
||||
|
||||
# 验证QQ号
|
||||
if not self._validate_qq_number(qq_number):
|
||||
return self.send_data(client_id, {
|
||||
"type": "forget_password_verification_code_response",
|
||||
"success": False,
|
||||
"message": "QQ号格式无效,请输入5-12位数字"
|
||||
})
|
||||
|
||||
# 检查账号是否存在
|
||||
player_data = self.load_player_data(qq_number)
|
||||
if not player_data:
|
||||
return self.send_data(client_id, {
|
||||
"type": "forget_password_verification_code_response",
|
||||
"success": False,
|
||||
"message": "该账号不存在,请检查QQ号是否正确"
|
||||
})
|
||||
|
||||
# 生成验证码
|
||||
verification_code = EmailVerification.generate_verification_code()
|
||||
|
||||
# 发送验证码邮件(专门用于密码重置)
|
||||
success, send_message = EmailVerification.send_verification_email(qq_number, verification_code, "reset_password")
|
||||
|
||||
if success:
|
||||
# 保存验证码(密码重置类型)
|
||||
EmailVerification.save_verification_code(qq_number, verification_code, 300, "reset_password")
|
||||
self.log('INFO', f"已向QQ号 {qq_number} 发送密码重置验证码: {verification_code}", 'SERVER')
|
||||
|
||||
return self.send_data(client_id, {
|
||||
"type": "forget_password_verification_code_response",
|
||||
"success": True,
|
||||
"message": "密码重置验证码已发送到您的QQ邮箱,请查收"
|
||||
})
|
||||
else:
|
||||
self.log('ERROR', f"发送密码重置验证码失败: {send_message}", 'SERVER')
|
||||
return self.send_data(client_id, {
|
||||
"type": "forget_password_verification_code_response",
|
||||
"success": False,
|
||||
"message": f"发送验证码失败: {send_message}"
|
||||
})
|
||||
|
||||
#处理重置密码请求
|
||||
def _handle_reset_password_request(self, client_id, message):
|
||||
"""处理重置密码请求"""
|
||||
from QQEmailSend import EmailVerification
|
||||
|
||||
username = message.get("username", "")
|
||||
new_password = message.get("new_password", "")
|
||||
verification_code = message.get("verification_code", "")
|
||||
|
||||
# 验证必填字段
|
||||
if not username or not new_password or not verification_code:
|
||||
return self.send_data(client_id, {
|
||||
"type": "reset_password_response",
|
||||
"success": False,
|
||||
"message": "用户名、新密码或验证码不能为空"
|
||||
})
|
||||
|
||||
# 验证QQ号格式
|
||||
if not self._validate_qq_number(username):
|
||||
return self.send_data(client_id, {
|
||||
"type": "reset_password_response",
|
||||
"success": False,
|
||||
"message": "用户名必须是5-12位的QQ号码"
|
||||
})
|
||||
|
||||
# 检查账号是否存在
|
||||
player_data = self.load_player_data(username)
|
||||
if not player_data:
|
||||
return self.send_data(client_id, {
|
||||
"type": "reset_password_response",
|
||||
"success": False,
|
||||
"message": "该账号不存在,请检查QQ号是否正确"
|
||||
})
|
||||
|
||||
# 验证验证码(密码重置类型)
|
||||
success, verify_message = EmailVerification.verify_code(username, verification_code, "reset_password")
|
||||
if not success:
|
||||
self.log('WARNING', f"QQ号 {username} 密码重置验证码验证失败: {verify_message}", 'SERVER')
|
||||
return self.send_data(client_id, {
|
||||
"type": "reset_password_response",
|
||||
"success": False,
|
||||
"message": f"验证码错误: {verify_message}"
|
||||
})
|
||||
else:
|
||||
self.log('INFO', f"QQ号 {username} 密码重置验证码验证成功", 'SERVER')
|
||||
|
||||
# 更新密码
|
||||
try:
|
||||
player_data["user_password"] = new_password
|
||||
|
||||
# 保存到缓存和文件
|
||||
self.player_cache[username] = player_data
|
||||
self.dirty_players.add(username)
|
||||
|
||||
# 立即保存重要的账户信息
|
||||
self.save_player_data_immediate(username)
|
||||
|
||||
self.log('INFO', f"用户 {username} 密码重置成功", 'ACCOUNT')
|
||||
|
||||
return self.send_data(client_id, {
|
||||
"type": "reset_password_response",
|
||||
"success": True,
|
||||
"message": "密码重置成功,请使用新密码登录"
|
||||
})
|
||||
|
||||
except Exception as e:
|
||||
self.log('ERROR', f"重置密码时出错: {str(e)}", 'ACCOUNT')
|
||||
return self.send_data(client_id, {
|
||||
"type": "reset_password_response",
|
||||
"success": False,
|
||||
"message": "密码重置失败,请稍后重试"
|
||||
})
|
||||
|
||||
#辅助函数-验证QQ号格式
|
||||
def _validate_qq_number(self, qq_number):
|
||||
"""验证QQ号格式"""
|
||||
@@ -5675,6 +5834,7 @@ class TCPGameServer(TCPServer):
|
||||
|
||||
safe_player_data = {
|
||||
"user_name": target_player_data.get("user_name", target_username),
|
||||
"username": target_username, # 添加username字段,用于购买商品时标识卖家
|
||||
"player_name": target_player_data.get("player_name", target_username),
|
||||
"farm_name": target_player_data.get("farm_name", ""),
|
||||
"level": target_player_data.get("level", 1),
|
||||
@@ -5690,6 +5850,9 @@ class TCPGameServer(TCPServer):
|
||||
"出战宠物": self._convert_battle_pets_to_full_data(target_player_data),
|
||||
"稻草人配置": target_player_data.get("稻草人配置", {}),
|
||||
"智慧树配置": target_player_data.get("智慧树配置", {}),
|
||||
"玩家小卖部": target_player_data.get("玩家小卖部", []), # 添加小卖部数据
|
||||
"小卖部格子数": target_player_data.get("小卖部格子数", 10), # 添加小卖部格子数
|
||||
"点赞数": target_player_data.get("点赞数", 0), # 添加点赞数
|
||||
"last_login_time": target_player_data.get("last_login_time", "未知"),
|
||||
"total_login_time": target_player_data.get("total_login_time", "0时0分0秒"),
|
||||
"total_likes": target_player_data.get("total_likes", 0)
|
||||
@@ -8502,6 +8665,454 @@ class TCPGameServer(TCPServer):
|
||||
#==========================智慧树系统处理==========================
|
||||
|
||||
|
||||
#==========================作物出售处理==========================
|
||||
def _handle_sell_crop(self, client_id, message):
|
||||
"""处理作物出售请求"""
|
||||
# 检查用户是否已登录
|
||||
logged_in, response = self._check_user_logged_in(client_id, "出售作物", "sell_crop")
|
||||
if not logged_in:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
# 获取玩家数据
|
||||
player_data, username, response = self._load_player_data_with_check(client_id, "sell_crop")
|
||||
if not player_data:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
crop_name = message.get("crop_name", "")
|
||||
sell_count = message.get("sell_count", 1)
|
||||
unit_price = message.get("unit_price", 0)
|
||||
|
||||
# 验证参数
|
||||
if not crop_name:
|
||||
return self._send_action_error(client_id, "sell_crop", "作物名称不能为空")
|
||||
|
||||
if sell_count <= 0:
|
||||
return self._send_action_error(client_id, "sell_crop", "出售数量必须大于0")
|
||||
|
||||
if unit_price <= 0:
|
||||
return self._send_action_error(client_id, "sell_crop", "单价必须大于0")
|
||||
|
||||
# 检查作物仓库中是否有足够的作物
|
||||
crop_warehouse = player_data.get("作物仓库", [])
|
||||
crop_found = False
|
||||
crop_index = -1
|
||||
available_count = 0
|
||||
|
||||
for i, crop_item in enumerate(crop_warehouse):
|
||||
if crop_item.get("name") == crop_name:
|
||||
crop_found = True
|
||||
crop_index = i
|
||||
available_count = crop_item.get("count", 0)
|
||||
break
|
||||
|
||||
if not crop_found:
|
||||
return self._send_action_error(client_id, "sell_crop", f"作物仓库中没有 {crop_name}")
|
||||
|
||||
if available_count < sell_count:
|
||||
return self._send_action_error(client_id, "sell_crop", f"作物数量不足,仓库中只有 {available_count} 个 {crop_name}")
|
||||
|
||||
# 验证价格(防止客户端篡改价格)
|
||||
crop_data = self._load_crop_data()
|
||||
if crop_name in crop_data:
|
||||
expected_price = crop_data[crop_name].get("收益", 0)
|
||||
if unit_price != expected_price:
|
||||
return self._send_action_error(client_id, "sell_crop", f"价格验证失败,{crop_name} 的正确价格应为 {expected_price} 元/个")
|
||||
else:
|
||||
return self._send_action_error(client_id, "sell_crop", f"未知的作物类型:{crop_name}")
|
||||
|
||||
# 计算总收入
|
||||
total_income = sell_count * unit_price
|
||||
|
||||
# 执行出售操作
|
||||
player_data["money"] += total_income
|
||||
|
||||
# 从作物仓库中减少数量
|
||||
crop_warehouse[crop_index]["count"] -= sell_count
|
||||
|
||||
# 如果数量为0,从仓库中移除该作物
|
||||
if crop_warehouse[crop_index]["count"] <= 0:
|
||||
crop_warehouse.pop(crop_index)
|
||||
|
||||
# 给予少量出售经验
|
||||
sell_experience = max(1, sell_count // 5) # 每5个作物给1点经验
|
||||
player_data["experience"] += sell_experience
|
||||
|
||||
# 检查是否升级
|
||||
self._check_level_up(player_data)
|
||||
|
||||
# 保存玩家数据
|
||||
self.save_player_data(username, player_data)
|
||||
|
||||
# 获取显示名称
|
||||
display_name = crop_name
|
||||
if crop_name in crop_data:
|
||||
mature_name = crop_data[crop_name].get("成熟物名称")
|
||||
if mature_name:
|
||||
display_name = mature_name
|
||||
else:
|
||||
display_name = crop_data[crop_name].get("作物名称", crop_name)
|
||||
|
||||
self.log('INFO', f"玩家 {username} 出售了 {sell_count} 个 {crop_name},获得 {total_income} 金币和 {sell_experience} 经验", 'SERVER')
|
||||
|
||||
return self.send_data(client_id, {
|
||||
"type": "action_response",
|
||||
"action_type": "sell_crop",
|
||||
"success": True,
|
||||
"message": f"成功出售 {sell_count} 个 {display_name},获得 {total_income} 金币和 {sell_experience} 经验",
|
||||
"updated_data": {
|
||||
"money": player_data["money"],
|
||||
"experience": player_data["experience"],
|
||||
"level": player_data["level"],
|
||||
"作物仓库": player_data["作物仓库"]
|
||||
}
|
||||
})
|
||||
#==========================作物出售处理==========================
|
||||
|
||||
|
||||
#==========================小卖部管理处理==========================
|
||||
def _handle_add_product_to_store(self, client_id, message):
|
||||
"""处理添加商品到小卖部请求"""
|
||||
# 检查用户是否已登录
|
||||
logged_in, response = self._check_user_logged_in(client_id, "添加商品到小卖部", "add_product_to_store")
|
||||
if not logged_in:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
# 获取玩家数据
|
||||
player_data, username, response = self._load_player_data_with_check(client_id, "add_product_to_store")
|
||||
if not player_data:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
product_type = message.get("product_type", "")
|
||||
product_name = message.get("product_name", "")
|
||||
product_count = message.get("product_count", 1)
|
||||
product_price = message.get("product_price", 0)
|
||||
|
||||
# 验证参数
|
||||
if not product_type or not product_name:
|
||||
return self._send_action_error(client_id, "add_product_to_store", "商品类型或名称不能为空")
|
||||
|
||||
if product_count <= 0:
|
||||
return self._send_action_error(client_id, "add_product_to_store", "商品数量必须大于0")
|
||||
|
||||
if product_price <= 0:
|
||||
return self._send_action_error(client_id, "add_product_to_store", "商品价格必须大于0")
|
||||
|
||||
# 初始化小卖部数据
|
||||
if "玩家小卖部" not in player_data:
|
||||
player_data["玩家小卖部"] = []
|
||||
if "小卖部格子数" not in player_data:
|
||||
player_data["小卖部格子数"] = 10
|
||||
|
||||
player_store = player_data["玩家小卖部"]
|
||||
max_slots = player_data["小卖部格子数"]
|
||||
|
||||
# 检查小卖部格子是否已满
|
||||
if len(player_store) >= max_slots:
|
||||
return self._send_action_error(client_id, "add_product_to_store", f"小卖部格子已满({len(player_store)}/{max_slots})")
|
||||
|
||||
# 检查作物仓库中是否有足够的商品
|
||||
if product_type == "作物":
|
||||
crop_warehouse = player_data.get("作物仓库", [])
|
||||
crop_found = False
|
||||
crop_index = -1
|
||||
available_count = 0
|
||||
|
||||
for i, crop_item in enumerate(crop_warehouse):
|
||||
if crop_item.get("name") == product_name:
|
||||
crop_found = True
|
||||
crop_index = i
|
||||
available_count = crop_item.get("count", 0)
|
||||
break
|
||||
|
||||
if not crop_found:
|
||||
return self._send_action_error(client_id, "add_product_to_store", f"作物仓库中没有 {product_name}")
|
||||
|
||||
if available_count < product_count:
|
||||
return self._send_action_error(client_id, "add_product_to_store", f"作物数量不足,仓库中只有 {available_count} 个 {product_name}")
|
||||
|
||||
# 从作物仓库中扣除商品
|
||||
crop_warehouse[crop_index]["count"] -= product_count
|
||||
if crop_warehouse[crop_index]["count"] <= 0:
|
||||
crop_warehouse.pop(crop_index)
|
||||
|
||||
# 添加商品到小卖部
|
||||
new_product = {
|
||||
"商品类型": product_type,
|
||||
"商品名称": product_name,
|
||||
"商品价格": product_price,
|
||||
"商品数量": product_count
|
||||
}
|
||||
player_store.append(new_product)
|
||||
|
||||
# 保存玩家数据
|
||||
self.save_player_data(username, player_data)
|
||||
|
||||
self.log('INFO', f"玩家 {username} 添加商品到小卖部: {product_name} x{product_count}, 价格 {product_price}元/个", 'SERVER')
|
||||
|
||||
return self.send_data(client_id, {
|
||||
"type": "action_response",
|
||||
"action_type": "add_product_to_store",
|
||||
"success": True,
|
||||
"message": f"成功添加 {product_count} 个 {product_name} 到小卖部",
|
||||
"updated_data": {
|
||||
"玩家小卖部": player_data["玩家小卖部"],
|
||||
"作物仓库": player_data.get("作物仓库", [])
|
||||
}
|
||||
})
|
||||
|
||||
def _handle_remove_store_product(self, client_id, message):
|
||||
"""处理下架小卖部商品请求"""
|
||||
# 检查用户是否已登录
|
||||
logged_in, response = self._check_user_logged_in(client_id, "下架小卖部商品", "remove_store_product")
|
||||
if not logged_in:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
# 获取玩家数据
|
||||
player_data, username, response = self._load_player_data_with_check(client_id, "remove_store_product")
|
||||
if not player_data:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
slot_index = message.get("slot_index", -1)
|
||||
|
||||
# 验证参数
|
||||
if slot_index < 0:
|
||||
return self._send_action_error(client_id, "remove_store_product", "无效的商品槽位")
|
||||
|
||||
# 检查小卖部数据
|
||||
player_store = player_data.get("玩家小卖部", [])
|
||||
if slot_index >= len(player_store):
|
||||
return self._send_action_error(client_id, "remove_store_product", "商品槽位不存在")
|
||||
|
||||
# 获取要下架的商品信息
|
||||
product_data = player_store[slot_index]
|
||||
product_type = product_data.get("商品类型", "")
|
||||
product_name = product_data.get("商品名称", "")
|
||||
product_count = product_data.get("商品数量", 0)
|
||||
|
||||
# 将商品返回到对应仓库
|
||||
if product_type == "作物":
|
||||
# 返回到作物仓库
|
||||
if "作物仓库" not in player_data:
|
||||
player_data["作物仓库"] = []
|
||||
|
||||
crop_warehouse = player_data["作物仓库"]
|
||||
# 查找是否已有该作物
|
||||
crop_found = False
|
||||
for crop_item in crop_warehouse:
|
||||
if crop_item.get("name") == product_name:
|
||||
crop_item["count"] += product_count
|
||||
crop_found = True
|
||||
break
|
||||
|
||||
if not crop_found:
|
||||
# 添加新的作物条目
|
||||
crop_data = self._load_crop_data()
|
||||
quality = "普通"
|
||||
if crop_data and product_name in crop_data:
|
||||
quality = crop_data[product_name].get("品质", "普通")
|
||||
|
||||
crop_warehouse.append({
|
||||
"name": product_name,
|
||||
"quality": quality,
|
||||
"count": product_count
|
||||
})
|
||||
|
||||
# 从小卖部移除商品
|
||||
player_store.pop(slot_index)
|
||||
|
||||
# 保存玩家数据
|
||||
self.save_player_data(username, player_data)
|
||||
|
||||
self.log('INFO', f"玩家 {username} 下架小卖部商品: {product_name} x{product_count}", 'SERVER')
|
||||
|
||||
return self.send_data(client_id, {
|
||||
"type": "action_response",
|
||||
"action_type": "remove_store_product",
|
||||
"success": True,
|
||||
"message": f"成功下架 {product_count} 个 {product_name},已返回仓库",
|
||||
"updated_data": {
|
||||
"玩家小卖部": player_data["玩家小卖部"],
|
||||
"作物仓库": player_data.get("作物仓库", [])
|
||||
}
|
||||
})
|
||||
|
||||
def _handle_buy_store_product(self, client_id, message):
|
||||
"""处理购买小卖部商品请求"""
|
||||
# 检查用户是否已登录
|
||||
logged_in, response = self._check_user_logged_in(client_id, "购买小卖部商品", "buy_store_product")
|
||||
if not logged_in:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
# 获取买家数据
|
||||
buyer_data, buyer_username, response = self._load_player_data_with_check(client_id, "buy_store_product")
|
||||
if not buyer_data:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
seller_username = message.get("seller_username", "")
|
||||
slot_index = message.get("slot_index", -1)
|
||||
product_name = message.get("product_name", "")
|
||||
unit_price = message.get("unit_price", 0)
|
||||
quantity = message.get("quantity", 1)
|
||||
|
||||
# 验证参数
|
||||
if not seller_username:
|
||||
return self._send_action_error(client_id, "buy_store_product", "卖家用户名不能为空")
|
||||
|
||||
if slot_index < 0:
|
||||
return self._send_action_error(client_id, "buy_store_product", "无效的商品槽位")
|
||||
|
||||
if quantity <= 0:
|
||||
return self._send_action_error(client_id, "buy_store_product", "购买数量必须大于0")
|
||||
|
||||
# 检查是否是自己购买自己的商品
|
||||
if buyer_username == seller_username:
|
||||
return self._send_action_error(client_id, "buy_store_product", "不能购买自己的商品")
|
||||
|
||||
# 加载卖家数据
|
||||
seller_data = self.load_player_data(seller_username)
|
||||
if not seller_data:
|
||||
return self._send_action_error(client_id, "buy_store_product", f"卖家 {seller_username} 不存在")
|
||||
|
||||
# 检查卖家小卖部
|
||||
seller_store = seller_data.get("玩家小卖部", [])
|
||||
if slot_index >= len(seller_store):
|
||||
return self._send_action_error(client_id, "buy_store_product", "商品不存在")
|
||||
|
||||
product_data = seller_store[slot_index]
|
||||
product_type = product_data.get("商品类型", "")
|
||||
store_product_name = product_data.get("商品名称", "")
|
||||
store_unit_price = product_data.get("商品价格", 0)
|
||||
available_count = product_data.get("商品数量", 0)
|
||||
|
||||
# 验证商品信息
|
||||
if store_product_name != product_name:
|
||||
return self._send_action_error(client_id, "buy_store_product", "商品名称不匹配")
|
||||
|
||||
if store_unit_price != unit_price:
|
||||
return self._send_action_error(client_id, "buy_store_product", "商品价格已变更,请刷新重试")
|
||||
|
||||
if available_count < quantity:
|
||||
return self._send_action_error(client_id, "buy_store_product", f"商品库存不足,仅剩 {available_count} 个")
|
||||
|
||||
# 计算总价
|
||||
total_cost = quantity * unit_price
|
||||
|
||||
# 检查买家金钱是否足够
|
||||
if buyer_data["money"] < total_cost:
|
||||
return self._send_action_error(client_id, "buy_store_product", f"金钱不足,需要 {total_cost} 元")
|
||||
|
||||
# 执行交易
|
||||
buyer_data["money"] -= total_cost
|
||||
seller_data["money"] += total_cost
|
||||
|
||||
# 扣除卖家商品
|
||||
seller_store[slot_index]["商品数量"] -= quantity
|
||||
if seller_store[slot_index]["商品数量"] <= 0:
|
||||
seller_store.pop(slot_index)
|
||||
|
||||
# 给买家添加商品
|
||||
if product_type == "作物":
|
||||
if "作物仓库" not in buyer_data:
|
||||
buyer_data["作物仓库"] = []
|
||||
|
||||
buyer_warehouse = buyer_data["作物仓库"]
|
||||
# 查找是否已有该作物
|
||||
crop_found = False
|
||||
for crop_item in buyer_warehouse:
|
||||
if crop_item.get("name") == product_name:
|
||||
crop_item["count"] += quantity
|
||||
crop_found = True
|
||||
break
|
||||
|
||||
if not crop_found:
|
||||
# 添加新的作物条目
|
||||
crop_data = self._load_crop_data()
|
||||
quality = "普通"
|
||||
if crop_data and product_name in crop_data:
|
||||
quality = crop_data[product_name].get("品质", "普通")
|
||||
|
||||
buyer_warehouse.append({
|
||||
"name": product_name,
|
||||
"quality": quality,
|
||||
"count": quantity
|
||||
})
|
||||
|
||||
# 保存两个玩家的数据
|
||||
self.save_player_data(buyer_username, buyer_data)
|
||||
self.save_player_data(seller_username, seller_data)
|
||||
|
||||
self.log('INFO', f"玩家 {buyer_username} 从 {seller_username} 的小卖部购买了 {quantity} 个 {product_name},花费 {total_cost} 元", 'SERVER')
|
||||
|
||||
return self.send_data(client_id, {
|
||||
"type": "action_response",
|
||||
"action_type": "buy_store_product",
|
||||
"success": True,
|
||||
"message": f"成功购买 {quantity} 个 {product_name},花费 {total_cost} 元",
|
||||
"updated_data": {
|
||||
"money": buyer_data["money"],
|
||||
"作物仓库": buyer_data.get("作物仓库", [])
|
||||
}
|
||||
})
|
||||
|
||||
def _handle_buy_store_booth(self, client_id, message):
|
||||
"""处理购买小卖部格子请求"""
|
||||
# 检查用户是否已登录
|
||||
logged_in, response = self._check_user_logged_in(client_id, "购买小卖部格子", "buy_store_booth")
|
||||
if not logged_in:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
# 获取玩家数据
|
||||
player_data, username, response = self._load_player_data_with_check(client_id, "buy_store_booth")
|
||||
if not player_data:
|
||||
return self.send_data(client_id, response)
|
||||
|
||||
cost = message.get("cost", 0)
|
||||
|
||||
# 验证参数
|
||||
if cost <= 0:
|
||||
return self._send_action_error(client_id, "buy_store_booth", "无效的购买费用")
|
||||
|
||||
# 初始化小卖部数据
|
||||
if "小卖部格子数" not in player_data:
|
||||
player_data["小卖部格子数"] = 10
|
||||
|
||||
current_slots = player_data["小卖部格子数"]
|
||||
|
||||
# 检查是否已达上限
|
||||
if current_slots >= 40:
|
||||
return self._send_action_error(client_id, "buy_store_booth", "小卖部格子数已达上限(40)")
|
||||
|
||||
# 验证费用
|
||||
expected_cost = 1000 + (current_slots - 10) * 500
|
||||
if cost != expected_cost:
|
||||
return self._send_action_error(client_id, "buy_store_booth", f"费用不正确,应为 {expected_cost} 元")
|
||||
|
||||
# 检查玩家金钱是否足够
|
||||
if player_data["money"] < cost:
|
||||
return self._send_action_error(client_id, "buy_store_booth", f"金钱不足,需要 {cost} 元")
|
||||
|
||||
# 执行购买
|
||||
player_data["money"] -= cost
|
||||
player_data["小卖部格子数"] += 1
|
||||
|
||||
# 保存玩家数据
|
||||
self.save_player_data(username, player_data)
|
||||
|
||||
self.log('INFO', f"玩家 {username} 购买小卖部格子,花费 {cost} 元,格子数:{current_slots} -> {player_data['小卖部格子数']}", 'SERVER')
|
||||
|
||||
return self.send_data(client_id, {
|
||||
"type": "action_response",
|
||||
"action_type": "buy_store_booth",
|
||||
"success": True,
|
||||
"message": f"成功购买格子,花费 {cost} 元,当前格子数:{player_data['小卖部格子数']}",
|
||||
"updated_data": {
|
||||
"money": player_data["money"],
|
||||
"小卖部格子数": player_data["小卖部格子数"]
|
||||
}
|
||||
})
|
||||
#==========================小卖部管理处理==========================
|
||||
|
||||
|
||||
# 控制台命令系统
|
||||
class ConsoleCommands:
|
||||
"""控制台命令处理类"""
|
||||
@@ -8516,6 +9127,7 @@ class ConsoleCommands:
|
||||
"lsplayer": self.cmd_list_players,
|
||||
"playerinfo": self.cmd_player_info,
|
||||
"resetland": self.cmd_reset_land,
|
||||
"weather": self.cmd_weather,
|
||||
"help": self.cmd_help,
|
||||
"stop": self.cmd_stop,
|
||||
"save": self.cmd_save_all,
|
||||
@@ -8790,6 +9402,51 @@ class ConsoleCommands:
|
||||
else:
|
||||
print("❌ 初始化模板中没有找到土地数据")
|
||||
|
||||
def cmd_weather(self, args):
|
||||
"""天气控制命令: /weather <天气类型>"""
|
||||
if len(args) != 1:
|
||||
print("❌ 用法: /weather <天气类型>")
|
||||
print(" 可用天气: clear, rain, snow, cherry, gardenia, willow")
|
||||
return
|
||||
|
||||
weather_type = args[0].lower()
|
||||
|
||||
# 定义可用的天气类型映射
|
||||
weather_map = {
|
||||
"clear": "晴天",
|
||||
"rain": "下雨",
|
||||
"snow": "下雪",
|
||||
"cherry": "樱花雨",
|
||||
"gardenia": "栀子花雨",
|
||||
"willow": "柳叶雨",
|
||||
"stop": "停止天气"
|
||||
}
|
||||
|
||||
if weather_type not in weather_map:
|
||||
print("❌ 无效的天气类型")
|
||||
print(" 可用天气: clear, rain, snow, cherry, gardenia, willow, stop")
|
||||
return
|
||||
|
||||
# 广播天气变更消息给所有在线客户端
|
||||
weather_message = {
|
||||
"type": "weather_change",
|
||||
"weather_type": weather_type,
|
||||
"weather_name": weather_map[weather_type]
|
||||
}
|
||||
|
||||
# 发送给所有连接的客户端
|
||||
for client_id in list(self.server.clients.keys()):
|
||||
try:
|
||||
self.server.send_data(client_id, weather_message)
|
||||
except Exception as e:
|
||||
print(f"⚠️ 向客户端 {client_id} 发送天气消息失败: {str(e)}")
|
||||
|
||||
print(f"🌤️ 已将天气切换为: {weather_map[weather_type]}")
|
||||
if len(self.server.clients) > 0:
|
||||
print(f" 已通知 {len(self.server.clients)} 个在线客户端")
|
||||
else:
|
||||
print(" 当前无在线客户端")
|
||||
|
||||
def cmd_help(self, args):
|
||||
"""显示帮助信息"""
|
||||
print("🌱 萌芽农场服务器控制台命令帮助")
|
||||
@@ -8803,6 +9460,10 @@ class ConsoleCommands:
|
||||
print(" /playerinfo <QQ号> - 查看玩家详细信息")
|
||||
print(" /resetland <QQ号> - 重置玩家土地状态")
|
||||
print("")
|
||||
print("游戏控制命令:")
|
||||
print(" /weather <类型> - 控制全服天气")
|
||||
print(" 可用类型: clear, rain, snow, cherry, gardenia, willow, stop")
|
||||
print("")
|
||||
print("服务器管理命令:")
|
||||
print(" /save - 立即保存所有玩家数据")
|
||||
print(" /reload - 重新加载配置文件")
|
||||
@@ -8841,6 +9502,7 @@ class ConsoleCommands:
|
||||
import sys
|
||||
sys.exit(0)
|
||||
|
||||
|
||||
def console_input_thread(server):
|
||||
"""控制台输入处理线程"""
|
||||
console = ConsoleCommands(server)
|
||||
|
||||
@@ -68,18 +68,5 @@
|
||||
"道具背包": [],
|
||||
"宠物背包":[],
|
||||
"巡逻宠物":[],
|
||||
"出战宠物":[],
|
||||
|
||||
"last_water_reset_date": "",
|
||||
"daily_likes": {},
|
||||
"seeds": {},
|
||||
"last_check_in_date": "",
|
||||
"check_in_count": 0,
|
||||
"daily_check_in": {},
|
||||
"lucky_draw_history": [],
|
||||
"total_likes": 0,
|
||||
"new_player_gift_claimed": false,
|
||||
"new_player_gift_time": "",
|
||||
"session_start_time": 0,
|
||||
"online_gift": {}
|
||||
"出战宠物":[]
|
||||
}
|
||||
@@ -1,6 +0,0 @@
|
||||
{
|
||||
"1232132": {
|
||||
"code": "5UFH2Z",
|
||||
"expire_at": 1748005553.6155243
|
||||
}
|
||||
}
|
||||
@@ -1,35 +1,35 @@
|
||||
{
|
||||
"experience": 3039,
|
||||
"level": 32,
|
||||
"money": 1224518,
|
||||
"experience": 1196,
|
||||
"level": 35,
|
||||
"money": 200812377,
|
||||
"farm_name": "柚大青の小农场",
|
||||
"player_name": "柚大青",
|
||||
"user_name": "2143323382",
|
||||
"user_password": "tyh@19900420",
|
||||
"last_login_time": "2025年07月14日08时03分08秒",
|
||||
"total_login_time": "5时36分14秒",
|
||||
"last_login_time": "2025年07月19日11时01分22秒",
|
||||
"total_login_time": "6时31分14秒",
|
||||
"farm_lots": [
|
||||
{
|
||||
"crop_type": "番茄",
|
||||
"grow_time": 724,
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 720,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 1440,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 4
|
||||
},
|
||||
{
|
||||
"crop_type": "小麦",
|
||||
"grow_time": 300,
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 300,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 2
|
||||
"土地等级": 4
|
||||
},
|
||||
{
|
||||
"crop_type": "野草1",
|
||||
@@ -40,158 +40,202 @@
|
||||
"max_grow_time": 5,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 3
|
||||
"土地等级": 4
|
||||
},
|
||||
{
|
||||
"crop_type": "龙果",
|
||||
"grow_time": 14492,
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 14400,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 300,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 4
|
||||
},
|
||||
{
|
||||
"crop_type": "小麦",
|
||||
"grow_time": 318,
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 300,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 1080,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "玉米",
|
||||
"grow_time": 918,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 900,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "小麦",
|
||||
"grow_time": 316,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 300,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"max_grow_time": 25200,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "橘子",
|
||||
"grow_time": 10234,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 10200,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"max_grow_time": 300,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"max_grow_time": 12000,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "小麦",
|
||||
"grow_time": 300,
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 1080,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 240,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 1080,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 720,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 300,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 2
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "玉米",
|
||||
"grow_time": 912,
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 900,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 2
|
||||
},
|
||||
{
|
||||
"crop_type": "杂交树1",
|
||||
"grow_time": 21632,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 21600,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 2
|
||||
},
|
||||
{
|
||||
"crop_type": "小麦",
|
||||
"grow_time": 314,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 300,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "稻谷",
|
||||
"grow_time": 614,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 600,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "胡萝卜",
|
||||
"grow_time": 240,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 240,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "花椰菜",
|
||||
"grow_time": 1334,
|
||||
"crop_type": "藏红花",
|
||||
"grow_time": 7006,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 1320,
|
||||
"max_grow_time": 7000,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "杂交树2",
|
||||
"grow_time": 25208,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 25200,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "杂交树1",
|
||||
"grow_time": 21642,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 21600,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 4
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 480,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 4
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 14400,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 3
|
||||
},
|
||||
{
|
||||
"crop_type": "芦荟",
|
||||
"grow_time": 6013,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 6000,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
@@ -200,144 +244,100 @@
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"max_grow_time": 240,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
},
|
||||
{
|
||||
"crop_type": "番茄",
|
||||
"grow_time": 726,
|
||||
"crop_type": "松露",
|
||||
"grow_time": 18001,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 720,
|
||||
"max_grow_time": 18000,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "土豆",
|
||||
"grow_time": 486,
|
||||
"crop_type": "藏红花",
|
||||
"grow_time": 7009,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 480,
|
||||
"max_grow_time": 7000,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "土豆",
|
||||
"grow_time": 486,
|
||||
"crop_type": "杂交树1",
|
||||
"grow_time": 21607,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 480,
|
||||
"max_grow_time": 21600,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "杂交树1",
|
||||
"grow_time": 21603,
|
||||
"is_dead": false,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 21600,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"max_grow_time": 3060,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"max_grow_time": 2500,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_diged": true,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"max_grow_time": 600,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"crop_type": "杂交树2",
|
||||
"grow_time": 25215,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"is_diged": true,
|
||||
"is_planted": true,
|
||||
"max_grow_time": 25200,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
"grow_time": 0,
|
||||
"is_dead": false,
|
||||
"is_diged": false,
|
||||
"is_planted": false,
|
||||
"max_grow_time": 5,
|
||||
"已浇水": false,
|
||||
"已施肥": false,
|
||||
"土地等级": 0
|
||||
"土地等级": 1
|
||||
},
|
||||
{
|
||||
"crop_type": "",
|
||||
@@ -561,45 +561,40 @@
|
||||
}
|
||||
],
|
||||
"player_bag": [
|
||||
{
|
||||
"name": "稻谷",
|
||||
"quality": "普通",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "土豆",
|
||||
"quality": "普通",
|
||||
"count": 6
|
||||
"count": 2
|
||||
},
|
||||
{
|
||||
"name": "小麦",
|
||||
"quality": "普通",
|
||||
"count": 8
|
||||
"count": 2
|
||||
},
|
||||
{
|
||||
"name": "胡萝卜",
|
||||
"quality": "普通",
|
||||
"count": 7
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "玉米",
|
||||
"quality": "优良",
|
||||
"count": 4
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "番茄",
|
||||
"quality": "普通",
|
||||
"count": 3
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "辣椒",
|
||||
"quality": "普通",
|
||||
"count": 2
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "草莓",
|
||||
"quality": "稀有",
|
||||
"count": 2
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "花椰菜",
|
||||
@@ -616,15 +611,94 @@
|
||||
"quality": "普通",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "月光草",
|
||||
"quality": "传奇",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "杂交树1",
|
||||
"quality": "传奇",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "杂交树2",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "荔枝",
|
||||
"count": 2
|
||||
},
|
||||
{
|
||||
"name": "玫瑰花",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "石榴",
|
||||
"count": 2
|
||||
},
|
||||
{
|
||||
"name": "芦荟",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "向日葵",
|
||||
"count": 3
|
||||
}
|
||||
],
|
||||
"last_water_reset_date": "2025-06-05",
|
||||
"注册时间": "2025年05月21日15时00分00秒",
|
||||
"个人简介": "其实我是一个梨子,真的,不骗你",
|
||||
"作物仓库": [
|
||||
{
|
||||
"name": "番茄",
|
||||
"quality": "普通",
|
||||
"count": 23
|
||||
},
|
||||
{
|
||||
"name": "小麦",
|
||||
"quality": "普通",
|
||||
"count": 44
|
||||
},
|
||||
{
|
||||
"name": "龙果",
|
||||
"quality": "稀有",
|
||||
"count": 4
|
||||
},
|
||||
{
|
||||
"name": "玉米",
|
||||
"quality": "优良",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "稻谷",
|
||||
"quality": "普通",
|
||||
"count": 3
|
||||
},
|
||||
{
|
||||
"name": "胡萝卜",
|
||||
"quality": "普通",
|
||||
"count": 20
|
||||
},
|
||||
{
|
||||
"name": "花椰菜",
|
||||
"quality": "优良",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "土豆",
|
||||
"quality": "普通",
|
||||
"count": 18
|
||||
},
|
||||
{
|
||||
"name": "咖啡豆",
|
||||
"quality": "稀有",
|
||||
"count": 1
|
||||
"count": 9
|
||||
},
|
||||
{
|
||||
"name": "人参",
|
||||
"quality": "史诗",
|
||||
"count": 1
|
||||
"count": 3
|
||||
},
|
||||
{
|
||||
"name": "藏红花",
|
||||
@@ -632,30 +706,36 @@
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "龙果",
|
||||
"quality": "稀有",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "松露",
|
||||
"name": "杨桃",
|
||||
"quality": "史诗",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "月光草",
|
||||
"quality": "传奇",
|
||||
"name": "冬虫夏草",
|
||||
"quality": "史诗",
|
||||
"count": 1
|
||||
},
|
||||
{
|
||||
"name": "仙人掌",
|
||||
"quality": "优良",
|
||||
"count": 4
|
||||
},
|
||||
{
|
||||
"name": "大豆",
|
||||
"quality": "普通",
|
||||
"count": 5
|
||||
},
|
||||
{
|
||||
"name": "荔枝",
|
||||
"quality": "优良",
|
||||
"count": 5
|
||||
},
|
||||
{
|
||||
"name": "杂交树2",
|
||||
"quality": "传奇",
|
||||
"count": 1
|
||||
}
|
||||
],
|
||||
"last_water_reset_date": "2025-06-05",
|
||||
"注册时间": "2025年05月21日15时00分00秒",
|
||||
"个人简介": "其实我是一个梨子,真的,不骗你",
|
||||
"作物仓库": [],
|
||||
"宠物背包": [
|
||||
{
|
||||
"场景路径": "res://Scene/Pet/SmallBeetle.tscn",
|
||||
@@ -812,14 +892,14 @@
|
||||
"2025年07月13日07时26分04秒": "金币302 经验63 土豆x5 小麦x3"
|
||||
},
|
||||
"在线礼包": {
|
||||
"当前日期": "2025-07-14",
|
||||
"当前日期": "2025-07-19",
|
||||
"今日在线时长": 0.0,
|
||||
"已领取礼包": [],
|
||||
"登录时间": 1752451388.1583223
|
||||
"登录时间": 1752894082.539563
|
||||
},
|
||||
"点赞系统": {
|
||||
"今日剩余点赞次数": 10,
|
||||
"点赞上次刷新时间": "2025-07-14"
|
||||
"点赞上次刷新时间": "2025-07-19"
|
||||
},
|
||||
"新手礼包": {
|
||||
"已领取": true,
|
||||
@@ -828,7 +908,15 @@
|
||||
"体力系统": {
|
||||
"当前体力值": 20,
|
||||
"最大体力值": 20,
|
||||
"上次刷新时间": "2025-07-14",
|
||||
"上次恢复时间": 1752451388.157905
|
||||
}
|
||||
"上次刷新时间": "2025-07-19",
|
||||
"上次恢复时间": 1752894082.5390205
|
||||
},
|
||||
"玩家小卖部": [],
|
||||
"道具背包": [
|
||||
{
|
||||
"name": "铲子",
|
||||
"count": 100
|
||||
}
|
||||
],
|
||||
"小卖部格子数": 10
|
||||
}
|
||||
@@ -12,43 +12,43 @@ uniform float height_curve : hint_range(1.0, 4.0) = 2.0; // 高度影响曲线
|
||||
|
||||
void fragment() {
|
||||
vec2 uv = UV;
|
||||
|
||||
|
||||
// 计算摆动强度(只有上半部分摆动)
|
||||
float height_factor = 0.0;
|
||||
if (uv.y < sway_start_height) {
|
||||
// 计算从底部到摆动开始位置的渐变
|
||||
height_factor = pow((sway_start_height - uv.y) / sway_start_height, height_curve);
|
||||
}
|
||||
|
||||
|
||||
// 创建多层摆动效果
|
||||
float time_offset = TIME * sway_speed;
|
||||
|
||||
|
||||
// 主摆动波
|
||||
float main_sway = sin(time_offset + uv.y * 3.14159) * sway_strength;
|
||||
|
||||
|
||||
// 次级摆动波(频率更高,幅度更小)
|
||||
float secondary_sway = sin(time_offset * 2.3 + uv.y * 6.28318) * sway_strength * 0.3;
|
||||
|
||||
|
||||
// 第三层摆动(更细微的抖动)
|
||||
float micro_sway = sin(time_offset * 4.7 + uv.y * 12.56636) * sway_strength * 0.1;
|
||||
|
||||
|
||||
// 结合所有摆动
|
||||
float total_sway = (main_sway + secondary_sway + micro_sway) * height_factor;
|
||||
|
||||
|
||||
// 添加风向偏移
|
||||
total_sway += wind_direction * sway_strength * height_factor * 0.5;
|
||||
|
||||
|
||||
// 添加摆动变化(随机性)
|
||||
float variation = sin(time_offset * 0.37 + uv.x * 6.28318) * sway_variation * 0.01;
|
||||
total_sway += variation * height_factor;
|
||||
|
||||
|
||||
// 应用摆动到UV坐标
|
||||
uv.x += total_sway;
|
||||
|
||||
|
||||
// 边界检查,防止UV超出范围
|
||||
if (uv.x < 0.0 || uv.x > 1.0) {
|
||||
COLOR = vec4(0.0, 0.0, 0.0, 0.0); // 透明
|
||||
} else {
|
||||
COLOR = texture(TEXTURE, uv);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Before Width: | Height: | Size: 25 KiB After Width: | Height: | Size: 25 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://xyj4ro44cwj5"
|
||||
path="res://.godot/imported/0.webp-9339f1eb71d8e2d2c9d6eff2a61109e8.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-e31b638e539187dd68d4f0b356b0ede9.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/人参/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-9339f1eb71d8e2d2c9d6eff2a61109e8.ctex"]
|
||||
source_file="res://assets/作物/人参/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-e31b638e539187dd68d4f0b356b0ede9.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 27 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://btro2s0v3vjvc"
|
||||
path="res://.godot/imported/0.webp-a498150286b3ef11bcaf7062fb7c4c72.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-d7486902f1f60fe55e6aa621b78d2bdd.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/仙人掌/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-a498150286b3ef11bcaf7062fb7c4c72.ctex"]
|
||||
source_file="res://assets/作物/仙人掌/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-d7486902f1f60fe55e6aa621b78d2bdd.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 30 KiB After Width: | Height: | Size: 30 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://nh4rwteg18hf"
|
||||
path="res://.godot/imported/1.webp-eac2af28e41e5166de4e45fa1d9b023c.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-e0f54244cf971f24edbb0bf5ab6f5b9d.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/仙人掌/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-eac2af28e41e5166de4e45fa1d9b023c.ctex"]
|
||||
source_file="res://assets/作物/仙人掌/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-e0f54244cf971f24edbb0bf5ab6f5b9d.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 24 KiB |
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://2tms3lcydcf7"
|
||||
path="res://.godot/imported/1.webp-1c762135840fee82b6f1524cf7b93c28.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/冬虫夏草/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-1c762135840fee82b6f1524cf7b93c28.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 19 KiB After Width: | Height: | Size: 19 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://dr3cu2f7agkgk"
|
||||
path="res://.godot/imported/0.webp-8e6372f99a77669bfdae2b147d801863.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-30da2eafd5a696c6c1eca5ffdc30f96f.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/冬虫夏草/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-8e6372f99a77669bfdae2b147d801863.ctex"]
|
||||
source_file="res://assets/作物/冬虫夏草/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-30da2eafd5a696c6c1eca5ffdc30f96f.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 26 KiB After Width: | Height: | Size: 26 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://dcn3nga3a3n6a"
|
||||
path="res://.godot/imported/2.webp-62669dec635d4d6139cbede94abc0c42.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-ab438ee4d595b7620c449192b5775f38.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/冬虫夏草/2.webp"
|
||||
dest_files=["res://.godot/imported/2.webp-62669dec635d4d6139cbede94abc0c42.ctex"]
|
||||
source_file="res://assets/作物/冬虫夏草/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-ab438ee4d595b7620c449192b5775f38.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 34 KiB After Width: | Height: | Size: 34 KiB |
34
assets/作物/凤凰木/幼苗.webp.import
Normal file
@@ -0,0 +1,34 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://b3yb6xi5dif75"
|
||||
path="res://.godot/imported/幼苗.webp-a4b4bf49ecdb32ea6d2abba5c9629e01.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/凤凰木/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-a4b4bf49ecdb32ea6d2abba5c9629e01.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 33 KiB After Width: | Height: | Size: 33 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://b7ko81p17vwd5"
|
||||
path="res://.godot/imported/1.webp-70a0c6dc2f51cf788ff580d54c9c392f.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-0769b207da58122cbb7ec64d5b2a2941.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/凤凰木/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-70a0c6dc2f51cf788ff580d54c9c392f.ctex"]
|
||||
source_file="res://assets/作物/凤凰木/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-0769b207da58122cbb7ec64d5b2a2941.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 29 KiB |
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://mtmunwgy1x3g"
|
||||
path="res://.godot/imported/3.webp-7bbb31894686faa8c9080a58b509200d.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/南瓜/3.webp"
|
||||
dest_files=["res://.godot/imported/3.webp-7bbb31894686faa8c9080a58b509200d.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 31 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://bhynib53o87sv"
|
||||
path="res://.godot/imported/0.webp-d98890577b76bfa710d6a00e6916c0c7.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-c454289b425b29d0c91fa12480484aa0.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/南瓜/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-d98890577b76bfa710d6a00e6916c0c7.ctex"]
|
||||
source_file="res://assets/作物/南瓜/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-c454289b425b29d0c91fa12480484aa0.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 27 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://dcmcy8sk6qeuj"
|
||||
path="res://.godot/imported/1.webp-113308ca15b586eaeb0bbd809b6997c6.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-180314de08cf809eae5e8bf494c6f569.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/南瓜/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-113308ca15b586eaeb0bbd809b6997c6.ctex"]
|
||||
source_file="res://assets/作物/南瓜/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-180314de08cf809eae5e8bf494c6f569.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 27 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://m0k2go1722l3"
|
||||
path="res://.godot/imported/0.webp-821822db21f66aa9245299fab7cf906e.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-afd9dee9030c742a3a58654be7b5150f.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/可可豆/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-821822db21f66aa9245299fab7cf906e.ctex"]
|
||||
source_file="res://assets/作物/可可豆/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-afd9dee9030c742a3a58654be7b5150f.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 30 KiB |
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://bxhe4pl7e2h4r"
|
||||
path="res://.godot/imported/2.webp-a4ac518035e8dc36ed57f415183fccf4.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/向日葵/2.webp"
|
||||
dest_files=["res://.godot/imported/2.webp-a4ac518035e8dc36ed57f415183fccf4.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 26 KiB After Width: | Height: | Size: 26 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://cgvoioriuf7y0"
|
||||
path="res://.godot/imported/0.webp-e38fa2090339e41d8e2bc2f4382d5f43.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-193e6077d0df53351f2012da9f7451e7.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/向日葵/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-e38fa2090339e41d8e2bc2f4382d5f43.ctex"]
|
||||
source_file="res://assets/作物/向日葵/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-193e6077d0df53351f2012da9f7451e7.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 30 KiB After Width: | Height: | Size: 30 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://wqfspwqqpcwa"
|
||||
path="res://.godot/imported/1.webp-39c5186218d6a70b3b214094d5602b76.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-6b7798c51cbe39e5ab328bc5836f3c9b.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/向日葵/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-39c5186218d6a70b3b214094d5602b76.ctex"]
|
||||
source_file="res://assets/作物/向日葵/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-6b7798c51cbe39e5ab328bc5836f3c9b.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 30 KiB After Width: | Height: | Size: 30 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://bvcmrkatbo0f1"
|
||||
path="res://.godot/imported/0.webp-6d779ef7b648b1e546e4ba9e87048adb.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-63eb1edffbc9e3e228ea5afcf106ea2a.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/咖啡豆/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-6d779ef7b648b1e546e4ba9e87048adb.ctex"]
|
||||
source_file="res://assets/作物/咖啡豆/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-63eb1edffbc9e3e228ea5afcf106ea2a.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 21 KiB |
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://b7rryqoraiind"
|
||||
path="res://.godot/imported/1.webp-1f85d6df04e3014f721dc62f7c60a301.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/哈密瓜/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-1f85d6df04e3014f721dc62f7c60a301.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 20 KiB After Width: | Height: | Size: 20 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://bilp5c3p4muup"
|
||||
path="res://.godot/imported/0.webp-44b93bb80f1aa61722d002b9c7673b92.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-8799bc4c3eb57cb4d190ad1a2f2aa952.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/哈密瓜/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-44b93bb80f1aa61722d002b9c7673b92.ctex"]
|
||||
source_file="res://assets/作物/哈密瓜/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-8799bc4c3eb57cb4d190ad1a2f2aa952.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 24 KiB After Width: | Height: | Size: 24 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://by01gwdqm2b25"
|
||||
path="res://.godot/imported/2.webp-241c30c524225cf14a34f44113ad84e5.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-ef1ae6a286c854a08ebc8551517f6823.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/哈密瓜/2.webp"
|
||||
dest_files=["res://.godot/imported/2.webp-241c30c524225cf14a34f44113ad84e5.ctex"]
|
||||
source_file="res://assets/作物/哈密瓜/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-ef1ae6a286c854a08ebc8551517f6823.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://cfbyrlvyw7mbm"
|
||||
path="res://.godot/imported/0.webp-7c561674e7465fe1b7ab139e2d86374d.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/土豆/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-7c561674e7465fe1b7ab139e2d86374d.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://dig8kyw0tib3"
|
||||
path="res://.godot/imported/2.webp-b2dbe3a142652718e988b49bbb0c0744.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/土豆/2.webp"
|
||||
dest_files=["res://.godot/imported/2.webp-b2dbe3a142652718e988b49bbb0c0744.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 28 KiB After Width: | Height: | Size: 28 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://bkn5q3cyenc0q"
|
||||
path="res://.godot/imported/1.webp-f108974cb62a8d6c198d2e6263bb15ff.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-2dd945057ed9aef6aa603482ab806e5d.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/土豆/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-f108974cb62a8d6c198d2e6263bb15ff.ctex"]
|
||||
source_file="res://assets/作物/土豆/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-2dd945057ed9aef6aa603482ab806e5d.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 34 KiB After Width: | Height: | Size: 34 KiB |
@@ -2,16 +2,16 @@
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://dnb0afavrjkbx"
|
||||
path="res://.godot/imported/4.webp-09e380791e9c9ce6f1a8aefbef1f05a1.ctex"
|
||||
uid="uid://dig8kyw0tib3"
|
||||
path="res://.godot/imported/未成熟.webp-e6ea031a6f258edaec1f424b49b0de94.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/茄子/4.webp"
|
||||
dest_files=["res://.godot/imported/4.webp-09e380791e9c9ce6f1a8aefbef1f05a1.ctex"]
|
||||
source_file="res://assets/作物/土豆/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-e6ea031a6f258edaec1f424b49b0de94.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 20 KiB |
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://dgdshxgx8b4wj"
|
||||
path="res://.godot/imported/1.webp-8e159514a2d5265435603e4f8abadb12.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/大白菜/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-8e159514a2d5265435603e4f8abadb12.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 24 KiB After Width: | Height: | Size: 24 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://cla1xws7k5qbo"
|
||||
path="res://.godot/imported/0.webp-95fd204d42c46a44e3c4313652f5ffce.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-43a7c9b6afafbf0d5e6af53488d2eff9.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/大白菜/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-95fd204d42c46a44e3c4313652f5ffce.ctex"]
|
||||
source_file="res://assets/作物/大白菜/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-43a7c9b6afafbf0d5e6af53488d2eff9.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 23 KiB After Width: | Height: | Size: 23 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://dftmxuhrl4jqa"
|
||||
path="res://.godot/imported/2.webp-bdd6486dc35f8c758136190cc6fa9895.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-2f315bd8829c1b18106ea1b7cbeb08d1.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/大白菜/2.webp"
|
||||
dest_files=["res://.godot/imported/2.webp-bdd6486dc35f8c758136190cc6fa9895.ctex"]
|
||||
source_file="res://assets/作物/大白菜/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-2f315bd8829c1b18106ea1b7cbeb08d1.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 25 KiB After Width: | Height: | Size: 25 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://8ncjpot0587o"
|
||||
path="res://.godot/imported/0.webp-667c2ea589e0f98450ef6af17a7a5f5b.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-9ff6d4c1a71eb35de524cfcce9a4d803.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/大蒜/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-667c2ea589e0f98450ef6af17a7a5f5b.ctex"]
|
||||
source_file="res://assets/作物/大蒜/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-9ff6d4c1a71eb35de524cfcce9a4d803.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 36 KiB |
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://lw4nejejuy3e"
|
||||
path="res://.godot/imported/2.webp-019081ecbc5fe5a76dd6093516a568f2.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/大豆/2.webp"
|
||||
dest_files=["res://.godot/imported/2.webp-019081ecbc5fe5a76dd6093516a568f2.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 19 KiB After Width: | Height: | Size: 19 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://d0j0eifp0iemu"
|
||||
path="res://.godot/imported/0.webp-d2cef997bf4d87930aa951d63b7c2706.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-bb6a44973037d348d8f253c2318a4b11.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/大豆/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-d2cef997bf4d87930aa951d63b7c2706.ctex"]
|
||||
source_file="res://assets/作物/大豆/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-bb6a44973037d348d8f253c2318a4b11.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 30 KiB After Width: | Height: | Size: 30 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://cofjstbs0r8h0"
|
||||
path="res://.godot/imported/1.webp-902de037c7b6f80519e6d76f562055ed.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-4e2ae24acb538888e1f85c849bd74a22.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/大豆/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-902de037c7b6f80519e6d76f562055ed.ctex"]
|
||||
source_file="res://assets/作物/大豆/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-4e2ae24acb538888e1f85c849bd74a22.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 32 KiB |
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://5x2uq2r3yjms"
|
||||
path="res://.godot/imported/2.webp-638bab14e5309cf618b4ad0d9893879c.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/富贵竹/2.webp"
|
||||
dest_files=["res://.godot/imported/2.webp-638bab14e5309cf618b4ad0d9893879c.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 20 KiB After Width: | Height: | Size: 20 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://clfqb3o1k4rby"
|
||||
path="res://.godot/imported/0.webp-a726644bf3d2533e1a0c1dab78519549.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-fc281ae82dc0894a59b7e69aa4caf221.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/富贵竹/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-a726644bf3d2533e1a0c1dab78519549.ctex"]
|
||||
source_file="res://assets/作物/富贵竹/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-fc281ae82dc0894a59b7e69aa4caf221.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://bd3omqp1ps1hw"
|
||||
path="res://.godot/imported/1.webp-e919d49ea2e08a7abff7233ed4b5039a.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-cdc0b439ef04abe0bed4481eaea3017c.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/富贵竹/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-e919d49ea2e08a7abff7233ed4b5039a.ctex"]
|
||||
source_file="res://assets/作物/富贵竹/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-cdc0b439ef04abe0bed4481eaea3017c.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 36 KiB |
@@ -1,34 +0,0 @@
|
||||
[remap]
|
||||
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://4cbuoe4jv4qf"
|
||||
path="res://.godot/imported/2.webp-944f6e4f9f746fb1e8751aa4709965cf.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/小麦/2.webp"
|
||||
dest_files=["res://.godot/imported/2.webp-944f6e4f9f746fb1e8751aa4709965cf.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.01
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
mipmaps/generate=true
|
||||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
process/hdr_as_srgb=false
|
||||
process/hdr_clamp_exposure=false
|
||||
process/size_limit=0
|
||||
detect_3d/compress_to=0
|
||||
|
Before Width: | Height: | Size: 33 KiB After Width: | Height: | Size: 33 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://lu6s5qts4hnv"
|
||||
path="res://.godot/imported/0.webp-01976b7393f4108b4278b5fddaf5c9f1.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-c9bfd368c0884062ab89b3e32f3a883f.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/小麦/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-01976b7393f4108b4278b5fddaf5c9f1.ctex"]
|
||||
source_file="res://assets/作物/小麦/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-c9bfd368c0884062ab89b3e32f3a883f.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 38 KiB After Width: | Height: | Size: 38 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://doqkqexho8u2"
|
||||
path="res://.godot/imported/1.webp-aecdb4ce7bebcc6234fa8729e020c125.ctex"
|
||||
path="res://.godot/imported/未成熟.webp-bb4304385d4c9de770a65d34847911d9.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/小麦/1.webp"
|
||||
dest_files=["res://.godot/imported/1.webp-aecdb4ce7bebcc6234fa8729e020c125.ctex"]
|
||||
source_file="res://assets/作物/小麦/未成熟.webp"
|
||||
dest_files=["res://.godot/imported/未成熟.webp-bb4304385d4c9de770a65d34847911d9.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 27 KiB |
@@ -3,15 +3,15 @@
|
||||
importer="texture"
|
||||
type="CompressedTexture2D"
|
||||
uid="uid://qgt86c1p2dn2"
|
||||
path="res://.godot/imported/0.webp-9ef5f54aba5e5ec96a14a0d1b8959df9.ctex"
|
||||
path="res://.godot/imported/幼苗.webp-49470da8a1d98df376f51873985985d2.ctex"
|
||||
metadata={
|
||||
"vram_texture": false
|
||||
}
|
||||
|
||||
[deps]
|
||||
|
||||
source_file="res://assets/作物/山楂/0.webp"
|
||||
dest_files=["res://.godot/imported/0.webp-9ef5f54aba5e5ec96a14a0d1b8959df9.ctex"]
|
||||
source_file="res://assets/作物/山楂/幼苗.webp"
|
||||
dest_files=["res://.godot/imported/幼苗.webp-49470da8a1d98df376f51873985985d2.ctex"]
|
||||
|
||||
[params]
|
||||
|
||||