Skip to content

Commit 8d2ac2c

Browse files
committed
FlyController release
0 parents  commit 8d2ac2c

16 files changed

Lines changed: 1726 additions & 0 deletions

.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
.gradle
2+
.idea
3+
build

LICENSE

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
MIT License
2+
3+
Copyright (c) 2025 FlyawayMaking
4+
5+
Permission is hereby granted, free of charge, to any person obtaining a copy
6+
of this software and associated documentation files (the "Software"), to deal
7+
in the Software without restriction, including without limitation the rights
8+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9+
copies of the Software, and to permit persons to whom the Software is
10+
furnished to do so, subject to the following conditions:
11+
12+
The above copyright notice and this permission notice shall be included in
13+
all copies or substantial portions of the Software.
14+
15+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21+
THE SOFTWARE.

README.md

Lines changed: 182 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,182 @@
1+
# FlyController
2+
3+
FlyController — умная система временного полёта с интеграцией CoinsEngine. Игроки покупают полёт за внутриигровую валюту, получая доступ к полёту в разрешённых мирах. Система автоматически сохраняет оставшееся время при выходе, смене мира или в бою.
4+
5+
---
6+
7+
## Возможности
8+
9+
- Настраиваемая система уровней полёта через config.yml
10+
- Интеграция с CoinsEngine для экономических транзакций
11+
- Автоматическое сохранение времени при выходе/смене мира/в бою
12+
- Автоматическое восстановление полёта при входе на сервер
13+
- ActionBar с таймером оставшегося времени полёта
14+
- Ограничение использования полёта только разрешёнными мирами
15+
- Настраиваемые скорости полёта через config.yml
16+
- Защита от конфликтов с Essentials
17+
- Команда перезагрузки конфигурации без перезапуска сервера
18+
19+
---
20+
21+
## Конфигурация (config.yml)
22+
23+
```
24+
# Настройки валюты
25+
currency: "money"
26+
27+
# Миры где разрешён полёт (список)
28+
worlds:
29+
- "world"
30+
31+
# Перезарядка после использования полёта (в миллисекундах)
32+
cooldown: 600000
33+
34+
# Уровни полёта
35+
flight-tiers:
36+
1:
37+
cost: 50000
38+
duration: 120
39+
2:
40+
cost: 100000
41+
duration: 300
42+
3:
43+
cost: 200000
44+
duration: 600
45+
46+
# Скорости полёта (значения от 0.0 до 1.0)
47+
fly-speeds:
48+
1: 0.1
49+
2: 0.2
50+
3: 0.4
51+
```
52+
53+
---
54+
55+
## Команды и права
56+
57+
### Основные команды для игроков
58+
59+
```
60+
/mfly info - информация о балансе и уровнях полёта
61+
/mfly deposit <сумма> - внести деньги на счёт полётов
62+
/mfly activate - активировать полёт (максимальный доступный уровень)
63+
/mfly continue - продолжить сохранённый полёт
64+
/flyspeed <скорость> - установить скорость полёта
65+
```
66+
67+
### Команды для администраторов
68+
69+
```
70+
/mfly reload - перезагрузить конфигурацию
71+
```
72+
73+
### Права доступа
74+
75+
```
76+
flyplugin.mfly - доступ к системе полётов (/mfly)
77+
flyplugin.flyspeed - доступ к команде /flyspeed
78+
flyplugin.admin - доступ к команде перезагрузки конфига
79+
```
80+
81+
---
82+
83+
## Особенности работы
84+
85+
### Автоматическое сохранение
86+
- При выходе из сервера - полёт ставится на паузу
87+
- При смене мира (не разрешённый) - полёт ставится на паузу
88+
- При вступлении в PvP-бой - полёт отключается с сохранением времени
89+
90+
### Автоматическое восстановление
91+
- При входе на сервер - полёт автоматически восстанавливается
92+
- Сохранённое время переживает перезагрузки сервера
93+
94+
### Ограничения
95+
- Полёт работает только в разрешённых мирах из config.yml
96+
- В PvP-бою полёт автоматически отключается
97+
- Скорость полёта настраивается через config.yml
98+
99+
---
100+
101+
## Пример использования
102+
103+
```
104+
1. Игрок вносит деньги: /mfly deposit 50000
105+
2. Активирует полёт: /mfly activate
106+
3. Видит в ActionBar: ⏰ 1:59 осталось полёта
107+
4. При выходе из мира: "Полёт отключён! Оставшееся время сохранено"
108+
5. При возвращении для продолжения полёта: /mfly continue
109+
6. Устанавливает скорость: /flyspeed 2
110+
```
111+
112+
---
113+
114+
## Настройка
115+
116+
### Добавление новых уровней полёта
117+
Отредактируйте `flight-tiers` в config.yml:
118+
```
119+
flight-tiers:
120+
1:
121+
cost: 50000
122+
duration: 120
123+
2:
124+
cost: 100000
125+
duration: 300
126+
3:
127+
cost: 200000
128+
duration: 600
129+
4:
130+
cost: 500000
131+
duration: 1200
132+
```
133+
134+
### Добавление новых скоростей
135+
Отредактируйте `fly-speeds` в config.yml:
136+
```
137+
fly-speeds:
138+
1: 0.05
139+
2: 0.1
140+
3: 0.2
141+
4: 0.4
142+
5: 0.8
143+
```
144+
145+
### Добавление новых миров
146+
Отредактируйте `worlds` в config.yml:
147+
```
148+
worlds:
149+
- "world"
150+
- "world_nether"
151+
- "world_the_end"
152+
- "my_custom_world"
153+
```
154+
155+
---
156+
157+
## Совместимость
158+
159+
- **Обязательно**: [CoinsEngine](https://github.com/nulli0n/CoinsEngine-spigot) (для экономики)
160+
- **Рекомендуется**: EssentialsX (для базового полёта)
161+
- **Поддержка**: Paper 1.21.8, Java 21
162+
163+
---
164+
165+
## Установка
166+
167+
1. Убедитесь, что установлен CoinsEngine
168+
2. Скачайте **последний релиз** из раздела [Releases](../../releases)
169+
3. Поместите .jar файл в папку /plugins
170+
4. Перезапустите сервер
171+
5. Настройте config.yml под свои нужды
172+
6. Используйте /mfly reload для применения изменений
173+
174+
---
175+
176+
## Примечания
177+
178+
- Полёт в креативе не отключается автоматически
179+
- При отключении плагина полёт сохраняется и восстанавливается
180+
- Система защищена от конфликтов с Essentials
181+
- Все транзакции логируются для отладки
182+
- Конфигурация применяется мгновенно через /mfly reload

build.gradle

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
plugins {
2+
id 'java'
3+
}
4+
5+
group = 'com.flyaway.flycontroller'
6+
version = '1.0.0'
7+
8+
java {
9+
toolchain {
10+
languageVersion = JavaLanguageVersion.of(21)
11+
}
12+
}
13+
14+
repositories {
15+
mavenCentral()
16+
maven { url = 'https://repo.nightexpressdev.com/releases'}
17+
maven {
18+
name = "papermc"
19+
url = "https://repo.papermc.io/repository/maven-public/"
20+
}
21+
}
22+
23+
dependencies {
24+
compileOnly 'io.papermc.paper:paper-api:1.21.8-R0.1-SNAPSHOT'
25+
compileOnly 'su.nightexpress.coinsengine:CoinsEngine:2.5.0'
26+
}
27+
28+
tasks.jar {
29+
archiveBaseName.set("FlyController")
30+
}

settings.gradle

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
rootProject.name = 'FlyController'
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
package com.flyaway.flycontroller;
2+
3+
import net.md_5.bungee.api.ChatMessageType;
4+
import net.md_5.bungee.api.chat.TextComponent;
5+
import org.bukkit.entity.Player;
6+
7+
public class ActionBarManager {
8+
private final FlyPlugin plugin;
9+
10+
public ActionBarManager(FlyPlugin plugin) {
11+
this.plugin = plugin;
12+
}
13+
14+
public void sendFlightTime(Player player, long endTime) {
15+
long remainingTime = endTime - System.currentTimeMillis();
16+
if (remainingTime <= 0) {
17+
return;
18+
}
19+
20+
long seconds = remainingTime / 1000;
21+
long minutes = seconds / 60;
22+
seconds = seconds % 60;
23+
24+
String timeString = String.format("§a⏰ §e%d:%02d §aосталось полёта", minutes, seconds);
25+
26+
player.spigot().sendMessage(ChatMessageType.ACTION_BAR, TextComponent.fromLegacyText(timeString));
27+
}
28+
}
Lines changed: 111 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,111 @@
1+
package com.flyaway.flycontroller;
2+
3+
import org.bukkit.configuration.file.FileConfiguration;
4+
import org.bukkit.configuration.file.YamlConfiguration;
5+
6+
import java.io.File;
7+
import java.io.IOException;
8+
import java.util.HashMap;
9+
import java.util.Map;
10+
import java.util.List;
11+
12+
public class ConfigManager {
13+
private final FlyPlugin plugin;
14+
private File configFile;
15+
private FileConfiguration config;
16+
17+
public ConfigManager(FlyPlugin plugin) {
18+
this.plugin = plugin;
19+
this.configFile = new File(plugin.getDataFolder(), "config.yml");
20+
this.config = YamlConfiguration.loadConfiguration(configFile);
21+
}
22+
23+
public void loadConfig() {
24+
if (!configFile.exists()) {
25+
plugin.saveResource("config.yml", false);
26+
config = YamlConfiguration.loadConfiguration(configFile);
27+
}
28+
29+
// Создаем папку если не существует
30+
if (!plugin.getDataFolder().exists()) {
31+
plugin.getDataFolder().mkdirs();
32+
}
33+
}
34+
35+
public Map<Integer, FlightTier> getFlightTiers() {
36+
Map<Integer, FlightTier> tiers = new HashMap<>();
37+
38+
if (config.contains("flight-tiers")) {
39+
for (String key : config.getConfigurationSection("flight-tiers").getKeys(false)) {
40+
try {
41+
int level = Integer.parseInt(key);
42+
double cost = config.getDouble("flight-tiers." + key + ".cost");
43+
int duration = config.getInt("flight-tiers." + key + ".duration");
44+
45+
tiers.put(level, new FlightTier(level, cost, duration));
46+
} catch (NumberFormatException e) {
47+
plugin.getLogger().warning("Неверный формат уровня полёта: " + key);
48+
}
49+
}
50+
}
51+
52+
// Если в конфиге нет уровней, используем значения по умолчанию
53+
if (tiers.isEmpty()) {
54+
tiers.put(1, new FlightTier(1, 50000, 120));
55+
tiers.put(2, new FlightTier(2, 100000, 300));
56+
tiers.put(3, new FlightTier(3, 200000, 600));
57+
plugin.getLogger().warning("Используются уровни полёта по умолчанию");
58+
}
59+
60+
return tiers;
61+
}
62+
63+
public Map<Integer, Float> getFlySpeeds() {
64+
Map<Integer, Float> speeds = new HashMap<>();
65+
66+
if (config.contains("fly-speeds")) {
67+
for (String key : config.getConfigurationSection("fly-speeds").getKeys(false)) {
68+
try {
69+
int level = Integer.parseInt(key);
70+
float speed = (float) config.getDouble("fly-speeds." + key);
71+
speeds.put(level, speed);
72+
} catch (NumberFormatException e) {
73+
plugin.getLogger().warning("Неверный формат скорости полёта: " + key);
74+
}
75+
}
76+
}
77+
78+
// Значения по умолчанию
79+
if (speeds.isEmpty()) {
80+
speeds.put(1, 0.1f);
81+
speeds.put(2, 0.2f);
82+
speeds.put(3, 0.4f);
83+
}
84+
85+
return speeds;
86+
}
87+
88+
public List<String> getWorlds() {
89+
return config.getStringList("worlds");
90+
}
91+
92+
public String getCurrency() {
93+
return config.getString("currency", "money"); // money по умолчанию
94+
}
95+
96+
public long getCooldownTime() {
97+
return config.getLong("cooldown", 600000); // 10 минут по умолчанию
98+
}
99+
100+
public FileConfiguration getConfig() {
101+
return config;
102+
}
103+
104+
public void saveConfig() {
105+
try {
106+
config.save(configFile);
107+
} catch (IOException e) {
108+
plugin.getLogger().warning("Не удалось сохранить config.yml: " + e.getMessage());
109+
}
110+
}
111+
}

0 commit comments

Comments
 (0)