1
0
mirror of https://github.com/mcMMO-Dev/mcMMO.git synced 2026-02-18 09:43:00 +01:00

Compare commits

...

1904 Commits
1.4.04 ... 1.12

Author SHA1 Message Date
Gabriel Harris-Rouquette
5dcdacee07 Start documenting some of the bradle scripts.
Signed-off-by: Gabriel Harris-Rouquette <gabizou@me.com>
2019-02-17 23:32:17 -08:00
Gabriel Harris-Rouquette
925ef21a8e Fix a few things with the git ignore file and wrapper.
Signed-off-by: Gabriel Harris-Rouquette <gabizou@me.com>
2019-02-17 13:43:09 -08:00
Gabriel Harris-Rouquette
cb01515451 First creation of an NMS Handler. Not sure if relocation works yet.
Signed-off-by: Gabriel Harris-Rouquette <gabizou@me.com>
2019-02-16 21:35:54 -08:00
Gabriel Harris-Rouquette
a9e81602b4 Merge upstream into fixed kotlin script changes.
Signed-off-by: Gabriel Harris-Rouquette <gabizou@me.com>
2019-02-16 18:58:54 -08:00
Gabriel Harris-Rouquette
8645ce641d Complete Kotlin-DSL Gradle scripting for multiple projects.
Added the shadow plugin integration with the entire project. Indvidual
modules each have their designated dependencies and each will assign
various dependencies based on constants now made through buildSrc.

Signed-off-by: Gabriel Harris-Rouquette <gabizou@me.com>
2019-02-16 18:41:28 -08:00
nossr50
3a765e1164 new config pt 8 (moving to configurable branch to test..) 2019-02-16 15:09:56 -08:00
nossr50
a5a613e200 Killing Dead Imports 2019-02-15 19:40:59 -08:00
nossr50
4e8e95e3cb new config system pt 7 (jesus) 2019-02-15 17:45:48 -08:00
nossr50
f9fb9a17a9 defining entitytype (wip) 2019-02-15 15:20:36 -08:00
nossr50
4ea9037dd4 new config system pt 6
doing some work on experience.yml
2019-02-15 15:08:15 -08:00
nossr50
1d9a7cc720 mcMMO is back to requiring bukkit instead of spigot 2019-02-14 14:02:36 -08:00
nossr50
f6a3084a47 new config system pt 5 2019-02-14 13:59:27 -08:00
nossr50
41b484b1c3 new config system pt 4 2019-02-14 13:21:43 -08:00
nossr50
df101e54b1 new config system pt 3 2019-02-14 13:07:12 -08:00
nossr50
9a65621f68 new config system pt 2 2019-02-13 22:43:34 -08:00
nossr50
9a91daf910 new config system pt 1 2019-02-13 22:08:20 -08:00
nossr50
3a7b6fef7d tweak blockpos abstraction 2019-02-13 10:22:58 -08:00
nossr50
9383b1c65c expanding the abstraction again... 2019-02-13 09:12:53 -08:00
nossr50
261d571be1 expanding the abstraction (this is going to happen a lot) 2019-02-13 09:02:30 -08:00
nossr50
4461cfacd2 Fleshing out the abstraction 2019-02-13 08:40:13 -08:00
nossr50
84353de71d More abstraction 2019-02-12 07:17:27 -08:00
nossr50
1ab4645223 Fleshing out the abstraction 2019-02-12 06:54:32 -08:00
nossr50
b6a56d6865 Configurable WIP 2019-02-10 00:46:31 -08:00
nossr50
67cc162e07 Configurate should be set for YAML 2019-02-10 00:35:25 -08:00
nossr50
401cc3e35b Repo & Depends below the plugin block 2019-02-10 00:34:08 -08:00
nossr50
d45aac713f Moving Stuff Around Pt 3 2019-02-10 00:31:53 -08:00
nossr50
83c1dab963 Adding Configurable lib 2019-02-10 00:31:35 -08:00
nossr50
bbcc1ee7da Changing the style of our code 2019-02-09 22:46:30 -08:00
nossr50
e749d5eb7f Moving Stuff around pt 2 2019-02-09 22:37:22 -08:00
nossr50
4d4dad0ccb Moving stuff around, what a mess this is going to be. 2019-02-09 21:14:45 -08:00
nossr50
380d4be9c9 Moving stuff into the core package and fleshing out some more abstractions 2019-02-09 21:03:28 -08:00
nossr50
b40b206bf5 Fleshing out Abstractions for World, Location, Block, BlockState 2019-02-09 19:38:31 -08:00
nossr50
a2c0a02d30 Planning this out is actually quite hard, getting sleepy now so I'll flesh this out tomorrow. 2019-02-09 03:03:21 -08:00
Gabriel Harris-Rouquette
196ace4b81 Split up dependencies for multiple version support.
The "core" module will house the entire abstraction layer of mcMMO, while
the "bukkit" and "sponge" modules will house common code to share between
the various versions being supported for each platform. Specifically,
spigot will be split up based on the listener handlers being registered,
and will be shadow packaged according to their targeted Minecraft version.
Sponge's multi-version dependency will be based on the API version, since
the only constant known between the various API versions is the plugin
annotations and basic listener annotations.

Signed-off-by: Gabriel Harris-Rouquette <gabizou@me.com>
2019-02-07 19:58:53 -08:00
nossr50
b14871d499 ignore .idea/ 2019-02-07 17:22:21 -08:00
Gabriel Harris-Rouquette
e80c183894 Cleanup and fix some of the gradle scripts. Add shadows to retain dependencies.
Signed-off-by: Gabriel Harris-Rouquette <gabizou@me.com>
2019-02-07 17:10:08 -08:00
Gabriel Harris-Rouquette
fe40748929 Migrate gradle scripts to have multiple modules and source sets. Using Kotlin-DSL for enhanced script debugging.
Signed-off-by: Gabriel Harris-Rouquette <gabizou@me.com>
2019-02-07 16:09:35 -08:00
nossr50
49a6ce7b8f specify utf8 for gradle compiler 2019-02-06 19:52:33 -08:00
nossr50
6127a7fe11 Supressing some warnings 2019-02-06 19:49:53 -08:00
nossr50
f1ac4ff265 gradle part 3 2019-02-06 19:44:26 -08:00
nossr50
d98b077be3 gradle part 2 2019-02-06 19:41:06 -08:00
nossr50
bbbf6777f9 Converting mcMMO to gradle (NOT DONE YET) 2019-02-06 18:06:04 -08:00
nossr50
c0a3d63213 Salvage entries are no longer case sensitive 2019-02-06 18:00:21 -08:00
nossr50
5e8a840418 Ignore Gradle Files 2019-02-06 17:47:06 -08:00
nossr50
dbf32b4715 Back to work 2019-02-06 17:07:08 -08:00
nossr50
017e32c30a Fishing will no longer cancel the exp dropped for ice fishing and will no longer bring xp values below zero with the xp multiplier
Not sure if this fixes the XP bug though!
2019-02-06 12:46:12 -08:00
nossr50
8e048300e8 2.1.11 2019-02-06 11:01:57 -08:00
nossr50
2569ed0565 2.1.10 2019-02-06 03:21:02 -08:00
nossr50
45b4f4a314 Fishing Locale did an oopsie 2019-02-06 03:09:12 -08:00
nossr50
98e6400dd8 Fishing command did an oopsie 2019-02-06 03:01:43 -08:00
nossr50
63d3a328c4 EndStone now gives the same XP as stone
Update your experience.yml
2019-02-05 20:43:56 -08:00
nossr50
06a4f964e8 Updating the mcMMO website link 2019-02-05 20:42:02 -08:00
nossr50
9aef304fd4 Fixing 2.1.9 pom version number 2019-02-05 20:38:33 -08:00
nossr50
f32834411d 2.1.9 Release 2019-02-05 20:35:05 -08:00
nossr50
577e3339f1 Grab the version of WG in a better way 2019-02-05 20:23:20 -08:00
nossr50
36f75457e3 2.2.0 Dev Starts now 2019-02-05 17:24:53 -08:00
nossr50
b67b0a5b94 2.1.8 2019-02-05 16:18:15 -08:00
nossr50
e389c4b8f1 WG API shouldn't be used unless WG is on version 7 2019-02-05 10:49:40 -08:00
nossr50
303a922165 Bite for Master Angler will no longer display so many decimal places
Fixes #3772
2019-02-04 23:29:24 -08:00
nossr50
4ea5432561 Abilities no longer activate if you don't have permission 2019-02-04 22:04:50 -08:00
nossr50
9a428332a9 RetroMode and Standard scaling now have specific keys in advanced.yml to reduce confusion 2019-02-04 21:56:57 -08:00
nossr50
c43fd9bc69 Back to dev 2019-02-03 21:30:12 -08:00
nossr50
77e6e79eb6 Prep for 2.1.7 Release 2019-02-03 18:20:56 -08:00
nossr50
1568f71d83 Fixing a styling bug for party member names 2019-02-03 17:59:29 -08:00
nossr50
f274450376 The bug where hidden players could be seen in the party list should be fixed 2019-02-03 17:56:13 -08:00
nossr50
0b3a642c95 Oopsie 2019-02-03 17:46:03 -08:00
nossr50
025183d434 Tweaks to the party info commands 2019-02-03 17:44:10 -08:00
nossr50
371a3ceec7 Unarmed now has some spam detection
Fixed an error in the skillranks.yml file as well
2019-02-03 13:17:42 -08:00
nossr50
84b3cfc309 Fixed an almost 6 year old bug involving salvage materials smh
Updated the new ExperienceAPI methods to check for level ups
2019-02-02 07:15:12 -08:00
nossr50
14e5998aa0 Added 4 new API methods for adding XP to a player based on blocks 2019-02-01 15:23:45 -08:00
nossr50
c839837d7a Fixing some coloring issues 2019-02-01 11:00:02 -08:00
nossr50
e65e6ad14e Prep for 2.1.6 release 2019-02-01 10:40:39 -08:00
nossr50
fc6c804caf Recolored some lines in the locale related to failure from white to red 2019-02-01 10:36:28 -08:00
nossr50
8228ae248f Fixed a bug where Arcane Salvage could never fail
SubSkillFailure renamed to SubSkillFailed in config.yml
SubSkillFailed now sends to chat by default and no longer sends to the action bar
2019-02-01 10:34:13 -08:00
nossr50
c6a4cbd715 Fixed a bug where Salvage was giving back too many materials 2019-02-01 10:22:55 -08:00
nossr50
90520cd50b 2.1.5 release
mcMMO no longer ignores cancelled PlayerInteractEvents due to conflicts with super ability activations
2019-01-31 20:53:36 -08:00
nossr50
8262711e7e Prep for release of 2.1.4
Fixed many display bugs
Added ranks to Super Repair, and Repair Mastery
Fixes #3754, #3746, #3745, #3756
2019-01-31 20:02:39 -08:00
nossr50
8aa92322d1 Fixed Styling for /salvage 2019-01-31 19:27:23 -08:00
nossr50
bdfac28b44 Fixed Alchemy XP Gain 2019-01-31 18:44:51 -08:00
t00thpick1
cb89a80fd8 Only have 1 xp gain instance for archery. 2019-01-31 19:55:09 -05:00
nossr50
a2f9ab70aa mcMMO no longer ignores cancelled block place events 2019-01-31 15:33:06 -08:00
nossr50
5d010594dd Temporarily disabled Flux Mining
I'll rework this skill in the future
2019-01-31 15:30:39 -08:00
nossr50
d609b45e68 Correcting a bug with the new Enderman Endermite farm exploit fix and making it toggleable for servers that wish to allow it! 2019-01-31 14:40:37 -08:00
nossr50
4c63eee6d5 Entities that target endermite no longer give XP (credits to TheBentoBox for the tip) 2019-01-31 14:30:35 -08:00
nossr50
f3aff37b46 Removing more debug code SORRY!
nossr50 did a double oopsie
2019-01-31 14:18:17 -08:00
nossr50
f2c32f07da Removing leftover debug code
nossr50 did an oopsie
2019-01-31 14:14:15 -08:00
nossr50
bff72486d0 Fixed a bug where static chance skills uses incorrect calculations for success
Cleaned up some leftover code from the old skill unlock system
2019-01-31 14:07:03 -08:00
nossr50
0193b53988 mcMMO now ignores cancelled events for PlayerInteractEvent 2019-01-31 12:56:15 -08:00
nossr50
039542f125 Iron Arm Style no longer checks for Iron Grip levels for its own unlock checks 2019-01-31 11:27:14 -08:00
nossr50
99b50319a3 Prep for 2.1.3 hotfix release 2019-01-30 14:56:31 -08:00
nossr50
7e5a8bc659 Temporarily removed unarmed item pickup until it gets fixed 2019-01-30 08:45:38 -08:00
nossr50
e66ed3f3f1 Prep for release 2019-01-29 17:14:52 -08:00
nossr50
cef9fad49f Fixing unarmed not picking up items properly 2019-01-29 16:13:04 -08:00
nossr50
8ad9419240 Endermen back to 1.0 2019-01-29 08:13:41 -08:00
nossr50
1871c1ec63 endermen and witches give 0.1x modifiers 2019-01-29 07:47:48 -08:00
nossr50
7a721c3229 Tweaking mob XP Values
Phantom added and set to 4.0
Witch is now set to 1.0 instead of 0.0
Ender Dragon is now set to 1.0 instead of 0.0
2019-01-29 07:13:06 -08:00
nossr50
370af987d6 Fixes #3737 2019-01-28 19:35:54 -08:00
nossr50
a22636b2d9 Flux Mining will now be a passive and not an item 2019-01-28 17:48:26 -08:00
nossr50
399a1529f4 Pummel now calculates correctly 2019-01-28 13:14:15 -08:00
nossr50
3734300e59 Fixing an error with shake and RNG calculations 2019-01-28 04:15:34 -08:00
nossr50
fc7b4a6790 Buffed Iron Arm, adding ranks to Iron Arm, Iron Grip, Arrow Deflect, and Disarm 2019-01-28 03:55:30 -08:00
nossr50
00f5491718 Added many styling options
Improved Smelting Style
You can now add the level required to a skills name in the locale (instructions can be found next to the locale string)
2019-01-28 03:40:32 -08:00
nossr50
67ed9d324e Fixing the styling on /smelting 2019-01-28 00:56:15 -08:00
nossr50
ddf953b3b7 Grass block did an oopsie
Fixed Grass not giving treasures
2019-01-27 23:15:53 -08:00
nossr50
f89b7ccc9f better debug stick 2019-01-27 23:12:04 -08:00
nossr50
154b10209d mcMMO will no longer put items into your hands 2019-01-27 22:46:45 -08:00
nossr50
fbc7cbf389 Anti-Cheat compatibility 2019-01-27 22:26:45 -08:00
nossr50
6f81cf7384 Static things shouldn't use a maxbonuslevel from config 2019-01-27 22:01:55 -08:00
nossr50
4f832edada Fixing the fishing AFK detection 2019-01-27 21:55:00 -08:00
nossr50
85a04c71f4 tweaking anti-afk 2019-01-27 21:13:42 -08:00
nossr50
c7ed3ee2a0 Magic Hunter requires treasure hunter and has ranks now 2019-01-27 20:56:16 -08:00
nossr50
7e34e87bc0 Magic Hunter stats now check for treasure hunter 2019-01-27 20:36:55 -08:00
nossr50
b2b623505d Removing traps from fishing command 2019-01-27 20:27:48 -08:00
nossr50
67a57f7472 This might be better 2019-01-27 20:09:32 -08:00
nossr50
d7fe01579b Make sure we clean up buffs from tools 2019-01-27 20:00:58 -08:00
nossr50
e969598f58 Fixing a lot of bugs involving calculating the success of skills 2019-01-27 19:36:16 -08:00
nossr50
be9aeacd70 Fixing lucky displays 2019-01-27 19:00:48 -08:00
nossr50
5f39a7cb80 Fixing a bug where Lucky perk wasn't adding to success 2019-01-27 18:53:10 -08:00
nossr50
7b38658310 Adding mushroom stems to Tree Feller 2019-01-27 18:28:14 -08:00
nossr50
d81c3d06c5 XP Gains now report sources, added some config options regarding XP bars
Fixed some issues with Roll
Fixes https://github.com/mcMMO-Dev/mcMMO/issues/3732
2019-01-27 18:11:51 -08:00
nossr50
a504bc407a Keep track of more fall locations 2019-01-27 00:20:18 -08:00
nossr50
67bcb8da11 Updating the fancy changelog 2019-01-26 23:14:12 -08:00
nossr50
55821f7703 Acrobatics now uses much better anti-exploit prevention 2019-01-26 23:08:05 -08:00
Robert A. C
a601360cbb Merge pull request #3730 from SXRWahrheit/patch-2
Update Changelog_2.1.0.md
2019-01-26 15:30:08 -08:00
SXRWahrheit
444feb1c2c Update Changelog_2.1.0.md 2019-01-26 17:26:37 -06:00
nossr50
6592562c56 Check the target fishing location 2019-01-26 14:41:17 -08:00
nossr50
9aae4825cc Fixing XP gain in fishing 2019-01-26 14:34:28 -08:00
nossr50
22c5280d4e AFK Fishing protection 2019-01-26 14:25:01 -08:00
nossr50
49a91617f0 Back to dev 2019-01-26 14:05:05 -08:00
nossr50
b5bc324f97 Excavation now uses archaeology instead of treasurehunter for its perm node address 2019-01-26 14:01:35 -08:00
Robert A. C
a120981e52 This is now a changelog specific to 2.1.0
Makes it easier to read
2019-01-26 13:35:13 -08:00
nossr50
1df4f74f8c Counter Attack now makes use of a rank system 2019-01-26 12:54:38 -08:00
nossr50
d4d5d9bac1 Gore, Pummel, and Call of The Wild now use the rank system 2019-01-26 12:50:35 -08:00
nossr50
28e963f1eb Disabling unfinished skills until they are finished 2019-01-26 12:45:45 -08:00
nossr50
9626c06b58 Added a nicer changelog 2019-01-26 12:23:30 -08:00
nossr50
baf1796b08 Taming's Beast Lore now uses a rank system 2019-01-26 11:21:42 -08:00
nossr50
b39340227f Greater Impact now uses the rank system 2019-01-26 10:57:04 -08:00
nossr50
105a81aede Axes' Critical Strikes now uses the rank system 2019-01-26 10:55:16 -08:00
nossr50
9ff8692625 Added Dodge, Arrow Retrieval to rank system 2019-01-26 10:52:22 -08:00
nossr50
280971042a Furnaces give XP to the last person to modify their contents 2019-01-26 09:32:28 -08:00
nossr50
6ac1c4fa2c JSON Styling will be handled in the Locale instead of the config 2019-01-26 08:27:58 -08:00
nossr50
d84d487435 Debug stick tells you about placestore & treasure data when hitting blocks 2019-01-26 08:14:06 -08:00
t00thpick1
43d8e08e83 Fix offline inspecting a player hitting an error if the casing didn't match up perfectly. Fixes #3727 2019-01-26 10:51:30 -05:00
nossr50
859063e406 You can now toggle off the skill commands sending blank lines 2019-01-26 07:33:23 -08:00
nossr50
ad990dbb28 Less blank lines on skill commands 2019-01-26 07:27:15 -08:00
nossr50
1c58bd392d Hover tips now show level requirements for upgrading skills 2019-01-25 18:51:04 -08:00
nossr50
cf9117097d MMOInfo command makes better wiki links 2019-01-25 17:54:02 -08:00
nossr50
71d1574a7d Fixing Daze, Counter-Attack, and Serrated Strikes hover tip messages containing {0} 2019-01-25 17:14:10 -08:00
nossr50
f1fc095876 Removed the Kraken 2019-01-25 14:00:18 -08:00
nossr50
3a367d71fa Fishing traps are stupid. 2019-01-25 13:46:26 -08:00
nossr50
f4cab35a46 Fix SkillShot display 2019-01-25 12:49:16 -08:00
nossr50
c22a1a0dd2 Fixing Rupture (Bleed) ConcurrentModificationException
Removed the internal limit on ticks for Rupture
Rupture no longer adds new ticks when applying bleed to an existing target, it instead refreshes the duration
2019-01-25 11:12:31 -08:00
nossr50
a421bd7e4c Fixing the RNG display calculations for RetroMode
I temporarily disabled the output for graceful roll in the stats, will be turning that on again in the morning.
2019-01-25 01:36:14 -08:00
nossr50
ef9b3d40e9 Actually fixing #3709 2019-01-24 21:19:04 -08:00
nossr50
24458879a4 Fixing a bug where an ability length cap of 0 did not properly update skill commands
Fixes #3709
2019-01-24 20:55:46 -08:00
nossr50
1d6a142b12 Rewrote the RNG system to be more unified 2019-01-24 20:45:26 -08:00
nossr50
b7fc3f05e9 Iron Arm & Impact scale with Retro properly now
Fixes #3723
2019-01-24 15:23:39 -08:00
nossr50
3cfd3b0109 Don't modify the list we are iterating over 2019-01-24 13:20:45 -08:00
nossr50
bb64221c6b Fixing some issues with the new skill system and retro mode 2019-01-23 16:44:51 -08:00
nossr50
96b46d31cf Only activate bleed if the target survives the initial strike 2019-01-23 16:21:34 -08:00
nossr50
4031674626 Send bleed messages to the correct player 2019-01-23 16:18:21 -08:00
nossr50
f028d91eb0 account for null entries in bleedtimer 2019-01-23 16:12:52 -08:00
nossr50
c46b7ed3bc dealNoInvulnerabilityTickDamage actually hurts things now 2019-01-23 16:08:41 -08:00
nossr50
71a3eb6a93 Fixed a lot of problems with the bleed task code... 2019-01-23 16:01:30 -08:00
nossr50
6ff13077be Mobhealth bars are no longer a per-player setting.
Removed the mobhealthbar command.
Removed the mobhealthbar permissions.
2019-01-23 15:39:04 -08:00
nossr50
c51be84b50 Serrated now uses Rupture rank to calculate its bleed effect's properties
Gore now actually uses Rupture rank 1 in its calculations
2019-01-23 15:29:31 -08:00
nossr50
3e5c4bc617 Fixing several issues related to Bleed/Rupture
Rupture now keeps track of who applied the damage and attributes it correctly in events
Rupture's bleed timer task no longer caps at the low value of 10 ticks internally
Ruptures bleed check code has had some minor refactoring
2019-01-23 15:22:16 -08:00
nossr50
e5e86246f3 Bleed no longer tells you when a target has stopped bleeding, because its obvious! 2019-01-23 15:08:04 -08:00
nossr50
8f906af99c Refactoring code related to pulling standard/retro mode variables.
Fixing the display and calculation of Super Ability lengths.
Removing the cap on super ability lengths for values less than 1.
Fixing some display errors regarding retro mode and standard.
2019-01-23 15:06:00 -08:00
nossr50
6c0da22d5e Put empty lines above a skill command to make it easier to distinguish from chat 2019-01-23 14:17:14 -08:00
nossr50
6e5feced2f fixing the compiling errors frok Oaks PR 2019-01-23 13:57:19 -08:00
nossr50
6be1319927 WG refactor 2019-01-23 13:55:43 -08:00
Robert A. C
cfeadb54be Merge pull request #3722 from Oaksworth/master
Update effects and stats to alphabetical order
2019-01-23 13:54:24 -08:00
Oaksworth
fd1a0db696 Merge branch 'master' of https://github.com/Oaksworth/mcMMO 2019-01-23 19:41:01 -02:00
Oaksworth
bf38f55f23 Update Woodcutting to alphabetical order 2019-01-23 19:40:44 -02:00
Oaksworth
c467f79d32 Update Unarmed 2019-01-23 19:39:32 -02:00
Oaksworth
9b0023d2d7 Update Taming to alphabetical order 2019-01-23 19:37:51 -02:00
Oaksworth
9be7c2af3c Update SwordsCommand.java 2019-01-23 19:35:15 -02:00
Oaksworth
c146384227 Update Smelting to alphabetical order 2019-01-23 19:32:36 -02:00
Oaksworth
f68ecd3214 Update Repair to alphabetical order 2019-01-23 19:20:25 -02:00
Oaksworth
58e506b041 Update Mining to alphabetical order 2019-01-23 19:16:23 -02:00
Oaksworth
40a13c4c81 Update Herbalism to alphabetical order 2019-01-23 19:14:14 -02:00
nossr50
02781f7458 refactoring WG 2019-01-23 13:13:53 -08:00
Oaksworth
0cd23c1b65 Update Fishing to alphabetical order 2019-01-23 19:11:15 -02:00
Oaksworth
c758346c3f Update Axes to alphabetical order 2019-01-23 19:04:13 -02:00
Oaksworth
a381b6379a Update Archery to alphabetical order 2019-01-23 19:02:09 -02:00
Oaksworth
6241b6dfe9 Update Archery to alphabetical order 2019-01-23 18:58:53 -02:00
Oaksworth
061a6c2a3a Update Acrobatics to alphabetical order 2019-01-23 18:53:38 -02:00
Oaksworth
ebf48e1870 Update SubSkillType.java to alphabetical order 2019-01-23 18:45:43 -02:00
nossr50
92de75e002 Bleed only tells you that you've started bleeding if you aren't already bleeding. 2019-01-23 12:39:51 -08:00
nossr50
c6e1edee91 Rupture will now check your rank before activating 2019-01-23 12:34:21 -08:00
nossr50
6428c65720 Bleed actually doesn't trigger iframes now 2019-01-23 12:28:30 -08:00
nossr50
3edc0bf63f Changing the COTW permission node 2019-01-23 12:19:16 -08:00
nossr50
fb5fd6cc39 Fixing Call of the Wild being missing from /taming 2019-01-23 12:12:17 -08:00
nossr50
f9b2776cb9 Getting rid of unused methods 2019-01-23 11:47:33 -08:00
nossr50
25c8dad1ea fixing XP gains LOL 2019-01-22 20:25:55 -08:00
t00thpick1
ad86db241c Hard fix maven on our end. 2019-01-22 22:12:58 -05:00
nossr50
3d0ba7ce52 work jenkins! 2019-01-22 18:39:13 -08:00
nossr50
9a8ced7aa7 adding SCM to maven pom.xml 2019-01-22 18:09:52 -08:00
nossr50
cf0b60d165 Fixing some errors related to WG 2019-01-22 17:59:45 -08:00
nossr50
cbb726e020 attempt to register flags if they are still not registered 2019-01-22 16:54:43 -08:00
nossr50
0ad1530505 mcMMO now supports WorldGuard, added "mcmmo" and "mcmmo-xp" flags! 2019-01-22 16:40:54 -08:00
nossr50
c0dde01f3e Fixing a display error for retromode and the acrobatics command 2019-01-22 14:21:48 -08:00
nossr50
db3d14fa9f Don't send the URL header if url links are disabled 2019-01-22 14:11:59 -08:00
nossr50
726b04f586 mcMMO now supports world blacklisting 2019-01-22 09:16:02 -08:00
nossr50
76ddcc4cf0 You can now enable Party Friendly Fire 2019-01-21 15:43:54 -08:00
nossr50
11c8374f6c Bleed doesn't suck anymore. 2019-01-21 15:15:10 -08:00
nossr50
848cee18a9 Adding back the mmoinfo string for roll stats 2019-01-21 13:53:45 -08:00
nossr50
42d286e265 Temporary fix to make Roll gain XP again 2019-01-21 13:49:06 -08:00
nossr50
ebbfe72259 Adding roll stats to Acrobatic's stat display 2019-01-21 13:41:56 -08:00
nossr50
6d720e6ab1 Fixing styling on Woodcutting 2019-01-21 13:11:42 -08:00
nossr50
661cf15be1 Fixing styling on Unarmed 2019-01-21 12:54:37 -08:00
nossr50
f30875ac4c Fixing styling on Swords 2019-01-21 12:41:31 -08:00
nossr50
ea0ad38fec Fixing styling on Repair 2019-01-21 11:31:02 -08:00
nossr50
e1f11b4059 Fixing styling on Mining 2019-01-21 11:14:50 -08:00
nossr50
42312349e1 Fixing styling on Herbalism 2019-01-21 10:56:28 -08:00
nossr50
c86012027e Fixing styling on Fishing 2019-01-21 10:43:47 -08:00
nossr50
0a900d9c65 Fixing styling on Excavation 2019-01-21 10:15:17 -08:00
nossr50
038265b033 Fixing styling on Alchemy 2019-01-21 10:09:18 -08:00
nossr50
ba34442ebb Fixing styling on Axes 2019-01-21 08:52:44 -08:00
nossr50
f9ce70e310 Fixing styling on Acrobatics, Archery 2019-01-21 08:46:08 -08:00
nossr50
c728b233e6 Locale files now support &-code formatting used by many plugins 2019-01-21 07:40:04 -08:00
nossr50
e8c8f8b6a1 Level up messages are now easier to modify in the Locale 2019-01-21 07:27:09 -08:00
nossr50
d3765effe0 Adding some missing color to party commands 2019-01-21 06:09:28 -08:00
nossr50
6c77017658 Ability lengths now have a default skill cap at which they stop increasing in length, you can change this in advanced.yml 2019-01-21 05:57:06 -08:00
nossr50
f8b7d5e10d mmoinfo command now links to the official wiki 2019-01-21 05:41:58 -08:00
nossr50
b42b4cadbe You can now turn off sound effects used by mcMMO 2019-01-21 05:23:48 -08:00
nossr50
11461cc220 "mcmmo help" command no longer shows players the category for admin type commands if they lack permissions for said commands 2019-01-21 05:17:59 -08:00
nossr50
4f3174c68b mcrank now works again with scoreboards disabled 2019-01-21 05:06:42 -08:00
nossr50
657e66f3c5 Updating strings related to Archaeology 2019-01-21 04:56:41 -08:00
nossr50
97670f14d1 Treasure Hunter (Exc.) is now Archaelogy, retro mode now scales up treasure drop level requirements by 10, the default file has been edited to reflect this change, I recommend regenerating your treasures.yml by deleting it for now 2019-01-21 04:54:48 -08:00
nossr50
fb8213d87c Swords Counter-Attacks no longer require blocking 2019-01-21 04:39:22 -08:00
nossr50
7c5ebb9902 Adding back some missing colors 2019-01-21 04:28:41 -08:00
nossr50
4e9f5b99b8 Fixing skill messages sent to other players 2019-01-21 03:48:11 -08:00
nossr50
b48fa2d8e5 On second thought I don't like this sound 2019-01-20 04:00:09 -08:00
nossr50
71fc9930ef Stripping Wood is no longer annoying. 2019-01-20 03:17:01 -08:00
nossr50
ec1e7b044c Accidentally made extra details on by default 2019-01-20 02:49:00 -08:00
nossr50
ba4e9e73c3 Forgot to update the changelog 2019-01-20 02:46:09 -08:00
nossr50
ac4b8068b0 Activating a super ability has a sound, and trying to cut down trees or activate skull splitter when on cooldown also has a sound. 2019-01-20 02:44:18 -08:00
nossr50
b1be43154a Roll & Gracefull Roll have sounds now 2019-01-20 02:23:18 -08:00
nossr50
87f84a5f66 Fixed a bug where Retro mode made you 10x luckier 2019-01-20 02:08:26 -08:00
nossr50
e962f645b6 Skill Unlock notifications now have sounds 2019-01-20 01:21:33 -08:00
nossr50
6ad9c8e664 Readying a Tool now has a sound 2019-01-20 00:46:33 -08:00
nossr50
b8a146f8bd Fixed a sync problem where XP bars were 1-step behind 2019-01-19 20:30:19 -08:00
nossr50
b7b0ff13e7 Fixing some redundancy 2019-01-19 19:18:29 -08:00
nossr50
96742e6c42 mcMMO now alerts you when you progress in a skill 2019-01-19 18:51:18 -08:00
nossr50
255ae6c426 Most Super Abilities require level 5 instead of 10 now 2019-01-19 15:14:24 -08:00
nossr50
8c5ea484eb XP Bars will no longer update for party xp or vampirism xp 2019-01-19 15:10:42 -08:00
t00thpick1
eb1f097d18 Fix chorus blocks ignoring blockstore. 2019-01-19 17:02:24 -05:00
t00thpick1
a073984621 This should not be here. 2019-01-19 15:52:53 -05:00
t00thpick1
34fc9725b9 Listen for block multiplace 2019-01-19 15:41:33 -05:00
nossr50
1e1212cd7c Tweaking the extra stats template for xp bars 2019-01-18 17:49:48 -08:00
nossr50
df8f050cf1 Child Skills will not trigger XP bars (for now) 2019-01-18 17:21:05 -08:00
nossr50
e74bc9fd95 XP bars can now be toggled off 2019-01-18 16:18:29 -08:00
nossr50
66878d72bf mcMMO will now start properly with scoreboards off 2019-01-18 14:24:37 -08:00
nossr50
29befac27e Scoreboards are now OFF by default
I don't like them.
2019-01-18 14:20:31 -08:00
nossr50
f5590ce334 XP Bars now can have custom titles (edit the locale) 2019-01-18 13:46:03 -08:00
nossr50
43da10a855 Levels now start at 1 (configurable advanced.yml) 2019-01-18 13:10:45 -08:00
nossr50
9ae58fd2f7 Whoops I forgot to push these 2019-01-18 12:42:05 -08:00
nossr50
cf6d95b575 More config options for XP bars 2019-01-18 12:41:38 -08:00
nossr50
92b8d13c71 Added XP Bars 2019-01-18 11:21:25 -08:00
nossr50
a9ed63d3d0 Adding color to the perk motd 2019-01-17 12:04:09 -08:00
nossr50
7889fe5249 More color tweaks 2019-01-17 12:03:07 -08:00
nossr50
6888a082fc Child Skill commands don't look so bad now 2019-01-17 11:44:01 -08:00
nossr50
1585d8157e Some color tweaks 2019-01-17 10:45:16 -08:00
nossr50
292fc8eff2 Correcting Shake rank requirements 2019-01-17 08:50:44 -08:00
nossr50
126e1c5942 All skills should be on the new rank system now 2019-01-17 08:46:10 -08:00
nossr50
a59907fcec Shake sends custom damagecause 2019-01-16 11:07:11 -08:00
nossr50
f1feeed670 bstats 2019-01-16 11:05:43 -08:00
nossr50
12af9af902 Fixes #3672, Fixes #3316, Fixes #3288, Fixes #2434, Fixes #1732, Fixes #1726, Fixes #1597, Fixes #941 2019-01-15 07:19:00 -08:00
nossr50
6ce44b7ce8 Cleaning up Herbalism & Mining Skill Command 2019-01-15 05:56:49 -08:00
nossr50
52355b2757 Fixing error in Farmer's Diet 2019-01-15 05:39:25 -08:00
nossr50
13a3e9a790 Adding ranks to Fisherman/Farmer's Diet and Green Thumb 2019-01-15 05:35:41 -08:00
nossr50
4137cc0d3d Fish now give XP based on their rarity 2019-01-15 04:55:44 -08:00
nossr50
8a57bbb5d9 Coral Blocks now give Mining XP 2019-01-15 04:44:55 -08:00
nossr50
f09fed465a Dolphins now give combat XP 2019-01-15 04:39:11 -08:00
nossr50
4e1f535fe2 Coral Plants & Blue Ice now give XP 2019-01-15 04:36:35 -08:00
nossr50
f15f25a3df Drowned now count for combat XP 2019-01-15 04:13:55 -08:00
nossr50
384804fefa Fixing a type in the key address 2019-01-15 03:57:00 -08:00
nossr50
5e3a72b30d XP event now uses titles for ending and fixed negative number bug 2019-01-15 03:50:12 -08:00
nossr50
f5b3cf4350 The remaining skills now hide stats until unlocked 2019-01-15 03:39:06 -08:00
nossr50
008e29117f RetroMode will default to false on new installs of mcMMO 2019-01-15 03:33:42 -08:00
nossr50
d48295bd72 Mining & Herbalism stats are hidden until unlock 2019-01-15 03:31:34 -08:00
nossr50
e9987a19ed Grammar + Spelling mistakes in skills.yml 2019-01-15 03:21:41 -08:00
nossr50
1aa4df01f9 Fishing stats are now hidden until skill is unlocked 2019-01-15 03:16:21 -08:00
nossr50
427d8c3b21 Excavation hides stats until skills are unlocked 2019-01-15 03:05:42 -08:00
nossr50
61d87eff10 Axe skill stats are hidden unless unlocked 2019-01-15 02:59:00 -08:00
nossr50
086e29c4ac Archery skills do not show stats until unlocked 2019-01-15 02:54:51 -08:00
nossr50
6cc6de6e82 Alchemy stats are now hidden until the appropriate skills are unlocked 2019-01-15 02:53:33 -08:00
nossr50
4a30fcc2de 2.1.0 is probably playable now, but not unfinished 2019-01-15 02:43:44 -08:00
nossr50
0acde4a8af Why are these empty part 2 2019-01-15 01:11:33 -08:00
nossr50
d6fea9a2df Why was this catch empty? 2019-01-15 01:08:11 -08:00
nossr50
5114bbc40d Fixing the YAML indentation 2019-01-14 22:52:15 -08:00
nossr50
4fcf0b0519 Reducing the amount of config confusion for retro mode
This is to avoid confusion, if you want this kind of customization I'll add it in but disassociate it with retro mode.
2019-01-14 22:48:37 -08:00
nossr50
da6b6841b7 Prevent commands from setting players to negative levels 2019-01-14 22:21:33 -08:00
nossr50
95d60e646d Diminishing returns now has an optional minimum gains setting 2019-01-14 22:11:58 -08:00
nossr50
9f8c9db4bc Setting SSL to false will now squelch MySQL warnings 2019-01-14 20:37:30 -08:00
nossr50
918b94b1ff Fixing Graceful Roll in the new system. 2019-01-14 18:35:37 -08:00
nossr50
d9dd4ea016 XP events now use the Title API
Configurable in advanced.yml
2019-01-14 02:32:02 -08:00
nossr50
43aad43bf3 Vampirism/Hardcore mode now use the ActionBar 2019-01-14 01:25:06 -08:00
nossr50
ed2c3975d8 ActionBar messages can now have copies sent to chat 2019-01-14 01:22:14 -08:00
nossr50
ee04bebcd9 All skills now use the ActionBar 2019-01-14 00:56:07 -08:00
nossr50
1769df98dc Archery now uses the ActionBar 2019-01-14 00:54:42 -08:00
nossr50
ca2eebf022 Axes now use the ActionBar 2019-01-14 00:52:25 -08:00
nossr50
4101f16580 Fishing now uses the ActionBar 2019-01-14 00:50:13 -08:00
nossr50
655a31d556 Herbalism now uses the ActionBar 2019-01-13 23:23:48 -08:00
nossr50
e1576e8d1c Repair now used the ActionBar 2019-01-13 23:16:24 -08:00
nossr50
2605235f2a Salvage now uses the ActionBar 2019-01-13 22:56:48 -08:00
nossr50
6bba647250 Woodcutting now uses the ActionBar 2019-01-13 22:47:27 -08:00
nossr50
79ae49a6d1 Unarmed now uses the ActionBar 2019-01-13 22:45:16 -08:00
nossr50
f007114753 Swords now use the ActionBar 2019-01-13 22:42:55 -08:00
nossr50
dad3e76c7c Taming now uses Action Bar 2019-01-13 22:32:35 -08:00
nossr50
ba5428ff12 Adding more combat messages to Action Bar 2019-01-13 22:21:16 -08:00
nossr50
1cf1c6fab8 ChimaeraWing now uses the action bar 2019-01-13 22:09:54 -08:00
nossr50
14ca84fa97 Holiday strings added to locale + some JSON integration for April Fools Day 2019-01-13 21:48:38 -08:00
nossr50
4a00758b6b Added locale strings for chatspy and moved some more party messages to action bar 2019-01-13 21:27:56 -08:00
nossr50
e817dbe081 Don't allow players to accept party invites if the party is full 2019-01-13 00:45:17 -08:00
nossr50
c3bacd8de6 Minor config change 2019-01-13 00:31:58 -08:00
nossr50
351abae475 Fixing Missing Locale Strings 2019-01-13 00:21:21 -08:00
nossr50
c1c249372a snake yaml demands 4 spaces 2019-01-13 00:10:13 -08:00
nossr50
6f77bb206d Refactoring + adding a new skillranks config (not functional yet) 2019-01-12 23:54:53 -08:00
nossr50
0beabbf1ec Added more missing strings 2019-01-12 22:45:54 -08:00
nossr50
51ab8d4b25 Child Skill commands work again (UGLY tho) 2019-01-12 22:41:06 -08:00
nossr50
a21b4585c5 Classic Scaling is now Retro Mode to avoid confusion 2019-01-12 22:14:23 -08:00
nossr50
cde11b64ed You will only gain shared party XP if you are visible to the player gaining XP 2019-01-12 21:51:31 -08:00
nossr50
d3c47935d4 Some refactoring 2019-01-12 19:56:54 -08:00
nossr50
c8ee5099e0 TextComponents will no longer use a cache
This will increase the cost of TextComponents by a negligible amount but in exchange I will be able to put player-specific data into them.
2019-01-12 19:29:06 -08:00
nossr50
85fd0a79bc Sounds volume and pitch are now configurable in the new sounds.yml file 2019-01-12 19:08:54 -08:00
nossr50
6927712a9d I'm dyslexic 2019-01-12 17:28:35 -08:00
nossr50
4cfb7a5f4b mcMMO now supports SSL and tries to use it by default for MySQL (turn this off in config.yml MySQL.Server.SSL)
this fixes a lot of console spam from default mysql installs
2019-01-12 17:26:17 -08:00
nossr50
1f2e6cd5f5 Fixed grabbing colors from the wrong file 2019-01-12 15:58:35 -08:00
nossr50
b38c589125 I guess I'm bad at git 2019-01-12 14:44:16 -08:00
nossr50
7f40b4294f mcMMO now fires many new custom events relating to scoreboards 2019-01-12 14:42:30 -08:00
nossr50
bfc26dc892 Reverting the scoreboard changes
Due to a naive understand of how scoreboards worked I made some incorrect assumptions and will be reverting this change
2019-01-12 13:26:54 -08:00
nossr50
b572c0aea9 Fixing some issues with scoreboards, it's getting late so I'll take a better look at them in the morning. 2019-01-11 10:27:11 -08:00
nossr50
1d62f8b177 Added some missing config items 2019-01-11 07:31:17 -08:00
nossr50
d141a28747 Most things that print to your chat will now print to action bar 2019-01-11 07:11:17 -08:00
nossr50
19c38f0cb1 Parties can now have max size limits (configurable), by default party sizes are unlimited. 2019-01-11 06:17:07 -08:00
nossr50
c7a49dd283 tool fix 2019-01-11 05:42:58 -08:00
nossr50
f11b98c29d Players need to have unique objectives 2019-01-11 05:26:05 -08:00
nossr50
adc83d29a7 The new URL links can now be disabled in config.yml 2019-01-11 02:24:11 -08:00
nossr50
1e8d950767 Converting from MySQL -> FlatFile now accounts for users that don't exist yet in mcmmo.users
Fixes #3130
2019-01-11 02:17:03 -08:00
nossr50
3dca32a226 mcMMO is now a lot more compatible with plugins that use scoreboards
Citizens 2 for example
2019-01-11 02:05:54 -08:00
nossr50
7c024314b7 Classic mode setting is now UseOldLevelScaling to lessen confusion 2019-01-11 01:52:16 -08:00
nossr50
f828084246 Added config option to easily disable all scoreboards 2019-01-11 01:47:36 -08:00
nossr50
626890ed95 Chimaera Wing exploit fix 2019-01-10 23:52:11 -08:00
nossr50
00a14ccb17 no more abusing the ice kids 2019-01-10 21:27:50 -08:00
nossr50
400e15b559 Party member list will only contain players visible to the player 2019-01-10 21:06:51 -08:00
nossr50
d5a4103858 new mmoinfo command and JSON click events 2019-01-10 01:17:47 -08:00
nossr50
0cb9bbb530 Overhaul Era MOTD 2019-01-09 18:25:37 -08:00
nossr50
fc2a8eec7b Updating the changelog 2019-01-08 20:37:57 -08:00
nossr50
362d036b16 4 days of work and I'm still not done ;_; 2019-01-08 19:52:52 -08:00
nossr50
ee765a0d30 Fix for mushrooms not counting as Logs for Tree Feller
Server admins will need to update their experience.yml manually (or delete it to make a new one)
2019-01-07 12:37:16 -08:00
t00thpick1
8aa919f834 should fix inspecting offline players
(cherry picked from commit ad715f51c6b8b87e3a78c18c7daaf4cdf7c10a8e)
2019-01-05 19:21:45 -05:00
t00thpick1
77c12dcc20 Tridents are tools too
(cherry picked from commit 1b74c0bd920cf32499ecdb2c285917f2e41cef44)
2019-01-05 12:13:46 -05:00
nossr50
7581425f87 reducing linecount since crowdin charges by linecount 2019-01-04 09:53:44 -08:00
Robert A. C
fce77b427f Update Crowdin configuration file 2019-01-04 09:42:12 -08:00
nossr50
01a7aa4d12 Reworked the relationship between SubSkill and Locale keys 2019-01-04 07:58:39 -08:00
nossr50
6dc75760d0 JSON hover objects now follow different templates based on the subskill's properties 2019-01-03 07:16:05 -08:00
nossr50
fe90f1e7eb Fixing a bug with Axe Mastery rank requirements 2019-01-03 04:59:56 -08:00
nossr50
54cf356b71 converting more SubSkills to be JSON friendly
AxeMaster & SkillShot
2019-01-03 04:32:46 -08:00
nossr50
4669e3e54d Starting to convert existing subskills to be JSON friendly
So far only a few have been converted
2019-01-03 03:42:11 -08:00
nossr50
f4ead570d4 Fixed some logic errors with the new mcchatspy command 2019-01-03 02:14:31 -08:00
nossr50
b34f3a1779 Fixing the message for when you toggle mcchatspy 2019-01-03 01:44:29 -08:00
nossr50
85e1f2eb7e mcchatspy is now a command based instead of permission node based 2019-01-03 01:26:08 -08:00
nossr50
6136e82ec6 mcmmo.admin.chatspy to spy on party chat 2019-01-03 00:52:24 -08:00
nossr50
ebec5d6f70 Added some JSON, much more to come. 2019-01-02 08:06:18 -08:00
nossr50
336e41b40c Merge branch 'master' of https://github.com/mcMMO-Dev/mcMMO 2018-12-31 10:10:31 -08:00
nossr50
bec088c969 Some work on milestones is done 2018-12-31 10:10:00 -08:00
Robert A. C
17f1062e96 Fixing formatting for website info 2018-12-30 01:12:45 -08:00
Robert A. C
92495ae9df Added website info 2018-12-30 01:12:21 -08:00
nossr50
b9c8743ee3 The next public release will be 2.1.0 not 2.0.1 2018-12-29 06:19:24 -08:00
nossr50
0d260a74c9 Refactoring to make my life easier 2018-12-29 05:24:55 -08:00
nossr50
35368db05d I forgot the imports like a dumbo 2018-12-28 11:28:26 -08:00
nossr50
5e6e8d7248 I don't think Jenkins likes @Nullable atm 2018-12-28 10:56:41 -08:00
nossr50
d50238caf1 Dunno if this is excessive, but adding some API notes to the changelog 2018-12-28 10:49:11 -08:00
nossr50
164d429acc Reverting a change regarding level caps 2018-12-28 10:12:21 -08:00
nossr50
a316bb7bd2 Not much work was done today because of testing & research
The real work begins soon
2018-12-28 06:29:08 -08:00
nossr50
55a4238030 Updating changelog.txt 2018-12-27 03:18:34 -08:00
nossr50
f9f2a0d691 Scaling skills from 0-1000 to 1-100 pt. II 2018-12-27 03:12:38 -08:00
nossr50
3831ca6b0f Burn it with fire 2018-12-27 03:04:55 -08:00
nossr50
7a6b8e3156 This was going to bug my OCD 2018-12-27 00:21:13 -08:00
nossr50
93d10c0739 Starting work on converting skills to use the new 100-scale system 2018-12-26 23:59:43 -08:00
Robert A. C
24e4c28355 Updating the readme to reflect current times. 2018-12-24 20:05:18 -08:00
nossr50
6ec61ecb76 Fireworks from ability activation will be Opt-In, updates to strings 2018-12-24 19:05:46 -08:00
nossr50
55a69006bf Merge branch 'master' of https://github.com/mcMMO-Dev/mcMMO 2018-12-24 17:53:03 -08:00
nossr50
8a02230fd2 Updating strings relating to the project. 2018-12-24 17:52:39 -08:00
t00thpick1
2a26b016d9 Only stop monitoring LOG To LOG transitions, there are a ton of non-air block placements we want to monitor 2018-12-24 19:33:26 -05:00
nossr50
7be5b4ecbd Monitor only blocks that replace air. This fixes the TreeFeller interaction with stripped wood. 2018-12-24 00:21:13 -08:00
t00thpick1
565fb35217 Update McmmoCommand.java 2018-12-23 16:40:57 -05:00
LogGits
d2b8c527ad Use dropItem instead of dropItemNaturally (#3644)
This could possibly eliminate a few issues.
2018-12-14 19:51:44 -05:00
LogGits
2cdb17d64f Use dropItem instead of dropItemNaturally (#3645)
Should fix #3641 and #3638
2018-12-14 19:51:38 -05:00
LogGits
96f06ca812 Fixed plugin.yml mistake (#3639)
Accidentally forgot to add the ":" to some of the permissions.
2018-12-09 22:59:16 -05:00
Fabrizio La Rosa
685f6d76a8 Corrected a word (#3629) 2018-12-09 18:29:40 -05:00
LogGits
840cfbe94d Updated plugin.yml to include command permissions (#3637)
This will stop people from seeing the commands in tabcomplete for 1.13.2 if they dont have the permission for it. Should fix #3625.
2018-12-09 18:26:09 -05:00
Josh
605535ed60 fix memory leak (#3631)
on servers with lots of spawner farms this metadata won't get GC'd unless removed, line 436 its added but never removed as far as I can tell
2018-12-06 22:05:55 -05:00
t00thpick1
71c72045b9 Revert "Update locale_zh_CN.properties (#3541)"
This reverts commit eb930883fa.
2018-12-02 23:28:36 -05:00
Ghost_chu
eb930883fa Update locale_zh_CN.properties (#3541) 2018-12-02 23:27:39 -05:00
CNAmira
30ed18eb95 Update Simplified Chinese localization (#3617) 2018-12-02 23:27:19 -05:00
Fabrizio La Rosa
8508f5b8b8 Bug fix for italian locale (#3616)
Fixed the command "/mctop Tiro con l'Arco" that with spaces was not recognized (/mctop archery is not usable if the English locale is not selected).
Now is "/mctop Arco".

That should fix also "/Tiro con l'Arco".
2018-12-02 23:26:58 -05:00
ゆき
dfab223eb2 Fix locale_ja_JP.properties colors (#3628) 2018-12-02 23:26:38 -05:00
Andrewkm
dd82fa0791 Duplicate shulker entry (#3623) 2018-11-26 23:30:08 -05:00
t00thpick1
af8d2dc2c7 Tridents are enchantable 2018-11-26 23:28:15 -05:00
t00thpick1
9f9529debf Has this ever not happened??? I don't understand why it only showed up in 1.13..... Fixes #3564 2018-11-26 23:10:51 -05:00
t00thpick1
495c4a33e5 Store skill totals rather than calculating them on the fly for faster leaderboard queries. 2018-11-14 20:31:57 -05:00
t00thpick1
203d3749ee Fix herbalism XP again 2018-10-14 21:27:55 -04:00
t00thpick1
1fcecbd3e7 Replant only the fully grown plants. 2018-10-13 17:09:08 -04:00
t00thpick1
d778616b2c Herbalism was the one that actually needed to remain blockdata. 2018-10-13 17:06:54 -04:00
t00thpick1
4bdd97a302 Not sure why this is even still here. 2018-10-09 21:57:01 -04:00
t00thpick1
ab2a031ee0 Missed file in commit 2018-10-09 21:56:47 -04:00
t00thpick1
5663b71387 Some of these should not have been blockdata, also this should check age of crops. 2018-10-09 21:52:23 -04:00
ProfLuz
2a43bce849 Fix spectators being affected by a combat ability (#3591)
* Fix spectators being affected by a combat ability
2018-10-01 22:21:22 -04:00
András Marczinkó
592c3a2142 Fix woodcutting double drop item names (#3585) 2018-09-23 14:43:38 -04:00
András Marczinkó
e9ca341476 End_Bricks renamed to End_Stone (#3584) 2018-09-23 11:52:48 -04:00
Captain Justin
76617c8a61 German spelling fix (#3576) 2018-09-23 11:52:35 -04:00
András Marczinkó
10ff097232 Fix config item names (#3583) 2018-09-22 13:45:25 -04:00
Sean Porter
1e043d481a Merge pull request #3582 from andris155/patch-7
Wood renamed to Wooden
2018-09-22 09:54:39 -07:00
Sean Porter
7f8c670dc1 Merge pull request #3581 from andris155/patch-6
QUARTZ_ORE was renamed to NETHER_QUARTZ_ORE
2018-09-22 09:54:24 -07:00
András Marczinkó
0e536a2cb3 Wood renamed to Wooden 2018-09-22 18:53:08 +02:00
András Marczinkó
090cf82a39 Fix Terracotta and stained Terracotta names (#3580) 2018-09-22 12:50:25 -04:00
András Marczinkó
6e60f39f82 QUARTZ_ORE was renamed to NETHER_QUARTZ_ORE 2018-09-22 18:49:02 +02:00
András Marczinkó
b8078e4730 Fix Mycelium name (#3579) 2018-09-22 12:21:23 -04:00
András Marczinkó
e08fe64db2 Fix End Stone name (#3578) 2018-09-22 12:21:13 -04:00
Sean Porter
2b576568a7 QUARTZ_ORE was renamed to NETHER_QUARTZ_ORE. 2018-09-16 18:47:15 -07:00
t00thpick1
e2edbaad34 Update herbalism permissions for new block names. Should fix replanting crops. 2018-09-14 22:44:21 -04:00
t00thpick1
184b98bbdc BREAKING CHANGE - Fix typo in secondary skill enum...... Fixes #2891 2018-09-14 22:36:47 -04:00
t00thpick1
7cc604dbdb Update potions.yml to reflect 1.13 potions and material names. 2018-09-14 20:50:28 -04:00
t00thpick1
44ed35825f more cleanup in the TreasureConfig. 2018-08-30 23:59:55 -04:00
t00thpick1
22833eea6c Slightly delay recipe loading because apparently spigot broke doing that on enable....... 2018-08-30 23:57:29 -04:00
t00thpick1
64dfc1e3d3 Fix hylian drops 2018-08-30 23:28:48 -04:00
nemba246
6619ca1d22 update excavation on experience.yml (#3551)
In 1.13, the name of the grass block changed from "grass" to "grass_block". This caused no experience to be given while using a shovel on grass. This change was part of something mojang called the flattening and could possibly be the cause of some other experience related issues. 
https://minecraft.gamepedia.com/1.13/Flattening
2018-08-30 22:37:01 -04:00
Devon Palma
2f2a80e1ce Various Fixes (#3537)
* Updated ItemUtils, added isBlock check to smelt functions

+ added a check in ItemUtils.isSmeltable() and ItemUtils.isSmelted() to make sure the Item type was a block to prevent an error occuring mentioned in https://github.com/mcMMO-Dev/mcMMO/issues/3536

* Fixed Green Thumb replant issue

see https://github.com/mcMMO-Dev/mcMMO/issues/3535

HerbalismManager
= fixed names of netherwart
= fixed handleBlockState, and slightly altered it
StringUtils
= fixed name of netherwart

* Fixes to herbalism skill

Herbalism
= fixed material name for grass in green terra block conversion
= fixed material name for grass in shroom thumb block conversion
EntityListener
= fixed material name for melon in food level change
experience config
= updated name for melon and sugar cane

* Minor Name Updates

experience config
= removed Stone|*
= added Stone, Granite, Adesite, Diorite
MaterialTypes
= updated material reference for wood

* Small fishing change

PlayerListener
= made it so COD, TROPICAL_FISH, and PUFFERFISH are no longer overwritten, so players can now catch these
2018-08-05 10:15:12 -04:00
Aaron Karras
fa1bbd2031 Updated SkillUtils to no longer use BlockData (#3533) 2018-08-03 18:21:13 -04:00
R4zorax
a39a77f89e Fix fishing in 1.13 (#3528)
* Fix fishing to use Material instead of BlockData (that was AIR)
2018-08-02 20:27:15 -04:00
R4zorax
7800e48f61 Make BiomeAdaptor support Bukkit 1.13 and bump java-version to 1.8 (#3526) 2018-08-01 21:23:29 -04:00
Shane Robertson
63378ae4c1 Updated herbalism (crop replaced by ageable) (#3523)
* [WIP] Replacing MaterialData with Blockdata

* Fixed most block based experience gain

* Removed debug prints

* Updated configs

* [WIP] Replacing MaterialData with Blockdata

* Fixed most block based experience gain & updated wooden_tools

* ACTAULLY removed debug prints

* [WIP] Replacing bukkit treespecies 

This feature has been unofficially deprecated, (not yet fixed/marked in bukkit)
Also updated config.yml to match changes

* Updated configs

* [WIP] Replacing MaterialData with Blockdata

* [WIP] Replacing MaterialData with Blockdata

* Fixed most block based experience gain

* Fixed most block based experience gain & updated wooden_tools

* Removed debug prints

* ACTAULLY removed debug prints

* [WIP] Replacing bukkit treespecies 

This feature has been unofficially deprecated, (not yet fixed/marked in bukkit)
Also updated config.yml to match changes

* Fixed greenterra

Replaced deprecated features
2018-07-31 21:35:45 -04:00
t00thpick1
fecf83c79c Don't break on double drops for woodcutting. 2018-07-30 20:44:10 -04:00
t00thpick1
f287b6d8a7 Update fishing experience config 2018-07-27 22:30:57 -04:00
Leomixer17
9082658357 Update locale_it.properties (#3509) 2018-07-27 18:28:44 -04:00
Shane Robertson
4bda175328 Removed misc, print statements (#3508)
* ACTAULLY removed debug prints
2018-07-26 20:47:45 -04:00
Shane Robertson
ee324c77a9 Fixed errors with block-based skill experience (#3506)
* Updated configs

* [WIP] Replacing MaterialData with Blockdata

* Fixed most block based experience gain

* Fixed most block based experience gain & updated wooden_tools

* Removed debug prints
2018-07-26 19:53:29 -04:00
Jamie Sinn
210b418e44 Get string before format. (#3507) 2018-07-26 19:52:15 -04:00
t00thpick1
b73eced36f Remove sound adapter 2018-07-25 20:29:40 -04:00
shanedrgn
6296a6adde Updated configs
Signed-off-by: t00thpick1 <t00thpick1dirko@gmail.com>
2018-07-25 20:20:31 -04:00
Leomixer17
99f6192965 Update locale_it.properties (#3502) 2018-07-25 19:53:23 -04:00
t00thpick1
bff454f397 Wood is not planks. 2018-07-24 20:50:17 -04:00
t00thpick1
8216dbe355 This is kinda important 2018-07-23 22:38:05 -04:00
t00thpick1
fbe26af2d7 Merge remote-tracking branch 'origin/master' 2018-07-23 22:14:44 -04:00
t00thpick1
0a1559511a Quick and dirty 1.13 update. I.e. it now compiles for 1.13. 2018-07-23 22:13:57 -04:00
Jamie Sinn
aee60f2c09 Mctop Cooldown message correction. Closes https://github.com/mcMMO-Dev/mcMMO/issues/3470 (#3481) 2018-07-15 10:08:52 -04:00
FabioZumbi12
9ce850f84f Re-added handlersList to event. (#3234) 2018-06-13 20:50:46 -04:00
t00thpick1
cbff8482ce Merge pull request #3427 from joblo2213/master
Add McMMOPlayerSalvageCheckEvent
2018-06-09 11:50:32 -04:00
joblo.2213
0035762a71 Add McMMOPlayerSalvageCheckEvent 2018-06-09 09:46:06 +02:00
t00thpick1
3d515aab23 Bump version 2018-05-25 22:52:10 -04:00
Glitchfinder
e77801f3c1 Ensure all entity types function in experience.yml
Fixes #3443
2018-05-16 08:07:07 -07:00
Glitchfinder
c83d011faa Don't convert raw salmon to raw fish when summoning ocelots.
Fixes #3366
2018-05-15 19:40:48 -07:00
Glitchfinder
5aa4949baa Allow experience on crops grown with bonemeal. 2018-05-15 11:31:52 -07:00
Glitchfinder
906ead53dd Merge branch 'patch-1' of github.com:ChrisLane/mcMMO 2018-05-11 10:09:37 -07:00
Glitchfinder
cbcdedc67a Merge branch 'patch-1' of github.com:MiniDigger/mcMMO 2018-05-11 10:08:26 -07:00
Glitchfinder
c87b410823 Merge branch 'anvil_unbreakables' of github.com:GiovanH/mcMMO 2018-05-11 10:07:53 -07:00
Glitchfinder
0a447f68c6 Merge branch 'patch-2' of github.com:GiovanH/mcMMO 2018-05-11 10:06:58 -07:00
Glitchfinder
e98d241452 Merge branch 'master' of github.com:ProgrammingAtDawn/mcMMO 2018-05-11 10:04:14 -07:00
GiovanH
421455224f Codebase! 2018-05-10 04:54:35 +01:00
t00thpick1
29c55312a5 Don't allow these commands on child skills. 2018-05-01 23:12:06 -04:00
Gio
6c474c8838 Added nether bricks to mining
As per https://github.com/mcMMO-Dev/mcMMO/issues/3426
2018-04-30 20:38:01 -05:00
t00thpick1
03182ea24c Merge pull request #3440 from GiovanH/patch-1
Handle playerdata without bukkit.lastKnownName info
2018-04-30 18:38:08 -04:00
Gio
2c6543da9e More descriptive text. 2018-04-30 13:30:41 -05:00
Gio
20bbdfc4ab Check playerdata for corruption
Fixed a null pointer exception that would occur if the offlinePlayer object did not have a defined string for .getName();
2018-04-30 12:54:35 -05:00
Glitchfinder
5b2ebf4aa8 Prevent shulker boxes from activating abilities.
Fixes #3438.
2018-04-29 23:09:52 -07:00
t00thpick1
2b159adefd Merge pull request #3330 from hoorigan/ench-book-fixes
Enchanted book fixes
2018-04-28 20:04:06 -04:00
Glitchfinder
be2de1d487 Fix a duping bug that uses a coordinate error. Fixes #2979 and fixes #3429. 2018-04-15 10:19:31 -07:00
t00thpick1
6876f192de Deflag blocks when they grow, Fixes #3311, #3207 2018-04-07 13:41:20 -04:00
t00thpick1
875db44afd Don't active skills on shulker blocks Fixes #3423 2018-04-07 13:33:28 -04:00
t00thpick1
2e120abe3a Merge pull request #3395 from ezeiger92/master
Fix a couple tickets
2018-02-15 23:00:30 -05:00
ezeiger92
feeb17d6f0 Scale fishing drop chance by lure rather than subtracting 1
Fixes mcMMO-Dev/mcMMO#3383
Added config option for lure enchantment modifier
Fixes lure enchantment having no effect on drops from offhand
2018-02-15 15:48:21 -08:00
ezeiger92
6d2003d577 Remove offhand fishing rod if not in main hand
Fixes mcMMO-Dev/mcMMO#3342
Fixed style error in last commit
2018-02-15 13:59:10 -08:00
ezeiger92
40b609ccd8 Respect unbreakable tag on items when attempting durability changes
Fixes mcMMO-Dev/mcMMO#3327
Fixes mcMMO-Dev/mcMMO#3391
2018-02-15 13:38:10 -08:00
ProgrammingAtDawn
d64399df49 Calculate experience gain before processing green thumb. 2018-01-24 20:53:59 +01:00
t00thpick1
d4f2f0e11b Use new recipe constructor to avoid deprecation errors. 2017-12-17 13:31:30 -05:00
hoorigan
916d9a7c8a ItemUtils: add ENCHANTED_BOOK to isEnchantable()
This will (hopefully) make mcMMO aware that ENCHATED_BOOK can have an enchantment.
2017-10-31 16:47:46 -04:00
hoorigan
6d5ab0edda FishingManager: force enchant on enchanted book
Added a small conditional to ensure that enchanted books get an enchantment.
2017-10-31 16:45:08 -04:00
t00thpick1
307d483323 Dont do diminishing returns on command caused xp gains Fixes #3312 2017-10-27 20:30:56 -04:00
t00thpick1
eb4960f307 Merge pull request #3300 from EasyMFnE/master
Add automatic Alchemy potion colorization and custom color config
2017-10-05 19:44:47 -04:00
t00thpick1
9df72e61a2 Mob Health bars global toggle 2017-10-03 23:32:54 -04:00
EasyMFnE
fcb6391ba3 Remove leftover debug code. 2017-09-28 11:44:15 -04:00
EasyMFnE
16a77f281e Add automatic Alchemy potion colorization and custom color configuration. 2017-09-23 15:35:38 -04:00
t00thpick1
87ebf7023f Additional changes that are less important but related to the dupe fix. 2017-09-12 20:01:09 -04:00
t00thpick1
028f87653a Check length of the Y dimension of the array, not the x dimension, which will only be 16 2017-09-08 23:16:41 -04:00
t00thpick1
0e51983819 Y, not Z, very very important. 2017-09-06 00:23:35 -04:00
t00thpick1
c174f2b829 Back to development 2017-09-05 20:57:25 -04:00
t00thpick1
8e9d393eb2 Bump version 2017-09-05 20:51:24 -04:00
t00thpick1
f1f02fd005 Don't fail out of saves just because a single player fails. 2017-09-01 00:45:22 -04:00
t00thpick1
f279a979e3 Also handle bottom of world 2017-09-01 00:44:37 -04:00
t00thpick1
e0bbe9cea4 Fix error with pistons retracting near top of world. Fixes #3172 2017-09-01 00:43:11 -04:00
t00thpick1
d3cc23f6a0 Fix smelting vanilla xp boost. Fixes #3270 2017-09-01 00:32:11 -04:00
t00thpick1
4c3f3ee4e2 Dont use named seeds in replanting. Fixes #3273 2017-08-31 23:47:28 -04:00
t00thpick1
2d7c5d7fd6 Merge pull request #3279 from ezeiger92/master
Pull downstream changes
2017-08-31 00:08:32 -04:00
t00thpick1
8be68aa6df Merge pull request #3252 from ezeiger92/fix-3250
Fix 3250
2017-08-31 00:02:37 -04:00
Erik
a731ad14ec Merge pull request #1 from ezeiger92/many-fixes
Pull in fixes
2017-08-15 21:44:49 -07:00
Erik
05ca96aa7f Build against 1.12.1 to NOT break getTargetBlock 2017-08-15 16:45:32 -07:00
Erik
60aa32d003 Patches!
* Update bukkit version
* Default vanilla  exp modifier for fishing is now 1
* Fixed beetroot permission for herbalism
2017-08-15 12:20:09 -07:00
Erik
0e7ee41444 Follow spacing convention 2017-08-05 11:53:38 -07:00
Erik
b5f6b1d97f Fix for 3250 - HashSet<Byte> to HashSet<Material> for getTargetBlock 2017-08-05 11:50:24 -07:00
t00thpick1
f1ac5739e4 [bugfix] Resolve issues with Herbalism exp.
Due to flaws the previous changes to the configuration system combined with some bad lines in the experience.config that I mistakenly recommended, herbalism was not granting experience in most cases, as it was marking newly planted crops and such as player placed no exp granting blocks, rather than ignoring them as it should.
block types now are evaluated in 3 steps:
1: Explicit Name  i.e. ("Crops|4", "Crops|0"), Which is the material name then data value
2: "friendly name"  i.e. ("Crops_Ripe", "Crops_Ungrown"), Which is a typically data valueless name,  some of which I make up in mcMMO, but most of which are just the Material name
3: Wildcard name  i.e. ("Crops|*") Which is any block with that block value, regardless of data value

In order to be sure herbalism grants exp for you once again, make sure your configuration for herbalism looks similar to this:
https://github.com/mcMMO-Dev/mcMMO/blob/master/src/main/resources/experience.yml#L151

In terms of which blocks are listed there.  Specifically, there should be no blocks marked "ungrown"
2017-08-01 01:33:02 -04:00
t00thpick1
8cbb57df97 Fix herbalism I think 2017-07-23 18:06:45 -04:00
t00thpick1
2c8d2998bb Merge pull request #3201 from wysohn/master
HandlerList should be present in every Events. (It's static you know)
2017-06-28 08:59:52 -04:00
t00thpick1
44684fcfd0 Fix green thumbing plants to grow. They need to be in the config to be used, but at 0 exp so we don't gain exp off them 2017-06-27 20:26:55 -04:00
t00thpick1
7081e03c23 Back to dev 2017-06-27 20:26:30 -04:00
t00thpick1
246db98519 bump version 2017-06-26 20:56:34 -04:00
Chris Lane
ee245d348f Remove duplicate "Beetroot_block" option 2017-06-23 14:34:24 +01:00
wysohn
f718741044 HandlerList should be present in every Events. (It's static you know) 2017-06-17 20:16:09 -07:00
t00thpick1
c054ff851a Fix excavation treasures 2017-06-14 21:14:09 -04:00
t00thpick1
755787f9ee Add sapling types 2017-06-10 14:30:06 -04:00
t00thpick1
24f8b2fbd5 More configuration for hylian luck 2017-06-10 14:16:31 -04:00
t00thpick1
ee02a19e9a Add more configuration to shake treasures 2017-06-10 13:59:49 -04:00
t00thpick1
cb5d38c11f Leftover debug 2017-06-10 13:49:19 -04:00
t00thpick1
15436b44da Update configurations and skill block checks to be more configurable. 2017-06-10 13:47:20 -04:00
t00thpick1
5c267663a2 Merge pull request #3160 from filoghost/patch-1
Fix permission error
2017-06-07 21:24:00 -04:00
t00thpick1
fda625b235 Merge pull request #3185 from nathanprocks/master
Add shaking from shulkers
2017-06-07 21:22:30 -04:00
t00thpick1
2cbd8789d8 Merge pull request #3175 from lucko/master
Fix for removed methods in Bukkit 1.12
2017-06-07 21:22:00 -04:00
Nathan Piercy
95167f44f1 Add shaking from shulkers 2017-06-04 16:34:48 +10:00
Luck
789b51fd05 Fix for removed methods in Bukkit 1.12 2017-05-14 16:36:31 +01:00
filoghost
0911c86422 Prevent players from resetting each other's skills
The child permission has the value set to false. From http://bukkit.gamepedia.com/Plugin_YAML: "a child node of false inherits the inverse parent permission". Having the value set to false grants the permission to reset other players' skills to everyone that doesn't have the mcmmo.skillreset permission, which by default nobody has.
2017-04-24 20:17:43 +02:00
t00thpick1
7d05c9d8e6 Add some more defaults into the config. Remove the parts that delete keys, I don't maintain config files well enough to have them remove unknown keys. 2017-04-15 00:24:39 -04:00
t00thpick1
a43ae4178a Some cleanups to mob related XP code 2017-04-15 00:04:07 -04:00
t00thpick1
c9c2c483fa Remove unneccessary code. 2017-04-14 23:34:54 -04:00
t00thpick1
133281faaa Merge pull request #3131 from TheComputerGeek2/master
Prevent disarming, bleed, and axe passives when dealing thorns damage
2017-04-14 23:26:49 -04:00
MiniDigger
ef8987917d Fix avatars in readme, link can't be in new line 2017-04-07 08:25:23 +02:00
TheComputerGeek2
d6a00eaf00 Prevent disarming, bleed, and axe passives when dealing thorns damage 2017-03-06 18:03:15 -08:00
t00thpick1
69151f0855 Forgot to actually add the funfetti 2017-02-22 00:01:39 -05:00
t00thpick1
bb27d753b1 I think this should stop my fireworks from damaging people 2017-02-22 00:00:47 -05:00
t00thpick1
37ce29a5e8 Merge pull request #3094 from SupaHam/fix-chimaera-tp-cancel
Set TeleportCommenceLocation to null after Chimaera cancellation.
2017-01-15 22:19:51 -05:00
t00thpick1
6297e1c79b Merge pull request #3104 from kanesada2/skeleton
Fix shake from WITHER-SKELETON. avoid to use depredated method: getSkeltonType().
2017-01-15 22:18:26 -05:00
kanesada2
4e2903e65c I used wrong treasure.yml... 2017-01-13 14:28:54 +09:00
kanesada2
2e7f56eeb5 fix shake for WITHER-SKELETON. avoid to use getSkeltonType() 2017-01-13 14:10:55 +09:00
Ali Moghnieh
7e46d5ca08 Set TeleportCommenceLocation to null after Chimaera cancellation.
This makes the item usable once again, as the prechecks check to make sure the location is null.
2016-12-26 21:26:38 +00:00
t00thpick1
a2bcce9ab1 I believe this resolves berserk allowing you to take drops into your equipment slots. 2016-12-17 17:32:16 -05:00
t00thpick1
2f7b1c38e1 Snapshot again 2016-12-04 21:54:11 -05:00
t00thpick1
789aaec186 I should probably compile before committing in the future. 2016-12-04 21:42:26 -05:00
t00thpick1
f3d6c1727b 1.5.07 - The "Thanks @TheBentoBox for the brewing fix" update 2016-12-04 21:40:30 -05:00
t00thpick1
c029b51c97 Doesn't look like CI handles this anymore :( 2016-12-04 21:39:15 -05:00
t00thpick1
6c5fb5f398 Fix entity kill xp 2016-12-04 20:53:51 -05:00
t00thpick1
4b20db47b2 Update spigot version 2016-12-02 00:12:16 -05:00
t00thpick1
e238ec8fc6 Merge pull request #3067 from TheBentoBox/master
Fix 1.11 brewing, remove health bar from armor stands
2016-12-01 00:54:39 -05:00
t00thpick1
9689f55e5c Merge pull request #3055 from jjm223/bugfix/fuel
Rapid fuel consumption fix
2016-12-01 00:54:32 -05:00
t00thpick1
ec0c7da494 Merge pull request #3050 from MLG-Fortress/master
Don't handle item pickups when Items_As_Unarmed is set to true
2016-12-01 00:54:23 -05:00
Jake Ben-Tovim
5f9f3e8167 Fix 1.11 brewing, remove health bar from armor stands
This fixes brewing on the newest Spigot API builds. The Alchemy skill was completely broken due to a change in the Spigot BrewEvent constructor, which this fixes via the changes to FakeBrewEvent.java and AlchemyPotionBrewer.java. This also adds a check in EntityListener.java for armor stands, so that health bars aren't displayed for them. The health bars never really displayed properly (armor stand health acts differently from most entities), and it allowed players to punch invisible armor stands server admins may have been intentionally hiding to temporarily reveal them via a health bar, which is an issue.
2016-11-28 21:28:05 -05:00
Jacob Martin
6388246418 Fix an issue where brewing stands will consume two fuel units for vanilla ingredients. 2016-11-13 10:26:29 -06:00
RoboMWM
86432eb426 Don't handle item pickups when Items_As_Unarmed is set to true
If `unarmed.Items_As_Unarmed` is set to true in config, then there's no
need to be manually handling item pickups.
2016-10-23 22:38:31 -07:00
t00thpick1
a51585f5d0 Merge pull request #3007 from FabioZumbi12/master
Fix pt-br strings
2016-08-20 22:00:05 -04:00
t00thpick1
9ec75fb470 Back to dev 2016-08-20 21:54:09 -04:00
t00thpick1
c8a7f6d76f Version Bump 2016-08-20 21:50:43 -04:00
t00thpick1
01a8a199d2 Fix a dupe bug that resulted from yet another change to piston code a couple mc patches ago. Oh well. 2016-08-20 21:47:29 -04:00
t00thpick1
f85c54596a Merge pull request #3011 from SidShakal/patch-chunkRefreshRadiusFix
Correcting loop conditions related to "ghost block" mitigation.
2016-08-07 20:55:09 -04:00
Sid Shakal
b3e1acc563 Correcting conditions related to "ghost block" mitigation.
If radius is 1 (as it is when called elsewhere in the class), the loop
conditions fail to refresh some of the neighboring chunks, allowing for
ghost blocks to continue to occur on eastern and southern edges of the
chunk the player is in.

This commit fixes the loop conditions.

= Chunk diagram of old behavior =
-----
-RR--
-RP--
-----
-----

= Chunk diagram of new behavior =
-----
-RRR-
-RPR-
-RRR-
-----

= Legend =
P: the chunk the player is in
R and P: chunks that are refreshed
-: chunks that do not get refreshed
2016-08-07 17:32:34 -05:00
FabioZumbi12
745ff21551 Merge pull request #2 from FabioZumbi12/FabioZumbi12-patch-1
Fix translated strings
2016-08-05 09:59:52 -03:00
FabioZumbi12
31c8cf9766 Fix translated strings
Fix translated strings
2016-08-05 09:59:39 -03:00
t00thpick1
8901db4e18 Add Beetroot to herbalism skill
Merge pull request #2918 from isokissa3/master

His was better.

(cherry picked from commit 3ed0fdf330)
2016-06-26 17:14:19 -04:00
t00thpick1
b1b8c4d713 Back to dev 2016-06-25 13:05:47 -04:00
t00thpick1
b14b37c22d Version bump 2016-06-25 13:00:47 -04:00
t00thpick1
e73e628051 Merge pull request #2951 from minoneer/brewing-fuel
Fix brewing stands consuming all remaining fuel items
2016-06-25 12:53:20 -04:00
t00thpick1
3bb920f22c This is completely untested but it probably works. Maybe Fixes #2966 2016-06-23 21:22:40 -04:00
t00thpick1
2bed26f18a Fix scoreboard numbering being off 2016-06-19 17:47:38 -04:00
t00thpick1
fb3363661b Remove invalid enchantment from default config 2016-06-19 17:42:40 -04:00
t00thpick1
315b713005 These should definently not be hard coded in the future... but allow rabbits and guardians to be shaken down 2016-06-19 17:41:18 -04:00
t00thpick1
70de0ba00b Enable Beetroot I think 2016-06-19 17:33:43 -04:00
minoneer
25cad3afc6 Fix brewing stands consuming all remaining fuel items when the fuel bar is refilled 2016-06-09 02:10:27 +02:00
t00thpick1
11aa126b80 Merge pull request #2918 from isokissa3/master
Exploit fix, turning spawned pigs into zombie pigmans using lightning stike allows you gain XP
2016-04-28 10:31:24 -04:00
isokissa3
d0e8bb3174 Fixed spacing 2016-04-27 13:45:26 +03:00
isokissa3
6b03108052 Fixed formatting 2016-04-26 15:26:50 +03:00
isokissa3
34447ef874 Exploit fix, turning spawned pigs into zombie pigmans using lightning stike allows you gain XP 2016-04-25 18:47:15 +03:00
t00thpick1
dcd79e87e1 This command probably works 2016-04-23 00:32:04 -04:00
t00thpick1
8822b4edae Fix typo 2016-04-03 00:25:50 -04:00
t00thpick1
a24d6ff018 Missed removals 2016-03-27 11:46:00 -05:00
t00thpick1
707195f237 I honestly forgot this was in here. Fixes #2863 2016-03-27 11:12:16 -05:00
t00thpick1
321fcd7b84 Merge pull request #2850 from DylanCare/master
Fixes Alchemy for Stage 1 Potions and Lingering
2016-03-23 21:21:51 -05:00
Dylan
c5970e9246 Ensure NETHER_WARTS are renamed to NETHER_STALK 2016-03-21 14:42:57 -04:00
Dylan
538a0c5d6c Fixes Stage 1 Potions
The 'NETHER_WARTS' material enum should be 'NETHER_STALK' to represent the actual item.
Adds Dragon's Breath as Tier 1 Ingredient so lingering potions are actually validated as an mcMMO brew.
Adds second type of Potion of Water to support water potions that are spawned in via commands or other plugins.
2016-03-21 14:38:58 -04:00
t00thpick1
4c4df60b81 Was in a second location as well. 2016-03-20 17:52:21 -05:00
t00thpick1
d1cf08c6ba Null check. Fixes #2840 #2842 2016-03-20 12:47:27 -05:00
t00thpick1
e091a8eb55 Fix material validation errors. 2016-03-20 12:42:16 -05:00
t00thpick1
d579c9a2af Merge pull request #2829 from DorCoMaNdO/master
Stop duplicate messages from abilities.
2016-03-17 19:38:55 -05:00
Dor
a711d3a3e3 Stop duplicate messages from abilities. 2016-03-18 02:18:40 +02:00
Dor
2c197af9fd Merge remote-tracking branch 'refs/remotes/mcMMO-Dev/master' 2016-03-18 02:17:03 +02:00
t00thpick1
d58d621f96 Bump java compat version (reverted from commit 0203252b63) 2016-03-17 16:57:27 -05:00
t00thpick1
0203252b63 Bump java compat version 2016-03-17 16:52:41 -05:00
t00thpick1
22edd121d3 Back to dev 2016-03-17 12:36:32 -05:00
t00thpick1
31b83becad Version bump 1.5.04 2016-03-17 12:36:08 -05:00
t00thpick1
6cce3098db Update PotionConfigGenerator and default potions.yml for missing potions 2016-03-17 12:31:20 -05:00
t00thpick1
fd3d60d112 Merge pull request #2828 from SidShakal/master
Moved center of block drops to block center. Fixes #2544.
2016-03-17 11:16:24 -05:00
t00thpick1
9094e5feb8 French Translation update provided by @HollishKid Resolves #2819 2016-03-17 12:12:22 -05:00
Sid Shakal
60bfabb097 Moved salvaged material spawn center to center of top face of anvil.
My fix for the central spawn points of various block-based item drops
moved them from the low corner of the block to the center of the block.
In the case of the salvaged materials, this moved the central spawn
point from the low corner of the top face of the anvil block to the
center of the block above the anvil block. This felt unnatural, so the
point has been moved to the center of the top face of the anvil block.
2016-03-17 02:06:19 -05:00
Sid Shakal
2d4cf76825 ... (completing the previous style fix)
Not sure how I missed this one. (Well, sure I do. I used the GitHub
editor for the re-casing of the variable name. Noob mistake.)
2016-03-16 20:38:24 -05:00
t00thpick1
6a7279ea05 Merge pull request #2824 from DorCoMaNdO/master
Custom potion brewing now consume fuel from the brewing stand.
2016-03-16 18:07:45 -05:00
Sid
4cb4a6224b Added javadoc for Misc.getBlockCenter(BlockState)
And camel-cased the parameter name to conform to style.
2016-03-16 15:47:24 -05:00
Sid Shakal
a6e445b7ef Minor formatting adjustments to keep my commit to code style.
Whoops. Eclipse removed a line in imports, and I placed a brace on the
wrong line. Fixed.
2016-03-16 12:01:52 -05:00
Sid Shakal
123a139e43 Moving the center of block drops to block center. Fixes #2544. 2016-03-16 11:47:40 -05:00
Dor
4054315c19 Custom potion brewing now consume fuel from the brewing stand.
Fixed a glitch that let players remove the ingredient of a custom potion
from the brewing stand without cancelling the brewing task (this doesn't
seem to have caused any duplicates, once the task finished nothing
happened).
2016-03-16 15:16:48 +02:00
Dor
d942cedb8e Merge remote-tracking branch 'refs/remotes/mcMMO-Dev/master' 2016-03-16 15:11:51 +02:00
t00thpick1
ec774b590b Fix potions. Fixes #2813, #2814 2016-03-16 00:39:36 -05:00
Dor
988a11a5da Merge remote-tracking branch 'refs/remotes/mcMMO-Dev/master' 2016-03-13 01:11:51 +02:00
t00thpick1
1488946fc5 Merge pull request #2694 from Maximvdw/patch-1
Fixed NPE when skill is not in config
2016-03-12 17:56:40 -05:00
t00thpick1
1f05967b0b Merge pull request #2725 from EvilOlaf/patch-3
Fix space and color code
2016-03-12 17:56:11 -05:00
t00thpick1
4924391ae8 Merge pull request #2726 from JamieSinn/master
If sender is console, strip colours for mctop
2016-03-12 17:55:59 -05:00
t00thpick1
f2668d7dbb Merge pull request #2735 from EvilOlaf/patch-2
fixed typo
2016-03-12 17:55:46 -05:00
t00thpick1
d26779bee9 Merge pull request #2810 from DorCoMaNdO/master
Fix Shroom Thumb not removing the item held.
2016-03-12 17:55:35 -05:00
t00thpick1
c75715b186 We need to name the custom potions. 2016-03-12 17:52:19 -05:00
t00thpick1
a238b7029d Update default potions.yml and add tool to do so in the future. 2016-03-12 17:45:14 -05:00
Dor
98511136ee Fix Shroom Thumb not removing the item held. 2016-03-12 20:35:19 +02:00
t00thpick1
6723b3a4c6 Merge pull request #2803 from DorCoMaNdO/master
Treat grass path as grass...
2016-03-12 12:17:04 -05:00
Dor
40c61149cf Treat grass paths as grass. 2016-03-12 08:12:27 +02:00
Dor
4f9a463b9d Merge remote-tracking branch 'refs/remotes/mcMMO-Dev/master' 2016-03-12 08:03:30 +02:00
t00thpick1
f3a8208425 Add new enchants and fallback to bukkit enchant name map 2016-03-11 22:55:01 -05:00
t00thpick1
cbf2f34f93 Update Treasures for potions 2016-03-11 22:42:55 -05:00
t00thpick1
898fad6be4 Merge pull request #2801 from DorCoMaNdO/master
Chorus plant experience reward is now 1 instead of 2.
2016-03-11 22:38:46 -05:00
Dor
eaa1a8edca Chorus plant experience reward is now 1 instead of 2.
Sneaking is required if the player has an item in the off hand and
they're not in a vehicle.
2016-03-12 05:31:11 +02:00
Dor
08db154791 Merge pull request #3 from mcMMO-Dev/master
Merge master
2016-03-12 05:29:35 +02:00
t00thpick1
e1cf4c0c67 Merge pull request #2800 from DorCoMaNdO/master
Fix config auto update.
2016-03-11 22:21:59 -05:00
Dor
529c43b0e6 Fix config auto update. 2016-03-12 05:10:41 +02:00
t00thpick1
376abdf49e Merge pull request #2799 from DorCoMaNdO/patch-3
Use getItemInMainHand()
2016-03-11 22:09:08 -05:00
t00thpick1
11a744a772 Properly calculate potionstage 2016-03-11 22:07:27 -05:00
Dor
47f73ba455 Merge pull request #2 from mcMMO-Dev/master
Merge master
2016-03-12 05:05:37 +02:00
t00thpick1
001b11efc6 Better Auto-Update config loader, still cannot handle multiple options with the exact same name and spacing, but will not break configs anymore in those situations, just mis-comment. 2016-03-11 21:54:57 -05:00
t00thpick1
089f3a0e71 Does this fix the CI? (reverted from commit af9a3c85c6) 2016-03-11 21:30:11 -05:00
t00thpick1
af9a3c85c6 Does this fix the CI? 2016-03-11 21:28:46 -05:00
t00thpick1
a534f9aac1 Update default Potions.yml to have some of the new format, someone should PR a full update. 2016-03-11 21:15:22 -05:00
t00thpick1
a08016647a Update to new Potions API, still supports old config options 2016-03-11 21:08:10 -05:00
Dor
a557fc7d3c Use getItemInMainHand()
Add 1.9 blocks to be detected for experience rewards.
Add experience rewards for the Chorus plant.
Add experience rewards for the Shulker mob.
2016-03-11 16:20:23 +02:00
Dor
2d3d11ec2d Merge pull request #1 from mcMMO-Dev/master
Merge master
2016-03-11 06:01:08 +02:00
t00thpick1
9bc97c6dd3 I think this fixes the auto update config function when a config file has two similar keys. (reverted from commit 52f1e33052) 2016-03-08 08:09:48 -05:00
t00thpick1
52f1e33052 I think this fixes the auto update config function when a config file has two similar keys. 2016-03-07 18:41:49 -05:00
t00thpick1
272e99d41f Master volume config option 2016-03-06 16:48:56 -05:00
t00thpick1
77b67d5a79 Merge pull request #2781 from Tslat/patch-1
Fix infinite GreenThumb & ShroomThumb usage bug

-Not sure if this is the correct way to fix this, but it is A way, and that will due in the meantime.
2016-03-05 23:57:25 -05:00
t00thpick1
8e1f464209 Merge pull request #2783 from Tslat/patch-2
Update ability blacklist to include 1.8 fence[gate] types
2016-03-05 23:56:08 -05:00
Tslat
5f960fd80a Update ability blacklist to include 1.8 fence[gate] types 2016-03-06 14:36:21 +10:00
Tslat
bddca30668 Fix infinite GreenThumb & ShroomThumb usage bug 2016-03-05 20:39:16 +10:00
t00thpick1
28a2b9668d I think preserve potions backwards compatability and also update documentation. 2016-03-01 17:16:59 -05:00
t00thpick1
f52d9feef8 Update Alchemy for 1.9 Configuration style has changed, but theoretically old version should still work I think. 2016-03-01 17:05:58 -05:00
t00thpick1
f77ae6ee15 Biome needs to be in the enum compatability as well. 2016-03-01 13:25:51 -05:00
t00thpick1
88b99a3835 I *think* this should be backwards compatible, I may be wrong and it could break both. 2016-03-01 13:08:11 -05:00
t00thpick1
8d16af8770 Why is my local compiler missing thigns the CI hits? 2016-03-01 12:42:26 -05:00
t00thpick1
fde9ba86a2 Actually update all sounds 2016-03-01 12:39:05 -05:00
t00thpick1
c9356f9ef5 Update for 1.9 Sound enum changes. Now only compatible with 1.9+ 2016-03-01 12:21:00 -05:00
t00thpick1
6a0529f02d Fully remove metrics. 2016-01-28 15:20:36 -05:00
t00thpick1
760178c061 Give custom perk boost the highest priority. 2016-01-28 13:37:21 -05:00
t00thpick1
0bb2642d24 Remove metrics 2016-01-11 14:12:54 -05:00
Very Evil Olaf
635a4f7265 fixed typo
smelt = Schmelzung, not Schmelung
2015-12-28 20:18:55 +01:00
Jamie Sinn
0e34202d4d Curly braces as toothpick requested
@andrewkm
2015-12-20 23:05:48 -05:00
JamieSinn
3a9c55a9ea Remove ternary operators and use if/else 2015-12-12 00:04:23 -05:00
JamieSinn
2dd1775d9a Remove regex replace, does nothing 2015-12-11 23:52:14 -05:00
JamieSinn
a0635eeb08 Remove escape character at EOL 2015-12-11 23:45:17 -05:00
JamieSinn
9677653c54 If sender is console, strip colours for mctop
Ugly ugly colours.
2015-12-11 23:30:21 -05:00
Very Evil Olaf
6cf7167c09 Fix space and color code 2015-12-10 21:37:42 +01:00
t00thpick1
9718123292 Catchup the changelog 2015-11-12 19:19:57 -05:00
t00thpick1
420559efec Append to existing lore when crafting Flux Pickaxes. Fixes #2557 2015-11-12 19:13:27 -05:00
t00thpick1
f4b6d7845e Add config option to auto-truncate player skill levels that exceed the configured max level. Adds #2512
Also removes a good bit of magic numbering from FlatFileDatabaseManager
2015-11-12 19:10:30 -05:00
t00thpick1
b966529487 Merge pull request #2709 from JamieSinn/master
Strip colours from party chat when logging to console.
2015-11-12 17:43:34 -05:00
JamieSinn
9c7b83a52e Strip colours from party chat when logging to console. 2015-11-12 16:06:43 -05:00
t00thpick1
ac9447d439 This is actually not correct. 2015-11-04 16:31:30 -05:00
t00thpick1
a5bcc3ce58 Correctly identify tree species. Fixes #2667 2015-11-04 16:06:28 -05:00
t00thpick1
a020890244 Remove hardcoded nerf to treefeller. Fixes #2666 2015-11-04 15:53:38 -05:00
t00thpick1
616200f20f Fix compile 2015-11-04 15:48:42 -05:00
t00thpick1
1f9c3759e7 Merge pull request #2441 from wolfdate25/patch-2
Update locale_ko.properties.  Hope this is right, I cannot read it personally.
2015-11-04 15:46:55 -05:00
t00thpick1
9fb72cfea8 Merge pull request #2648 from EvilOlaf/patch-2
Update locale_de.properties
2015-11-04 15:46:13 -05:00
t00thpick1
dd84abe927 Merge pull request #2647 from EvilOlaf/patch-1
Missing bracket
2015-11-04 15:45:11 -05:00
t00thpick1
aaa69adb0c Merge pull request #2663 from MinelinkNetwork/fix-child-skill-level
Remove hardcoded limit for parent skill levels when calculating child…
2015-11-04 15:45:00 -05:00
t00thpick1
982ee13631 Merge pull request #2697 from SilverCory/master
Monitor falling blocks.
2015-11-04 15:44:45 -05:00
t00thpick1
8927e16b1f Fix skillreset argument validation. Fixes #2651 2015-11-04 15:43:07 -05:00
t00thpick1
dd01504111 Treat nether portal spawned mobs as spawner mobs. Fixes #2662 2015-11-04 15:37:17 -05:00
t00thpick1
50e727d591 Fix salvaging to return more than 1 item. Fixes #2627 2015-11-04 15:35:22 -05:00
t00thpick1
f84e98d836 Simulate block break for flux mining. Fixes #2668 2015-11-04 15:27:03 -05:00
t00thpick1
7e92905618 Comments so I don't forget why I did it like this again 2015-11-04 13:48:29 -05:00
t00thpick1
9b24dd306c Actually use Hylian Treasure config values. Fixes #2688 2015-11-04 13:35:25 -05:00
t00thpick1
aa796266a7 Don't remember what this is for, but it was in my repo so its probably important 2015-11-04 13:26:47 -05:00
Cory Redmond
a783d0dfc8 Monitor falling blocks. 2015-10-04 21:39:22 +01:00
Maxim Van de Wynckel
f9879be439 Fixed NPE when skill is not in config
When a skill is not configured this would throw an NPE as the section is not found.

Found while trying to get information from an McMMOLevelUp event
2015-09-27 00:50:26 +02:00
Byteflux
5f21efb1cd Remove hardcoded limit for parent skill levels when calculating child skill level 2015-08-16 00:35:22 -07:00
Very Evil Olaf
8e2b8f111f Update locale_de.properties
Add missing space
`Fixen` can not be used in this context. `Reparatur` is slightly better.
2015-08-03 16:53:48 +02:00
Very Evil Olaf
08766a0ff7 Missing bracket 2015-08-03 15:17:52 +02:00
t00thpick1
5b19e2e9d2 Snapshot again for realz 2015-07-28 17:49:36 -04:00
t00thpick1
bef28583f3 Fix missed compile error. Re-release 1.5.03 2015-07-28 17:48:24 -04:00
t00thpick1
eff53d90ab We need to preserve block data with our double drops for silk touch. Fixes #2625 2015-07-25 22:30:22 -04:00
t00thpick1
2aade8b7ff Remove no longer needed DualSupport classes, we crossed that road long ago. 2015-07-25 22:29:19 -04:00
t00thpick1
de0ac51b3d This should ignore absorption damage for allied players. Fixes #2618 2015-07-25 21:59:10 -04:00
t00thpick1
b161a907a7 back to development 2015-07-25 16:53:38 -04:00
t00thpick1
397ec929aa Bump version for release 2015-07-25 16:52:26 -04:00
t00thpick1
f108de9ba2 Incorrect config key. 2015-07-25 16:32:44 -04:00
t00thpick1
e3a139f7bd Update website link 2015-07-18 11:51:53 -04:00
t00thpick1
90f8132030 Merge pull request #2540 from xion87/patch-2
Update locale_it.properties
2015-07-18 11:25:45 -04:00
t00thpick1
60d89c15e6 Merge pull request #2551 from lol768/patch-1
Escape apostrophes in localised strings
2015-07-18 11:24:59 -04:00
t00thpick1
58a0287be7 Merge pull request #2583 from lumis31/patch-1
Update locale_de.properties
2015-07-18 11:24:19 -04:00
t00thpick1
ac3b28da8b Merge pull request #2614 from ThundrRok/master
Fix for custom potions being missed in potion stage calculation. #2386
2015-07-18 11:22:48 -04:00
t00thpick1
12cb1e4161 Offload slightly more calculations to the async loading thread. kinda Fixes #2591 2015-07-18 11:18:42 -04:00
t00thpick1
4e013b44d8 Support offline player experience editing 2015-07-18 10:50:38 -04:00
t00thpick1
9934ab972e Clean up SQLDatabaseManager 2015-07-18 10:48:40 -04:00
t00thpick1
30adac5e63 Properly restore state when errors occur during uuid update 2015-07-18 10:41:55 -04:00
Stephen Jenkins
d3d7c254f4 Fix for custom potions being missed in potion stage calculation. #2386 2015-07-10 18:04:53 -04:00
t00thpick1
93ad040936 Syntax is important 2015-06-20 15:11:18 -04:00
t00thpick1
bfeac43f12 NULL uuids in flatfile should not be wiped as duplicates. Fixes #2594 2015-06-20 13:04:03 -04:00
t00thpick1
4388430491 When an older user no longer has a username that a new user now has, we will update the old entry to be _INVALID_OLD_USERNAME_, however we no longer strictly enforce name uniqueness, so people altering their DB's need to tweek with caution. Invalid old users will not display in the leaderboards. Fixes #2503 2015-06-20 12:57:01 -04:00
t00thpick1
b4e21a7817 Due to the unstable and volatile nature of pistons in the current versions of mc, we cannot reliably guarentee that we can track the position of blocks being moved by pistons, and therefore will no longer track piston moved blocks in the blockstore with 100% accuracy, and will instead just not refresh the potentially empty new blocks. This will not have any effect on regular usage of the plugin aside from 100% preventing any mcMMO related piston dupe bugs. Fixes #2565, #2582 2015-06-11 21:31:20 -04:00
t00thpick1
4fe41fe416 Check Item Type, not Material Type a second time. Fixes #2584 2015-06-11 21:15:40 -04:00
t00thpick1
d8184fb298 Properly calculate diff times for old user purge. Fixes #2541 2015-06-11 18:12:22 -04:00
lumis31
78dec51ad4 Update locale_de.properties
Major updates to the locale_de including:

Most important: added translations to ALL ABILITIES DESCRIPTIONS in german

Additionally:
-Adding a translation for the Alchemy skill
-Addition of translations for fishing
-removed salvage form repair
-added horses and holy hound to taming
->full translation to german except parties
For more changes please see the changelog at the beginnig of the file. No changes have been made to the existing translations except if the information was out of date due to the recent update to Minecraft 1.8. All translations are socially acceptable (usable for children).
2015-06-09 00:10:53 +02:00
lol768
de38826897 Escape apostrophes
"The java.text.MessageFormat class uses the apostrophe (\u0027) as an escape character. Consequently, you need to write two consecutive apostrophes in your translation if you wish to display a single apostrophe"
2015-04-25 22:59:33 +01:00
xion87
f63e793006 Update locale_it.properties
Fixed italian locale for use bow skill command
2015-04-21 09:46:51 +02:00
TfT_02
ecfdd75e36 This should be SNAPSHOT 2015-04-05 20:27:39 +02:00
TfT_02
90b31a29f5 We can simplify this!
Didn’t realize there was a event.getBlocks() method for
BlockPistonRetractEvent as well.
2015-03-22 14:49:51 +01:00
TfT_02
cfa0daefc5 Fix the issues with sticky pistons and slime blocks
This is a fix for issues #2419 and #2494
2015-03-21 19:24:06 +01:00
t00thpick1
4aeda6e9e8 Still not fully on track with the original event, but as we want them to see the potions we create, we can't be fully correct. However, correcting the behavior to decrement the ingredient after the event shouldn't harm anything. Fixes #2486 2015-03-18 16:23:07 -04:00
t00thpick1
4f1f10333f Use notification settings for critical hits Fixes #2498 2015-03-18 16:09:15 -04:00
t00thpick1
342c37a02c Merge pull request #2426 from zreed/master
Empty constructors don't take arguments  Sure why not.
2015-03-18 15:31:44 -04:00
t00thpick1
e347bc1c9e Short data, Fixed #1909 2015-03-18 15:28:57 -04:00
t00thpick1
42116f4467 Include license in builds 2015-03-18 03:56:46 -04:00
t00thpick1
7ce72bafb0 Merge pull request #2489 from isokissa3/master
Fixed duplication Bug #2489 
Tentatively pulling this as I assume its valid.
2015-03-18 03:51:35 -04:00
isokissa3
f76771f0a8 Fixed duplication bug #2419 (Correct fix) 2015-03-11 14:31:56 +02:00
isokissa3
6c29da94f3 Fixed duplication Bug #2419 2015-03-11 11:36:51 +02:00
t00thpick1
981523789e Add Debug and change a line 2015-03-09 14:20:52 -04:00
t00thpick1
d9aacfa059 Back to dev 2015-03-02 15:15:08 -05:00
t00thpick1
5efc5289f7 Version bump release 2015-03-02 15:14:16 -05:00
t00thpick1
1f68f4e654 More debug for rare cases where things don't work. 2015-02-23 20:37:03 -05:00
TfT_02
5670e6696a Archery distance XP bonus cannot exceed indefinitely anymore
Fixes #2465
2015-02-21 09:42:22 +01:00
t00thpick1
ca6dc5195d Properly convert SQL to Flatfile when UUIDs are null 2015-02-16 23:12:50 -05:00
t00thpick1
30ebe318e0 Since apparently we magically can no longer compile without these. 2015-02-16 22:13:32 -05:00
t00thpick1
a1c3f0d651 WHERE'S HARVEY DENT 2015-02-16 21:43:51 -05:00
t00thpick1
347e03d75e When did this break? It was working before. 2015-02-16 12:09:00 -05:00
t00thpick1
8543382bde We want answers for the issues. 2015-02-15 22:03:58 -05:00
t00thpick1
4f1004472c Possibly fix berserk bug 2015-02-15 22:03:58 -05:00
t00thpick1
7aee829b94 Merge pull request #2456 from ulumulu1510/patch-1
Resolve duplication Bug #2419
2015-02-15 12:34:08 -05:00
Benjamin
98701104d8 Resolve duplication Bug #2419
https://github.com/mcMMO-Dev/mcMMO/issues/2419
2015-02-11 20:17:08 +01:00
t00thpick1
7a14e61762 Fix flatfile UUID conversion I think. Fixes #2225, #2411 2015-01-31 14:38:49 -05:00
wolfwork
f42f5c31ed Update locale_ko.properties 2015-01-31 15:10:15 +09:00
t00thpick1
342662c944 Round 3: DeathMatch 2015-01-25 23:28:30 -05:00
t00thpick1
50088fe0bd Round 2 2015-01-25 23:04:02 -05:00
t00thpick1
687f87a748 No more opening inventories with ability tools. Fixes #2416 2015-01-25 22:55:18 -05:00
zreed
6815c66a0e Empty constructors don't take arguments 2015-01-22 07:14:14 -05:00
TfT_02
385fe1bb05 Added option for XP gained by killing bred animals
Fixes #2402
2015-01-10 12:31:13 +01:00
t00thpick1
eddadcc179 Properly allow searches by name without UUID 2015-01-01 23:56:30 -05:00
mjkaufer
9426f44cdd Added isUnarmed Method
Checks if the player is not holding a tool, as opposed to checking if
the player is holding air. This means that attacking with something such
as a dirt block would count as unarmed.
2014-12-29 16:31:18 +01:00
TfT_02
af7ff3df58 Make Archery distance multiplier configurable
Add #2385
2014-12-24 11:00:43 +01:00
TfT_02
7c0cc8794f Whoops, should've incremented these 2014-12-23 18:49:26 +01:00
TfT_02
eda18bc990 Only show the scoreboard tips a couple of times
We can assume a player knows how scoreboards work after showing them
the tips a few times across multiple login sessions

Adds #1833
2014-12-23 14:08:29 +01:00
TfT_02
a2c395db36 Fixed bug where MobHealthbarTypes were not saved 2014-12-23 14:07:10 +01:00
TfT_02
522b085499 Fix bug where no XP was granted when Flux Mining
Fixes #2359
2014-12-22 17:25:55 +01:00
TfT_02
3ea845cfd9 Changed Flux Mining mechanics
Previously, Flux Mining would get unlocked at a specified level with a
specified chance. Once unlocked, the player would have no control over
this ability and some players complained they would like to be able to
turn it on and off.

By adding a new furnace recipe, to craft a special pickaxe - a Flux
Pickaxe - this issue is solved. If a player doesn’t want to use Flux
Mining, they simply shouldn’t mine using a Flux Pickaxe.

Crafting a Flux Pickaxe is simple, just place one of the vanilla
pickaxes in a furnace and cook it up.

Every time the ability is successful, extra durability damage is dealt
to the tool. Just like with other abilities.

Adds #2320
2014-12-22 16:58:22 +01:00
TfT_02
93013b2db1 Fix an NPE when loading potion configs 2014-12-21 17:50:31 +01:00
TfT_02
d5a2dea06b Add option to shake items from player inventories 2014-12-20 23:55:49 +01:00
TfT_02
d188224c06 Make it possible to shake heads from players 2014-12-20 23:55:49 +01:00
TfT_02
3422c5d3eb Don't need this here 2014-12-20 19:14:52 +01:00
TfT_02
ebeebbde72 Randomize spawn location of Call of the Wild pets
So that when you’re spawning multiple pets at once, they don’t all
spawn at the same spot.
2014-12-20 19:14:52 +01:00
t00thpick1
e71eff852c Add ChatColor support for lore and custom item names. Add lore and custom item name support for potions and dyes. 2014-12-20 02:16:23 -05:00
t00thpick1
bfff5682b5 As a semi-temporary measure, lets move 1.8 specific objects into their own classes, so we can be 1.7 and 1.8 compatable. 2014-12-19 13:48:06 -05:00
t00thpick1
429a7d926a 1.8 changed the inheritance structure of Squids, this update resolves issues that cropped up from this change. 2014-12-18 18:15:02 -05:00
TfT_02
262e711bcc Add option for Chimaera Wings to ignore bed spawns
Adds #2365
2014-12-18 23:04:38 +01:00
t00thpick1
b44b1cc859 And back to development 2014-12-18 14:15:59 -05:00
t00thpick1
75dfec1236 Bump version for release build. 2014-12-18 14:14:58 -05:00
t00thpick1
8c2f3cff8f Silly me, prismarine isn't an ore. 2014-12-18 14:11:54 -05:00
t00thpick1
32336b712b Quick initial update for 1.8
Adds default configuration for new blocks and entities.
Updates a few hardcoded utilities to account for new blocks and entities.
2014-12-18 01:36:02 -05:00
t00thpick1
cfc51e9b96 use players for events 2014-12-17 22:34:42 -05:00
t00thpick1
31cefbfc8c Update readme 2014-12-17 18:54:21 -05:00
riking
2c940ecdac Try again later when Mojang ratelimits us 2014-11-26 01:52:17 -08:00
riking
e51809d066 Goddamnit, save more often to make sure progress is made 2014-11-26 01:24:44 -08:00
riking
01a18fa587 Revert "Downgrade Bukkit to 1.7.9 to compile"
This reverts commit d0881ab3fd.
2014-11-24 05:34:15 -08:00
Kane York
f93deeceb6 Merge pull request #2356 from riking/logout-method
This will allow for BungeeCord compat when the sending server knows about the move. It will NOT work if the proxy processes the transfer.
2014-11-24 05:30:49 -08:00
riking
3275395d53 Remove dead logoutParty() method 2014-11-24 05:28:46 -08:00
riking
d0881ab3fd Downgrade Bukkit to 1.7.9 to compile 2014-11-24 05:28:28 -08:00
riking
5db09bf45c Allow synchronous save on logout
This is intended for plugins that have foreknowledge of a logout
happening (e.g. a BungeeCord server hop about to happen), so that they
can tell mcMMO to save the data, and the new server will be able to pull
the profile correctly from the database.
2014-11-24 05:24:13 -08:00
riking
f4406bd9cf Move PlayerQuit logic to mcMMOPlayer.logout() 2014-11-24 05:23:37 -08:00
riking
3b441073fd Change PROFILES_PER_REQUEST to 50
@blood thinks this may fix the 429 issue
2014-11-18 17:25:03 -08:00
riking
da22a8ff93 Change UUID ratelimits to sane values 2014-11-18 17:21:44 -08:00
Harry
f8469cbe00 Fix an old bug where the config is read incorrectly
This should be "DamageModifier" not "DamagerModifier.". As seen here dbc7b98b0d/src/main/resources/advanced.yml (L140) . Thanks to @matagin for pointing this out.
2014-11-03 12:36:20 +01:00
TfT_02
0188629fe2 Should add these to the hash map to prevent a NPE
Fixes #2333
2014-10-25 17:33:55 +02:00
TfT_02
5d246d2701 Add missing UserManager check
Caused an java.lang.IndexOutOfBoundsException: Index: 0

Fixes #2335
2014-10-25 17:29:58 +02:00
t00thpick1
b3cd5486d6 Actually use settings 2014-10-19 01:55:10 -04:00
zreed
7e961fc2a3 Actually include Tomcat (and dependencies) 2014-10-15 22:00:11 -04:00
t00thpick1
8fcd286eb0 This might be important 2014-10-15 01:31:11 -04:00
t00thpick1
4723a7cbdb Switch to a different ConnectionPool implementation 2014-10-15 00:15:43 -04:00
TfT_02
dbc7b98b0d Properly name these config nodes
I forgot that we don’t use underscores here
2014-10-11 13:37:25 +02:00
TfT_02
a5bc547c40 Add settings for Bleed damage
Adds #2154
2014-10-11 12:18:31 +02:00
TfT_02
63b332216e Read summon item from config in /taming command 2014-10-11 11:38:53 +02:00
TfT_02
8e5340ebc3 Wolves attack a target when shot by their owner 2014-10-11 11:38:53 +02:00
TfT_02
e4af611c91 Fix formatting of TreeFeller threshold locale key 2014-10-11 11:38:52 +02:00
TfT_02
c31281971c Summon amount limits and new ability 2014-10-11 11:38:52 +02:00
TfT_02
eda38cba66 Add lifespan to Taming summons 2014-10-11 11:25:57 +02:00
TfT_02
b5a2e76926 Fixed diminished returns not getting disabled 2014-10-10 00:03:51 +02:00
TfT_02
38cc7435dc Prevent strings from getting larger than 16 chars
Fixes #2314
2014-10-04 20:31:37 +02:00
TfT_02
864a760e9c Better like this 2014-10-04 14:16:38 +02:00
TfT_02
0838cbb874 Add option to not show ability names on scoreboard
Adds #2249
2014-10-04 14:05:30 +02:00
TfT_02
4844be80da Fixed bug with Salvage and ability tools
Fixes #2311
2014-10-04 01:36:57 +02:00
TfT-02
62a767db89 Add enable toggle and per skill thresholds 2014-09-28 11:43:17 +02:00
TfT_02
ce3463ad6d Cleanup 2014-09-28 11:34:50 +02:00
TfT_02
5d059d8537 Move SkillXpGain to datatypes/experience 2014-09-28 11:34:49 +02:00
riking
332860b9ce Use a DelayQueue to manage rolling diminished returns 2014-09-28 11:34:49 +02:00
TfT_02
2a443cd9db Diminished instead of Deminished 2014-09-28 11:34:49 +02:00
NuclearW
f4d1004d32 Rolling xp diminishing returns
This adds on top of the diminishing returns system a mechanic such that gains will expire the configured number of minutes after they occured, rather than all being reset at once.

This prevents someone from not getting diminishing returns on the xp gain they recieved just before the reset would have occured.

Obligatory explanatory graphs: http://i.imgur.com/uSzicIR.png
2014-09-28 11:34:49 +02:00
TfT_02
9d8aec7eca Add diminished returns when a player has earned too much XP
When a player reaches a certain (configurable) threshold value of total
XP earned in a specific skill, his earned XP in this skill will be
decreased.

Depending on how far the player has exceeded the threshold value, his
XP will decrease more. After the (configurable) time interval of 10
minutes, the registered data will be cleared and the player can earn XP
as normal again.
2014-09-28 11:34:49 +02:00
Ivo Julca
958c116fd0 Acrobatics: cap same-location fall counter for XP gain
It used to increase boundlessly, thus preventing players from gaining XP for a while even after moving to another place.
2014-09-28 11:19:41 +02:00
Bestle
ec1a125809 These are the wrong way round
The UUID's are the keys, not the names
2014-09-28 11:13:23 +02:00
TfT_02
2dd8e719c8 UUID support for parties 2014-09-28 11:13:23 +02:00
TfT_02
d62c68a490 Fixes build 2014-09-28 11:08:57 +02:00
TfT_02
3c6dd290f4 Allow AdvancedSalvage unlock level 0
Fixes #2265
2014-09-06 20:23:41 +02:00
TfT_02
07e589aae3 Allow equal rank levels for Salvage
Fixes #2270
2014-09-06 19:59:26 +02:00
t00thpick1
1119d3c17f Actually fix flatfile player loading....
you lied to me @tft_02
2014-09-03 00:05:48 -04:00
TfT_02
eac5d1ee7a Improve auto mod config generator 2014-08-31 19:10:49 +02:00
TfT_02
56cb5c092f Should be this 2014-08-26 21:55:35 +02:00
Shevchik
9d7faf9ed9 Fix database loading data for wrong player
Fixes #2223
2014-08-24 15:25:56 -07:00
TfT_02
7da661546f Fixed bug where processing message would always get displayed
and the player could never execute /mctop or /mcrank if chat display
was disabled.
2014-08-24 09:21:40 -07:00
TfT_02
48d3280e5e Make sure that player has McMMOPlayer object before calling API 2014-08-22 15:50:40 -07:00
TfT_02
b61c65636b Add new ExperienceAPI method to specify if XP can be shared 2014-08-22 15:50:40 -07:00
TfT_02
087a0b079f Fixed bug with new Death API 2014-08-22 15:50:40 -07:00
t00thpick1
2147417322 This seems easier. 2014-08-22 15:16:40 -04:00
t00thpick1
4304970059 This was supposed to be a zero. 2014-08-22 00:59:20 -04:00
t00thpick1
fc981fda20 Better connection validation for us. 2014-08-21 19:42:03 -04:00
t00thpick1
be9ff51fd9 Should fix #2223 for realz this time. 2014-08-21 19:42:03 -04:00
TfT_02
adde56114e Cleanup the changelog 2014-08-21 16:40:06 -06:00
TfT_02
5cfd2dc799 Added API to ExperienceAPI to get the amount of XP needed for a level 2014-08-21 16:38:33 -06:00
TfT_02
c878775c72 Close the statement here as well 2014-08-21 14:33:50 -06:00
t00thpick1
574cdd374b Use a placeholder value. Fixes #2216 #2221 2014-08-20 22:19:36 -04:00
TfT_02
a3943aab24 Add checks for loaded/unloaded profiles in commands 2014-08-19 22:23:19 -06:00
t00thpick1
1503e58d11 More relevant donation information 2014-08-19 23:45:54 -04:00
TfT_02
2650d57d8e Added options to experience.yml for Dirt and Sand variations
Adds #2194
2014-08-19 21:28:53 -06:00
t00thpick1
4d402c7229 Use correct element 2014-08-19 19:11:07 -04:00
t00thpick1
d687543910 Prevent players from having more than one database querying command running at once. 2014-08-19 18:11:56 -04:00
t00thpick1
d8ad519cd0 Seperate pools for essential tasks like profile loading and profile saving. 2014-08-19 17:58:45 -04:00
TfT_02
a23d093271 Use provided instead of compile 2014-08-18 17:19:14 -06:00
TfT_02
8a35d69540 Move RefreshChunks setting from hidden.yml to config.yml
Adds #2213
2014-08-17 20:21:23 -06:00
t00thpick1
097a5a0894 Change purge a bit. Apparently andrewkm says this works. 2014-08-17 21:23:27 -04:00
t00thpick1
8760c2bbb0 This way is cleaner though. 2014-08-17 20:01:04 -04:00
t00thpick1
dc635fe7d7 SHould fix #2195 2014-08-17 19:57:52 -04:00
TfT_02
f10a1d0ffb Added McMMOPlayerPreDeathPenaltyEvent and McMMOPlayerStatLossEvent
McMMOPlayerPreDeathPenaltyEvent is fired before hardcore calculations
take place, use this if you want to cancel hardcore penalties.

Use McMMOPlayerVampirismEvent and McMMOPlayerStatLossEvent when you
want to know how many levels or experience the player lost or if you
want to modify this.
2014-08-16 21:13:46 -06:00
TfT_02
809779e508 Added McMMOPlayerVampirismEvent
Expands API possibilities regarding death penalty features.
2014-08-16 21:13:39 -06:00
TfT_02
80d358d1fd Fix dealing too much AOE damage
Bandaid for #2170
2014-08-13 21:24:32 -06:00
t00thpick1
a1be17c72c Add a rate limit for mojang api requests. Configurable via hidden.yml 2014-08-12 11:51:34 -04:00
t00thpick1
0a066f51bb Fix #2197 There is no wait forever option, so we actually need a timeout. 2014-08-12 11:39:43 -04:00
t00thpick1
294141c353 We should be reconnecting automagically. 2014-08-11 12:16:27 -04:00
t00thpick1
5a47f9fa86 Fix #1320 2014-08-08 00:42:33 -04:00
t00thpick1
6ee2d7d823 Do UUID saves in batches. 2014-08-08 00:13:30 -04:00
t00thpick1
f2881f02c8 Fix id retrieval 2014-08-08 00:09:00 -04:00
t00thpick1
9f5445689c Helpful debug on shutdown 2014-08-08 00:02:07 -04:00
t00thpick1
0ea163e3ee Lazy fix 2014-08-08 00:01:57 -04:00
t00thpick1
f097aa4a67 Missed loaded profile check, Fix #2189 2014-08-07 23:46:22 -04:00
t00thpick1
1fcb9e649e A bit more logic simplification in SQLDatabaseManager, also fixes error printing, Fix #2188 2014-08-07 23:45:40 -04:00
t00thpick1
1d0dc02013 Greatly simplify Profile loading in mySQL 2014-08-07 14:16:28 -04:00
t00thpick1
8766d31943 Fix #2182 and Fix #2178
NOW() is a numeric representation of the date, not a timestamp....  so thats a nono.

Also,  we need to update UUIDs grabbing by name.
2014-08-07 13:54:28 -04:00
t00thpick1
d857bf483e Fix #2184 2014-08-07 11:23:02 -04:00
t00thpick1
b7774251eb Remove need for thread locks in profile loading, just reschedule as needed. also stagger based on number of previous attempts. 2014-08-05 23:02:41 -04:00
t00thpick1
da7507fc75 Throw some sanity information into the info log. 2014-08-05 20:20:05 -04:00
t00thpick1
fe4699430d Fix #2177 2014-08-05 19:15:22 -04:00
t00thpick1
df4fc8149d Stagger load attempts more. 2014-08-05 19:03:55 -04:00
t00thpick1
c156f0c346 Missed an unlock condition, lets use a finally. Should Fix #2180 2014-08-05 18:57:13 -04:00
t00thpick1
79a17b0c1c Fix /mcrank when using flatfile. Fixes #2179 2014-08-05 09:20:12 -04:00
t00thpick1
d3051ad127 Use a slight delay to ensure its after the purge. 2014-08-04 11:49:09 -04:00
t00thpick1
f4c53aaf8a Prevent user purges and UUID updates from conflicting in mass database operations. 2014-08-04 11:42:02 -04:00
t00thpick1
432ff95a98 More constants 2014-08-04 11:40:47 -04:00
t00thpick1
fe29bb4b9f Accurate purge count 2014-08-03 21:14:24 -04:00
t00thpick1
ae5347bc0f Purging shouldn't be main thread, also we have no reason to refresh profiles of purged users, as old users aren't online, and powerless users have nothing to wipe. 2014-08-03 21:12:41 -04:00
t00thpick1
966de87ef9 Print reason 2014-08-03 20:57:28 -04:00
t00thpick1
3569f9a182 Woot, rushing things without looking! 2014-08-03 20:40:48 -04:00
t00thpick1
70a23f8a0a EnumMaps cannot use a null key 2014-08-03 20:39:37 -04:00
t00thpick1
857e12b96e SQLDatabaseManager optimizations, async profile loading -t00thpick1, zreed
This commit changes our shared connection into a connection pool utility to prevent
thread locks from multiple actions attempting to access the database at the same time.
In additon,  profile loading has been moved off the main thread at login time, to
allieviate the performance issues caused by it.

Fixes #2138, Fixes #2119, Fixes #1982, Fixes #1953
2014-08-01 20:31:17 +02:00
TfT_02
c10525ada9 Add UUID support! - zreed, slipcor, t00thpick1
This commit updates our database managers to use UUIDs instead
of usernames for persistent storage.

Fixes #1979
2014-08-01 20:23:03 +02:00
TfT_02
fb8592495d Only set detected durability if it's > 0 2014-08-01 01:09:00 +02:00
TfT_02
a48ada306c Add magical mod importer
Usage: Create a folder called 'import' inside /mcMMO/mods/. Place your latest Cauldron 1.7+ startup log in this folder and rename it to 'import.log'.
It is worth noting that it's advisable to create a short log by starting and stopping the server once, or by manually editing the log file to only include material mapping in order to speed up the import process.

When the server is running, use the command /mcimport. You will see the import progress in the console, once it is done the files are created in /mcMMO/mods/output/.

Any item that wasn't recognised gets placed in a .unknown.yml config file. Durability detection only works if the mod is installed when importing (it should be).
2014-08-01 00:22:29 +02:00
Lucas Savva
8db0d663dc More configs for 1.6.X mods
+ Added full tools and armor and some block configs for:
- Advanced Genetics
- Applied Energistcs
- Big Reactors
- Biomes O Plenty
- Emasher Resource
- Extra Utilities
- Factorization
- Forestry
- MineFactory Reloaded
- Natura
- Project Red
- Railcraft
- StargateTech 2
- Thermal Expansion
- Tinker's Construct
- Twilight Forest
2014-07-31 16:56:41 +01:00
TfT_02
70744371a3 Fix bug where Repair_Material_Quantity wasn't read 2014-07-31 00:47:22 +02:00
TfT_02
18c322e8d6 Check if the user wants this item repairable first
Stop complaining that the item is not repairable when Repairable is set
to false.
2014-07-31 00:46:41 +02:00
TfT_02
75cbfa1b1c Ensure player has mcMMOPlayer object in brewing
Fixes #2086
2014-07-24 12:29:42 +02:00
zreed
48c7aa3e84 Add an UpgradeManager 2014-07-23 12:37:02 +02:00
TfT_02
87bce65098 Update twilightforest.blocks.yml 2014-07-20 19:44:13 +02:00
TfT_02
c288dc433b Add Twilightforest mod configs, made by joulesbeef 2014-07-20 17:17:02 +02:00
TfT_02
0cc29d070f Move 1.6.x mod config to their own folder
and add a folder for 1.7.x mod config files
2014-07-20 16:11:41 +02:00
TfT_02
8fd94b625c Fix Blast Mining and change its behavior slightly
Fixed bug where Blast Minings ability "Demolition Expert" would not
work with certain CB versions. DanageCause.BLOCK_EXPLOSION was not
passed, ENTITY_EXPLOSION was used instead.

Changed behavior of the Blast Mining ability "Demolition Expert"; now
only decreases damage for the ability user and for Blast Mining
explosions.
2014-07-20 00:43:53 +02:00
TfT_02
ccca3fff26 Don't use hardcoded unlock levels for Blast Mining 2014-07-20 00:43:52 +02:00
TfT_02
f77446919f Can't use more function modifiers than necessary
Fixes #2139
2014-07-18 17:11:26 +02:00
TfT_02
96fdf265d5 Don't run party chat on a separate thread
Fixes #2080
2014-07-18 17:06:30 +02:00
TfT_02
b964e3f7c3 Show colors in console for party chat
Fixes #2129
2014-07-18 00:51:09 +02:00
TfT_02
d93c83f775 Add a modifier function for each DamageModifier
Must have a modifier function for each DamageModifier

Fixes #2139
2014-07-18 00:16:12 +02:00
TfT_02
6b9f6c29ec Actually fix the isWaterBottle() check
Fixes #2134

For some reason Bukkit wanted to use Potion(PotionType type, int level)
when calling .toPotion(), even though .getDataValue() is 0.
2014-07-17 00:14:06 +02:00
TfT_02
09b0bf62e2 Added SkillAPI used to get a list of skill names
This prevents having to rely on the SkillType enum
2014-07-16 20:07:23 +02:00
TfT_02
15d7d3f8a2 Add Snow to Excavation guide 2014-07-16 11:47:28 +02:00
TfT_02
dedbdf890a Fixed broken isWaterBottle() check 2014-07-15 17:50:39 +02:00
TfT_02
30085e1e34 Add option to control Unarmed item pickup behavior
By default when using Unarmed, picking up items is prevented when a
players entire inventory is full, except for his empty hand.
2014-07-15 15:40:49 +02:00
TfT_02
1c30146491 Fixed bug where Berserk deletes items
when the players inventory is full.

Fixes #1947
2014-07-15 15:25:02 +02:00
TfT_02
037022b175 Fixed bug where falling blocks were not tracked
Fixes #2130
2014-07-15 14:46:20 +02:00
TfT_02
0aa67727f5 Fixed bug with flatfile format updater 2014-07-12 14:02:53 +02:00
TfT_02
8e3e1d5f11 Use deprecated events for damage dealing for now 2014-07-11 21:33:35 +02:00
TfT_02
d2d70089ca Update for modifierFunctions 2014-07-11 14:02:42 +02:00
zreed
94a566acc9 Remove redundant maxReconnects database connection property 2014-07-09 19:03:15 +02:00
TfT_02
daab095557 I was actually using the wrong Map
Fixes #2113
2014-07-03 12:33:03 +02:00
TfT_02
2b9b5df1ee Alter original event and stop firing FakeDamageEvents
Fixes #2105
2014-07-02 11:28:21 +02:00
TfT_02
e7e62b8d40 SecondaryAbilityEvent now implements Cancellable
Fire SecondaryAbilityEvent for abilities with static chances

Also cleanup some of the event handling for Armor Impact, Greater
Impact and Fast Food
2014-07-02 11:25:13 +02:00
TfT_02
3d242bbdb6 Always call back events 2014-07-02 11:25:13 +02:00
TfT_02
e796eae3c3 Update for new damage API 2014-07-02 11:25:08 +02:00
TfT_02
a257e83a62 Update for new getOnlinePlayers behavior 2014-06-29 14:04:36 +02:00
Kane York
d527584248 A private method cannot be abstract >.> 2014-06-28 23:49:46 -07:00
Kane York
0a4de6e2fc Reword statement in standards.md 2014-06-28 23:48:12 -07:00
TfT_02
4b20f12eff Fix a NPE with getFlowerAndGrassXp()
Fixes #1975
2014-06-23 22:52:34 +02:00
TfT_02
0de1187012 Fixed setting custom names and lore with treasures 2014-06-22 20:42:48 +02:00
TfT_02
8e474170e4 Fix crafting with items received from Salvage
Only set metadata on Salvage items when it’s not set to -1
Fixes #2078

And cleanup some javadocs in Salvageable
2014-06-18 11:44:21 +02:00
TfT_02
2eeb9b1f35 Set a pretty repair material name in armor.yml
Adds #1863
2014-06-15 17:46:16 +02:00
TfT_02
3de6e2c3f1 Add full Repairable support in armor config files
You can now fully configure armor to be repairable from the armor.yml
config files.

Adds Repair_MinimumLevel and Repair_XpMultiplier to armor.yml
2014-06-15 17:46:16 +02:00
TfT_02
98d166808f Finish the tools.yml header 2014-06-15 17:45:52 +02:00
TfT_02
f75e15dfdc Set a pretty repair material name in tools.yml
Adds #1863
2014-06-15 17:31:50 +02:00
TfT_02
f2b892b7d5 Add full Repairable support in tools config files
You can now fully configure a tool to be repairable from the tools.yml
config files.

Adds Repair_MinimumLevel and Repair_XpMultiplier to tools.yml
2014-06-15 17:28:54 +02:00
TfT_02
883ada01f8 Fix typo with XP_Modifier in tools.default.yml 2014-06-15 17:18:49 +02:00
TfT_02
3a8f45a04d Fix bugs with pistons
This commit improves piston tracking and fixes a couple of bugs with
block tracking.

Fixes #2043
2014-06-15 14:26:02 +02:00
TfT_02
906609696b Workaround a CB bug by tracking piston events
There is a bug in Craftbukkit that causes piston events to fire
multiple times. We need to keep track of the extend and retract events
to see which piston events should be processed.
2014-06-15 14:26:02 +02:00
riking
66ccde4310 MCPC+ is now known as Cauldron 2014-06-14 11:34:35 -07:00
TfT_02
4970cdc3f4 Add mcmmo.skills.salvage permission to plugin.yml
Fixes issue where players would have access to the Salvage child skill
by default.

Mentioned in #2075
2014-06-12 13:42:42 +02:00
TfT_02
1becc874ba Check if input is a water bottle first 2014-06-09 22:55:03 +02:00
TfT_02
b107a8dc7c Fire brew event after outputs have changed
and before experience is granted.
Part 2 of fixing #2041
2014-06-09 02:04:59 +02:00
TfT_02
37aebc1716 Calculate Alchemy XP based on potion stage
Adds #1926
2014-06-09 01:56:07 +02:00
TfT_02
836877ff93 Alchemy should fire BrewEvents
Fixes #2041
2014-06-09 01:43:50 +02:00
TfT_02
28a846e0cb Update changelog 2014-06-08 18:23:07 +02:00
TfT_02
0185a30ec9 Fix an IndexOutOfBoundsException: Index: 0
In SaveTimerTask.java

Fixes #2039
2014-06-08 18:21:13 +02:00
TfT_02
38e1947302 Remove PvpLogger checks
No longer needed when testing with Combat Tag v6.1.4, the NPCs have
metadata „NPC”.

Fixes #2017
2014-06-08 18:11:18 +02:00
riking
4fb4d6fc0c Save users asynchronously 2014-06-08 14:12:25 +02:00
TfT_02
6d719988bf Remove this check here, allows Salvage in Adv mode
We’re already checking if the players game mode isn’t CREATIVE, so we
can safely remove this check.

Fixes #2059
2014-06-03 12:23:42 +02:00
TfT_02
b1c1f0e21e Added missing Salvage permissions to plugin.yml 2014-05-25 23:45:20 +02:00
TfT_02
3f34cc7365 Actually fix maximumQuantity reading from config
Now we try to automatically detect the maximum quantity if possible and
fall back to the config if the user has set a value there.

Also fixed the feedback message which said „Minimum quantity” instead
of „Maximum quantity”
2014-05-25 23:20:19 +02:00
TfT_02
3c6c2837bd Check permission before sending anvil messages 2014-05-25 22:46:35 +02:00
TfT_02
4bcef76fd8 Let config key take priority here 2014-05-24 15:42:15 +02:00
TfT_02
2fd5d7aa81 Cleanup RepairConfig leftovers in SalvageConfig
Some copy/pasta I forgot to remove
2014-05-24 15:24:25 +02:00
TfT_02
5080c68dce Fix Maximum Quantity in Salvage configs 2014-05-24 15:23:50 +02:00
TfT_02
3403aef37d Don't display child skills on scoreboards
This fixes an issue where the scoreboard would not display properly
when using /mcstats or /inspect.

Fixes #2037
2014-05-23 17:03:02 +02:00
TfT_02
53a34c12d2 Add SALVAGE to MISC_SKILLS List 2014-05-23 14:23:05 +02:00
TfT_02
59417d6721 Add changelog entry for Salvage child skill
Closes #561
2014-05-19 16:59:28 +02:00
TfT_02
93d63dbca5 Minor cleanup of imports 2014-05-18 17:06:50 +02:00
TfT_02
4643cf1070 A whole bunch of more work to convert Salvage to a child skill 2014-05-18 17:04:39 +02:00
GJ
91bf54019e Convert Salvage to a child skill. 2014-05-18 17:04:38 +02:00
TfT_02
ead716ef0d Fix a NPE when tab completing with /ptp
Fixes #2013
2014-05-11 18:33:50 +02:00
TfT_02
8fec1af257 Fix a bunch of small formatting issues 2014-05-11 15:15:44 +02:00
Sean Porter
99248caba3 Redstone ore now throws events when it flips on or off.
Fixes issue #2021
2014-05-11 01:30:11 -07:00
TfT_02
af64bdf742 Added API to check if an entity is bleeding 2014-05-02 19:41:44 +02:00
TfT_02
66a4925371 Use getAllyName() here instead 2014-05-02 00:53:05 +02:00
TfT_02
8eb6acd60f Add option to prevent hopper transfers of bottles 2014-04-27 15:03:07 +02:00
TfT_02
ce6892f2e6 Update README.md 2014-04-24 16:00:02 +02:00
TfT_02
c14a4e9305 Fix /party teleport command
Why did we use getCommand("ptp").getExecutor() again?

Fixes #1995
2014-04-21 14:54:09 +02:00
TfT_02
5825eb1696 Make sure to shorten long ability and skill names
(cherry picked from commit 236ccd6ebdd0834f87b373794e1597ef36fb2ff6)
2014-04-21 14:09:52 +02:00
TfT_02
bfebbd0095 Fix formatting
(cherry picked from commit 4e36073e6e2dc3aeba087d605cef79fc4a8a9779)
2014-04-21 14:09:41 +02:00
GJ
b204507a82 Use strings instead of OfflinePlayers for scoreboards.
(cherry picked from commit 89b596591ec1974e0201395dc6e76353e4709572)
2014-04-21 14:09:09 +02:00
TfT_02
9f53426511 Added API to XP events to get XP gain reason 2014-04-18 22:32:32 +02:00
Sean Porter
03c2282c3f Fix the calculations for Iron Arm Style in the Unarmed command. 2014-04-18 02:16:35 -07:00
TfT_02
20092d55fd Fix bug where dodge would check the wrong player 2014-04-18 00:49:40 +02:00
TfT_02
69a2a5cfff Check if player has a mcMMOPlayer object
Fixes #1976
2014-04-12 17:06:14 +02:00
TfT_02
618cfad100 Prevent accidentally breaking regrown crops
Adds #828
2014-04-06 14:41:40 +02:00
TfT_02
56e625a9df Added option to open /mcstats after logging in
Added #1033
2014-04-06 13:27:38 +02:00
TfT_02
79a1ef5d3e Players need to be in a party to use /ptp
Fixes #1967
2014-04-06 12:43:42 +02:00
TfT_02
10dd7619bf Support MATERIAL|data format in treasures.yml
Allows users to use the same material type for multiple treasures in
treasures.yml

Fixes #1965
2014-04-05 18:31:01 +02:00
TfT_02
f9dfec5bd0 Check event.getBow() != null
Fixes #1933
2014-04-05 13:55:10 +02:00
TfT_02
a9488bc18b Vanished players no longer get hit by AoE effects
Fixes #1964
2014-04-05 13:12:20 +02:00
TfT_02
f0ee708710 Updater should not be running on the main thread
Fixes #1957
2014-04-05 12:10:02 +02:00
TfT_02
3390a31cc6 Move PlayerUpdateInventoryTask to runnables.player 2014-04-05 11:59:36 +02:00
t00thpick1
0b4b272223 Account for level 0 2014-04-01 14:58:24 -04:00
TfT_02
8d200ea653 Back to active development 2014-03-29 18:28:26 +01:00
TfT_02
eb359c5595 Update pom.xml and changelog.txt for 1.5.00 release 2014-03-29 17:52:08 +01:00
TfT_02
e1b8088c17 Improve holiday manager with 1.7 changes 2014-03-29 17:50:29 +01:00
TfT_02
70a1eea231 Nerf Herbalism XP from Tall Grass 2014-03-29 17:12:55 +01:00
TfT_02
c744974192 Added option to config.yml to override vanilla Minecraft treasures 2014-03-29 17:12:55 +01:00
TfT_02
faa11a87a9 Removed "Treasure found!" message
Because when treasures are found in vanilla Minecraft, there isn’t a
message either
2014-03-29 17:12:55 +01:00
TfT_02
91da5c4ab1 Add option to drop extra fish
Allows enabling of old fishing mechanic where fish was always caught,
even when a treasure was found
2014-03-29 17:12:54 +01:00
GJ
da5e770e06 Add Podzol & Red Sand to Excavation 2014-03-29 17:12:54 +01:00
TfT_02
09557e378b Update to the new ProjectileSource API 2014-03-29 17:12:54 +01:00
TfT_02
72d26fed0f Update version number to 1.5.00 2014-03-29 17:12:54 +01:00
TfT_02
225de799e8 Increase TreasureHunter chances for Luck enchantment
When the player is using a fishing rod with the ”Luck of the Sea”
enchantment, the drop chances will increase with 1% for each level of
the enchantment.
2014-03-29 17:12:36 +01:00
TfT_02
334c44760f Workaround for ClassCastException: MaterialData cannot be cast to Tree 2014-03-29 17:12:36 +01:00
TfT_02
ac7fc1020d Use tree species for Woodcutting double drops in config.yml
Oak is now Generic, and Spruce is now Redwood.
2014-03-29 17:12:36 +01:00
riking
461871327b Include new 1.7 biomes in fishing biome XP boost and Ice Fishing check 2014-03-29 17:12:36 +01:00
GJ
60ddd799de Update mcMMO for Minecraft 1.7.2 2014-03-29 17:12:35 +01:00
GJ
80571fbe8f Remove deprecated permission nodes 2014-03-29 17:12:35 +01:00
TfT_02
d407f85704 Update pom.xml and changelog.txt for 1.4.08 release 2014-03-29 17:06:01 +01:00
TfT_02
458dc7db42 Make database command cooldown configurable 2014-03-29 17:02:08 +01:00
TfT_02
beab794c0e Fixed some issues with the HolidayManager
Was severely lacking more lols
2014-03-29 16:52:41 +01:00
TfT_02
8256f5461c Using an axe is required to earn Woodcutting XP
Not really sure why or when this check had gone missing..
2014-03-26 09:52:59 +01:00
TfT_02
0fe3ad7432 Reworked COTW config options + made COTW item configurable
Adresses #1481 partially
2014-03-23 14:33:57 +01:00
TfT_02
04e5dda127 Actually fix Repair lucky perk with Arcane Forging downgrade chance 2014-03-23 14:33:57 +01:00
TfT_02
f65adea2f9 Added minimum jump strength requirement and config option
for horses summoned with "Call of the Wild"
2014-03-23 13:41:31 +01:00
TfT_02
cdfb0da5c9 Fixed bug where shift right clicking potion ingredients was broken 2014-03-23 12:59:43 +01:00
TfT_02
cfa3d34dff Fix important bug regarding pistons 2014-03-14 15:23:28 +01:00
TfT_02
01b7d4f742 Repair lucky perk should decrease the Arcane Forging downgrade chance,
instead of increasing it.
2014-03-14 15:16:22 +01:00
TfT_02
9a359bf42c We need to use event.getBlock() here
Fix my boo boo from previous commit
2014-03-11 13:33:54 +01:00
TfT_02
ebdf11300b We do need to use a runnable. 2014-03-10 20:51:52 +01:00
TfT_02
e1a8f02bce Make Acrobatics XP prevention cool down, after teleporting configurable
Adds #1906
2014-03-09 15:24:24 +01:00
TfT_02
862d38b587 Clean up all of the imports 2014-03-03 18:27:45 +01:00
GJ
2415767c06 Clean up imports. 2014-03-03 12:22:28 -05:00
GJ
aa59348a94 We only care about blocks that award XP.
Also, this fixes a possible issue where blocks changed by entities other than falling blocks could have been left as tracked even after they were destroyed.
2014-03-03 12:14:01 -05:00
GJ
9c925d3327 We can do this without needing a runnable. 2014-03-03 11:40:36 -05:00
GJ
30f7521a3a Handle healthbars even when skills are disabled. Fixes #1194 2014-03-03 10:29:14 -05:00
GJ
7b3869e385 Use .equals instead of deprecated ID method. 2014-03-03 09:24:24 -05:00
GJ
0e641f7c5b Clean up some of our metadata handling. 2014-03-03 08:48:16 -05:00
GJ
733d16cf35 Don't clone if it's null. Fixes #1894 2014-03-03 08:03:30 -05:00
TfT_02
833bc1b251 Fixed bug where disbanded parties could still see alliance chat 2014-02-28 22:41:47 +01:00
TfT_02
840f3d9382 Fix /party kick command 2014-02-28 22:32:09 +01:00
TfT_02
34d6d867f2 Prevent combat abilities from damaging allied players 2014-02-28 22:08:48 +01:00
TfT_02
e56d5a0454 Exclude vanished players from tab complete list
Part 2 of fixing #1745
2014-02-28 21:56:30 +01:00
TfT_02
53fdf750f4 Pretend like the player is offline when he is vanished
Part 1 of fixing #1745
2014-02-28 21:56:30 +01:00
TfT_02
f096e915cf Changed default amount of XP from mining Quartz Ore
#1886
2014-02-28 19:24:41 +01:00
GJ
ce59488e8e Add FakeEntityTameEvent to match expected behavior for an animal being tamed. 2014-02-28 12:04:00 -05:00
GJ
47db522cc1 Because Bukkit doesn't set this automatically with setTamed. Go figure. Fixes #1888 2014-02-28 11:50:36 -05:00
TfT_02
a2cac82cba Check if player has data key here as well
Fixes #272
2014-02-28 14:45:44 +01:00
GJ
2e74333eb7 Oops. 2014-02-28 08:40:00 -05:00
GJ
0056be2d5f Assorted cleanup. 2014-02-28 08:36:42 -05:00
TfT_02
1d7e034d5e Fix the updater 2014-02-27 22:26:58 +01:00
GJ
8deac175d1 Repair damaged user files. Fixes #1869 2014-02-22 09:52:36 -05:00
GJ
d0b766a2d3 Fixed bug with updating (very) old user data. 2014-02-21 11:38:22 -05:00
GJ
65692f2a83 Fixed bug with checking maximum durability of mod items. Fixes #1634 2014-02-20 12:43:11 -05:00
GJ
d0b0786284 Fixed exploit involving Call of The Wild. Fixes #1877 2014-02-20 11:50:56 -05:00
Luuk Jacobs
87ac1002de Fix potion datavalues for Splash poison II potions 2014-02-18 08:45:44 +01:00
TfT_02
c51fde7f1f Added new permission node to control who can check version number
Negate this permission node to hide the version number from /mcmmo and
motd
2014-02-17 16:31:59 +01:00
TfT_02
0a6735110f Get mod config file resources properly
Fixes #1870 for real
2014-02-16 23:32:14 +01:00
TfT_02
8a284c50a2 Rename mod files to type.default.yml
Fixes #1870
2014-02-16 23:08:22 +01:00
roblikescake
09431ef27c Check durability before repairMaterial 2014-02-16 00:18:27 +01:00
TfT_02
9f9de86d21 The defender isn't necessarily a player here
Besides, the defender doesn’t need to have the player data key anyways
2014-02-16 00:11:15 +01:00
TfT_02
d9c04a09ba No need to clone here and it's not null checked
Fixes #1864
2014-02-15 23:35:14 +01:00
t00thpick1
04a02cfdc8 Store McMMOPlayer objects as metadata 2014-02-15 14:21:25 +01:00
TfT_02
b3a6c32ef6 Skip glass bottles as well
Fixes #1859
2014-02-15 11:18:11 +01:00
TfT_02
254f3b5ac9 Cleanup finishBrewing a bit 2014-02-15 11:17:31 +01:00
TfT_02
7f9ada14c8 Schedule check after putting a new bottle in the brewing stand 2014-02-15 01:37:41 +01:00
TfT_02
f79a4741cc Store Locations, not BlockStates
Fixes #1862
2014-02-15 01:31:13 +01:00
TfT_02
f3fd48d0c0 Don't set potion meta data - for Vanilla potions 2014-02-14 23:58:22 +01:00
GJ
fbee3318bd These go the other way around. 2014-02-12 08:29:14 -05:00
TfT_02
813f807876 Fix remaining potion data values
Fixes #1844
2014-02-12 13:48:24 +01:00
TfT_02
0060a86b20 Compile with 1.6.4-R2.0 2014-02-12 12:00:04 +01:00
TfT_02
15743c5f46 Don't set potion meta data
It causes incompatibilities with other plugins.

Fixes #1849
2014-02-12 11:54:21 +01:00
TfT_02
4b9d472f10 Fix ConcurrentModificationException with alchemyBrewTask.finishImmediately()
Fixes #1848
2014-02-12 11:16:05 +01:00
GJ
988006f913 Alchemy cleanup, part 1. 2014-02-11 16:22:57 -05:00
TfT_02
2f05c472ce Make party names case insensitive
Fixes #1846
2014-02-10 17:14:34 +01:00
TfT_02
5c836cdaaf Check party level before sending party chat
Fixes #1847
2014-02-10 16:07:43 +01:00
TfT_02
9e39c3495d Fix IllegalArgumentException: 1 > 0 2014-02-09 17:15:42 +01:00
TfT_02
b653aa57b7 You can't accept an alliance request when you already have an ally 2014-02-09 16:10:43 +01:00
Sean Porter
2ffdd340af The command is spelled xpshare, not expshare.
Fixes #1841
2014-02-09 12:31:30 +01:00
Sean Porter
d63c3fc6d0 Ensure the FlatFile directory exists.
Fixes #1842
2014-02-09 12:31:29 +01:00
TfT_02
4486261413 Schedule an Alchemy check after using a hotkey to add ingredients
Fixes #1834
2014-02-07 13:39:24 +01:00
TfT_02
a2e32179bb Fix /mcstats command
Fixes #1819
2014-02-05 19:24:14 +01:00
TfT_02
72b106e71f Fix ptp Accept_Required setting
I forgot to change this, oops!
2014-02-05 19:15:39 +01:00
TfT_02
679f1ed629 Use default Vanilla MC potion data values in potions.yml
Fixes #1821
2014-02-04 16:48:10 +01:00
GJ
734815c58d No reason to have our scoreboard stuff in a different listener. 2014-02-04 08:34:17 -05:00
GJ
abfedf381d Allow mod name to go in the middle or at the beginning. 2014-02-04 07:53:54 -05:00
GJ
8e040ae8d9 Refactor to match existing conventions 2014-02-03 14:57:45 -05:00
GJ
0c9836eb03 Made mod config files modular. Addresses #1802 2014-02-03 14:48:43 -05:00
TfT_02
62b13a9a84 Fixed bug where Snow would never drop treasures
Fixes #1820
2014-02-01 00:30:42 +01:00
TfT_02
c48ccae484 Compile with RELEASE to remain 1.6 compatibility for now 2014-02-01 00:30:37 +01:00
TfT_02
6264bfa15f Don't store Block objects, use BlockState
Fixes #1811, Closes #1822
2014-01-30 20:45:21 +01:00
TfT_02
b50ba9c02e Fix wrong data value of Potion of Hunger II
Fixes #1817
2014-01-26 15:13:35 +01:00
GJ
b3474c04c7 Increment SQL query numbers due to addition of Alchemy. Fixes #1803
Thanks to @roastnewt for the help!
2014-01-21 11:16:39 -08:00
TfT_02
a1c1271d21 Fix issues pointed out by the FindBugs plugin 2014-01-20 23:20:51 +01:00
md-5
79155887b0 You can only ever deploy one release.
Use -SNAPSHOT to indicate this is a dev build and not a release.
2014-01-20 23:06:37 +01:00
TfT_02
4178604833 Update pom.xml with md_5 Maven repo settings 2014-01-20 22:48:27 +01:00
TfT_02
d1fcd6958f Check if brewingStand == null
Fixes #1804
2014-01-20 22:38:20 +01:00
TfT_02
f39623c279 Bit of Alchemy cleanup 2014-01-20 22:38:04 +01:00
GJ
520f5cb116 Fix the broken build. Shame on me. 2014-01-20 14:53:31 -08:00
GJ
43e2c813d1 Clean up some of our messes. 2014-01-20 13:58:40 -08:00
TfT_02
c6ea32f0b0 Added Ender Dragon, Wither, and Witch to combat experience multipliers
They do not give any XP by default.

Fixes #1763
2014-01-19 19:40:33 +01:00
TfT_02
976c3b8494 Fix bug which prevented Hoppers from inserting new bottles
Fixes #1801
2014-01-19 15:35:27 +01:00
TfT_02
f3db90b6a9 Fix a couple of typos in plugin.yml
Mulitplies => Multiplies
2014-01-19 01:08:38 +01:00
TfT_02
82509fb476 Added custom XP boost perk 2014-01-19 01:08:38 +01:00
TfT_02
c27d79cf25 Added new XP perk - 10% boost
Adds #1698
2014-01-19 01:08:37 +01:00
TfT_02
de912c1e07 Make sure the player is valid as well 2014-01-19 01:08:37 +01:00
TfT_02
2159aa91ff Add missing alchemy ingredient tiers to ingredient check 2014-01-18 20:28:28 +01:00
TfT_02
748dba41dc Randomize the treasure drop amounts instead of always dropping everything
For example, the guaranteed 5 diamonds will now be a 1-5 diamond drop.
2014-01-18 19:15:38 +01:00
TfT_02
9349416326 Check if brewing stand still exists before processing AlchemyBrewTask 2014-01-18 19:11:15 +01:00
TfT_02
3b794c897d Make sure the party leader is online before attempting to notify 2014-01-18 19:06:20 +01:00
TfT_02
b460f7a564 Add more debug messages in onDisable()
So that we can track down why the disable proces slows down
2014-01-18 16:59:16 +01:00
TfT_02
383b048fef Changed config validation for Rank_Levels, successive Ranks can now be less than or equal to each other
Closes #1790
2014-01-18 12:02:05 +01:00
TfT_02
243a3bfbf6 Remove trailing whitespaces 2014-01-18 12:02:05 +01:00
TfT_02
c108a475e3 Fix a typo in the Alchemy skill guide
Concotions => Concoctions
2014-01-17 19:25:48 +01:00
TfT_02
6b653fa606 Changed appearance of party member list 2014-01-17 18:58:07 +01:00
TfT_02
818962e668 Added party levels
Parties now have XP and Levels. Party features such as party teleport and party chat have to be unlocked before they can be used by the party members
2014-01-17 18:56:27 +01:00
TfT_02
c729297615 Added party alliances
Adds the following commands:
`/party alliance`
`/party alliance invite <target>`
`/party alliance accept`

Allies will share party chat and will not be able to harm eachother.
Item and XP sharing is limitied to a single party. Allowing two parties
to team up without sharing resources and XP.

Closes #1009
2014-01-17 18:55:58 +01:00
TfT_02
e6e90954a9 Changed config validation for UnlockLevels, they can now also be 0
Closes #1790
2014-01-17 15:51:28 +01:00
TfT_02
4e86f60fd2 Replace ingredient strings correctly
Fixes #1789
2014-01-17 14:00:22 +01:00
TfT_02
27ff545d46 Add Alchemy hardcore settings to default config.yml file
These setting were already working, just forgot to add them to the
default file as well.
2014-01-17 00:17:10 +01:00
TfT_02
7c891e9ba8 Optimize imports 2014-01-16 22:32:40 +01:00
TfT_02
6143003516 Update PR to changes in master
- Special thanks, instead of in dev team
- Fix formatting issues
  * Remove trailing whitespaces
  * Rename method names of event listeners
  * Check for negative instead of positive
- Added Alchemy skill guide
2014-01-16 22:32:40 +01:00
Eric Hildebrand
8f83e328b0 Introduction of new Alchemy skill! 2014-01-16 22:32:40 +01:00
TfT_02
9afa8efd7d No need to hardcode the max tier here 2014-01-15 12:20:05 +01:00
TfT_02
393d9ca74e Fixed bug where Hylian Luck was broken
Fixes #1771
2014-01-13 14:18:16 +01:00
nossr50
97c95c1c49 This doesn't belong in the main branch 2014-01-12 14:49:05 -08:00
TfT_02
491df2cc82 Changed the appearance of /mcmmo commands
Closes #978
2014-01-12 13:51:12 +01:00
TfT_02
b4a6ecc58c Abstract HolidayManager a little more
Now we don’t have to manually edit this each year.
2014-01-12 12:08:47 +01:00
TfT_02
103bf593f3 Check null here as well
Fixes #1664
2014-01-12 10:30:04 +01:00
TfT_02
0332c0f5e0 Move this comment up
#1538
2014-01-11 15:14:39 +01:00
TfT_02
a004d6976d We already had a key called Confirm_Required
Another attempt to fix #1583
2014-01-11 14:54:01 +01:00
TfT_02
730f786d5b Fix issue with /ptp command
Fixes #1773
2014-01-11 10:30:12 +01:00
Foxtail
8993c71577 Update extrabiomesxl.blocks.yml
Config file was missing a section of 2x2 trees, called Quarter logs.
Missing logs were added to appropriate divided sections.
2014-01-10 10:56:04 -05:00
Sean Porter
cc524bb2ab Map.remove() can return Null. 2014-01-09 22:52:25 -08:00
TfT_02
2e94eecda0 Fix a small error with the config validation of advanced.yml
Fixes #1769
2014-01-08 13:19:51 +01:00
TfT_02
2466270b22 Removed /stats alias for /mcstats
Closes #1667
2014-01-08 01:10:12 +01:00
TfT_02
54a514edfa Added a LOTR mod config files, made by Dragyn 2014-01-07 23:28:16 +01:00
TfT_02
1336aeaef0 Remove/move more comments on identical keys
#1583
2014-01-07 22:05:18 +01:00
TfT_02
3c078100e8 Another attempt to fix the broken config updater
An attempt to solve #1583
2014-01-07 20:50:48 +01:00
GJ
13a623ea1f Misc was getting crowded again. 2014-01-03 11:07:13 -05:00
GJ
05b21eae5f Clean up our inventory event handling. 2014-01-03 10:41:38 -05:00
GJ
e0358d42d6 Ensure we're not dealing with a fake player. Fixes #1749 2014-01-03 09:19:07 -05:00
GJ
26174d88f4 Remove unused import 2014-01-03 08:30:59 -05:00
Sean Porter
c12d4319ac Don't cancel death message fixes for NPCs. 2013-12-27 15:21:25 -08:00
Sean Porter
a87bd14342 The attack target can still be an NPC without being an instance of Player. 2013-12-27 14:50:01 -08:00
TfT_02
d5990eee71 Added a ton of mod config files, made by Dragyn 2013-12-17 19:36:41 +01:00
TfT_02
f94343f13b Only grant taming XP once when taming a horse
Fixes #1651
2013-12-15 23:36:43 +01:00
TfT_02
ea4c424e0f Added level thresholds to hardcore modes
Players will not lose stats when their level is below the
Level_Threshold.
2013-12-15 23:27:37 +01:00
riking
f99e5e015d Add checks to rectify the potential for negative XP
Fixes #1573
2013-12-15 23:26:57 +01:00
riking
56b57da077 Only call one Death Penalty Event 2013-12-15 23:26:57 +01:00
TfT_02
4b402d9837 Fixed validation feedback message for Chimaera Wing recipe cost
Fixes #1703
2013-12-15 22:25:15 +01:00
TfT_02
6c2b1f555f Improve CleanBackupsTask a bit
* Print proper file names to the console when the date could not be
determined
* Skip all directories
* Skip every file that doesn’t have .zip in the file name
2013-12-13 00:17:56 +01:00
TfT_02
cdcda03e92 Moved repair config classes to the config package 2013-12-12 19:53:27 +01:00
TfT_02
65aa05a660 Fix /addlevels all and /skillreset all commands
Fixes #1675
2013-12-12 16:50:36 +01:00
TfT_02
7c7aa994a5 Added pre-made metallurgy.tools.yml by Skuli 2013-12-11 15:02:25 +01:00
riking
2aec4a69ea Database conversion bug: Integral division in output format 2013-12-10 14:56:07 -08:00
Glitchfinder
06c9ea7068 Minecraft handles block drop chances internally.
Fixes #1678
2013-12-08 12:49:43 -08:00
TfT_02
c88583c1c0 Use Matcher.quoteReplacement here!
Fixes #1676 - for real this time
2013-12-08 17:07:45 +01:00
TfT_02
d2b6838453 Fix config.yml formatting 2013-12-08 11:40:09 +01:00
TfT_02
c9f1f8f662 Fixed bug where party chat broke if the display name contained special characters
Fixes #1676
2013-12-08 11:35:02 +01:00
TfT_02
7a08343304 Actually keep all weeks, not just from the past year
Week numbers are obviously the same every year, we need to check the
year as well as the week number to determine if we should keep the
backup file or not.
2013-12-07 13:18:14 +01:00
riking
3b1bb3e08a Minor changes to Tree Feller - use a HashSet, move comment
LinkedHashSet doesn't actually do anything for us - we were never using the consistent ordering it promises, and openjdk-7 doesn't even provide that consistent ordering. Better to just not use it.
2013-12-06 23:55:26 -08:00
TfT_02
07cafd4866 Fixed bug where disabling hardcore mode for specific skills didn't work
Fixes #1661
2013-12-03 22:15:23 +01:00
GJ
48821a710f Fixed bug with cooldown donor perks 2013-12-02 08:30:45 -05:00
GJ
30a1b333b9 Need a space here. 2013-12-02 08:18:28 -05:00
GJ
696bf71962 Remove unused import 2013-12-02 08:13:53 -05:00
t00thpick1
2d577e92f1 AntiTheft option for Disarm Ability 2013-12-01 19:08:22 -05:00
Luuk Jacobs
86b92b5b30 add alias to mcscoreboard 2013-11-27 00:35:58 +01:00
GJ
24c1dec046 Fix missing import & broken build.
That's what I get for editing through Github's web UI...
2013-11-25 09:32:16 -05:00
GJ
6c478a26c4 Fix issue with custom axes not working with Tree Feller.
Most custom materials don't properly report their max durability, so we need to use our repairable manager to handle them instead.
2013-11-25 09:29:41 -05:00
t00thpick1
2d3da6daf8 Space not underscore 2013-11-24 18:01:05 -05:00
t00thpick1
de3b2b8024 Damage should probably actually be fatal I would think. 2013-11-23 12:34:14 -05:00
t00thpick1
02a064ffc6 These need spaces to be called pretty 2013-11-23 00:45:12 -05:00
t00thpick1
cb5303ce4d These strings return with Spaces, not underscores 2013-11-23 00:42:43 -05:00
t00thpick1
c0dee19cb0 Missed a refactor :P Also, javadoc event 2013-11-22 12:48:53 -05:00
t00thpick1
870987bba7 SecondaryAbility's API additions 2013-11-22 12:32:23 -05:00
riking
5d63a4b910 Run PlayerProfileSaveTask async, as intended 2013-11-21 12:41:26 -08:00
riking
3236ee5ec9 Harden save() method by making a defensive copy 2013-11-21 11:17:24 -08:00
riking
12ed2ac07b Have ExperienceCommand and SkillresetCommand explicitly handle 'all' 2013-11-19 18:56:47 -08:00
t00thpick1
729f3b1df9 There is no usage of this method in which "all" will not cause NPE's 2013-11-19 21:00:29 -05:00
TfT_02
ee1be3599c .length doesn't start at 0 2013-11-18 21:01:41 +01:00
TfT_02
12a6aca8cd Assume that block data = 0 if there isn't one in the config 2013-11-18 20:48:37 +01:00
TfT_02
2b81b8daeb Fix Commands.Scoreboard.Timer locale string
Closes #1626
2013-11-18 19:56:29 +01:00
GJ
5edbdec151 Actually fix broken locale string. 2013-11-15 07:25:50 -05:00
GJ
eaa38c11b8 Fix broken locale string.
Fixes #1615
2013-11-13 09:47:13 -05:00
GJ
e904e34556 Update Korean translation
Closes PR #1613 from @wolfdate25
2013-11-12 08:15:58 -05:00
TfT_02
445f805bb8 Set the treasure drop after using .clone()
Fixes #1603
2013-11-12 12:49:16 +01:00
t00thpick1
df77b9d0ed Parenthesis 2013-11-10 13:56:15 -05:00
t00thpick1
29f2525b58 Tend toward the smaller values, and configurable maximum for horse jump strength 2013-11-10 13:54:45 -05:00
TfT_02
5a68c7a335 Fixed bug which prevented gaining Acrobatics XP 2013-11-10 00:52:30 +01:00
GJ
69ef7f40d8 Command cleanup. 2013-11-08 23:14:11 +01:00
GJ
d1d6b80676 Allow repair of items without a recipe. 2013-11-08 10:52:43 -05:00
GJ
dfe83ff497 Fix divide by zero bug
Minimum Level & Minimum Quantity were accidentally flipped.
2013-11-07 09:13:56 -05:00
riking
e5acf6d936 Also clone fishing treasures, use alternate Wool method
The alternate wool method is testing, the treasure clone is there to stay ;)
2013-11-06 21:34:16 -08:00
riking
bca0ca6766 Fix Shake poisoning the treasure cache with Wither skeletons
The returned ItemStack is modified for both Sheep and Skeletons, so a copy should be returned.
2013-11-06 21:03:13 -08:00
GJ
f17b5faaf6 Parenthesis are good. 2013-11-06 14:52:19 -05:00
GJ
f20fa571f1 Update changelog. 2013-11-06 11:56:50 -05:00
GJ
b90d1c31c7 Updated localization files
Includes new Portuguese (Brazil) translation provided by @FabioZumbi12
in #1585

Includes new Korean translation provided by @wolfwork in #1258
2013-11-06 09:48:05 -05:00
GJ
cf56ca35eb Tweaked durability handling slightly.
Now routes everything through one function to handle enchants and max
durability. Use max durability from RepairableManager by default to
account for mod tools.
2013-11-06 08:45:20 -05:00
TfT_02
c31f5b5782 Account for Unbreaking enchantment when using abilities 2013-11-05 14:51:54 +01:00
GJ
af98c8eb59 Best way to handle minimum quantities.
Check repair function first, assuming the item isn't null, otherwise
check the config. If not found, check config.
2013-11-04 11:01:14 -05:00
TfT_02
3a10b2d83c Make sure we're not setting a bite chance > 1.0
Fixes #1592
2013-11-04 10:32:05 +01:00
TfT_02
32e7c48fd8 Change this message to something that makes sense
The old message was confusing see #1593
2013-11-03 22:49:39 +01:00
Glitchfinder
af578870c7 Defaulted quantities should be defaulted everywhere.
Fixes #1581
2013-11-03 09:40:04 -08:00
TfT_02
cd470d5497 Fix a NPE which occured when there was no backups folder 2013-11-03 14:09:41 +01:00
TfT_02
a9c5e2a04f Don't send a message to the console if no backups were deleted 2013-11-02 21:50:49 +01:00
TfT_02
0196fd8447 Fix the update checker 2013-11-02 21:49:20 +01:00
TfT_02
b1458840e7 Permissions should be lowercase 2013-11-02 19:29:36 +01:00
TfT_02
1fea786669 Added bypass permission for finding Fishing traps 2013-11-02 19:25:02 +01:00
TfT_02
6f9a57751e We can't schedule tasks in onDisable() 2013-11-01 17:39:03 +01:00
GJ
2e1c585005 Fix issue with updating players that are offline. 2013-11-01 12:38:40 -04:00
GJ
811626e67b Cleanup. 2013-11-01 11:54:51 -04:00
TfT_02
cdfd81a67a Cleanup ZipLibrary class 2013-11-01 16:44:03 +01:00
TfT_02
408b8b2107 Added automatic cleanup of backups folder
By default mcMMO keeps the following files:
 * All files from the last 24 hours
 * Daily backups of the past week
 * Weekly backups of the past months

Adds #1574
2013-11-01 16:43:56 +01:00
GJ
6d5f3a52f4 Don't process chat if the mcMMOPlayer is null.
The player should ALWAYS be online when chatting, but depending on
external plugins and applications, this is not always properly
implemented. Fixes #1578
2013-11-01 09:30:10 -04:00
GJ
2cdf08de9f Allow offline players for chat events.
This fixes issues with plugins or applications that rely on JSONAPI to
chat. Fixes #1578
2013-11-01 09:12:06 -04:00
GJ
71141a0f8d Minimum quantity should default to 2.
Fixes #1581
2013-11-01 08:22:14 -04:00
TfT_02
bded936af5 Cleanup our imports 2013-10-31 22:30:05 +01:00
GJ
caaac232d7 Cleanup CombatUtils.
Opting to stick with the if-else rather than the switch statement,
because I think it's slightly easier to read.
2013-10-31 15:03:06 -04:00
GJ
a9d51dad34 Clean up Smelting checks.
Now uses recipes to check if an item is the result of smelting.
2013-10-31 14:29:06 -04:00
GJ
88296da0af Removed MCPC+ workaround.
This has been fixed by MCPC+ starting with build 112.

Addresses #1549
2013-10-31 13:28:54 -04:00
GJ
de3c4f8fd7 Smelting now works with custom ores.
Also fixed exploit where smelting XP could be awarded for some
non-smeltable materials.
2013-10-31 13:25:06 -04:00
GJ
1785bab504 Fix bug with Salvage config value.
After our renames and updates, Salvage was not reading the config value
for the anvil material properly.
2013-10-31 09:09:52 -04:00
GJ
41da32cd1b Added options to disable various sound effects.
Fixes #1577
2013-10-31 09:03:29 -04:00
GJ
93d586592e Move these checks up.
These checks need to happen sooner because they may impact config
loading, specifically the MCPC+ check.

Fixes #1549
2013-10-31 08:15:30 -04:00
Glitchfinder
d6c6c75157 Experience is occasionally zero or cast to zero.
Fixes #1575 and fixes #1576
2013-10-30 15:49:47 -07:00
GJ
4889769522 Workaround MCPC+ shortcomings for now.
Fixes #1549
2013-10-30 15:33:37 -04:00
TfT_02
6c70de6a58 Also backup experience.yml 2013-10-30 12:33:34 +01:00
GJ
fd9154e009 Fixed bug with toggle commands not properly displaying the success message. 2013-10-29 11:45:27 -04:00
GJ
97b9214d6e Wrap these inside McMMOPlayer for easier access. 2013-10-29 11:02:57 -04:00
GJ
a8d1376533 More minor cleanup. 2013-10-29 10:01:30 -04:00
GJ
3be443c63c Cleanup some XP functions, remove unused scoreboard values, minor refactoring. 2013-10-29 09:49:41 -04:00
GJ
cc2c9eb21d Move this to the skill itself. 2013-10-28 16:32:40 -04:00
GJ
9b3ae5c729 These belong in their managers, not in McMMOPlayer 2013-10-28 16:14:52 -04:00
GJ
ccb7fc5886 Remove, don't just comment out. 2013-10-28 16:04:55 -04:00
GJ
60d69e3cc4 Create wrapper to handle all PTP data. 2013-10-28 15:49:48 -04:00
riking
f64f62492f Reinstate static color list, clarify intent 2013-10-28 12:47:25 -07:00
GJ
3fe936306b Oops. 2013-10-28 15:19:47 -04:00
GJ
c79f8043ad Use proper functions where they exist, and move functions to better locations. 2013-10-28 15:12:24 -04:00
GJ
8369ae4616 Don't use a class variable here. 2013-10-28 14:14:20 -04:00
GJ
4715688fe8 Update changelog. 2013-10-28 14:07:41 -04:00
GJ
62e03a4ef5 Black is hard to read. 2013-10-28 13:58:34 -04:00
GJ
9ef3c721df Formatting cleanup from the scoreboard update. Also handle skill permissions differently. 2013-10-28 13:04:46 -04:00
TfT_02
f55039ac6b Earn XP when using Shake
Adds #1564
2013-10-28 17:38:03 +01:00
TfT_02
be792a1052 Fix exploitPrevention() and add Javadocs 2013-10-28 15:39:47 +01:00
GJ
c612036db3 Don't try to find a treasure if there aren't any.
Fixes #1572
2013-10-28 08:52:55 -04:00
GJ
ad4ee6f402 Cleanup exploit prevention method. 2013-10-28 08:17:06 -04:00
TfT_02
49a5bd2ba6 We can move this check to exploitPrevention() 2013-10-26 00:50:31 +02:00
GJ
8aac6a992b Back to active development. 2013-10-25 17:11:54 -04:00
GJ
5da66f05d4 Update pom.xml for 1.4.07 release 2013-10-25 17:11:04 -04:00
GJ
134e0db2e9 Cleanup more of Riking's mess. 2013-10-25 17:07:56 -04:00
GJ
b3415ee2f4 Cleanup some of Riking's mess. 2013-10-25 17:05:36 -04:00
TfT_02
14175a6dfd Don't complain about missing Guide strings 2013-10-25 22:16:18 +02:00
TfT_02
7b3fb46a9a Improved AFK Acrobatics prevention mechanism 2013-10-25 22:02:39 +02:00
Kane York
0aea165a8f Add note about temporary dev build setup to README 2013-10-25 11:46:29 -07:00
riking
17b7a9bf10 Add message to /mcscoreboard time [n] 2013-10-25 11:41:21 -07:00
riking
bd611ee11c Add message to /mcscoreboard keep when a board is not shown 2013-10-25 11:39:24 -07:00
riking
c6ca65f5c9 Create a utility method in SkillUtils to easily check ability cooldowns 2013-10-25 09:49:02 -07:00
riking
95f15e68fe New and Improved Scoreboard System
- Scoreboards now AUTO-UPDATE
 - Scoreboards now COME IN COLOR
 - If you want, they can come in EVERY COLOR (Config setting)
 - Scoreboards can be displayed alongside chat output!
 - Prevention of denial of service to SQL via spamming /mctop using a cooldown
 - Added /mccooldown command to show cooldowns for all available skills
2013-10-25 09:49:02 -07:00
TfT_02
89dabaeb43 Hook location cleanup 2013-10-24 23:14:23 +02:00
TfT_02
c2e100b1e3 Use hook location in Master Angler 2013-10-24 21:19:24 +02:00
GJ
9f33c6cef1 Use addUnsafeEnchantment instead of addEnchantment
Since the enchantment was already present on the item, there's no need to check if it's valid. This also avoids any errors that may occur when trying to repair an item with non-standard enchants.

Fixes #1561
2013-10-22 09:57:13 -04:00
GJ
7e241e3993 Useless else statement. 2013-10-21 13:15:41 -04:00
GJ
bc51505150 More cleanup. 2013-10-21 08:31:35 -04:00
TfT_02
e0599a0dea Subtract XP with Hardcore mode
Adds #1529
2013-10-20 20:02:16 +02:00
TfT_02
d410251595 Changed kraken default behavior
It will no longer broadcast chat messages globally by default, as well as strike lightning on it's target. Instead it will spawn explosion effects.
2013-10-20 17:04:50 +02:00
TfT_02
810c74dc2a Fixed bug which prevented players from leveling up
Any affected players will get their levels back when they gain some
more XP in that particular skill.
2013-10-19 14:08:04 +02:00
TfT_02
100f2c7e56 Added a warning message if the server is running NoCheatPlus without CompatNoCheatPlus 2013-10-19 00:27:07 +02:00
TfT_02
e13e5295e8 Notify about updates if user is running dev1 and beta1 is available 2013-10-18 17:25:21 +02:00
TfT_02
b100b7bcc7 Gravity's Updater version 2.0 2013-10-18 16:58:12 +02:00
TfT_02
f4ff8518c2 Cleanup progress feedback 2013-10-18 16:43:37 +02:00
riking
dbd27b641e Give periodic status messages to the console in conversion 2013-10-18 16:40:44 +02:00
TfT_02
4a428a47af Fix bug with HolidayManager and some cleanup 2013-10-18 16:24:01 +02:00
GJ
3252137ed7 Update locale files. 2013-10-18 10:20:38 -04:00
GJ
68c4b99d1b Oops. 2013-10-18 10:16:51 -04:00
GJ
f282891d0a More info for armor errors. 2013-10-18 10:15:23 -04:00
GJ
7f4e3fedb3 Need different methods for mod files and regular files. 2013-10-18 10:12:55 -04:00
GJ
2042e0cdbd How did I not realize this would loop forever... 2013-10-18 10:02:11 -04:00
GJ
2662fee9fb ACTUALLY use the proper path. 2013-10-18 10:02:10 -04:00
TfT_02
e8e2dcff46 -levelsChanged instead of - levelsChanged 2013-10-18 15:26:15 +02:00
TfT_02
3b09012b35 Also use getServer() here as well 2013-10-18 15:26:14 +02:00
GJ
a774733af4 Use proper path 2013-10-18 09:23:10 -04:00
GJ
4a7e1e2b94 Update pom.xml to fix resource issues. 2013-10-18 08:54:07 -04:00
GJ
b8c1f868f5 Event updates 2013-10-18 08:54:06 -04:00
GJ
3f56a8fbcf Importing Bukkit.java is bad, always use getServer() instead 2013-10-18 08:54:05 -04:00
Bestle
d8e86d0fc7 Fix logic error in fireworkParticleShower
If a player is inside a vehicle, the y position of the spawned firework should be modified, not the x
2013-10-18 12:59:21 +01:00
TfT_02
e125700b43 Fixed Fishing ability "Shake" 2013-10-18 12:25:49 +02:00
t00thpick1
819a1c62ed Merge pull request #1550 from Bestle/master
Add missing ignoreCancelled checks - MERGE COMMIT HAHAHAHA
2013-10-17 16:38:38 -07:00
Bestle
4bc446e306 Add missing ignoreCancelled checks
If a plugin cancels a piston retract or extend event, mcMMO still considers that block or blocks to have moved.

This allow players to gain xp and double drops from blocks that they shouldn't. Checking for cancelled events fixes this.
2013-10-17 21:05:29 +01:00
TfT_02
7f2f15d88e Revert "Don't forget to include the mod files!"
This reverts commit be4736fffd.
2013-10-16 01:41:31 +02:00
TfT_02
be4736fffd Don't forget to include the mod files!
Fixes #1546
2013-10-16 01:38:09 +02:00
riking
b4f4de4628 Get all logs in Tree Feller, and optimize performance
Tree Feller has been shown, both anecdotally and with timings, to put a strain on the server, and therefore is worthy of the effort of optimization.
Prior to this change, on jungle trees, Tree Feller would take around 20-40 milliseconds to process a Jungle Tree after the JIT kicked in, and around 15-25 milliseconds for a normal tree.

Additionally, logs would be left up in the air for jungle trees.

After this change, Tree Feller takes 2-5 milliseconds on normal trees, and 10-15 milliseconds on jungle trees, and no logs are left up in the air.
2013-10-16 00:59:11 +02:00
TfT_02
b9c652ef2b This check shouldn't be inverted
Fixes #1545
2013-10-16 00:57:56 +02:00
GJ
bf4e8d43ea Because the entity that exploded might be null (or might not be TNT) 2013-10-15 13:10:29 -04:00
GJ
468fbdab56 SkillUtils cleanup, EventUtils creation
Move some functions in SkillUtils to more relevant locations.

Begin work on utility class to handle all event calls.
2013-10-15 13:03:33 -04:00
GJ
309dfd50cd Revert change to smoke particle handling
Have to do it this way, because not all block directions are valid for
smoke
2013-10-15 08:38:59 -04:00
riking
44e3e4d1e1 Localize several command results
Also don't nullcheck the null-guarded mcMMOPlayer in PartyManager
2013-10-14 20:48:36 +02:00
riking
476f426590 Remove RepairableManagerFactory until we actually need it
Let's hold off on the factory pattern until we actually offer choices.
2013-10-14 20:48:35 +02:00
riking
766f1f4127 Oh! So that's why it's never used here 2013-10-14 20:48:35 +02:00
riking
b3cf9bf839 When an error occurs updating the leaderboards, print out the current player name if possible 2013-10-14 09:53:42 -07:00
GJ
056f7cc93b Nicer handling of some particle effect code. 2013-10-14 11:29:25 -04:00
TfT_02
741f629ab8 Don't spawn fireworks under a boat (for real this time)
Fixes #1534
2013-10-14 17:07:15 +02:00
TfT_02
dd64c4008b Account for Master Angler config values in /fishing
Fixes #1537
2013-10-14 16:28:48 +02:00
TfT_02
3a5de8e2ce This should be on LOWEST 2013-10-14 09:28:16 +02:00
TfT_02
2d78c0738d Color party leader names only once 2013-10-12 20:50:42 +02:00
TfT_02
77617ebee2 Add bow to fishing treasures 2013-10-12 20:29:52 +02:00
TfT_02
67e9d9c535 Fishing TNT traps should not destroy blocks 2013-10-12 03:30:10 +02:00
TfT_02
800786111c Fix apostrophe issues
Fixes #1523
2013-10-12 02:41:13 +02:00
TfT_02
ed8197bd50 Remove level based bonus from Master Angler
Let's try this another way, instead of removing this passive ability all togheter I think it would be nice to keep the boat/biome catch rate boost. The level based boost was out of hand and counter-intuitive as it made leveling easier on high skill levels.
2013-10-12 02:41:13 +02:00
TfT_02
82f8c4ce36 Fishing Treasure Hunter overhaul 2013-10-12 02:41:13 +02:00
TfT_02
b1cf7d0348 Fire FakeBlockBreakEvent when using Hylian Luck
Fixes #1528
2013-10-11 23:47:42 +02:00
GJ
ae77313007 We forgot one...
Fixes #1527
2013-10-11 15:46:34 -04:00
TfT_02
49cbaad47f Clean up advanced.yml comments and keys 2013-10-11 16:22:30 +02:00
TfT_02
1d96ed72dc Move Acrobatics XP settings to experience.yml 2013-10-11 15:18:57 +02:00
TfT_02
ec378d046f Reformat advanced.yml making the keys consistent 2013-10-11 15:18:56 +02:00
GJ
a25dc24c6c No reason to have this many functions... 2013-10-11 15:18:56 +02:00
TfT_02
68eb51a3d0 Removed Shake_UnlockLevel config option
because it is no longer needed.
2013-10-11 15:18:56 +02:00
TfT_02
2eda3a9c83 Add extra tiers! Every ability now has 8 tiers 2013-10-11 15:18:55 +02:00
GJ
ad8e200a84 Make sure we update the blocks config after this too. 2013-10-09 11:45:49 -04:00
GJ
0c83bf2a80 Improve our drop handling. 2013-10-09 11:44:45 -04:00
GJ
6eaec5ffab We don't need this anymore. 2013-10-09 10:27:06 -04:00
GJ
8a2c5fb051 Check 0 first. 2013-10-09 10:26:51 -04:00
GJ
9485869014 Move these functions to SkillType. 2013-10-09 09:20:32 -04:00
GJ
e1bf55b077 Backup old mod configs & replace with new. 2013-10-08 13:10:09 -04:00
GJ
81140824e4 Backup and replace updated treasures.yml file. 2013-10-07 13:09:46 -04:00
GJ
d5545de81f Backup & replace the repair config files that have been updated. 2013-10-07 13:04:36 -04:00
GJ
8632baed27 No reason to handle this ourselves, Bukkit does it for us. 2013-10-07 11:54:23 -04:00
GJ
9aaea7e44f Fix old files if they exist. 2013-10-07 10:43:22 -04:00
GJ
c2f8f4d016 User data is now saved in flatfile, not FlatFileStuff 2013-10-07 10:33:14 -04:00
GJ
5131e74349 Save mod config files to "mods" rather than "ModConfigs", mirror directory structure inside the jar file. 2013-10-07 10:32:40 -04:00
GJ
3927427b5b Refactor all our repairable stuff into a special package. 2013-10-07 10:23:04 -04:00
TfT_02
4aef4c63fc Split the locale skill guides into seperate sections
This will make it easier for translators to keep up with translating our skill guides. Closes #560
2013-10-07 16:05:11 +02:00
GJ
fb4777e7f0 Added XP boost to Acrobatics when wearing Boots of Feather Falling.
Adds #1098
2013-10-07 09:53:32 -04:00
GJ
d8f3a54f9b Compiler throws warnings all over the place about our close methods, this one is no different. 2013-10-07 07:56:13 -04:00
GJ
de964a3a60 This naming bothers me. 2013-10-07 07:53:42 -04:00
t00thpick1
ce3bc07aa8 Reasonably sure this needs to be this way 2013-10-06 17:46:45 -04:00
TfT_02
5a6bb363cf Don't spawn fireworks under the player if they're in a vehicle 2013-10-06 12:08:22 +02:00
TfT_02
3f9c98d72e Update changelog & minor formatting fixes 2013-10-06 10:25:28 +02:00
riking
96b54387fe SQL database - split loadProfile to have retry flag
Instead of assuming that newUser() worked as intended, we cycle back around into the method.
This also removes the possibility of infinite loops from the writeMissingRows() code path.
2013-10-06 10:09:09 +02:00
riking
70eb67dd6a Flatfile loadProfile - place newUser() inside of try block
This fixes incorrect behavior in the edge-case where an IOException occurs when reading (but not writing) the flatfile database.
2013-10-06 10:09:09 +02:00
riking
77f9f40065 Do not save an un-loaded PlayerProfile 2013-10-06 10:09:09 +02:00
riking
14ae1a69c4 Attempt clean recovery from an unloaded PlayerProfile
This change should cause McMMOPlayer to create a graceful recovery when the database is temporarily unavailable.
When a McMMOPlayer is constructed and recieves an unloaded PlayerProfile, it schedules a task to re-attempt profile retrieval. This task can run for a maximum of 5 seconds, after which a second warning is printed indicating that it has given up (and a message given to the user).
2013-10-06 10:09:09 +02:00
riking
c9858dfd49 Do not mark a PlayerProfile as clean if it failed to save
DatabaseManager.saveUser() now returns a success value, which is used by PlayerProfile to determine whether or not it should be considered clean.
2013-10-06 10:09:09 +02:00
riking
f75fe3cc89 Potential fix for loss of data due to SQL connection dropping
The idea behind this change is to send a ping every hour, which is shorter than the driver's 'dead connection' threshold of 8 hours.

As a side effect, this also will fix a subset of the situations where the MySQL server is restarted.
2013-10-06 10:09:08 +02:00
TfT_02
c19ccbccac Use only 1 extra durability by default, instead of 2 2013-10-06 10:08:06 +02:00
TfT_02
2f90e533a5 Improve validation messages of treasures.yml 2013-10-06 09:51:33 +02:00
Kane York
0cd0919447 /mcconvert: Fix mismatched type in list.remove() call
The databaseTypes collection is a List<String>, so attempting to remove a DatabaseType object will have no effect.
2013-10-05 14:07:06 -07:00
TfT_02
e8b886fcc6 This check somehow got removed 2013-10-05 01:18:51 +02:00
GJ
b8e937a234 ALWAYS remove pots broken by swords. 2013-10-04 13:16:41 -04:00
GJ
eb2e0d3abf Fixed Hylian Luck not working at all.
Fixes #1508
2013-10-04 10:27:18 -04:00
GJ
3365da7f8d MCPC+ checks, notify server owners that they're missing out. 2013-10-04 09:50:49 -04:00
TfT_02
a0e37a4a09 I forgot to invert this check 2013-10-03 22:04:39 +02:00
GJ
5541c15753 Try/catch was stupid. 2013-10-02 09:07:30 -04:00
GJ
f87110749e ACTUALLY fix the NPE here. 2013-10-02 09:03:09 -04:00
GJ
a0ef0d5708 Check vanilla's maxDurability here as well, just to be safe.
Fixes #1504
2013-10-02 08:56:48 -04:00
TfT_02
2e2abcd645 Handle this nicer 2013-10-02 10:42:06 +02:00
TfT_02
6baf820afa Cleanup and formatting 2013-10-01 22:14:29 +02:00
Kane York
288287badf Add holiday celebration for the console 2013-10-01 22:06:51 +02:00
TfT_02
ca4feca073 Cleanup changelog.txt a bit 2013-10-01 15:09:45 +02:00
GJ
7c9356955e ACTUALLY handle SQL passwords (or other fields) with '#' in them properly. 2013-09-30 16:17:44 -04:00
GJ
57541ec233 This can never be null, and there's no reason to pass that as a variable. 2013-09-30 14:19:07 -04:00
TfT_02
9c6d1ce020 Fixing these infinite recursing methods
Oops, that was silly. Thanks @t00thpick1
2013-09-30 19:38:22 +02:00
TfT_02
c72ead9d0a Prevent breaking other plugins who use this API 2013-09-30 19:03:44 +02:00
TfT_02
4262a1b2a5 Added two more treasures to Excavation 2013-09-30 16:24:21 +02:00
TfT_02
eb589b6e78 Renamed some config options in the Commands section.
The following keys have been renamed:
* General => Generic
* p => partychat
* a => adminchat
2013-09-30 15:43:37 +02:00
GJ
98e5e53fda Ignore "#" in SQL passwords. 2013-09-30 08:36:32 -04:00
TfT_02
00918fbdc1 Change this back, getPlayerExact() is faster 2013-09-30 14:04:34 +02:00
TfT_02
5ad0f2c624 Do a little bit of localebending 2013-09-30 11:32:35 +02:00
TfT_02
babb9baa2b Handle joining disbanded parties properly 2013-09-30 11:22:15 +02:00
TfT_02
45143836e5 Fixed /party kick
Fixes #1499
2013-09-30 10:39:33 +02:00
TfT_02
ceacd7dc52 Fixed /party disband 2013-09-30 10:39:14 +02:00
TfT_02
6eb255632f Clean this up a little bit 2013-09-30 10:24:36 +02:00
TfT_02
3a37d0e092 Fixing an error due to confusingly named check
Refactored healthBarEnabled to healthBarPluginEnabled to avoid this
from happening again.
2013-09-29 23:57:13 +02:00
TfT_02
4c7fb1854d addRawXP should use float instead of int 2013-09-29 15:48:11 +02:00
TfT_02
763cff6898 Fixed a bug where Repair wasn't asking for confirmation 2013-09-28 19:46:47 +02:00
riking
fa34d06341 Clear child skill FamilyTree on reload 2013-09-27 15:46:19 -07:00
TfT_02
1ca53da0e2 Also try to count recipe ingredients regardless of repairMaterial
when the normal counting and the config value result in 0

Fixes #1484
2013-09-27 13:42:50 +02:00
TfT_02
57dfa00541 Fixed a NPE when an invalid repair material was entered
#1484
2013-09-27 10:46:54 +02:00
TfT_02
36ae84eada Update README.md 2013-09-26 23:06:07 +02:00
GJ
7f290504ad Set random jump strength for horses as well. 2013-09-26 10:43:45 -04:00
GJ
92b4be9a01 We don't use these parts of the updater. 2013-09-26 09:39:13 -04:00
GJ
8cb8dea642 Move Updater to independent package due to custom changes being overwritten by other plugins using the updater. 2013-09-26 09:37:31 -04:00
GJ
a63f745c73 Add custom mobs automatically as they're killed. 2013-09-26 15:06:36 +02:00
GJ
4a0fee5796 Use class names to better find custom entities. 2013-09-26 15:06:21 +02:00
GJ
cf90236e57 Redo blocks.yml
** YOU WILL NEED TO UPDATE THIS FILE **
2013-09-26 15:06:21 +02:00
GJ
fc6c7bb1de Rework custom tool config.
** YOU WILL NEED TO UPDATE YOUR CONFIG TO THE NEW FORMAT **
2013-09-26 15:06:21 +02:00
GJ
1b92131ce9 Added Carrot on a Stick, and Flint & Steel to repair.vanilla.yml 2013-09-26 14:58:31 +02:00
GJ
792ecd6aad Rework armor.yml to take item names instead of IDs in advance of 1.7 changes.
** YOU WILL NEED TO REDO YOUR armor.yml FILE **
2013-09-26 14:58:30 +02:00
TfT_02
933b6f278b Disable partial name matching for offline players by default
#1482
2013-09-25 14:26:24 +02:00
TfT_02
45dfc13ebd Match playernames using OfflinePlayers instead
Fixes #1482
2013-09-24 11:40:53 +02:00
dddeeefff
1254ab232a Add randomized Horse appearance to Call Of The Wild 2013-09-23 22:29:02 +02:00
dddeeefff
b49e56c857 Added missing COTW message when there are too many Horses nearby 2013-09-23 22:29:01 +02:00
TfT_02
d5bd9a1693 Fixed some small mistakes in CommandUtils 2013-09-23 20:22:41 +02:00
GJ
9b60cd96f9 Don't need these keys with the new format either. 2013-09-23 10:33:50 -04:00
TfT_02
0a05ed98d0 Updated to the new format! 2013-09-22 23:28:09 +02:00
TfT_02
6a3a564bd4 Use cooldownExpired here as well. 2013-09-22 23:28:09 +02:00
TfT_02
3828f78480 Fixed respawn cooldown checks
Thanks @Riking for pointing this out!
2013-09-22 23:28:08 +02:00
Travis Ralston
239d7e33cb Revert "Metrics be dead"
This reverts commit 0a9fd4a92e.
2013-09-22 12:33:01 -06:00
TfT_02
b8c479549c Disable our healthbars when the plugin "HealthBar" is found
Adds #1477
2013-09-22 16:55:02 +02:00
t00thpick1
0a9fd4a92e Metrics be dead 2013-09-20 22:23:38 -04:00
TfT_02
4c96161acb Don't throw errors about dropped columns 2013-09-20 21:39:20 +02:00
TfT_02
ce7a7a31a7 A bit of cleaning up 2013-09-20 00:15:22 +02:00
TfT_02
834e26b44e Minor improvements 2013-09-19 21:47:12 +02:00
GJ
f71b302f6f Don't need this anymore. 2013-09-19 15:19:16 -04:00
GJ
566a381e95 Remove debug message, use recipe method for salvage. 2013-09-19 15:17:19 -04:00
GJ
5d7d779a49 Changed format of repair.vanilla.yml. **YOU WILL NEED TO UPDATE YOUR FILE TO THE NEW FORMAT** 2013-09-19 11:02:47 -04:00
GJ
59a35b170c Oh yeah, that's why. 2013-09-18 15:42:54 -04:00
GJ
14eb473355 Why we were making this so complicated, I'll never know. 2013-09-18 14:55:17 -04:00
GJ
a8e23e08ee Remove HudType from Flatfile records. 2013-09-18 11:54:23 -04:00
GJ
15f5dcf860 Removed HudType references from the database. 2013-09-18 09:57:28 -04:00
GJ
9be9908a22 Remove unused imports. 2013-09-18 09:39:54 -04:00
GJ
446b6c107b Remove empty lines from FlatFile - the plugin will not enable if these are present. 2013-09-18 08:34:47 -04:00
GJ
5a3f8ad15f Add COTW info for horses to the Taming command. 2013-09-17 14:13:11 -04:00
GJ
3a2c6a0827 We can have ' again! 2013-09-17 14:09:39 -04:00
GJ
e865acd871 Fix locale parsing issues.
Fixes #1463
2013-09-17 14:03:00 -04:00
TfT_02
4a0e1ba444 Fix a small boo boo 2013-09-16 23:26:06 +02:00
GJ
1a88b0b944 Better way to handle ink sacks, allows for dropping of multiple types. 2013-09-16 12:48:08 -04:00
GJ
e0592b3f62 Don't try to ever pull the mcMMOPlayer here.
Fixes #1466
2013-09-16 12:12:31 -04:00
GJ
1ec55c2d7e Remove the last bits of Spout from our code. 2013-09-16 12:05:39 -04:00
GJ
6427a7dcdf Fix issues with Skulls in treasures.yml 2013-09-16 11:45:57 -04:00
TfT_02
7bac0e2ca5 Dropped SpoutPlugin support
Because SpoutPlugin is not being updated to 1.6.x and mcMMO 1.4.07 does
not support any CB version below 1.6.x SpoutPlugin support is no longer
needed.
https://blog.spout.org/minecraft-1-6-and-the-legacy-finale/
2013-09-16 16:48:42 +02:00
GJ
e8bc2475c3 Add sound for level-up even when not using Spout. 2013-09-16 09:52:09 -04:00
GJ
816b08b14a Make sure the attacker is a valid player too.
Fixes #1464
2013-09-16 08:53:55 -04:00
GJ
64e1448782 Added ability to give items names & lore through treasures.yml.
Adds #1419
2013-09-15 21:09:32 -04:00
TfT_02
ae0a27991b Register when the config files were last updated 2013-09-15 23:10:35 +02:00
TfT_02
f1b82dcbe6 Fixed regex of version string parsing 2013-09-15 23:09:06 +02:00
TfT_02
bfbd50d8f4 Fix another wrong default Material name 2013-09-15 22:52:59 +02:00
GJ
de07316261 Just in case there's something broken in the file. 2013-09-15 16:49:41 -04:00
GJ
eae196c6a1 Fix wrong default material name. 2013-09-15 16:48:05 -04:00
GJ
8af41975ff Don't keep trying to load if they've got an old file. 2013-09-15 16:09:41 -04:00
GJ
957bbbc9b2 Warn if treasures.yml is outdated. 2013-09-15 15:59:29 -04:00
TfT_02
17faf1561f Refactor to getMaxLength 2013-09-15 21:45:16 +02:00
TfT_02
ec6419f0ff Fix formatting of the new Updater 2013-09-15 21:45:16 +02:00
GJ
f6e60bebcc Fix dropping sideways logs and leaf blocks.
Fixes #1460
2013-09-15 15:09:48 -04:00
GJ
797ac20567 Added Horses to the "Shake" ability.
Witches no longer drop water bottles from Shake, since they no longer drop them in Vanilla.
Changed format of treasures.yml.

**YOU WILL NEED TO UPDATE YOUR FILE TO THE NEW FORMAT**
2013-09-15 01:07:04 -04:00
GJ
3bc029a0de Make Updater work with our versioning setup. 2013-09-13 11:46:55 -04:00
GJ
4eba33a1c6 Use doubles in config.yml where appropriate. Change item IDs to item names
in light of upcoming Minecraft changes that will remove access to item
IDs.
2013-09-13 09:52:52 -04:00
GJ
800a452d62 Remove use of deprecated function. 2013-09-13 09:11:34 -04:00
GJ
177604e94a Condense this into one function. 2013-09-13 08:11:32 -04:00
GJ
088015dd4d Switch to H31ix's updater for security reasons. 2013-09-13 00:59:07 -04:00
t00thpick1
0f2d0aee5f Fix NPE on /addxp 2013-09-12 21:21:00 -04:00
t00thpick1
1004e2a32b These duplicate checks are handled in config validation. 2013-09-12 20:52:26 -04:00
t00thpick1
5c2b523f7a Allow less than one percentages for hardcore losses 2013-09-12 20:52:26 -04:00
GJ
de42063171 Fixed a bug where Kraken messages couldn't be disabled.
Fixes #1174
2013-09-12 15:53:43 -04:00
GJ
a49d373af0 Back to active development. 2013-09-12 14:28:51 -04:00
GJ
0095f7f9c7 Update pom.xml for 1.4.07 beta release (finally!) 2013-09-12 14:20:18 -04:00
GJ
f53820e4de Update changelog. 2013-09-12 14:18:52 -04:00
GJ
25e4700ef9 Changed various values to double in advanced.yml for the sake of consistency. 2013-09-12 14:18:13 -04:00
GJ
58c7dcb705 Fix issues with double damage, double death messages, and other damage oddities.
Fixes #1450
2013-09-12 11:52:34 -04:00
GJ
44626c36a9 Nerfed Archery damage to eliminate constant one-hit kills 2013-09-11 11:43:06 -04:00
TfT_02
cfd5bfe2c4 Deal skillShot bonus damage properly 2013-09-11 17:08:59 +02:00
t00thpick1
f7928787dc Skill shot should be after deflect check 2013-09-11 10:17:24 -04:00
GJ
d6630a0eb5 Prevent multiple events from being fired. 2013-09-11 08:51:51 -04:00
GJ
af39e84aef Actually remove /mmoupdate, fix usage strings for /mcconvert, fix tab completion
Fixes #1451
2013-09-10 15:47:47 -04:00
TfT_02
93fe2ff504 Cleanup our imports 2013-09-10 15:28:11 +02:00
GJ
b42f2d4073 Refactor, plus store these values rather than checking them twice. 2013-09-10 08:38:06 -04:00
TfT_02
c5c231920d Cleaning up the changelog and comments 2013-09-09 23:19:59 +02:00
GJ
89ddf8c4fa Fixed issues with dealing damage to Entities 2013-09-09 20:41:06 +02:00
GJ
71ab678945 Fix bug where mcMMO damage wasn't awarding XP.
Fixes #1400
2013-09-09 12:00:37 -04:00
GJ
14daee3b1b Fixed a bug where squid were not awarding XP. 2013-09-09 10:46:26 -04:00
GJ
d2bbbb0fe7 More deprecation fixes. 2013-09-05 16:36:02 -04:00
GJ
fd8d9b02a9 Begin trying to remove newly-deprecated "magic numbers" 2013-09-05 14:55:08 -04:00
GJ
a639a37637 Add per-skill XP boost perks.
Fixes #1412
2013-09-03 09:24:58 -04:00
GJ
7eec53d621 Added Horses to Taming. 2013-08-30 14:25:46 -04:00
GJ
7523afffb5 Updated permissions for more control over Call of the Wild. 2013-08-30 13:50:34 -04:00
GJ
2c8b9334b6 THis should stay false. 2013-08-28 13:13:34 -04:00
GJ
d41ccf9072 Don't loop forever if not connected. 2013-08-28 13:12:24 -04:00
GJ
c98d298cf1 Actually make use of the checkConnected calls. 2013-08-28 11:44:58 -04:00
GJ
73d0b377ae Reduce code duplication. Also verify that our target is alive before trying to damage them.
Fixes #1403
2013-08-28 11:29:30 -04:00
TfT_02
df29306a1f Cleanup Javadocs and fix StackOverflowError 2013-08-26 22:09:29 +02:00
GJ
435522415d This is better too. 2013-08-26 12:20:56 -04:00
GJ
a17d1d3a2f More cleanup to PartyManager. 2013-08-26 11:55:35 -04:00
GJ
94a5bef62c Cleaning up PartyManager 2013-08-26 08:39:24 -04:00
GJ
2cd9a5658e Remove unused import 2013-08-26 08:39:24 -04:00
TfT_02
3c5bd3cedd Fix a NPE in MobHealthDisplayUpdateTask
Band aid for broken isValid() function.
Fixes #1396
2013-08-25 17:35:41 +02:00
GJ
8e02b57369 Align these. 2013-08-23 14:52:21 -04:00
GJ
935b8b7bc4 Update localization files. Adds Estonian translations for some strings. 2013-08-23 14:29:01 -04:00
TfT_02
9c54f8fd11 Fix Javadocs issues 2013-08-23 20:14:13 +02:00
GJ
6bfc1b84de Let's do this the right way. 2013-08-23 20:14:13 +02:00
TfT_02
59f545d5ce Fixed FakeEntityDamageByEntityEvent not getting fired 2013-08-23 20:14:13 +02:00
GJ
23983422e0 Cleanup & remove code duplication. 2013-08-23 14:08:16 -04:00
TfT_02
956bf2d763 Added McMMOPlayerLevelDownEvent and McMMOPlayerLevelChangeEvent 2013-08-23 19:54:30 +02:00
TfT_02
964b2636fb Move experience related settings from config.yml to experience.yml 2013-08-23 19:37:44 +02:00
GJ
490bc195d8 We don't care about teleports to the same spot. 2013-08-23 08:58:23 -04:00
TfT_02
0ce41150c6 Vampirism can now be enabled without having Skill Death Penalty enabled 2013-08-22 22:54:05 +02:00
TfT_02
0455416dec Reorganized Hardcore locale strings 2013-08-22 22:54:05 +02:00
TfT_02
a6e7febf77 Hardcore mode can now be toggled for each skill individually 2013-08-22 22:54:05 +02:00
GJ
ede0757d83 Remove /mmoupdate and replace with /mcconvert database 2013-08-22 22:33:06 +02:00
GJ
8282d84b16 Validate, and nicer loading. 2013-08-22 22:22:19 +02:00
GJ
223649ec28 Formatting and localizing. 2013-08-22 22:22:19 +02:00
TfT_02
68e433b3b7 Added new ExperienceFormula config and /mcconvert command 2013-08-22 22:22:19 +02:00
GJ
1a51b93ec9 Another quick check to avoid issues with NPCs. 2013-08-22 14:45:30 -04:00
GJ
c31ffa5ab4 Remove unused import. 2013-08-22 13:51:01 -04:00
TfT_02
ca6bee07ea Fix formatting 2013-08-22 00:37:48 +02:00
TfT_02
9acaa7b126 We're expecting a null object here as well. 2013-08-21 16:48:08 +02:00
gmcferrin
2bae937b28 Don't throw a warning if we're expecting a null object. 2013-08-21 14:20:12 +00:00
TfT_02
51bf989418 Counter Attack now only activates when the player is blocking
Closes #1018
2013-08-20 23:23:49 +02:00
GJ
07dd460d78 Validate in a seperate function. 2013-08-20 15:51:12 -04:00
GJ
045d74fb9d These were basically the same function. 2013-08-20 15:15:42 -04:00
GJ
c8c76f4174 Put this function in a better place. 2013-08-20 15:12:38 -04:00
GJ
83c4d09093 Fix formatting 2013-08-20 15:08:10 -04:00
GJ
50ef8d9610 Improvements to mcMMOPlayer lookup. 2013-08-20 14:10:49 -04:00
GJ
98c6abad36 No reason to cast here. 2013-08-19 15:14:33 -04:00
GJ
62146480db Hardcoding this is a bad idea. 2013-08-19 15:12:08 -04:00
TfT_02
6518d192ec Improved partial name matcher
Fixes #1164
2013-08-19 10:37:04 +02:00
TfT_02
3fe9cfee74 Slightly improved update checker feedback 2013-08-18 18:04:20 +02:00
T00thpick1
d495054eb5 Config Validation 2013-08-18 02:42:13 -04:00
T00thpick1
ce80636141 Min value for IronArm configurable 2013-08-18 02:38:57 -04:00
TfT_02
fe93be66ad Changed the color of party leader names in Party chat 2013-08-17 13:53:46 +02:00
TfT_02
1f712063bf Admin and Party chat prefixes are now customizable
Closes #578
2013-08-17 12:18:29 +02:00
TfT_02
560c3860b4 Fixed bug which allowed players to bypass fishing's exploit prevention
Fixes #1319
2013-08-17 10:11:46 +02:00
TfT_02
36f1a2d78a Changed the way Repair hands out XP
Closes #373
2013-08-15 20:50:19 +02:00
TfT_02
3ddd8d2056 Added API to get a players rank on the leaderboards 2013-08-13 09:37:45 +02:00
TfT_02
5441fcc374 Fix broken Dodge_DamageModifier config node
Also fix a derp with the validation of
Arcane_Forging.Keep_Enchants.Chance
2013-08-11 15:55:25 +02:00
TfT_02
1d83784820 Arcane Forging downgrade chance can also be 0
Fixes #1367
2013-08-11 09:26:02 +02:00
TfT_02
fb5bab6e92 String values are compared using '.equals()' not '==' 2013-08-10 22:24:13 +02:00
TfT_02
90fcf35c34 Javadocs cleanup 2013-08-10 20:10:45 +02:00
TfT_02
4ff6b5fbc7 Don't try to register listeners when mcMMO was disabled 2013-08-10 19:33:21 +02:00
TfT_02
ead1398132 Super Breaker & Giga Driller now use more durability
A configurable amount is added to the vanilla durability loss.

Use `Abilities.Tools.Durability_Loss` to disable (set to 0) or set it
to -1 for no durability loss while using abilities. Closes #1363
2013-08-09 22:21:45 +02:00
TfT_02
6330c4a69e Move the noErrorsInConfig check to Misc 2013-08-09 19:10:03 +02:00
TfT_02
dcc18049a1 Removed Abilities.Tools.Durability_Loss_Enabled
Set Abilities.Tools.Durability_Loss to 0 to disable instead.
Addresses #1357
2013-08-09 18:13:22 +02:00
TfT_02
fcb8909a54 Kick interval can be disabled with '-1'
Fixes #1356
2013-08-09 13:36:04 +02:00
TfT_02
37e3bfe7d9 Fixed formatting 2013-08-07 19:58:49 +02:00
riking
d61b837dcf Implement checkStructure() 2013-08-07 19:49:00 +02:00
riking
f079e22789 Use provided last-saved information for purge.
The new method, OfflinePlayer.getLastPlayed(), is used as a backup for when the data is unparsable.
TODO check if StringUtils is available here
2013-08-07 19:45:27 +02:00
TfT_02
1f53c62ced Added McMMOPlayerDeathPenaltyEvent
Called when a player dies and mcMMO tries to invoke Hardcore mode or
Vampirism
2013-08-07 01:21:52 +02:00
TfT_02
9fb4e0988b Save / load party itemshare category states.
Closes #1336
2013-08-07 00:38:17 +02:00
TfT_02
d8bbe459b9 Fix minor Javadoc errors 2013-08-07 00:15:51 +02:00
TfT_02
8bd7526b43 String values are compared using '.equals()' not '==' 2013-08-06 21:48:09 +02:00
TfT_02
24b1485555 Validate advanced.yml settings 2013-08-06 21:37:19 +02:00
TfT_02
7683dfc436 Move validation to proper location 2013-08-06 21:27:16 +02:00
TfT_02
ccbffca278 Validate config.yml settings 2013-08-06 21:17:14 +02:00
Glitchfinder
aeaab43f44 Fixing a multitude of reported NPEs. 2013-08-04 12:15:01 -07:00
Glitchfinder
a2450d2d07 If a variable can be null, check it before using it. 2013-08-04 11:48:44 -07:00
T00thpick1
c85bd8ab70 One more last try 2013-08-04 11:56:37 -04:00
T00thpick1
3f6bce0fc6 One last try 2013-08-04 11:51:34 -04:00
T00thpick1
e566b20e2b This might be important 2013-08-04 11:38:52 -04:00
T00thpick1
f37a7d759a Hack around nms bug 2013-08-04 11:34:04 -04:00
T00thpick1
d1341b0be0 Would help if I actualized the value... Fix dupe bug for realz 2013-08-04 11:05:53 -04:00
T00thpick1
4ea3d690db Fix Dupe bug...... why was this overlooked? 2013-08-03 11:37:29 -04:00
TfT_02
d5dc9895e4 Move Blast Mining activation check to MONITOR priority
Fixes #1331
2013-08-02 21:11:58 +02:00
Glitchfinder
b1fc72e8a9 When a variable can be null, check it before using it. Fixes #1308. 2013-08-01 08:47:14 -07:00
GJ
7479a02220 Update changelog. 2013-07-30 15:23:32 -04:00
GJ
d1bf48ad79 Fix bug where teleport location was never reset if warmup was set to 0
for Chimera Wing.

Fixes #1323
2013-07-30 15:20:18 -04:00
GJ
a345737b8b Add more detailed error messages on SQL connection failure.
Fixes #1322
2013-07-30 15:09:22 -04:00
GJ
c501ebb357 Clean up after our experience commands. Fixes #1324 2013-07-30 14:47:11 -04:00
GJ
15e0570a8c Else if > if 2013-07-29 08:45:30 -04:00
GJ
09e77c8c94 Move break event to the initial check. 2013-07-29 08:29:10 -04:00
TfT_02
f5c58f3679 Added config option for Acrobatics teleport cooldown,
also updated the changelog.
2013-07-29 00:57:43 +02:00
GJ
ddcbe64db6 Fix some possible issues with handler priority, more javadoc work. 2013-07-28 13:55:48 -04:00
GJ
c5137eb884 Begin work on cleaning up our listeners and their Javadocs. 2013-07-25 14:52:21 -04:00
GJ
e073eca458 Validation is important. 2013-07-24 20:29:32 -04:00
GJ
78f2e0a064 Check the range in a seperate function 2013-07-24 14:13:58 -04:00
TfT_02
df2defe969 Added extra settings for Call of the Wild
* Requested in issue #910
* Adds a setting to configure the range check
* Adds a setting to summon multiple pets with one summon
2013-07-24 20:01:26 +02:00
TfT_02
6d4a2feaae Slighty changed a Green Thumb string
Make this fit on one line in the chat window
2013-07-24 20:01:26 +02:00
GJ
8939fc09b3 Patch potential exploit relating to teleportation and acrobatics. 2013-07-24 13:57:53 -04:00
GJ
e0e574c19e Fix a potential issue with PTP and Chimera Wing teleportation cooldowns. 2013-07-24 13:50:33 -04:00
GJ
02126c93b9 This function is never used. 2013-07-24 12:35:28 -04:00
GJ
37671bad9a We already have the mcMMOPlayer here. 2013-07-24 12:30:02 -04:00
TfT_02
0e8ce005d7 This is also a change 2013-07-24 16:10:26 +02:00
GJ
584a225d6e Only get the mcMMOPlayer once. 2013-07-24 09:37:45 -04:00
riking
736359056f Add checkConnected() calls to re-establish dead SQL connections 2013-07-23 15:03:19 -07:00
TfT_02
bf2e527e72 Fixed NPE with Beast Lore
Fixes #1289
2013-07-22 11:35:48 +02:00
TfT_02
be7992d541 Disable all abilities when a player quits
Fixes #1295
2013-07-22 11:25:56 +02:00
TfT_02
435eb7f8b9 Added new experience curve option 2013-07-21 23:14:42 +02:00
GJ
001f1dbd3c Fix issue with truncating things that don't need truncating. 2013-07-17 13:45:31 -04:00
GJ
7b5372a985 Temporary fix for MCPC+ entity issues. This change will be reverted
after the fix is made in MCPC+.

Fixes #1197
2013-07-17 10:29:42 -04:00
GJ
1647ef4fae Fixed issue where locale strings could cause the scoreboard header to be
longer than 16 characters.

Fixes #1278
2013-07-17 08:18:54 -04:00
GJ
ee86f8244f Put ShareMode in its own class. 2013-07-15 09:56:45 -04:00
GJ
e518b58b23 Better way to do locale strings there. 2013-07-15 09:48:14 -04:00
GJ
5af1164b5c Tweak ShareHandler a bit. 2013-07-15 09:40:07 -04:00
GJ
c9aba059e2 Don't provide direct access to the players map. 2013-07-15 09:14:23 -04:00
GJ
dc9469c0cc Refactor to match standards set for where datatypes should be located. 2013-07-15 08:44:13 -04:00
TfT_02
696e82e622 Add missing Axes locale string
* Somehow, the message notifying a player that he was struck by Skull
Splitter wasn't in the locale files anymore.
 * Re-added this string and renamed it.
 * Fixes #1271
2013-07-15 13:18:13 +02:00
TfT_02
18a5ec73d7 Fixed Level up announcement
Fixes #1270
2013-07-14 10:58:51 +02:00
TfT_02
83ee8dd3f8 Update README.md
* Updated the about section so its similar with BukkitDev
 * Updated required libraries list, we're using EMetrics instead of Metrics
2013-07-11 20:53:35 +02:00
GJ
04224b309a Add snow to excavation. No treasures will drop from snow by default,
but they can be added to the treasures.yml file by specifying

"Drops_From:
	Snow: true"

Adds #1229
2013-07-11 14:41:23 -04:00
GJ
01a1cf5765 Update changelog. 2013-07-11 13:22:44 -04:00
GJ
8fdf4042bb Tweaked for readability. 2013-07-11 13:22:14 -04:00
GJ
621969459a Use profile instead of mcMMOPlayer 2013-07-11 13:19:04 -04:00
T00thpick1
6fe1c85592 Save on logout 2013-07-11 13:16:51 -04:00
T00thpick1
79346d92d7 Only save on changes 2013-07-11 13:16:42 -04:00
GJ
24ceeb626b Updated localization files 2013-07-11 13:03:38 -04:00
GJ
68727496ad Useless casting and elses. 2013-07-11 12:49:01 -04:00
GJ
d07b67b5bf Health and damage are now doubles, not ints. 2013-07-11 12:43:36 -04:00
GJ
4dc9c97978 Build from LATEST again. 2013-07-11 12:26:31 -04:00
GJ
99916f99fd Back to new development 2013-07-11 12:25:21 -04:00
GJ
4a5307f47b New 1.4.06 release before work starts on adding new features from 1.6 2013-07-11 12:09:24 -04:00
GJ
69aead58a7 Using getPlayerExact is faster. 2013-07-08 19:15:44 -04:00
T00thpick1
f0dcfb0346 Temporary for building for old peoples 2013-07-02 12:48:35 -04:00
T00thpick1
c85d52e594 Make Riking's stuff work 2013-07-02 12:42:09 -04:00
Travis Ralston
4342abca3d Update EMetrics version to use 0.0.5-SNAPSHOT (MCStats R7) 2013-07-01 17:11:58 +02:00
T00thpick1
11e4ff34d6 Flatfile repair 2013-07-01 02:36:21 -04:00
Kane York
f118ac14ca Specify returning of generated keys before using them
This is a herp derp fix
2013-07-01 00:35:07 -04:00
T00thpick1
f5eb7a10de Only set custom class when valid class 2013-07-01 00:34:54 -04:00
T00thpick1
36b09421e8 These should all be 0 too, for consistancy 2013-06-29 23:42:28 -04:00
T00thpick1
d6b39a11e7 0 is nonexistant, not -1 2013-06-29 23:41:08 -04:00
riking
23729f45ee Pull changes from dev-dbman (commit f63c5e3) 2013-06-28 15:02:58 -07:00
T00thpick1
27d7b73e57 Pretty sure this should be Fake 2013-06-28 16:22:55 -04:00
TfT_02
af60f08a8b Localize the ScoreboardManager
Closes #1232
2013-06-28 19:17:39 +02:00
TfT_02
c19d3fd068 Fixed bug with Ice Fishing which allowed players to break protected blocks
Fixes #2074
2013-06-28 14:06:54 +02:00
TfT_02
0f8312dd5e Minor cleanup 2013-06-28 14:06:13 +02:00
TfT_02
1edb11cedf Disable mob healthbars for boss mobs!
Fixes #1210
2013-06-28 13:36:48 +02:00
TfT_02
6fea7c8d74 Update the changelog: Fixed update check 2013-06-27 22:23:09 +02:00
riking
a4a1ba4331 Make UpdateChecker run asynchronously and not block startup
Closes #1049
2013-06-27 09:48:39 -07:00
TfT_02
de46277bea Realized that it wasn't only happening in the Nether 2013-06-24 17:10:39 +02:00
TfT_02
6d7d811814 Fixed bug with Ice Fishing in the Nether
Fixes  #1218
2013-06-24 16:25:49 +02:00
GJ
98b98256b7 Make our oldUserRemover actually work... 2013-06-13 12:23:58 -04:00
GJ
abd389f4de Try to speed up our PartyKickTask a bit. 2013-06-13 12:18:18 -04:00
GJ
602956a555 Fix duplicate prefix sending with party chat & logging. 2013-06-13 11:10:46 -04:00
GJ
8d0601babc Fix bug where all ranks less than 10 show as 0 with /mctop. 2013-06-13 10:56:46 -04:00
GJ
050be563bf Less magic numbers. 2013-06-12 19:26:09 -04:00
GJ
965dbda101 Clean up some stuff with our DATS. 2013-06-12 19:20:05 -04:00
GJ
f2b2cd9cc0 Oops. 2013-06-12 15:59:51 -04:00
GJ
3a78e1b487 More code duplication removal. 2013-06-12 15:56:42 -04:00
GJ
db637f0bc9 Remove more code duplication. 2013-06-12 15:41:26 -04:00
GJ
b15f1dde28 We don't need that potato. 2013-06-12 15:15:56 -04:00
GJ
28a78d820a Tidy up our InventoryListener. 2013-06-12 15:10:43 -04:00
GJ
a1792fe125 We were calling deflect twice. Also made individual functions for each
type of combat.
2013-06-07 15:47:00 -04:00
T00thpick1
3f7b17961f Reset mob healthbars on death to avoid conflicting with loot plugins 2013-06-07 15:46:59 -04:00
GJ
0ea07d4bc7 Fixed bug where spawned arrows could throw
ArrayIndexOutOfBoundsException. Fixes #1171
2013-06-07 15:46:59 -04:00
GJ
190b7ee1f5 ChatManagers... 2013-06-07 15:46:58 -04:00
GJ
4ff4271da2 These should be protected. 2013-06-07 15:46:57 -04:00
T00thpick1
8705974e08 Use a single manager to handle our databases. 2013-06-07 15:46:57 -04:00
TfT_02
de0487d16f This should make it work properly 2013-06-07 15:46:56 -04:00
TfT_02
fc0c386ecb Fixing this as pointed out by Riking 2013-06-07 15:46:55 -04:00
TfT_02
86db4251a2 Check visibility before range 2013-06-07 15:46:55 -04:00
TfT_02
effe5ec305 We were deprecating these kind of permission nodes 2013-06-07 15:46:54 -04:00
TfT_02
8fb92292bd Move adding users to UserManager from onLogin to onJoin 2013-06-07 15:46:54 -04:00
TfT_02
375fa4f75c Added permission node to prevent inspecting hidden players 2013-06-07 15:46:53 -04:00
TfT_02
da25b02e0a Only set the item in hand null if it's actually a fishing rod 2013-06-07 15:46:53 -04:00
GJ
d43ae17bd2 Tweak a few things on the UpdateChecker. 2013-06-07 15:46:52 -04:00
Kane York
f81a763d6c Use finally to close the update checker stream 2013-06-07 15:46:52 -04:00
Kane York
385f8ca0b3 Reduce code duplication in ExperienceAPI 2013-06-07 15:46:46 -04:00
GJ
0ba4bc25c7 Use player objects instead of names - should be more efficient and less
buggy.
2013-05-28 13:33:20 -04:00
GJ
b0eb4b93a8 Cleaner way to avoid salvaging chainmail. 2013-05-28 12:59:10 -04:00
GJ
54f135aebd We're checking this twice and shouldn't be. 2013-05-28 12:53:12 -04:00
GJ
10e369f9c5 Increased auto-fishing detection. 2013-05-28 12:42:39 -04:00
TfT_02
1ae9b0f4d2 Animals can also have the "Spawned Entity" tag 2013-05-26 17:55:24 +02:00
T00thpick1
198ee6a7ed I think this is case sensitive 2013-05-26 11:51:42 -04:00
TfT_02
2414ddf485 Fix broken Tree Feller
Fixes #1139
2013-05-25 14:45:24 +02:00
GJ
2cd52db8c9 The ; is important. 2013-05-22 22:30:40 -04:00
GJ
5e00636761 And a little more... 2013-05-22 22:30:09 -04:00
GJ
a82cc9609b Cleaning up a bit. 2013-05-22 22:13:40 -04:00
T00thpick1
45c6c20ccd Null parties! Hurray! 2013-05-22 21:20:35 -04:00
GJ
7a61f55e49 Remove some code duplication in our ShareHandler. 2013-05-22 17:22:06 -04:00
GJ
aa0b77a64c Updates to our parties. 2013-05-22 13:02:26 -04:00
GJ
030c8e59d7 The other way leaks memory like a sieve. 2013-05-22 00:01:19 -04:00
GJ
f21fbe2d40 Make repair & salvage respect the sneaking settings. Fixes #1108 2013-05-21 22:34:06 -04:00
GJ
9a5f4b638f Little more cleaning. 2013-05-21 14:15:28 -04:00
GJ
9aa49a09da Little more cleanup. 2013-05-21 14:03:00 -04:00
GJ
bf8945ac59 Try to clean CombatUtils a bit... 2013-05-21 13:36:44 -04:00
GJ
d9926bab4e Try to clean up our poor EntityListener... 2013-05-21 13:27:52 -04:00
GJ
38ba2c21e5 Back to normal development. 2013-05-21 12:22:11 -04:00
GJ
a48fb30edf New beta! 2013-05-21 12:20:50 -04:00
GJ
92ec04bd46 Better boolean handling. 2013-05-21 11:44:16 -04:00
GJ
0b6372a6ea Don't run these calculations twice. Also, pretty sure one of these was
bugged.
2013-05-21 11:41:39 -04:00
GJ
4f8b66f94d Clean up our block listener some. 2013-05-21 11:11:55 -04:00
GJ
0c52b3016c We've got these functions, might as well use them. 2013-05-21 10:02:09 -04:00
GJ
a2f80569e3 Fire McMMOPlayerLevelUp events for our experience commands, when
applicable. Fixes #921
2013-05-21 09:31:25 -04:00
GJ
87df536a1f Only check for kraken if you're actually fishing. 2013-05-21 09:14:54 -04:00
T00thpick1
12e70490d8 Cooldowns messages need to be affected by perks too 2013-05-20 22:35:34 -04:00
TfT_02
23b1518dc0 More formatting :) 2013-05-20 17:28:02 -04:00
T00thpick1
6dbf2e0d95 FishingTreasureEvent, FishingShakeEvent and MagicHunterEvent 2013-05-20 17:27:59 -04:00
GJ
60304e9643 Because Minecraft does stupid things with "/" in the chat.
Fixes #994
2013-05-20 08:56:02 -04:00
GJ
614557e2fa It'd be nice if Ice Fishing actually worked. 2013-05-20 08:07:39 -04:00
TfT_02
e312e95aed Refactor to a more descriptive name,
also fixes a small typo.
2013-05-20 10:55:17 +02:00
t00thpick1
2ee919b51f Update gravatar 2013-05-19 18:18:55 -03:00
T00thpick1
22f6ae858b Update inventories after chimera wing 2013-05-19 16:13:19 -04:00
T00thpick1
3c3b4af2c4 No salvaging chainmail - FIXES 1118 2013-05-19 12:55:18 -04:00
T00thpick1
feb0d1fe5d Things that should never happen, but are. 2013-05-18 22:15:32 -04:00
TfT_02
2d66b8ed12 Cleanup - fixing various formatting issues 2013-05-18 22:41:42 +02:00
TfT_02
483f348403 Fixed bug with Blast Mining where the Ability refreshed message was being send too early 2013-05-18 22:27:17 +02:00
TfT_02
a8a5100f58 Update the changelog
Also made a minor edit to a comment about the powerlevel display
2013-05-18 14:27:14 +02:00
TfT_02
1f9dc70bb1 I forgot to remove the setting from advanced.yml 2013-05-18 14:12:45 +02:00
TfT_02
7f1ef61657 Get rid of the SuccessModifier
There's no need for this modifier, because the user can define the
exact chance for Rolls and Gracefull Rolls in the config file. This
means that the ratio between the two is already configurable.
2013-05-18 14:12:07 +02:00
TfT_02
2e74c079b0 Set the enchant buff level to 1 if it's lower than 0
Prevents issue #1006 from happening again.

If a user wants to disable SuperBreaker, they should do this using
permissions and not by setting the Enchant Buff level to zero.
2013-05-18 11:37:40 +02:00
TfT_02
ce4295289a Changed powerlevel display setting to disabled by default.
Because scoreboards are being cached by Minecraft in scoreboard.dat it
is no user friendly to enabled this by default. Users will have to
manually delete this file in order to actually disable this.
Described in #1105
2013-05-18 11:27:17 +02:00
T00thpick1
7fde04851d Typo 2013-05-17 18:44:23 -04:00
riking
71d030e5ad Change rounding strategy to ceiling for mob healthbars 2013-05-17 00:19:59 -04:00
T00thpick1
b08649d0a4 Not much help if not static 2013-05-16 23:58:49 -04:00
T00thpick1
0a11a9a2c8 More methods for SkillType 2013-05-16 22:00:40 -04:00
T00thpick1
068f47b523 Option for any distance 2013-05-16 19:53:58 -04:00
T00thpick1
79aab57abc Configure the inspect distance 2013-05-16 19:31:12 -04:00
T00thpick1
2cf58f1b5b Why break when we can return? 2013-05-16 18:04:14 -04:00
T00thpick1
9678875b4b We do enjoy killing off orphans 2013-05-16 17:26:16 -04:00
GJ
d1a7ce827a Back to active development. Again. 2013-05-16 16:24:19 -04:00
GJ
9b2f4b7bde Because the old beta broke all the things. 2013-05-16 16:23:12 -04:00
GJ
24e5147a2a This was never an issue. 2013-05-16 16:13:53 -04:00
T00thpick1
0423a7831d Those were right the first time... 2013-05-16 15:55:25 -04:00
T00thpick1
feea22b3a4 Correctly order 2013-05-16 15:52:49 -04:00
T00thpick1
7f40a9f284 Explicitely state columns wanted to account for altered tables 2013-05-16 15:50:19 -04:00
GJ
bc706109e0 Fix issue with tables without party names. 2013-05-16 13:37:22 -04:00
GJ
a25bddba5e Back to active development. 2013-05-16 10:55:13 -04:00
GJ
ab897724d3 Weekly beta! 2013-05-16 10:54:40 -04:00
GJ
a7861fc54b Move all miscellaneous Spout code to a single location. 2013-05-16 10:51:18 -04:00
GJ
936bec8ff5 Unused import. 2013-05-16 09:32:48 -04:00
GJ
01d10971a1 Calling things that many times is BAD. 2013-05-16 09:32:27 -04:00
T00thpick1
12e388a392 Null checks 2013-05-16 09:30:02 -04:00
T00thpick1
fb450671d6 Alternative SQL player loading 2013-05-16 09:29:59 -04:00
GJ
fca5f9ec98 We shouldn't need to do this. If issues arise, then there's a bug in
Bukkit that needs patching.
2013-05-16 09:23:35 -04:00
GJ
c9ae6436bd Because we forget things too often. 2013-05-16 08:41:57 -04:00
GJ
b6c4d2b4ad Fixed bug where Nether Quartz wasn't included in Smelting or item
sharing
2013-05-16 08:13:01 -04:00
GJ
27ab2f5b12 Update localization files. 2013-05-16 07:35:00 -04:00
T00thpick1
9b08062a58 Typo 2013-05-15 20:36:43 -04:00
T00thpick1
401bdfa9ac Reset ability modes safely 2013-05-15 20:35:30 -04:00
TfT_02
68d8d6dd30 Added permission node to bypass the fishing exploit prevention
Permission node: `mcmmo.bypass.kraken` false by default.
2013-05-15 23:35:17 +02:00
GJ
2a57d7007d Don't go through everything twice. Also, those were horrible variable
names.
2013-05-15 17:28:47 -04:00
GJ
fd675ac291 Changed Spout notification tiers to be stored in SpoutConfig instead of
AdvancedConfig. Also restructured some Spout stuff for easier
readability.
2013-05-15 17:08:43 -04:00
GJ
41f020bbb7 Cleaning up our listeners, as well as some Spout stuff. 2013-05-15 15:39:40 -04:00
GJ
00dee500e0 Caching options is bad, and so was that way of getting the menu key. 2013-05-15 15:28:05 -04:00
GJ
36bdb8a63e Fixed mcMMO overwritting Spout titles set by other plugins. 2013-05-15 15:14:47 -04:00
GJ
aa9eb0868c Add option to use scoreboards for power level display, similar to the
Spout titles. This will NOT override any existing plugin that uses the
overhead scoreboard slot.
2013-05-15 15:13:11 -04:00
T00thpick1
48aafa9834 Unused import 2013-05-15 14:27:31 -04:00
T00thpick1
78f53f294a Debris should drop normal drops 2013-05-15 13:02:21 -04:00
TfT_02
3158c7e3eb List /party itemshare and /party expshare in /party ?
Closes #913
2013-05-15 19:00:34 +02:00
GJ
47d27ebf31 Update changelog. 2013-05-15 09:29:54 -04:00
GJ
bc3773ae75 Because apparently you can have metadata and an empty list too.
Fixes #1080
2013-05-15 09:29:24 -04:00
GJ
d8ddd27d71 Calculate bonus XP based on initial arrow location, rather than final
shooter location.
2013-05-15 08:35:12 -04:00
GJ
8d5696507a Add bow force multiplier to Archery XP. 2013-05-15 01:20:12 -04:00
T00thpick1
9ec376a228 Unused import and update changelog 2013-05-15 00:53:01 -04:00
T00thpick1
a05a0da9fb Mob Spawner XP multiplier 2013-05-15 00:48:18 -04:00
T00thpick1
5029ad9d93 Apply Perks after cutoff 2013-05-14 23:54:54 -04:00
T00thpick1
1444be665c No reason to specify MyISAM 2013-05-14 23:54:52 -04:00
GJ
3dedb94bdc Add new Experience API functions and clarify some old ones. 2013-05-14 23:30:36 -04:00
T00thpick1
c0f6c15a80 Fix SQL Syntax 2013-05-14 23:28:45 -04:00
T00thpick1
00626a4893 Update changelog.txt 2013-05-14 23:03:26 -04:00
T00thpick1
b416a59bb7 Don't cache config options to prepare for eventual config reload support 2013-05-14 22:59:16 -04:00
GJ
bf96fb2214 Update changelog 2013-05-14 22:45:10 -04:00
GJ
2e79c8d770 Properly track infinite arrows. 2013-05-14 22:45:09 -04:00
T00thpick1
6c9d1c4953 Make SQL removes delete from all tables 2013-05-14 22:20:06 -04:00
T00thpick1
df8df192d3 Update Changelog 2013-05-14 19:57:18 -04:00
T00thpick1
e5f43462c8 Certain operations do not work with child skills 2013-05-14 19:31:40 -04:00
GJ
1867a3e040 If they aren't in a party, they shouldn't be in party chat mode. 2013-05-14 13:10:54 -04:00
GJ
6818f98de3 Feedback is good. 2013-05-14 13:10:07 -04:00
GJ
f910c76248 Conventions. 2013-05-14 12:46:45 -04:00
GJ
975cbf0bf8 The cache should be here, not in the manager. 2013-05-14 12:46:04 -04:00
GJ
f10b3cef01 Config option for escaping from the Kraken. 2013-05-14 12:43:02 -04:00
T00thpick1
ad39c94773 AbilityDeactivateEvent 2013-05-14 12:18:52 -04:00
T00thpick1
f189ab30e5 Default should be default 2013-05-14 11:32:57 -04:00
GJ
0ad18ee971 Fix some config formatting issues. 2013-05-14 11:32:22 -04:00
GJ
501f5de55a Fixing everything you guys broke while I was gone... 2013-05-14 11:28:50 -04:00
T00thpick1
0b18ae8ff2 Formatting and things 2013-05-13 22:28:42 -04:00
T00thpick1
de12970486 New api event 2013-05-13 22:28:39 -04:00
Glitchfinder
7550b99aaa Patching more NPEs involving invbalid players, plus mob health bars. 2013-05-13 18:46:19 -07:00
Glitchfinder
ed5a43966d Patching NPEs involving invalid player objects and player interactions. 2013-05-13 18:46:18 -07:00
Glitchfinder
95ea6703f1 Fixing an NPE involving invalid players chatting. 2013-05-13 18:46:17 -07:00
T00thpick1
55f9092aa6 Fireworks adjustment 2013-05-13 21:23:16 -04:00
Glitchfinder
5f50a46603 Setting the treasure config to only enforce data limits for blocks. 2013-05-13 20:22:09 -04:00
Paul J Thordarson
c5e6704530 Magic Hunter fix and optimization
There was a small bug in magic hunter, where it tried to apply an
enchantment level between 1 and the Enchantment.getMaxLevel(), however
it didn't take into account Enchantment.getStartLevel(), so when it
tried to apply an enchantment level below the start level, an
IllegalArgumentException was being thrown and the magic hunter event
wasn't happening.

Also, it's potentially inefficient to recalculate which enchantments
are possible for each ItemStack every time, so I added a HashMap to
cache the possibleEnchantments for each material type, then check this
cache instead of just looping to regenerate the list each time.
2013-05-13 20:22:08 -04:00
T00thpick1
8552192894 Only apply permissions when skill is enabled 2013-05-13 20:19:50 -04:00
NuclearW
0261d16140 Give no mcMMO xp for skeletons that spawn as a spider jokey pair from spawners. 2013-05-11 18:54:25 -04:00
NuclearW
2b414526e5 Unleash the Quacken! 2013-05-09 11:04:34 -04:00
NuclearW
c0b7eb526a Change Squid variables to Creature. 2013-05-09 11:00:28 -04:00
t00thpick1
7b7196a8c4 Potatoes shouldn't explode by default 2013-05-05 23:00:14 -03:00
t00thpick1
f648289035 Potato fixes 2013-05-05 22:58:04 -03:00
TfT_02
8a0b1d548d Add item weights for armor and tools in the default file 2013-05-05 11:32:10 +02:00
NuclearW
1f17d5d11e Move the comment section attached to the Kraken in advanced.yml
This is to fix a shortcoming in the autoupdate-config loader, which will attach related comments to nodes.
Issue: A nodes will get comments from another node of the same name, anywhere else in the config.
Solution: Move the comment to be attached to the "Kraken" node.

Long term: This can be a known bug and worked around by the team, or can be addressed more seriously by looking into changing how comments are applied to configs.  For now, this is a patch solution that should work fine.

Fixes #1043
2013-05-05 05:27:11 -04:00
TfT_02
18efd09421 Remove \' since it somehow breaks the name display
For some reason using \' will show the pets name as:
"<player-name>'s {1}"
2013-05-05 00:36:58 +02:00
TfT_02
18d3b30647 Add a missing space 2013-05-04 23:34:19 +02:00
GJ
7f0243b2df For Iaccidentally. 2013-05-03 18:16:42 -04:00
GJ
33610c8997 Whoops. 2013-05-03 16:15:34 -04:00
GJ
8e0a1f4f70 Summon the kraken at will! 2013-05-03 16:14:03 -04:00
GJ
b07cf6bdde It's now possible to run away from the Kraken. 2013-05-03 15:49:29 -04:00
GJ
7ed218ee7f Cleanup this task a bit. 2013-05-03 13:43:23 -04:00
GJ
3aedeea220 Remove client-side rain if the player kills the kraken. 2013-05-03 12:11:52 -04:00
GJ
4f9b7b2609 Because you might be legitimately fishing at 5 seconds. 2013-05-03 07:51:59 -04:00
GJ
09abab1b5d Kraken sounds can now be set to either player-only or global (default). 2013-05-03 07:51:58 -04:00
GJ
499713c8e7 Because autoclicking to shake is OK. 2013-05-03 07:51:57 -04:00
GJ
cb953a1619 Disable global chat spam from the kraken by setting the server message
to an empty string in the config.
2013-05-03 07:51:56 -04:00
TfT_02
3ab4938f3d Also need to locale these two strings
Closes #1019
2013-05-02 21:08:20 +02:00
TfT_02
f6e9fd9f3a Add more localisation 2013-05-02 21:02:12 +02:00
GJ
8dab75f3cb Can't use brackets in YAML. 2013-05-02 08:48:17 -04:00
GJ
b36096e54d Fixed bug where non-player arrows couldn't be deflected. 2013-05-02 08:23:18 -04:00
GJ
0574de4a29 Configure the Kraken! 2013-05-02 07:56:29 -04:00
GJ
6d6bc3de76 Trim player names to 16 chars when needed. 2013-05-02 07:16:07 -04:00
GJ
5c4c3cf59c The Kraken hates boats. 2013-05-01 22:50:12 -04:00
GJ
0033c8864e A dead kraken can't attack. 2013-05-01 22:17:48 -04:00
GJ
e7c749ee3a Added boosts to Fishing chance depending on conditions. Also, the
kraken, now with 100% more sound!
2013-05-01 21:57:42 -04:00
GJ
5c026be0cd Don't need those. 2013-05-01 21:19:29 -04:00
GJ
c465546871 Unleash the Kraken! 2013-05-01 21:17:59 -04:00
GJ
3322677d32 Added "Ice Fishing" ability to Fishing 2013-05-01 10:18:19 -04:00
GJ
76cf0ebb01 Only play ability effects if there's room above the player. 2013-05-01 08:59:45 -04:00
GJ
d34a0cca30 Fix issue with using /mcpurge, /mcremove, and /mmoupdate from the
console. These commands now default to OP, because frankly there are
much worse things someone can do with OP status than mess with the mcMMO
database.
2013-05-01 08:40:01 -04:00
GJ
a77a916fcc One more time... 2013-04-30 17:31:06 -04:00
GJ
e1ebb96545 Still need to remove from pending even if offline. 2013-04-30 15:47:19 -04:00
GJ
d85a6bec43 Don't create a task we'll possibly never run. 2013-04-30 15:19:41 -04:00
GJ
78eb7787e9 We don't need this any more. 2013-04-30 15:13:55 -04:00
GJ
b55ce30b2d Clean up our main class a bit more. Still not perfect, but it's getting
there.
2013-04-30 15:07:29 -04:00
GJ
14050cf096 Oops. 2013-04-30 14:24:31 -04:00
GJ
5930128b7f Add soft-depend on CombatTag so it loads before mcMMO, allowing us to
ensure the name check is ONLY run if CombatTag is installed.
2013-04-30 13:53:21 -04:00
GJ
08be78fa35 Avoid possible IllegalStateException if player has logged out before
this processes.
2013-04-30 10:02:28 -04:00
GJ
88f43d9a91 Add command to clear or change scoreboards. 2013-04-30 09:48:53 -04:00
GJ
6cbf960dea Use the right value here. 2013-04-30 08:24:16 -04:00
TfT_02
374d34f76d Fixed that for you 2013-04-30 14:20:16 +02:00
GJ
cc486c2dc7 Update the localization files. 2013-04-29 16:27:25 -04:00
GJ
724dce07a9 Back to regular development. 2013-04-29 15:59:56 -04:00
GJ
1486e2063b Beta time! 2013-04-29 15:59:35 -04:00
GJ
50c9649b23 mcMMO - Now with 100% more scoreboards!
mcMMO now allows for the use of scoreboards to display information in
several instances. By default, all scoreboards are enabled in the config,
and will only display for 10 seconds. After 10 seconds, the scoreboard
will go away and revert to the previously displayed scoreboard, if one
exists.

A global scoreboard now exists for tracking all player stats, and will be
displayed when /mctop is used. Your name will be highlighted in gold when
looking through the scoreboard. Additionally, the scoreboard will display
players in groups of 15, rather than groups of 10 like in chat.
Unfortunately, due to the limitations of scoreboards, the player's rank
will not be displayed in front of their name.

The scoreboard area is now also used for displaying data for /mcrank,
/inspect. and /mcstats. Due to the way scoreboards are handled, the power
level is not guarenteed to show up at any given location in the
scoreboard, but is instead displayed in gold so that it can be easily
found.

Lastly, the scoreboard area is also now used for displaying current data
on skills when the relevant /<skillname> command is used. The effects and
ability stats will still be shown in chat, but the current level, xp, and
remaining xp will be shown in the scoreboard.
2013-04-29 15:45:07 -04:00
GJ
339a54b0ac Replace SkillMonitorTask with 3 unique timers instead. This should greatly
optimize our tool and ability cooldown tracking and hopefully reduce
server load.
2013-04-29 15:33:55 -04:00
GJ
b97afb85a1 Only check names if CombatTag is enabled. 2013-04-29 00:29:38 -04:00
GJ
15da9d580b The previous CombatTag fix should take care of these. 2013-04-28 16:52:14 -04:00
GJ
62aed496cc Fix issue with CombatTag NPC errors. Fixes #1012
NOTE: Do NOT change the default NPC name for CombatTag in your config,
or this fix won't work.
2013-04-28 16:50:41 -04:00
GJ
fba131936a Fix issue with tab-completing /party commands. 2013-04-28 01:11:51 -04:00
t00thpick1
70601a4560 Debug code - Why you be in main branch 2013-04-28 01:08:07 -03:00
t00thpick1
83604ecb6d Syntax fixes 2013-04-27 14:18:10 -03:00
TfT_02
b912f7072c Actually use float experience 2013-04-26 17:28:18 +02:00
GJ
7e7e468408 Fix /mcrank showing everything as unranked... 2013-04-26 10:51:17 -04:00
T00thpick1
748c97f6c1 Expand AbilityAPI capabilities 2013-04-25 21:47:41 -04:00
GJ
a3aab57cf8 I am bad at SQL. 2013-04-25 20:08:27 -04:00
GJ
5548e26dd9 Fixed bug where players could remain in party chat after leaving or
being kicked from a party.
2013-04-25 19:52:25 -04:00
GJ
89d2f07c03 Because the block is null if they click air. 2013-04-25 19:36:34 -04:00
GJ
f42a28f34f Use defaults in case these are null. 2013-04-25 19:26:50 -04:00
TfT_02
bdc753f03c Also add the cancel feature for the Salvage Anvil 2013-04-25 23:40:21 +02:00
TfT_02
68a7b540c5 Ask a confirmation when a player tries to repair an enchanted item 2013-04-25 23:29:49 +02:00
GJ
b2dd820507 Clean up a few more things. 2013-04-25 09:27:48 -04:00
GJ
612308eb9a No reason to have those variables. 2013-04-25 09:20:03 -04:00
GJ
98dc7b853a Protect our managers. 2013-04-25 09:16:42 -04:00
GJ
a2fefd6fb6 Oops. 2013-04-25 07:48:14 -04:00
TfT_02
17a0382283 Changed experience storage from integers to floats
This will make sure no experience is lost when the server has high
skill modifiers configured, or when low amounts of experience are being
shared.
2013-04-25 07:42:38 -04:00
GJ
eea5784527 Abstract our database operations into a single class.
This allows the logic between SQL and Flatfile to remain more hidden in
most cases and makes the code easier to read.
2013-04-25 07:41:23 -04:00
GJ
1aff2cf9eb Cleaning out some crap from our PlayerListener. 2013-04-24 21:18:31 -04:00
GJ
4fc6349824 Move healthbar stuff to it own class. 2013-04-24 11:40:34 -04:00
GJ
7a3921eace Make these actually random. 2013-04-24 11:05:40 -04:00
GJ
e99599c377 Fixed Smelting returning ink sacs instead of Lapis when double-dropping.
Fixes #986
2013-04-24 07:08:24 -04:00
GJ
e1f6366a00 Don't make a new File every time. 2013-04-23 09:32:28 -04:00
GJ
182b01ac2f Redundant check is redundant 2013-04-23 09:10:22 -04:00
GJ
18f3914428 Use the path we already have. 2013-04-23 09:10:03 -04:00
GJ
bd0a045da3 No need to handle the load ourselves. 2013-04-23 09:00:42 -04:00
t00thpick1
9a4bed8c67 Already set to config default in constructor 2013-04-23 01:25:54 -03:00
t00thpick1
ae0cf692cd Use defaults when using defaults. 2013-04-23 01:22:01 -03:00
GJ
2ca7d139fe Fix NPEs relating combat checks and world changing. Fixes #976, #979 2013-04-22 23:19:26 -04:00
TfT_02
7e67505dfb Remove redundant ChimaeraWing check
Also indent the code
2013-04-21 21:50:08 +02:00
TfT_02
21100de85d Move the ChimaeraWing permission check and add feedback 2013-04-21 21:48:42 +02:00
TfT_02
d8f799f8b4 Add a few missing items to the Shareables list 2013-04-20 16:11:07 +02:00
TfT_02
cb03a98113 Add pickup sounds to cancelled PlayerPickupItemEvents
This will make the player aware that he has picked up an item.
2013-04-20 13:24:50 +02:00
GJ
4b36a11dda Make sure the target is online.
This ensures that the McMMOPlayer object *should* be valid.
2013-04-18 22:18:06 -04:00
GJ
8099490213 Minor DB tweaks. 2013-04-18 22:18:05 -04:00
GJ
6cb2843707 Remove a stupid line. 2013-04-18 22:18:05 -04:00
TfT_02
e831f0561a Changed Call of the Wild, newly summoned pet's will have a custom name
Closes #972
2013-04-18 23:04:27 +02:00
GJ
d57c253b19 Returns in finally are bad. 2013-04-18 11:28:07 -04:00
GJ
c8c68ea7d9 A little file cleanup. 2013-04-18 11:23:45 -04:00
GJ
150fe730bd No point in having a class & method for one line of code. 2013-04-18 09:19:48 -04:00
GJ
8af425d067 Make this a bit more sane. 2013-04-18 09:09:12 -04:00
GJ
c3845abd2a Clean up a bit, and make the /party itemshare command recognize the new
"misc" option
2013-04-18 08:11:47 -04:00
GJ
eba6820ec6 Clean this up a bit. 2013-04-18 07:51:53 -04:00
TfT_02
822e40bc1f Added a new Party item share category "Misc" which contains a list of configurable items. 2013-04-17 16:03:34 +02:00
TfT_02
3ffcaae122 Track items dropped by a player, prevent them from being party shared 2013-04-17 15:20:09 +02:00
GJ
42a30b4521 Fixed Fishing treasures always having the same enchants. 2013-04-17 07:47:43 -04:00
GJ
377ed9e8e5 Fix not being able to change party owners. 2013-04-17 07:07:54 -04:00
GJ
be76fe61d8 Fixed being unable to kick party members. 2013-04-17 07:05:28 -04:00
GJ
07ba7a8d9e Nerf fishing again... AGAIN 2013-04-16 23:48:36 -04:00
GJ
2be3e3b43c Changed Berserk to add items to inventory rather than denying pickup 2013-04-16 23:44:41 -04:00
GJ
49bf190895 Update changelog. 2013-04-16 07:00:39 -04:00
GJ
c9a53bdaca Fixed NPE when trying to tab-complete /mctop 2013-04-15 12:52:11 -04:00
GJ
3a76a111d3 Use the mob name when we have it. 2013-04-14 02:10:48 -04:00
TfT_02
e59c7ac34a Reduced the amount of info messages in the console when enabling/disabling 2013-04-13 21:53:00 +02:00
TfT_02
f05b9ae365 Use LinkedHashSet instead of List 2013-04-13 18:43:22 +02:00
GJ
c60e5a65d6 Fixed shake drops not working.
NOTE: You need to delete your treasures.yml and allow it to regenerate.
2013-04-13 11:34:38 -04:00
TfT_02
1b4eda713f Moar magical fixes!
This will automagically fix bugged players who have joined multiple
parties.
2013-04-13 01:17:07 +02:00
TfT_02
cb133ced80 No longer needed! 2013-04-13 01:16:17 +02:00
TfT_02
062a3028f4 This makes it easier to read 2013-04-13 01:11:26 +02:00
TfT_02
682c2631f0 Fixed bug where players were able to join the same party multiple times
This change should automagically fix broken parties which have multiple
instances of the same player in it.

This will not fix bugged players who have joined multiple parties.
2013-04-13 00:41:36 +02:00
NuclearW
faecb9a439 Fix players not having ptp.send by default. 2013-04-12 18:25:52 -04:00
GJ
5dc40f3c03 Nerf fishing... again. 2013-04-12 17:48:04 -04:00
GJ
569e87847f Fixed fishing chance display values. 2013-04-12 10:25:00 -04:00
GJ
b448315f20 And now, back to your regularly scheduled development. 2013-04-11 23:55:13 -04:00
GJ
2c87ce06eb Weekly beta releases are back! 2013-04-11 23:54:10 -04:00
GJ
875091a1ce Added ability to configure drops from Shake in treasures.yml 2013-04-11 21:40:09 -04:00
GJ
5ad7716137 Don't need to store that. 2013-04-11 10:24:22 -04:00
GJ
8c97399cec This is important. 2013-04-11 10:02:08 -04:00
GJ
27e0a9d3b6 Fixed experience commands affecting all skills. Fixes #951 2013-04-11 09:55:39 -04:00
GJ
07f9b287e7 Move exceptions to their own package.
This will break plugins that directly catch these exceptions.
2013-04-10 20:21:55 -04:00
GJ
fbee4f1b37 Remove debug messages. 2013-04-10 19:41:55 -04:00
GJ
26542f3d6e Because otherwise you can't fish at low levels. 2013-04-10 19:32:26 -04:00
GJ
14630fe956 Nerfin' it. 2013-04-10 18:44:11 -04:00
GJ
30f5c761d9 Because some plugins do stupid things. 2013-04-10 17:04:32 -04:00
GJ
365abaaa8f Reverse the order to avoid NPE 2013-04-10 14:04:46 -04:00
GJ
f4681a282c Better handling of picking up items with unarmed. 2013-04-10 13:20:44 -04:00
TfT_02
8a14d9ac26 Update the changelog 2013-04-10 17:19:34 +02:00
TfT_02
0ab1986202 Set a seperate cooldowns between getting hurt and teleportations
Closes #880
2013-04-10 17:19:14 +02:00
TfT_02
e11dc680de Add configurable warmup and cooldown timers for party teleportation
Closes #348
2013-04-10 17:18:06 +02:00
TfT_02
71249334c3 Change the ChimaeraWing timestamp into a general teleportation timestamp 2013-04-10 17:15:48 +02:00
NuclearW
fa41dbce16 Regex used mean look, could not escape! 2013-04-10 00:00:57 -04:00
GJ
4246e6c900 Use char codes instead of symbols, just to be safe. 2013-04-09 23:41:02 -04:00
GJ
1b421a24b0 Remove the drop. 2013-04-09 21:44:27 -04:00
GJ
9cc9eead52 Unbreak the API 2013-04-09 21:09:47 -04:00
GJ
8b21aea9c7 Check Fisherman's Diet permission when checking for display headers. 2013-04-09 20:53:55 -04:00
GJ
4f87cb6446 Added "Master Angler" ability to Fishing.
This ability increases the chance that a fish will bite the line while
fishing.
2013-04-09 20:53:54 -04:00
GJ
7525de1a72 ExperienceAPI methods will now throw InvalidSkillException if the skill
name passed in is invalid
2013-04-09 20:52:58 -04:00
GJ
78d2fa7520 Only care if it was unarmed. 2013-04-09 16:52:41 -04:00
GJ
7fe8122499 Avoid picking up items to the hotbar while using unarmed. Fixes #939 2013-04-09 16:52:38 -04:00
GJ
532c2e7450 Remove unused import 2013-04-09 16:52:35 -04:00
GJ
b391a53c6b Make our commands support tab-complete. 2013-04-08 17:34:23 -04:00
GJ
f3c6346b95 Clear mob health display if it gets stuck. Fixes #933 2013-04-08 00:34:54 -04:00
GJ
dd8984314f Validate here instead. 2013-04-08 00:26:12 -04:00
GJ
b82c3f41d3 Remove metadata, validation checks. 2013-04-08 00:24:38 -04:00
GJ
7d6eb65776 No need to reset. 2013-04-08 00:11:09 -04:00
GJ
dc0800e7e1 Even better regex. 2013-04-08 00:07:07 -04:00
GJ
c151366952 Better regex for this. 2013-04-07 23:58:53 -04:00
GJ
212137ec3e Fix issues with mob healthbars being used in death messages. Fixes #934 2013-04-07 23:22:59 -04:00
GJ
31f36935d3 Avoid NPE when using experience commands on offline players. 2013-04-07 09:01:31 -04:00
TfT_02
a14fc3e3c9 Fixed broken /party chat command
Closes #931
2013-04-06 12:20:20 +02:00
GJ
158b3c43f8 Fixed wolves from Call of the Wild only having 8 health. 2013-04-05 16:17:59 -04:00
GJ
e31c1e33d9 Don't handle removing the name if the entity is dead. 2013-04-05 16:15:24 -04:00
GJ
25dfa6d34d Better way to get the HUD type. 2013-04-04 23:15:37 -04:00
GJ
431429a29c Broken config files are bad. 2013-04-04 23:03:54 -04:00
GJ
d4c8cc28a1 Use new hasConflictingEnchant method. 2013-04-04 22:26:48 -04:00
GJ
ce08405c00 Use new NetherWartState values. 2013-04-04 22:24:02 -04:00
GJ
da29185b7d Added health display for mobs during combat.
During combat, players will now see a healthbar appear over the head of
hostile mobs when they are damaged. This healthbar will have two display
options - HEARTS and BAR - which can be changed via the /mobhealth
command.

New Permissions:
mcmmo.mobhealthdisplay - Allows viewing of mob health display
mcmmo.commands.mobhealth - Allows access to the /mobhealth command

New Config Options (config.yml):
Mob_Healthbar.Display_Type - the default health display type
Mob_Healthbar.Display_Time - the amount of time to show health display
2013-04-04 22:11:11 -04:00
TfT_02
87feb8c250 Added new API method to McMMOPlayerLevelUpEvent to set levels gained
Closes #352
2013-04-04 23:00:21 +02:00
TfT_02
12797893df Update the changelog 2013-04-04 22:50:32 +02:00
TfT_02
6d47e43ba9 Display partial names when trying to use the ptp command 2013-04-04 22:50:22 +02:00
TfT_02
f6b1643378 Minor formatting, added a missing white space 2013-04-04 22:21:13 +02:00
TfT_02
f1c16df63b Added new permission node for party teleportation.
`mcmmo.commands.ptp.send`
This permission node will be check before sending a teleport request
(or teleporting the sender if no request is required), this allows
admins to grant certain groups of users permissions to accept incoming
party teleport request without being able to send ptp requests
themselves.

Closes #927
2013-04-04 22:20:19 +02:00
TfT_02
c16e5231f4 Changed Chimaera Wing's recipe result to use the ingredient Material 2013-04-04 21:35:09 +02:00
GJ
2365c253dd Back to active development. 2013-04-04 10:23:06 -04:00
GJ
c4e7f2597e 1.4.05 bugfix release. 2013-04-04 10:22:09 -04:00
GJ
13fd522bd4 Updated localization files. Adds Thai (Thailand) and Lithuanian support. 2013-04-04 10:17:55 -04:00
GJ
b74f6e92dc Fixed party & admin chat errors when not aysnc 2013-04-04 10:14:52 -04:00
GJ
630c3e81e6 Fixed Chimera Wing displaying warmup message if warmup was set to 0 2013-04-04 09:59:10 -04:00
GJ
0f77cf8066 Fixed Chimera Wing spamming console if Metrics was disabled 2013-04-04 09:48:48 -04:00
GJ
52746fca76 Speed up our BlockBreakEvent checks a bit. 2013-04-04 09:29:07 -04:00
GJ
dae25c2f2d Don't check if we don't watch. 2013-04-04 08:10:24 -04:00
GJ
a272316301 Don't even bother running these checks if we don't watch the block. 2013-04-04 08:05:48 -04:00
GJ
6772f4f169 Track these IF they're somehow full-grown when placed. 2013-04-04 08:02:45 -04:00
GJ
9463e210b8 Compact our checks. 2013-04-04 07:42:33 -04:00
GJ
4c44b72f78 50 != 100 2013-04-04 07:06:07 -04:00
GJ
c849f751bb Fixed potion buff option not using the appropriate # of ticks 2013-04-03 11:41:43 -04:00
GJ
1cde45599e Fixed huge mushroom blocks not being properly tracked 2013-04-03 11:16:24 -04:00
GJ
f1a22f5f6b Shouldn't track this either, just to be safe. 2013-04-02 21:30:18 -04:00
GJ
90d6fbde48 Fix ClassCastException with Taming. Fixes #924 2013-04-02 21:24:02 -04:00
GJ
802ad84613 Fixed Berserk getting "stuck" when /mcrefresh is used. 2013-04-02 17:38:33 -04:00
GJ
c4aa9396fd Update changelog. 2013-04-02 13:48:05 -04:00
GJ
f0c937ad47 Fixed parties and /reload not playing nice together. 2013-04-02 13:47:52 -04:00
GJ
fcc36ee5d7 Trying to fix reload more. 2013-04-02 11:17:40 -04:00
GJ
0f023f627c Metadata > Hashmap 2013-04-02 08:41:51 -04:00
GJ
fa645b5e00 Clear after saving, save before clearing. 2013-04-02 08:29:38 -04:00
GJ
1fb28eeee0 Because reload is evil. 2013-04-02 08:20:55 -04:00
TfT_02
d7f67d43b3 I quite liked the fireworks display! 2013-04-02 13:08:07 +02:00
TfT_02
5a1ec745ce Update the changelog 2013-04-01 22:55:19 +02:00
TfT_02
6fd599bd31 Fixed bug where /addxp was not processessing level-ups for online players
Fixes #918
2013-04-01 22:54:36 +02:00
GJ
afd706bed8 Fix NPE with smelting & /mctop. Fixes #917 2013-04-01 16:41:58 -04:00
TfT_02
6c3820c747 Because some people really wanted to disable this,
mostly due to clientside lag.
2013-04-01 16:38:22 +02:00
TfT_02
0ebc555136 Fixed bug with ChimaeraWings not taking Wings from a players inventory properly
Fixes #914
2013-04-01 11:32:28 +02:00
TfT_02
4992c50098 Sharing with the dead is bad, they have nothing to gain. 2013-04-01 00:22:24 +02:00
NuclearW
4e9322485a Flush write buffer for saving PlayerProfile before closing it. 2013-03-31 17:12:45 -04:00
TfT_02
fc8ad40b00 Fixed bug where /addxp was setting instead of adding experience
Fixes #898
2013-03-30 10:50:05 +01:00
TfT_02
f62e053a84 Update the changelog 2013-03-30 10:42:50 +01:00
T00thpick1
0af3c7ab7d Just in case. 2013-03-29 22:35:55 -04:00
NuclearW
7f4efe1775 Added option to allow refreshing of chunks after block-breaking abilities.
This, if enabled, should fix the problem of clients believing they have broken more blocks than they really have when the enchanced enchantment is removed.
If testing proves it to be useful, could be enabled by default.  This currently send a 3x3 set of chunks centered around the player, so some servers may wish to disable it in that case.
2013-03-29 18:29:31 -04:00
GJ
80a5c2f9c4 Back to active development 2013-03-28 12:49:57 -04:00
1061 changed files with 73558 additions and 34846 deletions

344
.gitignore vendored
View File

@@ -1,42 +1,330 @@
# Eclipse stuff
/.classpath
/.project
/.settings
# netbeans
/nbproject
### Eclipse template
# we use maven!
/build.xml
.metadata
bin/
tmp/
*.tmp
*.bak
*.swp
*~.nib
local.properties
.settings/
.loadpath
.recommenders
# maven
/target
# External tool builders
.externalToolBuilders/
# vim
.*.sw[a-p]
# Locally stored "Eclipse launch configurations"
*.launch
# various other potential build files
/build
/bin
/dist
/manifest.mf
# PyDev specific (Python IDE for Eclipse)
*.pydevproject
/world
# CDT-specific (C/C++ Development Tooling)
.cproject
# Mac filesystem dust
*.DS_Store
# CDT- autotools
.autotools
# intellij
# Java annotation processor (APT)
.factorypath
# PDT-specific (PHP Development Tools)
.buildpath
# sbteclipse plugin
.target
# Tern plugin
.tern-project
# TeXlipse plugin
.texlipse
# STS (Spring Tool Suite)
.springBeans
# Code Recommenders
.recommenders/
# Annotation Processing
.apt_generated/
# Scala IDE specific (Scala & Java development for Eclipse)
.cache-main
.scala_dependencies
.worksheet
### Android template
# Built application files
*.apk
*.ap_
# Files for the ART/Dalvik VM
*.dex
# Java class files
*.class
# Generated files
gen/
out/
# Gradle files
.gradle/
build/
# Local configuration file (sdk path, etc)
# Proguard folder generated by Eclipse
proguard/
# Log Files
*.log
# Android Studio Navigation editor temp files
.navigation/
# Android Studio captures folder
captures/
# IntelliJ
*.iml
*.ipr
.idea/workspace.xml
.idea/tasks.xml
.idea/gradle.xml
.idea/assetWizardSettings.xml
.idea/dictionaries
.idea/libraries
.idea/caches
# Keystore files
# Uncomment the following line if you do not want to check your keystore files in.
#*.jks
# External native build folder generated in Android Studio 2.2 and later
.externalNativeBuild
# Google Services (e.g. APIs or Firebase)
google-services.json
# Freeline
freeline.py
freeline/
freeline_project_description.json
# fastlane
fastlane/report.xml
fastlane/Preview.html
fastlane/screenshots
fastlane/test_output
fastlane/readme.md
### Dropbox template
# Dropbox settings and caches
.dropbox
.dropbox.attr
.dropbox.cache
### Windows template
# Windows thumbnail cache files
Thumbs.db
ehthumbs.db
ehthumbs_vista.db
# Dump file
*.stackdump
# Folder config file
[Dd]esktop.ini
# Recycle Bin used on file shares
$RECYCLE.BIN/
# Windows Installer files
*.cab
*.msi
*.msix
*.msm
*.msp
# Windows shortcuts
*.lnk
### Maven template
target/
pom.xml.tag
pom.xml.releaseBackup
pom.xml.versionsBackup
pom.xml.next
release.properties
dependency-reduced-pom.xml
buildNumber.properties
.mvn/timing.properties
.mvn/wrapper/maven-wrapper.jar
### NetBeans template
nbproject/private/
nbbuild/
dist/
nbdist/
.nb-gradle/
### macOS template
# General
.DS_Store
.AppleDouble
.LSOverride
# Icon must end with two \r
Icon
# Thumbnails
._*
# Files that might appear in the root of a volume
.DocumentRevisions-V100
.fseventsd
.Spotlight-V100
.TemporaryItems
.Trashes
.VolumeIcon.icns
.com.apple.timemachine.donotpresent
# Directories potentially created on remote AFP share
.AppleDB
.AppleDesktop
Network Trash Folder
Temporary Items
.apdisk
### Linux template
*~
# temporary files which can be created if a process still has a handle open of a deleted file
.fuse_hidden*
# KDE directory preferences
.directory
# Linux trash folder which might appear on any partition or disk
.Trash-*
# .nfs files are created when an open file is removed but is still being accessed
.nfs*
### GPG template
secring.*
### Gradle template
.gradle
/build/
# Ignore Gradle GUI config
gradle-app.setting
# Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored)
!gradle-wrapper.jar
# Cache of project
.gradletasknamecache
# # Work around https://youtrack.jetbrains.com/issue/IDEA-116898
# gradle/wrapper/gradle-wrapper.properties
### SBT template
# Simple Build Tool
# http://www.scala-sbt.org/release/docs/Getting-Started/Directories.html#configuring-version-control
dist/*
lib_managed/
src_managed/
project/boot/
project/plugins/project/
.history
.cache
.lib/
### Example user template template
### Example user template
# IntelliJ project files
.idea
out
gen### JetBrains template
# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio and WebStorm
# Reference: https://intellij-support.jetbrains.com/hc/en-us/articles/206544839
# User-specific stuff
.idea/**/workspace.xml
.idea/**/tasks.xml
.idea/**/usage.statistics.xml
.idea/**/dictionaries
.idea/**/shelf
# Sensitive or high-churn files
.idea/**/dataSources/
.idea/**/dataSources.ids
.idea/**/dataSources.local.xml
.idea/**/sqlDataSources.xml
.idea/**/dynamic.xml
.idea/**/uiDesigner.xml
.idea/**/dbnavigator.xml
# Gradle
.idea/**/gradle.xml
.idea/**/libraries
# Gradle and Maven with auto-import
# When using Gradle or Maven with auto-import, you should exclude module files,
# since they will be recreated, and may cause churn. Uncomment if using
# auto-import.
# .idea/modules.xml
# .idea/*.iml
# .idea/modules
# CMake
cmake-build-*/
# Mongo Explorer plugin
.idea/**/mongoSettings.xml
# File-based project format
*.iws
.idea/
# Project Stuff
/src/main/resources/mcMMO
# IntelliJ
# mpeltonen/sbt-idea plugin
.idea_modules/
# Other Libraries
# JIRA plugin
atlassian-ide-plugin.xml
# Cursive Clojure plugin
.idea/replstate.xml
# Crashlytics plugin (for Android Studio and IntelliJ)
com_crashlytics_export_strings.xml
crashlytics.properties
crashlytics-build.properties
fabric.properties
# Editor-based Rest Client
.idea/httpRequests
### Kotlin template
# Compiled class file
# Log file
# BlueJ files
*.ctxt
# Mobile Tools for Java (J2ME)
.mtj.tmp/
# Package Files #
*.jar
*.war
*.nar
*.ear
*.zip
*.tar.gz
*.rar
# Atlassian Stuff
/atlassian-ide-plugin.xml
# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml
hs_err_pid*
### Java template
# Compiled class file
# Log file
# BlueJ files
# Mobile Tools for Java (J2ME)
# Package Files #
# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml

View File

@@ -7,6 +7,627 @@ Key:
! Change
- Removal
Version 2.2.0
mcMMO has a new config system (WIP)
mcMMO for Bukkit no longer requires Spigot in order to play, you can now use Bukkit instead (WIP)
mcMMO is now abstracted from the Bukkit API in order to support more platforms (WIP)
mcMMO has changed from using maven to gradle!
mcMMO is now a gradle project (this makes it much easier for us to support older versions of MC and other APIs)
Version 2.1.12
Salvage config entries are no longer case sensitive
Fixed a bug where Fishing was not rewarding vanilla XP orbs
Version 2.1.11
Fixed a bug where Rupture was using the wrong permission node (new permission node: mcmmo.ability.swords.rupture)
Version 2.1.10
Fishing command did an oopsie
Endstone now gives the same XP as Stone (update your experience.yml)
Version 2.1.9
Fixed a bug where grabbing the version of WG would throw classnotdefined errors
Version 2.1.8
mcMMO now checks for WG 7 before attempting to use the WG API
Made some optimizations for our WG integration
Fixed a bug where Bite chance for Master Angler was displaying too many decimal places
Fixed a bug where Abilities didn't check for permission nodes before activating
MaxBonusLevel now has specific entries for Standard and Retro in advanced.yml
MaxBonusLevel for Critical Strikes changed from 75/750 to 100/1000
MaxBonusLevel of Dodge changed from 80/800 to 100/1000
MaxBonusLevel of Rupture changed from 20/200 to 100/1000
MaxBonusLevel of Counter Attack changed from 60/600 to 100/1000
Version 2.1.7
Fixed an almost 6 year old bug where Salvage materials did not have a defined material count so they defaulted to 2 (which could lead to shovels giving back more diamonds than normal)
Added spam detection for Unarmed's bonus damage and disarm
Corrected an error where master angler for retro only required level 150 instead of 500 (update your skillranks.yml)
Fixed a bug where Players could see hidden party members in the party member listings
(API) Added addXpFromBlocks to ExperienceAPI to help make adding XP for a player easier
(API) Added addXpFromBlocksBySkill to ExperienceAPI to help make adding XP for a player easier
(API) Added addXpFromBlock to ExperienceAPI to help make adding XP for a player easier
(API) Added addXpFromBlockBySkill to ExperienceAPI to help make adding XP for a player easier
Version 2.1.6
Fixed a bug where Arcane Salvage could never fail
Recolored some lines in the locale related to failure from white to red
Fixed a bug where Salvage was giving back too many resources
SubSkillFailure renamed to SubSkillFailed in config.yml
SubSkillFailed now sends copies to chat by default
SubSkillFailed no longer sends messages to the action bar by default
Version 2.1.5
mcMMO no longer ignores cancelled events relating to the player left or right clicking
Version 2.1.4
Fixed a bug where Alchemy didn't gain XP
Fixed a bug where Archery gained XP from mob spawned entities
Fixed a display bug with Roll on /acrobatics command
Fixed a display bug for bite chance on Fishing
Fixed a display bug for treasure drop chances on Fishing
Fixed a display bug for Arcane Forging on Repair
Fixed a display bug for Super Repair on Repair
Fixed a display bug for Repair Mastery on Repair
Fixed a display bug for Second Smelt on Smelting
Repair Mastery now uses a rank system
Super Repair now uses a rank system
Changed the stat for bite chance to be more clear that its additive chance
Fixed Styling for the /salvage command
Temporarily disabled Flux Mining
Removed XP from entities that target endermite to prevent easy exploitation (Credits to TheBentoBox for the tip!) [Can be turned off in experience.yml]
Fixed a bug where static chance skills like Arcane Salvage were using incorrect calculations for success
Advanced Salvage now uses a rank system
Arcane Salvage now goes by your rank to determine the maximum amount of materials salvaged and is no longer percentage based
Fixed a bug where Iron Arm was checking for Iron Grip to be unlocked instead of itself
(Plugin Compatibility) mcMMO no longer ignores cancelled block place events (this is to prevent XP gains from placed blocks)
(Plugin Compatibility) mcMMO now ignores cancelled events relating to the player left or right clicking
(Locale) Changed the string for "Salvage.Ability.Bonus.1" to fit the new material recovery mechanics of Salvage
(Config) Added a toggle for the new endermite enderman xp farm fix in experience.yml "ExploitFix.EndermanEndermiteFarms"
(Config) Cleaned up some leftover 'unlocklevel' settings, this stuff is now handled in skillranks.yml
(Config) Removed Salvage.MaxPercentage
(Config) Removed Salvage.MaxPercentageChance
(Config) Added Salvage.ArcaneSalvage.MaxBonusLevel
(Config) Added Salvage.ArcaneSalvage.MaxChance
Version 2.1.3
Temporarily removed the unarmed no-item pickup feature until its fixed
Version 2.1.2
(Compatibility) mcMMO now deals custom damage type for all damage sources to be more compatible with other plugins (such as anti-cheat)
(Perks) Fixed a bug where the Lucky perk wasn't adding to success
(Skills) mcMMO will now listen to cancelled events to remove our temporary enchantments from tools
(Skills) Fixing a bug where Shake didn't calculate success correctly
(Skills) Fixed a bug where Arcane Forging didn't calculate success and failure correctly
(Skills) Fixed a bug where Salvage didn't calculate success and failure correctly
(Skills) Fixed a bug where Flux Mining didn't calculate success correctly
(Skills) Fixed a bug where Shake didn't calculate correctly
(Skills) Fixed a bug where Pummel didn't calculate correctly
(Skills) Tree Feller now works on Mushroom Stems
(Skills) Fixed a bug where magic chance would show as null
(Skills) Fixed a bug where Trap percentages were added to Fishing even though they no longer exist
(Skills) Magic Hunter now uses a rank system
(Skills) Fixed a bug where Magic Hunter would work without treasure hunter
(Skills) As long are you are empty handed mcMMO will no longer put items into your hands
(Skills) Improved the styling on /smelting
(Skills) Iron Arm Style can now reach a bonus damage of 10 (up from 8)
(Skills) Iron Arm Style now uses a rank system
(Skills) Iron Grip now uses a rank system
(Skills) Disarm now uses a rank system
(Skills) Arrow Deflect now uses a rank system
(Skills) Flux Mining is now a passive effect when you mine ore instead of requiring a special pickaxe
(Skills) Removed the Flux Mining mcMMO Pickaxe Item
(Style) Locked skills now are styled differently in the skill command display
(Experience) Phantoms have been added to the default experience.yml with a value of 4.0 (update your config!)
(Experience) Default XP value for witch set to 0.1 instead of 0.0
(Experience) Default XP value for ender dragon set to 1.0 instead of 0.0
(Style) Added @ symbol styling for hover tooltips to the locale
(Style) Added the skill names in the skill commands display to the locale so it can now be edited and styled
(Experience) Renamed Grass to Grass_Block in treasures.yml to allow grass to give items again (update your configs manually or delete to regen)
(Experience) Wood blocks now give XP and are affected by Tree Feller (6 sided bark blocks)
(API) Moved XPGainReason from skills to experience package
(API) Added XpGainSource for tracking sources of XP
(API) You can now specify XpGainSource when adding xp to players
(Config) The Extra Stats option for XP bars now overrides the setting for updating XP bars every time XP is gained
(Config) Added an option for Party XP gains to not update XP bars
(Config) Added an option for Passive XP gains to not update XP bars (smelting/brewing)
(Config) Added warnings if mcMMO finds a MaxBonusLevel of 0 for any skill that incorporates RNG
(Config) Removed config options for Iron Arm
(Config) Removed the options related to the Flux Mining Item
(Config) Second Smelt has a max activation chance of 50% instead of 100% (you can update your configs or gen new ones to get this change)
Version 2.1.1
= Fixed an issue where excavation wasn't using the correct permission node
= Added protection against AFK fishing
= Acrobatics now uses much better anti-exploit detection
Version 2.1.0
+ mcMMO now features XP bars! Configurable in experience.yml
+ Locale files now support & codes for colors and formatting!
+ Prevented exploits involving blocks made from entities (snowmen, etc..)
+ Added JSON integration to all Skill Commands
+ Added config setting to enable or disable old mcMMO skill scaling (General.RetroMode) this is on by default for existing installs
+ You can now disable specific skills in coreskills.yml without the need for permissions
+ Added links to mcMMO related websites to various commands
+ Certain elements of mcMMO's UI have been restyled
+ Added the tagline "Overhaul Era" to various locations until 3.0.0 comes out
+ You can now disable mcMMO completely for specific worlds via world_blacklist.txt in /plugins/mcMMO/
+ (WorldGuard) mcMMO now supports worldguard, you can use the flags "mcmmo" and "mcmmo-xp" on regions (they default to on unless otherwise specified)
! (Scoreboards) Scoreboards are now disabled by default, I don't like them. You can turn them back on in config.yml
+ (Sounds) Rolling now plays a sound (Graceful Roll has a different sound :) )
+ (Sounds) Activating Super abilities plays a sound (other plays can hear this)
+ (Sounds) Skill Unlock Notifications have sounds
+ (Sounds) Readying a tool for a super ability now plays a sound
+ (Sounds) Bleed DOT now plays a sound
+ (Experience) mcMMO now notifies you when you progress in a skill!
+ (Experience) Coral (blocks) now give Mining XP
+ (Experience) Coral (plants) now give Herbalism XP
+ (Experience) Blue Ice now gives Mining XP
+ (Experience) Dolphins now give combat XP
+ (Experience) Drowned mobs now count towards combat XP
+ (Experience) You can now set guaranteed minimum values for XP gained if diminishing returns are enabled, this value defaults to 5% (experience.yml)
+ (Events) Starting an XP event will now use the title API (toggle this in advanced.yml)
+ (Sound) Volume and Pitch of sounds can now be configured in the new sounds.yml file
+ (MySQL) Added support for SSL for MySQL/MariaDB (On by default)
! (Skills) Taming's Gore now uses Rupture Rank 1 for its DoT calculations
! (Skills) Sword's Bleed has been renamed to Rupture
! (Skills) Sword's Rupture no longer has an internal hard coded limit
! (Skills) Sword's Serrated Strikes now uses your Rupture rank to determine the damage/ticks for its bleed effect.
! (Skills) Sword's Rupture now ticks four times as fast
! (Skills) Sword's Rupture now refreshes bleed duration instead of adding duration when applying bleed to the same target
! (Skills) Sword's Rupture will now deal lethal damage
= (Skills) Fixed a bug where Rupture would apply an incorrect amount of bleed ticks
! (Skills) Sword's Rupture now reaches its max proc chance at level 20 (200 in Retro)
! (Skills) Sword's Rupture now has a max chance to proc of 33% instead of 70%
! (Skills) Sword's Rupture now deals 50% more damage at above Rank 3 and can last much longer! The base damage for Bleed has been increased as well (update your advanced.yml admins)
! (Skills) Sword's Rupture no longer triggers invincibility frames when damaging your opponent
= (Skills) Furnaces now give XP to the last person to modify their inventory instead of the first person to open them
+ (Skills) Ability Lengths now have a default skill cap at which they stop increasing in length, configurable in advanced.yml (endurance perks extend this limit)
+ (Skills) Added a new subskill to some skills 'Understanding The Art' this adds nothing new, but tracks benefits that increase together that seemed unrelated, which was previously a bit obfuscated.
+ (Skills) Tool alerts now are sent to the Action Bar
+ (Skills) Super Ability activation alerts are now sent to the Action Bar
+ (Skills) Certain Skill messages are now sent to the Action Bar
+ (Skills) Added some missing information to skill stats
+ (Config) Skill Rank requirements are now defined in skillranks.yml you cannot add or remove ranks from this file
+ (Config) Added option to use SSL for MySQL in config.yml
+ (Config) Added option to disable the new URL links to config.yml
+ (Config) New config file added coreskills.yml
+ (Config) Added rank settings for the new Woodcutting skill
+ (Config) Added configurable parameters for the new Tree Feller
+ (Config) Added retro toggle for Tree Feller
+ (Config) Added toggle to disable all scoreboards
+ (Chat) Added ability for admins to spy on party chat (off unless toggled on)
+ (Commands) Added new info command /mmoinfo or /mcinfo
+ (Commands) Added toggle command /mcchatspy
+ (API) Added many missing SubSkills to SubSkillType class
+ (Permissions) Added permission node mcmmo.commands.mcchatspy & mcmmo.commands.mcchatspy.others
+ (Permissions) Added permission nodes for Harvest Lumber, Splinter, Nature's Bounty, and Bark Surgeon
+ (Permissions) Added mcmmo.commands.mmoinfo for the new mmoinfo/mcinfo command
! (Permissions) Call of the wild now uses mcmmo.ability.taming.callofthewild instead of mcmmo.ability.taming.callofthewild.all
+ (Locale) Added locale strings for new Woodcutting abilities
+ (Locale) Added locale strings for mcchatspy command
+ (Locale) Added locale strings for JSON integration
+ (Locale) Added locale strings for Taming's Pummel SubSkill
+ (Locale) Added locale strings for Unarmed's Block Cracker SubSkill
- (Locale) Removed localizations with the following codes for being almost empty: id, HR_hr, et_EE, lv, lt, no, pl_PL, pt_PT, tr_TR
- (Config) Removed SkillShot's IncreaseLevel & IncreasePercentage (replaced by RankDamageMultiplier)
- (Config) Removed AxeMastery's MaxBonus & MaxBonusLevel (replaced by RankDamageMultiplier)
= (Events) Fixed bug where XP rate could be a negative number
= (Experience) Fixed a bug where you could set a players levels into the negative and bad things would happen
= (Plugin Compatibility) mcMMO now fires new custom events relating to changes it makes to player scoreboards, plugin authors can listen to these events to improve compatibility
= (Items) Chimaera Wing now tracks cooldowns between sessions for players (no more disconnect abuse)
= (Skills) Added missing mushroom blocks to experience.yml defaults
= (Skills) Tridents will no longer be considered unarmed
= (MySQL) You can now inspect offline players
= (MySQL) When converting from MySQL to flatfile mcMMO will now properly include all users in the conversion process
= (Commands) '/mcMMO help' no longer displays the other/special commands category to players lacking permissions
+ (Party) Parties can now have size limits (configurable in config.yml), party size is unlimited by default
+ (Party) You can now turn on Friendly Fire for parties in config.yml
+ (Debug Stick) The Debug stick can now tell you about properties of a block related to Excavation
! (Deaths) Fixed the bug where mob names would be replaced by hearts
! (Experience) The XP values of fish are now based on their rarity and have been drastically changed
! (Experience) Skills now start at level 1 (configurable in advanced.yml)
! (Item) Improved some of the messages sent to the player regarding the Chimaera Wing
! (Party) Party member list will only include members of the party that you can see (aren't vanished)
! (Skills) Excavation Treasure Hunter is renamed to Archaeology
! (Skills) Swords no longer require blocking with a shield to trigger counter attacks
! (Skills) Stripping wood and right clicking on stripped wood will no longer ready your Axe
! (Skills) Some skill level rank requirements have changed
! (Skills) Green Thumb now uses a rank system
! (Skills) Farmer's Diet & Fisherman's Diet now use a rank system
! (Skills) Fixed an edge case bug where Blast Mining wouldn't inform the player that it was on cooldown
! (Skills) mcMMO skills will now be on a scale from 1-100 instead of 0-1000 (for existing mcMMO installs this is opt-in and off by default)
! (Skills) Skill Super Powers now use a rank system, almost all of them unlocking first at level 10
! (Skills) Acrobatics' Roll exploit detection was tweaked to still allow for Roll to trigger even if it rewards no XP
! (Skills) Acrobatics' Roll & Gracefull Roll are now considered the same skill (both mechanics are still there)
! (Skills) Woodcutting's Double Drop subskill is now named Harvest Lumber
! (Skills) Archery's Skill Shot now uses a rank system
! (Skills) Swords' Bleed now uses a rank system
! (Skills) Swords' Counter Attack now uses a rank system
! (Skills) Axe's Axe Mastery now uses a rank system
! (Skills) Axe's Impact now uses a rank system
! (Skills) Herbalism's Farmer's Diet now uses a rank system
! (Skills) Herbalism's Green Thumb now uses a rank system
! (Skills) Shake now uses a rank system
! (Skills) Flux Mining now uses a rank system
! (Skills) Removed traps from fishing
! (Skills) Dodge now uses a rank system
! (Skills) Arrow Retrieval now uses a rank system
! (Skills) Axes' Critical Strikes now uses a rank system
! (Skills) Axes' Greater Impact now uses a rank system
! (Skills) Taming's Beast Lore now uses a rank system
! (Skills) Taming's Gore now uses a rank system
! (Skills) Taming's Call of the Wild now uses a rank system
! (Skills) Taming's Pummel now uses a rank system
! (Kraken) Removed everything involving the kraken
= (Skills) Shake now sends custom damage types for better nocheat compat
! (Config) Unarmed.IronArm in advanced.yml is now Unarmed.IronArmStyle
! (Config) Unarmed.Deflect in advanced.yml is now Unarmed.ArrowDeflect
! (Config) Swords.Counter in advanced.yml is now Swords.CounterAttack
! (Config) Archery.Retrieve in advanced.yml is now Archery.ArrowRetrieval
! (Config) Axes.CriticalHit in advanced.yml is now Axes.CriticalStrikes
! (Config) Archery's Skill Shot now uses RankDamageMultiplier for its damage bonus calculations
! (Config) Axe's Axe mastery now uses RankDamageMultiplier for its damage bonus calculations
! (Permissions) Replaced the old Double Drop permission node for woodcutting with a new Harvest Lumber permission node
! (Permissions) Fast Food Service permission node renamed to mcmmo.ability.taming.fastfoodservice
! (Permissions) Counter Attack permission node renamed to mcmmo.ability.swords.counterattack
! (Permissions) Arrow Deflect permission node renamed to mcmmo.ability.unarmed.arrowdeflect
! (Permissions) Iron Arm Style permission node renamed to mcmmo.ability.unarmed.ironarmstyle
! (Permissions) Remove all mob health bar permissions, this is no longer a per-player setting.
! (Commands) Removed the mobhealthbar command, this is no longer a per-player setting.
! (Locale) The descriptions of a few skills have changed
! (Locale) Removed redundant information from some skill names and descriptions en_US (other locales will need to be updated)
! (Locale) SubSkill locale keys are now located at {ParentSkill}.SubSkill.SubSkillName
! (Locale) Super Abilities no longer have (ABILITY) in their Skill.Effect strings
! (API) mcMMO is now built against Spigot-API instead of Bukkit
! (API) Moved a lot of methods from SkillCommand to SkillUtils
! (API) SkillType is now PrimarySkillType
! (API) SecondarySkill is now SubSkillType
! (API) AbilityType is now SuperAbilityType
! (API) SecondaryAbilityEvent is now SubSkillEvent
! (API) SubSkillType has had many helpful methods added to it
! (API) GREEN_THUMB_PLANT & GREEN_THUMB_BLOCK are replaced by GREEN_THUMB
! (Code) Refactored some unreadable code relating to SecondaryAbilityType activation in SkillUtils
Version 2.0.0
= Fixed an interaction between Tree Feller and Stripped Wood
! Fireworks no longer fire by default for ability activation/deactivation
! Website has been changed and the MOTD string relating to it reflects this
! Discord link added to mcMMO command
! Updated misc strings relating to mcMMO
Version 1.5.05-SNAPSHOT
Version 1.5.04
+ Added option to config.yml to control mcMMO generated sound volume
+ Added option to config.yml to truncate existing player skill levels that exceed the skill level cap
+ Falling blocks persist mcMMO natural data
= Woodcutting double drops correctly identify acacia and dark oak logs
= Skill Reset command now correctly identifies arguments
= Hylian Treasure config options are now actually used
= Child skills now use parent skills configured skill caps properly
= Auto Update config now properly works
! Item dropped from blocks now drop from the center
! Potions Config updated for 1.9
! Flux mining now simulates a block break event for other plugins to act upon
! Zombie Pigmen spawned from nether portals are now considered spawner mobs
! Flux Pickaxe lore now appends to existing lore as opposed to replacing it
! Party chat no longer displays colors when logged in server console
- Treefeller no longer lowers exp for big trees
- No longer supports 1.8 :(
- Removed plugin metrics
Version 1.5.03
= Fixed bug where absorption hearts could be attacked by allied players
= Fixed bug where new forms of stone would drop the wrong type when mined with Silk Touch
= Fixed bug where blocks would not get tracked correctly when using sticky pistons and slime blocks in certain situations
= Fixed bug where config value for Daze damage was ignored
= Fixed UUID updater to not lose data on errors
= Fixed bug where uuid update could result in large amounts of user data being deleted
= Fixed bug where custom potions were missed in potion stage calculation
= Fixed piston dupe bugs permanently
= Fixed bug involving user name changes
= Fixed old user purge to properly calculate months
= Fixed bug where Repair would incorrectly check items
= Fixed bug where apostrophes in locale files would not read correctly
= Fixed bug where treasure data was limited to 255 instead of Short.MAX_VALUE
! Moved more user loading calculations to async loading thread to reduce lag on login
Version 1.5.02
+ Added option to config.yml for Chimaera Wings to stop using bed spawn points
+ Added option to config.yml to let non-tools in hand count as unarmed
+ Added option to experience.yml to control XP gained by killing bred animals
+ Added support for 1.8 mobs and features
= Fixed bug where no Mining XP was granted when Flux Mining was successful
= Fixed bug with UUID conversions in Flatfile
= Fixed a couple Dupe bugs that were introduced recently
= Fixed bug where MobHealthbarTypes were not saved between server restarts
! Changed Flux Mining mechanics. In order to use the ability, you need to infuse a pickaxe with furnace powers first.
! Scoreboard tips are only shown a couple of times to the player, instead of once per login session
! Changed Archery distance multiplier to be configurable
! Archery distance XP bonus cannot exceed indefinitely anymore
Version 1.5.01
+ Added new child skill; Salvage
+ Added UUID support!
+ Added SQL connection pooling and async loading!
+ Added the long awaited Diminished Returns feature
+ Added new feature to Herbalism. Instantly-regrown crops are protected from being broken for 1 second
+ Added option to config.yml to show the /mcstats scoreboard automatically after logging in
+ Added option to config.yml for Alchemy. Skills.Alchemy.Prevent_Hopper_Transfer_Bottles
+ Added option to config.yml for Scoreboards, display "Ability" instead of ability names on the scoreboards
+ Added options to experience.yml for Dirt and Sand variations
+ Added support for `MATERIAL|data` format in treasures.yml
+ Added API to experience events to get XP gain reason
+ Added API to check if an entity is bleeding
+ Added API to ExperienceAPI to get the amount of XP needed for a level
+ Added API class SkillAPI used to get a list of valid skill names
+ Added API events for hardcore features, McMMOPlayerPreDeathPenaltyEvent, McMMOPlayerStatLossEvent and McMMOPlayerVampirismEvent
+ Added API to ExperienceAPI to specify if XP can be shared
+ Added options to tools.yml and armor.yml config files to set a pretty repair material name
+ Added full support for repairables in tools.yml and armor.yml config files
+ Added magical mod config file import command, for Cauldron 1.7+. Check wiki for usage
+ Added particle effects and sounds to "Call of the Wild" (Taming)
+ Added summon length to "Call of the Wild". Summons will now commit suicide after their lifespan expires
+ Added feature which makes tamed wolves attack a target shot by the owner
= Fixed bug where pistons would mess with the block tracking
= Fixed bug where the Updater was running on the main thread.
= Fixed bug when players would use /ptp without being in a party
= Fixed bug where player didn't have a mcMMOPlayer object in AsyncPlayerChatEvent
= Fixed bug where dodge would check the wrong player skill level
= Fixed bug which causes /party teleport to stop working
= Fixed bug where SaveTimerTask would produce an IndexOutOfBoundsException
= Fixed bug where Alchemy would not fire BrewEvents
= Fixed bug with setting custom names and lore in treasures config
= Fixed bug which would cause a NullPointerException with getFlowerAndGrassXp()
= Fixed bug which could cause and SQLException regarding the connection property 'maxReconnects'.
= Fixed bug where falling blocks were incorrectly tracked
= Fixed bug where items would get deleted when in Berserk with a full inventory
= Fixed bug where the console would not correctly show party chat colors
= Fixed bug where party chat was using non thread safe methods
= Fixed bug where Blast Mining unlock levels could be to high in certain occasions
= Fixed bug where Blast Minings ability "Demolition Expert" would not work
= Fixed bug where Repair_Material_Quantity wasn't read in mod config files
! Changed SecondaryAbilityEvent to implement Cancellable and it now gets fired for damage related secondary abilities
! Changed the way mcMMO handles bonus damage, updated for the new damage event API
! Changed player data saving. Save tasks are now asynchronous
! Vanished players no longer get hit by AoE effects
! Changed Alchemy config option 'Prevent_Hopper_Transfer' renamed to 'Prevent_Hopper_Transfer_Ingredients'
! Changed Alchemy XP distribution. XP is granted based on the stage of the potion.
! Changed behavior of the Blast Mining ability "Demolition Expert"; now only decreases damage for the ability user
! Updated for new getOnlinePlayers() behavior
! Updated for new blocks and entities
! Changed McMMOPlayerDeathPenaltyEvent to get fired after hardcore penalty calculations, use McMMOPlayerPreDeathPenaltyEvent for old behavior
! Moved Refresh_Chunks setting from hidden.yml to config.yml
- Removed salvage ability from Repair, salvage has it's own (child) skill now
Version 1.5.00
+ Added Podzol & Red Sand to Excavation
+ Added Hardened Clay, Stained Clay, and Packed Ice to Mining blocks
+ Added Acacia and Dark Oak to Woodcutting blocks
+ Added Salmon, Clownfish, and Pufferfish to Fishing XP
+ Added new flowers and grasses to Herbalism XP
+ Added option to config.yml which allows players to always catch fish, even when a treasure is found
+ Added option to config.yml to override vanilla Minecraft treasures
! Fishing XP now depends on the type of fish.
! Woodcutting XP in experience.yml and Woodcutting double drops in config.yml now use the tree species names. Oak is now Generic, and Spruce is now Redwood.
! Red_Rose was replaced by Poppy, and so the key in experience.yml has been updated accordingly.
- Removed deprecated permission nodes
- Removed "Treasure found!" message
Version 1.4.08
+ Added a new skill; Alchemy. Special thanks to EasyMFnE for creating this!
+ Added SecondaryAbilityType enum, and new SecondaryAbilityWeightedActivationCheckEvent, fired when a secondary ability checkes its activation chances
+ Added the possibility to gain experience when using Fishing "Shake"
+ Added config options to disable various sound effects
+ Smelting now works with custom ores - add smelting XP value to blocks.yml, or it will default to 1/10th of normal XP.
+ Added automatic cleanup of backups folder.
+ Added bypass permission for finding Fishing traps
+ Added level threshold settings to hardcore modes. When a players skill level is below this threshold, they will not lose any stats
+ Added party alliances, two parties can now team up. Allies share party chat and cannot harm each other.
+ Added new experience bonus perk 'mcmmo.perks.xp.10percentboost.<skillname>' multiplies incoming XP by 1.1
+ Added new experience bonus perk 'mcmmo.perks.xp.customboost.<skillname>' multiplies incoming XP by the boost amount defined in the experience config
+ Added Ender Dragon, Wither, and Witch to combat experience multipliers - they do not give XP by default
+ Added support for multiple mod config files, naming can be done as either armor.<modname>.yml or <modname>.armor.yml
+ Added config options to configure the items used in "Call of the Wild"
+ Added config option to configure the database command cooldown
= Fixed bug where healthbars wouldn't display if skills were disabled
= Fixed bug with "Call of the Wild" entities despawning
= Fixed bug with updating (very) old user data.
= Fixed bug with checking maximum durability of mod items.
= Fixed exploit involving Call of The Wild.
= Fixed bug where LeafBlower permissions were ignored
= Fixed bug with toggle commands not properly displaying the success message.
= Fixed IllegalArgumentException caused by an empty Fishing treasure category
= Fixed bug with Salvage not reading the config value for the anvil material.
= Fixed exploit where you could receive smelting XP for improper items
= Fixed bug where the Unbreaking enchantment was ignored when using "Super Breaker" or "Giga Drill Breaker"
= Fixed bug which prevented players from gaining Acrobatics XP when the setting 'Prevent_XP_After_Teleport' was set to false
= Fixed bug where cooldown donor perks were reducing more than expected
= Fixed bug where disabling hardcore mode for specific skills didn't work
= Fixed bug which caused the net.shatteredlands.shatt.backup cleanup to delete old backups while it should have kept those
= Fixed bug where party chat broke if the display name contained special characters
= Fixed bug where `/addlevels all` and `/skillreset all` didn't work
= Fixed bug which made it possible to gain XP by taming the same horse multiple times, if a player "untamed" that horse
= Fixed bug where some horses summoned with "Call of the Wild" were unable to jump
= Fixed bug where the /ptp request expiration time was checked wrongly - preventing players from using the command
= Fixed bug where Hylian Luck was broken
= Fixed bug where Snow would never drop treasures
= Fixed issues with commands giving away vanished players.
= Fixed bug where the Repair lucky perk would increase the Arcane Forging downgrade chance, instead of decreasing it
! Changed party system. Parties now have XP and Levels. Party features such as party teleport and party chat have to be unlocked before they can be used by the party members
! Changed appearance of party member list. Gold = party leader, White = online, Gray = offline, Italic = not nearby
! Updated localization files
! Changed the appearance of /mcmmo commands
! Changed AxesCritical to CriticalHit in config file
! Changed several secondary ability permissions(deprecated versions still exist)
! Changed /ptp config setting, Commands.ptp.Confirm_Required is now Commands.ptp.Accept.Required
! Changed config validation for UnlockLevels, they can now also be 0
! Changed config validation for Rank_Levels, successive Ranks can now be less than or equal to each other
! Changed default amount of XP gained from mining Quartz Ore. From 250 to 100 XP.
! Changed Acrobatics config setting, Skills.Acrobatics.Prevent_XP_After_Teleport is now Skills.Acrobatics.XP_After_Teleport_Cooldown
- Removed /stats alias for /mcstats
Version 1.4.07
+ Added XP boost to Acrobatics when wearing Boots of Feather Falling
+ Added SQL Database can now recover from a dropped connection without losing data. (Thanks Riking!)
+ Added more tiers to Fishing, Repair and Smelting!
+ Added Carrot on a Stick and Flint & Steel to repair.vanilla.yml
+ Added horses to the "Shake" ability
+ Added ability to summon horses via "Call of the Wild" using apples
+ Added XP gain to Taming for horses
+ Added new permission nodes to allow more control over Taming and "Call of the Wild"
+ Added new experience.yml config file! Moved all experience related settings from config.yml to experience.yml
+ Added support for EXPONENTIAL formula curves to experience.yml
+ Added new /mcconvert command to convert players levels and experience from one formula curve to another.
+ Added snow to Excavation blocks
+ Added new experience curve option. Cumulative curve, calculates experience needed for next level using power level.
+ Added extra settings to config.yml for "Call of the Wild" (Taming)
+ Added a 5 second cooldown after teleporting before Acrobatics XP can be earned. Plus a config option to disable
+ Added new API methods to ExperienceAPI to get a players rank on the leaderboards
+ Added new McMMOPlayerDeathPenaltyEvent, fired when a player dies and would lose levels
+ Added new McMMOPlayerLevelChangeEvent, fired when a players level changes
+ Added new McMMOPlayerLevelDownEvent, fired when a player loses levels
+ Added ability to give custom names to items in treasures.yml - use the key "Custom_Name" to set, expects a string.
+ Added ability to give lore to items in treasures.yml - use the key "Lore" to set, expects a list of strings.
+ Added Quartz and Name Tags to the default Excavation treasures
+ Added a warning message if the server is running NoCheatPlus without CompatNoCheatPlus
+ Added cooldown to commands with heavy database access to prevent denial of service
+ Added /mcscoreboard keep, to keep the scoreboard up forever
+ Added Rainbow Mode to scoreboards
+ Added new /mccooldowns command to show all ability cooldowns
+ Commands may now both print text and display a scoreboard
+ Killing a custom entity will automatically add it to the custom entity config file with default values.
= Fixed bug which allowed players to bypass fishing's exploit prevention
= Fixed bug where FakeEntityDamageByEntityEvent wasn't being fired
= Fixed bug with "Skull Splitter" not finding the locale string
= Fixed issue where locale strings could cause the scoreboard header to be longer than 16 characters.
= Fixed a bug with "Beast Lore" when the entity had no owner but was tamed.
= Fixed a bug where AbilityDeactivateEvent would throw an error if the player logged out before his ability ran out.
= Fixed a bug where LevelUpEvent would be called for an offline player.
= Fixed a bug where teleport location was never reset if warmup was set to 0 for "Chimaera Wing".
= Fixed a bug where the "Dodge" DamageModifier wasn't being read from advanced.yml
= Fixed a bug where squid were not awarding XP.
= Fixed a bug where Combat XP was granted within 5 seconds for respawned players
= Fixed a bug where wrong feedback messages were being send when using a command on an offline player
= Fixed a bug where players were able to gain Herbalism XP in mine carts, even though Prevent_AFK_Leveling was enabled
= Fixed a bug where players would get hit by fireworks if they leveled up while in a boat
! Changed Fishing "Treasure Hunter" and "Magic Hunter" drop percentages
! Changed format of mod config files. (blocks.yml, tools.yml, armor.yml and entities.yml) **YOU WILL NEED TO UPDATE YOUR FILE TO THE NEW FORMAT**
! Changed format of treasures.yml. **YOU WILL NEED TO UPDATE YOUR FILE TO THE NEW FORMAT**
! Changed format of repair.vanilla.yml. **YOU WILL NEED TO UPDATE YOUR FILE TO THE NEW FORMAT**
! Changed default XP multiplier for repairing shears
! Changed "Shake" drops for Witches. They no longer drop water bottles, since they no longer drop them in Vanilla.
! Changed fishing exploit prevention, by default it will no longer send global sounds, effects and messages.
! Changed Hardcore modes, they will also subtract experience
! Changed various values to double in advanced.yml for the sake of consistency.
! Nerfed Fishing "Master Angler" (removed skill level based bonus) and also made the modifiers configurable
! Nerfed Archery damage to eliminate constant one-hit kills.
! Changed the way Repair hands out XP, also added config options to control Repair XP
! Changed Swords "Counter Attack" ability from passive to active. Blocking is required to activate.
! Hardcore modes can now be toggled for each skill individually
! Vampirism can now be enabled without having Skill Death Penalty enabled
! Admin and Party chat prefixes are now customizable
! Changed the color of party leader names in Party chat
! Improved "Tree Feller" algorithm (Thanks Riking!)
! Improved AFK Acrobatics prevention mechanism
! Improved profile saving
! Improved partial name matcher
! Improved update checker
! Updated localization files
! Party item share category states are now saved when the server shuts down.
! When using "Super Breaker" or "Giga Driller" abilities extra tool durability is used (again)
! Mob healthbars are automatically disabled when the plugin "HealthBar" is found
! Massively improved scoreboard handling
! Reworked scoreboard configuration (config.yml) - **you will need to update**
- The /mmoupdate command has been removed. It is replaced by /mcconvert database
- Removed Abilities.Tools.Durability_Loss_Enabled, set Abilities.Tools.Durability_Loss to 0 to disable instead.
- Removed Skills.Fishing.Shake_UnlockLevel from advanced.yml, now using Skills.Fishing.Rank_Levels.Rank_1 instead.
- Removed SpoutPlugin support
Version 1.4.06
+ Added "Ice Fishing" ability to Fishing
+ Added global scoreboards to track skill rankings (display using /mctop)
+ Added per-player scoreboard displays for the /inspect, /mcrank, /mcstats, and /<skillname> commands
+ Added tab-complete support for all commands
+ Added ability to configure drops from Shake in treasures.yml
+ Added "Master Angler" ability to Fishing.
+ Added health display for mobs during combat.
+ Added new API method to McMMOPlayerLevelUpEvent to set levels gained
+ Added new permission node for /ptp; mcmmo.commands.ptp.send (enabled by default)
+ Added configurable cooldown and warmup times when using /ptp
+ Added a new Party item share category "Misc" which contains a list of configurable items. (By default all tools and armor)
+ Added fishing exploit prevention
+ Added permission node to bypass the fishing exploit prevention
+ Added boosts to Fishing chance depending on conditions
+ Added McMMOAbilityActivateEvent and McMMOAbilityDeactivateEvent
+ Added config option to toggle the size of fireworks
+ Added config option to multiply xp gains from mob spawner mobs
+ Added multiplier to Archery XP based on bow force
+ Added information about /party itemshare and /party expshare to the party help page
+ Added option to use scoreboards for power level display instead of Spout.
+ Added permission node to prevent inspecting hidden players
+ Added SQL to Flatfile database conversion
+ Added ability to use custom database managers and convert to/from them
= Fixed bug which could cause the server to hang for a minute when checking for updates. (Thanks to Riking)
= Fixed bug where spawned arrows could throw ArrayIndexOutOfBoundsException
= Fixed bug where custom Spout titles were overwritten by mcMMO.
= Fixed bug where Nether Quartz wasn't included in Smelting or item sharing
= Fixed bug where players were able to join the same party multiple times
= Fixed displaying partial names when trying to use /ptp
= Fixed wolves from Call of the Wild only having 8 health
= Fixed bug where /party chat was not working
= Fixed bug where experience commands were adding levels to all skills when they shouldn't
= Fixed mcmmo.commands.ptp.send not being set by default
= Fixed NPE when trying to tab-complete /mctop
= Fixed Fishing treasures always having the same enchants
= Fixed Smelting returning ink sacs instead of Lapis when double-dropping
= Fixed bug where players could remain in party chat after leaving or being kicked from a party.
= Fixed bug where non-player arrows couldn't be deflected.
= Fixed experience being applied even when the permission for a skill was denied
= Fixed possible item duplication bug with infinity bows
= Fixed bug with removing players from mySQL database
= Fixed bug with empty metadata lists and Smelting
= Fixed bug where Blast Mining would drop wrong items
= Fixed bug with Blast Mining where the Ability refreshed message was being send too early
= Fixed bug where the chance of a successful Gracefull Roll was twice as high as displayed
= Fixed bug where lucky perks where not working
= Fixed bug with Ice Fishing on a single block of ice
= Fixed bug with Ice Fishing which allowed players to break ice in protected areas
= Fixed a small bug with mob healthbars and bosses, such as EnderDragons and Withers
! Changed Spout notification tiers to be stored in SpoutConfig instead of AdvancedConfig
! Changed Berserk to add items to inventory rather than denying pickup
! Changed Call of the Wild, newly summoned pet's will have a custom name. (added permission node to disable this)
! Changed Chimaera Wing's recipe result to use the ingredient Material
! Changed Repair to ask a confirmation of the player when he tries to repair an enchanted item
! Players will no longer pickup items to their hotbar while using Unarmed
! ExperienceAPI methods will now throw InvalidSkillException if the skill name passed in is invalid.
! Changed default value for recently-hurt cooldown between teleports, this is also fully configurable now
! Changed the amount of info messages in the console when enabling/disabling, enable Verbose_Logging to enable them again
! Items dropped by players are now being tracked and are not being shared with party members
! Optimized tracking of tool & ability cooldowns.
! Updated the localization files
Version 1.4.05
+ Added option to allow refreshing of chunks after block-breaking abilities. (Disabled by default)
+ Added fireworks effects when a player levels-up, for every 100 levels (configurable)
= Fixed bug where /addxp was setting instead of adding experience
= Fixed bug where /addxp was not processessing level-ups for online players
= Fixed bug which allowed players to share experience with nearby dead players
= Fixed bug with ChimaeraWings not taking Wings from a players inventory properly
= Fixed bug which caused a NPE when trying to use /mctop smelting
= Fixed Berserk misbehaving when /reload was used
= Fixed parties misbehaving when /reload was used
= Fixed Berserk getting "stuck" when /mcrefresh was used
= Fixed ClassCastException with Taming
= Fixed huge mushroom blocks not being properly tracked
= Fixed potion buff option not using the appropriate # of ticks
= Fixed Chimera Wing spamming console if Metrics was disabled
= Fixed Chimera Wing displaying warmup message if warmup was set to 0
= Fixed party & admin chat errors when not aysnc
! Updated localization files
Version 1.4.04
+ Added functions to ExperienceAPI for use with offline players
+ Added Nether Quartz Ore to Mining
@@ -173,7 +794,7 @@ Version 1.4.00
! Changed Excavation to have individual XP values for each block type, rather than a base XP value.
! Changed the way party teleportation works. When using /ptp, the target player needs to confirm the teleport before it takes place. (Configurable)
! Changed BeastLore: Now also displays offline player names
! Changed backup task to include ALL config files
! Changed net.shatteredlands.shatt.backup task to include ALL config files
! Deprecated most functions in ExperienceAPI, replaced them with identical versions that use a String for the SkillName rather than the SkillType enum values
! Changed Super Breaker & Giga Drill Breaker to be an enchantment-based boost, rather than an instabreak. Option exists in hidden.yml to change this to an potion-based buff.
! Changed locales to fall back on English when translated strings cannot be found.
@@ -396,7 +1017,7 @@ Version 1.3.07
+ Added permission nodes for Treasure & Magic Hunter for Fishing
+ Added a permission node for Farmer's Diet
+ Added config options for enabling/disabling specific double drops
+ Added automatic zip backup of flatfile database & config files
+ Added automatic zip net.shatteredlands.shatt.backup of flatfile database & config files
+ Added config options to enable/disable specific skills for PVP & PVE
= Fixed bug where Tree Feller was looking at the wrong blocks for determining how much to take down.
= Fixed bug where Green Terra consumed seeds even on Mossy Stone Brick
@@ -982,7 +1603,7 @@ Fixed bug with randomly receiving Taming XP
mcmmo.users file moved into /plugins/mcMMO/FlatFileStuff/
Leaderboard files now moved into /plugins/mcMMO/FlatFileStuff/Leaderboards
Locale files now have the prefix locale_ instead of messages_
Locale files are now located inside com/gmail/nossr50/locale/ instead of com/gmail/nossr50/
Locale files are now located inside com/com.gmail/com.gmail.nossr50/locale/ instead of com/com.gmail/com.gmail.nossr50/
Updated the code that handles permissions (this may mean 3.1.6 will finally play well!)
Some more source code organization
Fixed warnings for compiler

234
Changelog_2.1.0.md Normal file
View File

@@ -0,0 +1,234 @@
# **Version 2.1.0+**
### Please use Spigot or Paper!
* **mcMMO is now built against Spigot-API instead of Bukkit**
### New Level Scaling
* mcMMO now features an optional 1-100 scaling mode!
* This is on by default for new installs, if you are upgrading mcMMO you will be put into Retro Mode instead (1-1000) scaling.
* The two scaling modes are the same, the changes are completely cosmetic!
* Skill Requirements in the config file will be multiplied by 10 if you are using Retro mode unless the setting has Retro in its name, keep this in mind if you need to edit anything!
### WorldGuard Support
* Added support for WorldGuard regions!
* `mcmmo` region flag turns on or off a players ability to use anything related to mcMMO other than commands
* `mcmmo-xp` region flag turns on or off a player's ability to gain XP
* These flags default to on unless you specify otherwise
### World Blacklist
* You can now disable mcMMO completely for specific worlds via `world_blacklist.txt` in /plugins/mcMMO/
* This file appears once mcMMO has been run at least once
* Every line of this file should be the name of a world where you don't want mcMMO to be enabled!
### Rank System
* Skills that are not yet unlocked will show up as `???` until learned
* Many skills now make use of a rank system!
* Rank level requirements are modified in `skillranks.yml`
* Woodcutting's Double Drop subskill is now named Harvest Lumber
* Archery's Skill Shot now uses a rank system
* Swords' Bleed now uses a rank system
* Swords' Counter Attack now uses a rank system
* Axe's Axe Mastery now uses a rank system
* Axe's Impact now uses a rank system
* Herbalism's Farmer's Diet now uses a rank system
* Herbalism's Green Thumb now uses a rank system
* Shake now uses a rank system
* Flux Mining now uses a rank system
* Removed traps from fishing
* Dodge now uses a rank system
* Arrow Retrieval now uses a rank system
* Axes' Critical Strikes now uses a rank system
* Axes' Greater Impact now uses a rank system
* Taming's Beast Lore now uses a rank system
* Taming's Gore now uses a rank system
* Taming's Call of the Wild now uses a rank system
* Taming's Pummel now uses a rank system
* Green Thumb now uses a rank system
* Farmer's Diet & Fisherman's Diet now use a rank system
### mcMMO Chat Alerts
* mcMMO no longer spams your chat!
* Most messages are sent to your action bar instead!
* Completely configurable! You can have mcMMO spam your chat again if you want!
* You can configure it so that messages will be sent to your action bar AND your chat system!
* Improved some of the messages sent to the player regarding the Chimaera Wing
### Localization File
* The descriptions of a few skills have changed
* Locale files now support & codes for colors and formatting!
* Added locale strings for new Woodcutting abilities
* Added locale strings for mcchatspy command
* Added locale strings for JSON integration
* Added locale strings for Taming's Pummel SubSkill
* Added locale strings for Unarmed's Block Cracker SubSkill
* Removed localizations with the following codes for being almost empty: `id`, `HR_hr`, `et_EE`, `lv`, `lt`, `no`, `pl_PL`, `pt_PT`, `tr_TR`
* Removed redundant information from some skill names and descriptions `en_US` (other locales will need to be updated)
* SubSkill locale keys are now located at `{ParentSkill}.SubSkill.SubSkillName`
* Super Abilities no longer have `(ABILITY)` in their `Skill.Effect` strings
### UI
* Certain elements of mcMMO's UI have been restyled
* Skills can now be clicked on and hovered over for more information!
* Added links to mcMMO related websites to various commands
* Customizeable and optional XP Bars
* Added the tagline "Overhaul Era" to various locations until 3.0.0 comes out
* Added option to disable the new URL links to `config.yml`
### Sounds
* Volume and Pitch of sounds can now be configured in the new `sounds.yml` file
### Super Ability Changes
* Skill Super Abilities now use a rank system, the default rank to unlock is level 5
* Activating Super abilities plays a sound (other plays can hear this)
* Ability Lengths now have a default skill cap at which they stop increasing in length
* Setting the cap to 0 removes it!
* Configurable in `advanced.yml` (endurance perks extend this limit)
### Skills
* mcMMO now notifies you when you progress in a skill!
* Excavation Treasure Hunter is renamed to Archaeology
* Readying a tool for a super ability now plays a sound
* Skill Unlock Notifications have sounds
* Stripping wood and right clicking on stripped wood will no longer ready your Axe
* Added new skill 'Understanding The Art' which adds nothing new but tracks previously hidden benefits of raising a skill
* Tool alerts now are sent to the Action Bar
* Super Ability activation alerts are now sent to the Action Bar
* Almost all Skill-related messages are now sent to the Action Bar
* Added some missing information to skill stats
* Swords no longer require blocking with a shield to trigger counter attacks
* Sword's Bleed has been renamed to Rupture
* Sword's Rupture no longer has an internal hard coded limit
* Sword's Serrated Strikes now uses your Rupture rank to determine the damage/ticks for its bleed effect.
* Sword's Rupture now ticks four times as fast
* Sword's Rupture now refreshes bleed duration instead of adding duration when applying bleed to the same target
* Sword's Rupture will now deal lethal damage
* Sword's Rupture now reaches its max proc chance at level 20 (200 in Retro)
* Sword's Rupture now has a max chance to proc of 33% instead of 70%
* Sword's Rupture now deals 50% more damage at above Rank 3 and can last much longer!
* The base damage for Bleed has been increased as well (update your `advanced.yml` admins)
* Sword's Rupture no longer triggers invincibility frames when damaging your opponent
* Sword's Rupture now plays a sound
* Taming's Gore now uses Rupture Rank 1 for its DoT calculations
* Furnaces now give XP to the last person to modify their inventory instead of the first person to open them
* Rolling now plays a sound (Graceful Roll has a different sound :) )
* Acrobatics' Roll exploit detection was tweaked to still allow for Roll to trigger even if it rewards no XP
* Acrobatics' Roll & Gracefull Roll are now considered the same skill (both mechanics are still there)
* Some skill level rank requirements have changed
### Experience
* Skills now start at level 1 (configurable in advanced.yml)
* Starting an XP event will now use the title API (toggle this in `advanced.yml`)
* The XP values of fish are now based on their rarity and have been drastically changed
* Coral (blocks) now give Mining XP
* Coral (plants) now give Herbalism XP
* Blue Ice now gives Mining XP
* Dolphins now give combat XP
* Drowned mobs now count towards combat XP
* Added missing mushroom blocks for XP
* You can now set guaranteed minimum values for XP gained if diminishing returns are enabled, this value defaults to 5% (`experience.yml`)
### Bug Fixes
* Fixed the bug where mob names would be replaced by hearts
* Fixed a bug where Rupture would apply an incorrect amount of bleed ticks
* Fixed bug where XP rate could be a negative number
* Fixed a bug where you could set a players levels into the negative and bad things would happen
* Fixed an edge case bug where Blast Mining wouldn't inform the player that it was on cooldown
### Plugin Compatibility
* mcMMO now fires new custom events relating to changes it makes to player scoreboards, plugin authors can listen to these events to improve compatibility
### Exploit Fixes
* Prevented exploits involving blocks made from entities (snowmen, etc..)
* Chimaera Wing now tracks cooldowns between sessions for players (no more disconnect abuse)
* Tridents will no longer be considered unarmed
* Prevented exploits involving 2 high herbs and chorus flowers
* Vastly Improved the Acrobatics exploit detection checks
### Parties
* Parties can now have size limits (configurable in `config.yml`), party size is unlimited by default
* You can now turn on Friendly Fire for parties in `config.yml`
* Party member list will only include members of the party that you can see (aren't vanished)
### Scoreboards
* Scoreboards are now disabled by default since most of their functionality is handled better by XP bars.
* Added toggle to disable all scoreboards (previously you had to disable them one by one)
* You can turn them back on in `config.yml`
* You can have XP bars and scoreboards on at the same time
### MySQL
* Added support for SSL for MySQL/MariaDB in config.yml (On by default)
* mcMMO no longer spams your console if you are not using SSL for your MySQL server
* You can now inspect offline players
* When converting from MySQL to flatfile mcMMO will now properly include all users in the conversion process
### Admins
* Added ability for admins to spy on party chat (off unless toggled on) /mcchatspy
* The Debug stick can now tell you about properties of a block related to Excavation
### API
* Detailed guide to API changes is available at http://api.mcmmo.org
* Added many missing `SubSkills` to `SubSkillType` class
* Moved a lot of methods from `SkillCommand` to `SkillUtils`
* `SkillType` is now `PrimarySkillType`
* `SecondarySkill` is now `SubSkillType`
* `AbilityType` is now `SuperAbilityType`
* `SecondaryAbilityEvent` is now `SubSkillEvent`
* `SubSkillType` has had many helpful methods added to it
* `GREEN_THUMB_PLANT` & `GREEN_THUMB_BLOCK` are replaced by `GREEN_THUMB`
### Permissions
* Removed all mob health bar permissions, this is no longer a per-player setting.
* Added permission node `mcmmo.commands.mcchatspy` & `mcmmo.commands.mcchatspy.others`
* Added `mcmmo.commands.mmoinfo` for the new `mmoinfo`/`mcinfo` command
* Added permission nodes for Harvest Lumber, Splinter, Nature's Bounty, and Bark Surgeon
* Call of the wild now uses `mcmmo.ability.taming.callofthewild` instead of `mcmmo.ability.taming.callofthewild.all`
* Replaced the old Double Drop permission node for woodcutting with a new Harvest Lumber permission node
* Fast Food Service permission node renamed to `mcmmo.ability.taming.fastfoodservice`
* Counter Attack permission node renamed to `mcmmo.ability.swords.counterattack`
* Arrow Deflect permission node renamed to `mcmmo.ability.unarmed.arrowdeflect`
* Iron Arm Style permission node renamed to `mcmmo.ability.unarmed.ironarmstyle`
### Commands
* Added new info command `/mmoinfo` or `/mcinfo`
* Added toggle command `/mcchatspy`
* `/mcMMO help` no longer displays the other/special commands category to players lacking permissions
* Removed the `mobhealthbar` command, this is no longer a per-player setting.
### Misc Config Changes
* Removed `SkillShot`'s `IncreaseLevel` & `IncreasePercentage` (replaced by `RankDamageMultiplier`)
* Removed `AxeMastery`'s `MaxBonus` & `MaxBonusLevel` (replaced by `RankDamageMultiplier`)
* `Unarmed.IronArm` in `advanced.yml` is now `Unarmed.IronArmStyle`
* `Unarmed.Deflect` in `advanced.yml` is now `Unarmed.ArrowDeflect`
* `Swords.Counter` in `advanced.yml` is now `Swords.CounterAttack`
* `Archery.Retrieve` in `advanced.yml` is now `Archery.ArrowRetrieval`
* `Axes.CriticalHit` in `advanced.yml` is now `Axes.CriticalStrikes`
* Archery's Skill Shot now uses `RankDamageMultiplier` for its damage bonus calculations
* Axe's Axe mastery now uses `RankDamageMultiplier` for its damage bonus calculations
### Misc Changes
* Removed everything involving the kraken
* Code cleanup in a lot of places... unfortunately there is still much left to do!

View File

@@ -1,47 +1,66 @@
# mcMMO
## The RPG lovers mod
### Dev builds
Our latest development builds are available [here](http://ci.mcmmo.info).
## Website
I'm working on a brand new website for mcMMO
You can check it out here http://www.mcmmo.org
I plan to post links to our new wiki (its still under development), downloads, and dev blogs there.
### Contributing
As the plugin is being developed for multiple Minecraft versions, and multiple Minecraft platforms (read: [sponge](https://spongepowered.org/), [spigot](https://spigotmc.org/), bukkit, and [paper](https://papermc.io)), the
overall build process is handled by [Gradle](https://gradle.org/) with [Kotlin-dsl](https://github.com/gradle/kotlin-dsl) based scripts.
As such, an IDE is strongly recommended when attempting to contribute features, additions, changes, bug fixes, etc. to mcMMO as the scripts handle a
majority of our dependencies and rebuilding a production worthy jar.
To get started, a few things need to be installed:
- JDK 8 (not 9, 10, 11, or 7)
- git
- Your favorite IDE (can be [Eclipse](https://eclipse.org/), [IntelliJ](https://jetbrains.org/)
- BuildTools.jar from [Spigot](https://www.spigotmc.org/wiki/buildtools/)
##### Using BuildTools
BuildTools is used to generate the craftbukkit/spigot dependencies used for varoius versions of Minecraft.
The key with this tool is that it can build and deploy multiple vesions of Minecraft based on "reviewions".
### Builds
Currently, you can obtain our builds via the Spigot resource page: https://spigot.mcmmo.org
### Brief Description
mcMMO takes core Minecraft game mechanics and expands them to add an extensive RPG experience, the goal of the project has always been a quality RPG experience. Everything in mcMMO is carefully thought out and is constantly improving. mcMMO adds eleven skills to train in and level in, while also offering a high level of customization for server admins. There are countless features, including custom sounds, graphical elements, and more added when running mcMMO in conjunction with Spout. I carefully read feedback and evaluate the mechanics of mcMMO in every update to provide an ever-evolving experience.
If you want an original RPG experience like no other mod out there, mcMMO is for you.
The goal of mcMMO is to take core Minecraft game mechanics and expand them into add an extensive and quality RPG experience. Everything in mcMMO has been carefully thought out and is constantly being improved upon. Currently, mcMMO adds fourteen unique skills to train and level in. Each of these skills is highly customizable through our configuration files, allowing server admins to tweak mcMMO to best suit the needs of his or her server. Know that the mcMMO team is dedicated to providing an ever-evolving experience, and that we carefully read all feedback and bug reports in order to evaluate and balance the mechanics of mcMMO in every update.
## About the Team
mcMMO is currently developed by a team of individuals from all over the world.
### Glorious Leader
[![gmcferrin](http://www.gravatar.com/avatar/b64c52daf25d206b27650788b5813b7b.png)]
(https://github.com/gmcferrin)
### Project Lead & Founder
[![com.gmail.nossr50](http://www.gravatar.com/avatar/f2ee41eedfd645fb4a3a2c8f6cb1b18c.png)](https://github.com/com.gmail.nossr50)
### Former Lead
[![gmcferrin](http://www.gravatar.com/avatar/b64c52daf25d206b27650788b5813b7b.png)](https://github.com/gmcferrin)
### Developers
[![bm01](http://www.gravatar.com/avatar/ec8146f5358177f12e9a252271bbc391.png)]
(https://github.com/bm01)
[![Glitchfinder](http://www.gravatar.com/avatar/5aa4cce22f72ae9c002ecec30f061d00.png)]
(https://github.com/Glitchfinder)
[![nossr50](http://www.gravatar.com/avatar/f2ee41eedfd645fb4a3a2c8f6cb1b18c.png)]
(https://github.com/nossr50)
[![NuclearW](http://www.gravatar.com/avatar/90926bdcf1c8a75918df5ea5fa801ce6.png)]
(https://github.com/NuclearW)
[![shatteredbeam](http://www.gravatar.com/avatar/cad3b5d7d39cf5387afb87f494389610.png)]
(https://github.com/shatteredbeam)
[![TfT_02](http://www.gravatar.com/avatar/b8914f9970e1f6ffd5281ce4770e20a7.png)]
(https://github.com/TfT-02)
[![t00thpick1](http://www.gravatar.com/avatar/??.png)]
(https://github.com/t00thpick1)
[![bm01](http://www.gravatar.com/avatar/ec8146f5358177f12e9a252271bbc391.png)](https://github.com/bm01)
[![Glitchfinder](http://www.gravatar.com/avatar/5aa4cce22f72ae9c002ecec30f061d00.png)](https://github.com/Glitchfinder)
[![NuclearW](http://www.gravatar.com/avatar/90926bdcf1c8a75918df5ea5fa801ce6.png)](https://github.com/NuclearW)
[![shatteredbeam](http://www.gravatar.com/avatar/cad3b5d7d39cf5387afb87f494389610.png)](https://github.com/shatteredbeam)
[![TfT_02](http://www.gravatar.com/avatar/b8914f9970e1f6ffd5281ce4770e20a7.png)](https://github.com/TfT-02)
[![t00thpick1](http://www.gravatar.com/avatar/ee23c7794a0c40120c3474287c7bce06.png)](https://github.com/t00thpick1)
[![riking](https://1.gravatar.com/avatar/aca9f37e569ac3a63929920035a91ba4.png)](https://github.com/riking)
### Special thanks
[![EasyMFnE](https://www.gravatar.com/avatar/99c9a1fa3bbf957791ceac7b45daadb0.png)](https://github.com/EasyMFnE)
Added the Alchemy skill
## Compiling
mcMMO uses Maven 3 to manage dependancies, packaging, and shading of necessary classes; Maven 3 is required to compile mcMMO.
mcMMO uses Maven 3 to manage dependencies, packaging, and shading of necessary classes; Maven 3 is required to compile mcMMO.
The typical command used to build mcMMO is: mvn clean package install
The typical command used to build mcMMO is: `mvn clean package install`
Required Libraries:
* Spout API
* JUnit
* Metrics
* Bukkit
* JUnit
http://dev.bukkit.org/server-mods/mcmmo for more up to date information.
https://spigot.mcmmo.org for more up to date information.

139
build.gradle.kts Normal file
View File

@@ -0,0 +1,139 @@
import com.github.jengelman.gradle.plugins.shadow.tasks.ConfigureShadowRelocation
import com.github.jengelman.gradle.plugins.shadow.tasks.ShadowJar
/*
* Declares the version of the Gradle wrapper. We need 4.9 for now because
* ForgeGradle 3+ is a hard dependency for Gradle 4.9, 4.10 is not compatible
*/
val wrapper by tasks.getting(Wrapper::class) {
gradleVersion = "4.9"
}
/*
* Sets up project references to be used in child scripts, like
* ":bukkit", ":core", ":sponge" where these projects need to be
* referred to for dependencies, paths, outputs etc.
* Projects is specifically an object stored in <root>/buildSrc/src/main/java/Config.kt
* It's a nullable variable, but we just store it here and use it elsewhere.
*/
Projects.core = project("core")
Projects.bukkit = project("bukkit")
Projects.sponge = project("sponge")
/*
Declares the various other projects and stores them to Gradle's `extra` properties.
These are potentially usable for other purposes, but for now, they're here only to
declare the values for this root project's dependency (for shadowjar)
*/
var core: Project by extra { project("core") }
val bukkit by extra { project("bukkit") }
val bukkit_18 by extra { bukkit.project("1_8_8") }
val bukkit_112 by extra { bukkit.project("1_12") }
val bukkit_113 by extra { bukkit.project("1_13") }
val sponge by extra { project("sponge") }
val sponge_7 by extra { sponge.project("api7") }
group = properties["pluginGroup"]!!
version = properties["pluginVersion"]!!
/*
Even though all projects declares some of these plugins, we want to declare them the traditional
way so that we can have IDE utiliziation and processing, it helps with writing these scripts.
*/
plugins {
`java-library`
`maven-publish`
id("com.github.johnrengelman.shadow") version "4.0.4"
}
/*
Default management for ALL projects, not just root, or ":bukkit", but all projects and
their children projects.
*/
allprojects {
/*
We need the java library processing, and shadow allows us to run
shadowJar to relocate dependencies and bundle dependencies into a fat jar.
*/
apply(plugin="java-library")
apply(plugin="com.github.johnrengelman.shadow")
/*
Defines all the repositories for all project dependency resolutions. Some of these
repositories are meant for specific dependencies, so the content filters will
prevent attempts at resolving those dependencies being requested at those repositories.
Constants are defined in <root>/buildSrc/src/main/java/Config.kt
*/
repositories {
mavenCentral()
maven(Repos.sk89q) // WorldEdit/WorldGuard
maven(Repos.bstats) // bstats
maven(Repos.sponge) // Sponge, Configurate, and some other things
maven(Repos.spigot) // Spigot and Bukkit
maven(Repos.sonatype) // General Maven
mavenLocal() // For nms packages
}
// Sets all projects compatibility level to Java 8
java {
sourceCompatibility = JavaVersion.VERSION_1_8
targetCompatibility = JavaVersion.VERSION_1_8
}
// Encoding for all packages is UTF-8
tasks.getting(JavaCompile::class) {
options.encoding = "UTF-8"
}
// Default shadow jar configuration. Sub projects will override and add on,
// but this sets up at the very least the jdbc connection dependencies to be relocated
val shadowJar by tasks.getting(ShadowJar::class) { // Configure basics of relocation
relocate(Shadow.Origin.juli, Shadow.Target.juli)
relocate(Shadow.Origin.tomcat, Shadow.Target.tomcat)
exclude(Shadow.Exclude.ForgeGradle.dummyThing)
exclude(Shadow.Exclude.ForgeGradle.template)
}
}
/*
All subprojects shadowjar tasks that will exclude various dependencies, while
the root project will include some of these dependencies (like jdbc, configurate)
so that the sub project jars are already somewhat minimized, in the event those
platform jars are to be deployed individually versus an overall "all platforms"
jar.
*/
subprojects {
val shadowJar by tasks.getting(ShadowJar::class) {
dependencies {
exclude(dependency("${Deps.Groups.sponge}:${Deps.Modules.configurate_yaml}"))
exclude(dependency(Shadow.Exclude.guava))
exclude(dependency(Shadow.Exclude.snakeyaml))
exclude(dependency(Shadow.Exclude.tomcat))
exclude(dependency(Shadow.Exclude.juli))
}
}
}
// Sets up this root project to depend on all the implementations supported.
// By default, they all already should have shadow relocations and packaging,
// and their dependencies should not be leaking into this project.
dependencies {
compile(bukkit)
compile(sponge)
compile(bukkit_18)
compile(bukkit_112)
compile(bukkit_113)
compile(sponge_7)
}
// Configure shadow for the root project, we want to relocate bstats-bukkit
// and whatever else is configured in the allProjects configuration
val shadowJar by tasks.getting(ShadowJar::class) { // Root shadow relocation
relocate(Shadow.Origin.bstatsBukkit, Shadow.Target.bstatsBukkit)
baseName = "mcMMO"
classifier = "bundle"
}
// Tell the build task to depend on shadowjar.
val build by tasks
build.dependsOn(shadowJar)

View File

@@ -0,0 +1,8 @@
plugins {
`kotlin-dsl`
}
repositories {
jcenter()
}

View File

@@ -0,0 +1,191 @@
@file:Suppress("MayBeConstant", "unused")
import org.gradle.api.Project
object Plugins {
const val spongeGradleId = "${Deps.Groups.sponge}.plugin"
object FG2_3 {
const val classpath = "net.minecraftforge.gradle:ForgeGradle:${Versions.fg23}"
const val extensionName = "minecraft"
const val id = "net.minecraftforge.gradle.forge"
}
}
object Repos {
const val sk89q = "https://maven.sk89q.com/repo"
// bStats
const val bstats = "https://repo.codemc.org/repository/maven-public"
// configurate
const val sponge = "https://repo.spongepowered.org/maven/"
const val spigot = "https://hub.spigotmc.org/nexus/content/repositories/snapshots"
const val sonatype = "https://oss.sonatype.org/content/repositories/snapshots"
const val forge = "https://files.minecraftforge.net/maven/"
}
object Config {
object Libs {
const val configurate = "${Deps.Groups.sponge}:${Deps.Modules.configurate_yaml}:${Versions.configurate}"
const val jdbc = "${Deps.Groups.tomcat}:${Deps.Modules.jdbc}:${Versions.jdbc}"
const val juli = "${Deps.Groups.tomcat}:${Deps.Modules.juli}:${Versions.jdbc}"
const val junitDep = "${Deps.Groups.junit}:${Deps.Modules.junit}:${Versions.junit}"
const val flowmath = "${Deps.Groups.flowpowered}:${Deps.Modules.flowmath}:${Versions.flowmath}"
object Bukkit {
object `1_8` {
const val api = "$bukkit:${Versions.bukkit18}"
const val spigotApi = "${Bukkit.spigotApi}:${Versions.bukkit18}"
const val spigot = "$${Bukkit.spigot}:${Versions.bukkit18}"
const val nms = "$craftbukkit:${Versions.bukkit18}"
// only legacy existed at this point, no core.
const val wgLegacy = "${Bukkit.wgLegacy}:${Versions.wg18}"
}
object `1_12` {
const val api = "$bukkit:${Versions.bukkit112}"
const val spigotApi = "${Bukkit.spigotApi}:${Versions.bukkit112}"
const val spigot = "$${Bukkit.spigot}:${Versions.bukkit112}"
const val nms = "$craftbukkit:${Versions.bukkit112}"
// only legacy existed at this point, no core.
const val wgLegacy = "${Bukkit.wgLegacy}:${Versions.wg112}"
}
object `1_13` {
const val api = "$bukkit:${Versions.bukkit113}"
const val spigotApi = "${Bukkit.spigotApi}:${Versions.bukkit113}"
const val spigot = "$${Bukkit.spigot}:${Versions.bukkit113}"
const val nms = "$craftbukkit:${Versions.bukkit113}"
const val wgCore = "${Bukkit.wgCore}:${Versions.wg113}"
const val wgLegacy = "${Bukkit.wgLegacy}:${Versions.wg113}"
}
const val bukkit = "${Deps.Groups.bukkit}:${Deps.Modules.bukkit}"
const val craftbukkit = "${Deps.Groups.bukkit}:${Deps.Modules.craftbukkit}"
const val wgCore = "${Deps.Groups.worldguard}:${Deps.Modules.wgCore}"
const val wgLegacy = "${Deps.Groups.worldguard}:${Deps.Modules.wgLegacy}"
const val spigotApi = "${Deps.Groups.spigot}:${Deps.Modules.spigotApi}"
const val spigot = "${Deps.Groups.spigot}:${Deps.Modules.spigot}"
const val bstats = "${Deps.Groups.bstats}:${Deps.Modules.bstatsBukit}:${Versions.bstats}"
}
object Sponge {
object API7 { // All of these are specific to the API7 module, API8 will change
const val forgeGradleId = "net.minecraftforge.gradle.forge"
const val spongeGradleId = "${Deps.Groups.sponge}.plugin"
const val spongeGradleVersion = "0.9.0"
const val api = "${Sponge.api}:${Versions.sapi7}"
const val common = "${Sponge.common}:${Versions.spongeImpl7}"
const val forge_version = "14.23.5.2768"
const val minecraftVersion = "1.12.2-$forge_version"
const val mappings = "snapshot_20180808"
}
object Exclude {
const val group = Deps.Groups.sponge
const val module = Deps.Modules.spongeAPI
}
const val api = "${Deps.Groups.sponge}:${Deps.Modules.spongeAPI}"
const val common = "${Deps.Groups.sponge}:${Deps.Modules.spongecommon}"
const val bstats = "${Deps.Groups.bstats}:${Deps.Modules.bstatsSponge}:${Versions.bstats}"
}
}
}
object Deps {
object Groups {
const val nossr = "com.gmail.nossr50"
const val google = "com.google"
const val guava = "com.google.guava"
const val gson = "com.google.code.gson"
const val yaml = "org.yaml"
const val sk89q = "com.sk89q"
const val apache = "org.apache"
const val worldguard = "$sk89q.worldguard"
const val worldedit = "$sk89q.worldedit"
const val sponge = "org.spongepowered"
const val spigot = "org.spigotmc"
const val md5 = "net.md_5"
const val bukkit = "org.bukkit"
const val bstats = "org.bstats"
const val tomcat = "org.apache.tomcat"
const val junit = "junit"
const val checker = "org.checkerframework"
const val flowpowered = "com.flowpowered"
}
object Modules {
const val guava = "guava"
const val gson = "gson"
const val snakeyaml = "snakeyaml"
const val wgCore = "worldguard-core"
const val wgLegacy = "worldguard-legacy"
const val bungeecordChat = "bungeecord-chat"
const val spongeAPI = "spongeapi"
const val spongecommon = "spongecommon"
const val spongeforge = "spongeforge"
const val spongevanilla = "spongevanilla"
const val bukkit = "bukkit"
const val craftbukkit = "craftbukkit"
const val bstatsBukit = "bstats-bukkit"
const val bstatsSponge = "bstats-sponge"
const val spigotApi = "spigot-api"
const val spigot = "spigot"
const val configurate = "configurate"
const val configurate_core = "${configurate}-core"
const val configurate_yaml = "${configurate}-yaml"
const val jdbc = "tomcat-jdbc"
const val juli = "tomcat-juli"
const val junit = "junit"
const val checker = "checker-qual"
const val flowmath = "flow-math"
}
}
object Projects {
var core: Project? = null
var bukkit: Project? = null
var sponge: Project? = null
}
object Shadow {
object Origin {
const val juli = "${Deps.Groups.apache}.juli"
const val tomcat = "${Deps.Groups.apache}.tomcat"
const val apache = "${Deps.Groups.apache}.commons.logging"
const val bstatsBukkit = "${Deps.Groups.bstats}.bukkit"
const val configurate = "ninja.leaping.configurate"
const val checker = "org.checkerframework"
}
object Target {
const val juli = "${Deps.Groups.nossr}.database.tomcat.juli"
const val tomcat = "${Deps.Groups.nossr}.database.tomcat"
const val apache = "${Deps.Groups.nossr}.commons.logging"
const val bstatsBukkit = "${Deps.Groups.nossr}.metrics.bstat"
const val configurate = "${Deps.Groups.nossr}.${Deps.Modules.configurate}"
const val checker = "${Deps.Groups.nossr}.${Deps.Modules.configurate}.checkerframework"
}
object Exclude {
const val tomcat = "${Deps.Groups.tomcat}:${Deps.Modules.jdbc}"
const val juli = "${Deps.Groups.apache}:${Deps.Modules.juli}"
const val guava = "${Deps.Groups.guava}:${Deps.Modules.guava}"
const val snakeyaml = "${Deps.Groups.yaml}:${Deps.Modules.snakeyaml}"
const val bukkit = Deps.Groups.bukkit
const val spigot = Deps.Groups.spigot
const val sk89q = "com.sk89q"
const val wg = "$sk89q.worldguard"
const val intake = "$sk89q.intake"
const val flyway = "com.flywaydb"
const val khelekore = "org.khelekore"
const val findbugs = "com.google.code.findbugs"
const val bstats = "${Deps.Groups.bstats}"
object ForgeGradle {
const val dummyThing = "dummyThing"
const val template = "Version.java.template"
}
}
}

View File

@@ -0,0 +1,16 @@
object Versions {
const val configurate = "3.6" // Latest configurate
const val flowmath = "1.0.4-SNAPSHOT"
const val bukkit18 = "1.8.8-R0.1-SNAPSHOT" // Last bukkit 1.8.8
const val bukkit112 = "1.12.2-R0.1-SNAPSHOT" // Last bukkit 1.12.2
const val bukkit113 = "1.13.2-R0.1-SNAPSHOT" // Latest bukkit
const val sapi7 = "7.1.0" // Latest SpongeAPI stable
const val spongeImpl7 = "7.1.5" // Latest SpongeCommon stable
const val jdbc = "7.0.52"
const val junit = "4.12"
const val fg23 = "2.3-SNAPSHOT" // ForgeGradle to support MC 1.12.2
const val wg18 = "6.1.2" // Bukkit/CraftBukkit/Spigot 1.8.8 supported build, works on newer, but last one to support 1.8.8
const val wg112 = "6.2" // Last WorldGuard to support 1.12
const val wg113 = "7.0.0-SNAPSHOT" // Latest WorldGuard to support 1.13.2
const val bstats = "1.4" // Supports all backwards compatible. Always relocated
}

View File

@@ -0,0 +1,27 @@
import Config.Libs.Bukkit.`1_12` as Bukkit
// Config is located in <root>/buildSrc/src/main/java/Config.kt
// It provides a bunch of constant values we use as dependency
// strings, so we don't have to duplicate a bunch of them in
// various scripts.
plugins {
java // This is already provided, but for static compilation,
// we declare it here so we can use the IDE static type references
}
/*
Dependency inheritance is as follows
- ":core", which provides
configurate, tomcat jdbc/juli, and flowmath. It excludes sub
dependencies like guava and apache commons lang.
- ":bukkit", which provides nothing on it's own, except the
core bukkit classes that can be built on 1.13.2 API (which may change).
It also defines all subprojects to depend on ":core", and ":bukkit",
and bstats-bukkit.
*/
dependencies {
compileOnly(Bukkit.api) // Bukkit API for 1.12.2
compileOnly(Bukkit.nms) // CraftBukkit for 1.12.2
compileOnly(Bukkit.wgLegacy) // WorldGuard for 1.12.2 bukkit
}

View File

@@ -0,0 +1,106 @@
package com.gmail.nossr50.bukkit.v1_12;
import com.gmail.nossr50.VersionedHandler;
import com.gmail.nossr50.mcMMO;
import com.google.common.base.Joiner;
import com.google.common.collect.ImmutableMap;
import net.minecraft.server.v1_12_R1.Chunk;
import net.minecraft.server.v1_12_R1.EntityTypes;
import net.minecraft.server.v1_12_R1.IBlockData;
import net.minecraft.server.v1_12_R1.IBlockState;
import net.minecraft.server.v1_12_R1.MinecraftKey;
import net.minecraft.server.v1_12_R1.RegistryBlocks;
import net.minecraft.server.v1_12_R1.RegistryMaterials;
import org.bukkit.block.Block;
import org.bukkit.block.BlockState;
import org.bukkit.craftbukkit.v1_12_R1.CraftChunk;
import org.bukkit.craftbukkit.v1_12_R1.block.CraftBlockState;
import org.bukkit.craftbukkit.v1_12_R1.entity.CraftEntity;
import org.bukkit.entity.Entity;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
public class NmsHandler extends VersionedHandler {
/**
* Static reference to the block registry. Don't really care about the fact that
* it is being stored as a reference here, but for imports reasons, it's smaller
* line length makes it optimal to read for method usages.
*/
private static final RegistryBlocks<MinecraftKey, net.minecraft.server.v1_12_R1.Block> BLOCK_REGISTRY = net.minecraft.server.v1_12_R1.Block.REGISTRY;
/**
* We can keep track of block state id's by generating them on demand, i.e., when
* they're being requested from Blocks, or BlockDatas.
*/
private static final RegistryMaterials<MinecraftKey, IBlockData> BLOCK_STATE_REGISTRY = new RegistryMaterials<>();
NmsHandler(mcMMO plugin) {
super(plugin);
}
@Override
public String getIdFor(Block block) {
// We have to get the underlying nms block by the block, which might as well just be the type id.
final Chunk chunk = ((CraftChunk) block.getChunk()).getHandle();
// Get the block state from the underlying chunk (stored by reference in CraftBlock)
final IBlockData blockState = chunk.a(block.getX(), block.getY(), block.getZ());
// Sadly, Mojang doesn't store the string id onto blocks, states, or any of their types, they just call the registry.
final MinecraftKey key = BLOCK_REGISTRY.b(blockState.getBlock());
return key.toString();
}
@Override
public String getIdFor(Entity entity) {
// Every entity knows it's "type". Here, we just use the right method getter to get the EntityTypes instance for that entity
final net.minecraft.server.v1_12_R1.Entity nmsEntity = ((CraftEntity) entity).getHandle();
// And then... well. we get the string id from the registry, based on the entity class to id mapping in EntityTypes.
final MinecraftKey key = EntityTypes.a(nmsEntity);
// If the key is null, well, we've got bigger problems...
return key == null ? "minecraft:slime" : key.toString();
}
@SuppressWarnings("Duplicates")
@Override
public String getIdFor(BlockState block) {
// Since we don't really want to trust what "BlockState" gives us, and the API doesn't give us anything but
// what the API wants to give us, we have to dig into internals to get the true BlockState representation
final CraftBlockState craftState = (CraftBlockState) block;
// Because CraftBlock also stores the chunk reference, we can short cut in to use the chunk, instead of pinging
// the chunk map on WorldServer
final CraftChunk craftChunk = (CraftChunk) craftState.getChunk();
// Then query for the block state from the chunk.
final IBlockData nmsState = craftChunk.getHandle().a(block.getX(), block.getY(), block.getZ());
// And then we're gucci
final net.minecraft.server.v1_12_R1.Block nmsBlock = nmsState.getBlock();
final MinecraftKey blockKey = BLOCK_REGISTRY.b(nmsBlock);
// Now we can check if our blockstate registry actually has the block state.
final MinecraftKey stateKey = BLOCK_STATE_REGISTRY.b(nmsState);
if (stateKey != null) { // If the state has been registered by the handler, then by all means.
return stateKey.toString();
}
// If not, well, it needs to have a key generated and registered.
final String nameSpace = blockKey.getKey();
StringBuilder builder = new StringBuilder();
builder.append(nameSpace); // We only want to get the block id, not the domain id, since that's going to be appended later
// Get the full Property -> Value mapping for the block state
final ImmutableMap<IBlockState<?>, Comparable<?>> properties = nmsState.t();
if (!properties.isEmpty()) {
builder.append('[');
Joiner joiner = Joiner.on(',');
List<String> propertyValues = new ArrayList<>();
// Yadadadada, go through all property entries and add each as a string for the "propertyName=value" (like "variant=oak")
for (Map.Entry<IBlockState<?>, Comparable<?>> entry : properties.entrySet()) {
// a() gets the inputted "name" for the state, the value, well, that gets the value, which is always toStringable.
propertyValues.add(entry.getKey().a() + "=" + entry.getValue());
}
builder.append(joiner.join(propertyValues));
builder.append(']');
}
// Now we can make the MinecraftKey...
final MinecraftKey newKey = new MinecraftKey(builder.toString());
BLOCK_STATE_REGISTRY.a(newKey, nmsState);
return newKey.toString();
}
}

View File

@@ -0,0 +1,27 @@
import Config.Libs.Bukkit.`1_13` as Bukkit
// Config is located in <root>/buildSrc/src/main/java/Config.kt
// It provides a bunch of constant values we use as dependency
// strings, so we don't have to duplicate a bunch of them in
// various scripts. The import allows us to "import as" for shorthand
plugins {
`java-library` // This is already provided, but for static compilation,
// we declare it here so we can use the IDE static type references
}
/*
Dependency inheritance is as follows
- ":core", which provides
configurate, tomcat jdbc/juli, and flowmath. It excludes sub
dependencies like guava and apache commons lang.
- ":bukkit", which provides nothing on it's own, except the
core bukkit classes that can be built on 1.13.2 API (which may change).
It also defines all subprojects to depend on ":core", and ":bukkit",
and bstats-bukkit.
*/
dependencies {
compileOnly(Bukkit.api) // Bukkit API for 1.13.2 - Defined in <root>/buildSrc/src/main/java/Config.kt
compileOnly(Bukkit.nms) // CraftBukkit-1.13.2-R0.1-SNAPSHOT - Defined in <root>/buildSrc/src/main/java/Config.kt
compileOnly(Bukkit.wgCore) // WorldGuard-core - Defined in <root>/buildSrc/src/main/java/Config.kt
compileOnly(Bukkit.wgLegacy) // WorldGuard-legacy - Defined in <root>/buildSrc/src/main/java/Config.kt
}

View File

@@ -0,0 +1,101 @@
package com.gmail.nossr50.bukkit.v1_13;
import com.gmail.nossr50.VersionedHandler;
import com.gmail.nossr50.mcMMO;
import com.google.common.base.Joiner;
import com.google.common.collect.ImmutableMap;
import net.minecraft.server.v1_13_R2.EntityTypes;
import net.minecraft.server.v1_13_R2.IBlockData;
import net.minecraft.server.v1_13_R2.IBlockState;
import net.minecraft.server.v1_13_R2.IRegistry;
import net.minecraft.server.v1_13_R2.MinecraftKey;
import net.minecraft.server.v1_13_R2.RegistryMaterials;
import net.minecraft.server.v1_13_R2.WorldServer;
import org.bukkit.block.Block;
import org.bukkit.block.BlockState;
import org.bukkit.craftbukkit.v1_13_R2.block.CraftBlock;
import org.bukkit.craftbukkit.v1_13_R2.block.CraftBlockState;
import org.bukkit.craftbukkit.v1_13_R2.entity.CraftEntity;
import org.bukkit.entity.Entity;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
public class NmsHandler extends VersionedHandler {
private static final IRegistry<net.minecraft.server.v1_13_R2.Block> BLOCK_REGISTRY = IRegistry.BLOCK;
private static final IRegistry<EntityTypes<?>> ENTITY_REGISTRY = IRegistry.ENTITY_TYPE;
/**
* We use {@link RegistryMaterials} because we don't want to default to another block state,
* if a {@link IBlockData} is not registered, we need to generate an ID and register that key to
* that {@link IBlockData}. By default, this should be populated during plugin startup by
* calling some init method, but that will be determined later.
*/
private static final IRegistry<IBlockData> BLOCK_STATE_REGISTRY = new RegistryMaterials<>();
NmsHandler(mcMMO plugin) {
super(plugin);
}
@Override
public String getIdFor(Block block) {
// We have to get the underlying nms block by the block, which might as well just be the type id.
final WorldServer world = ((CraftBlock) block).getCraftWorld().getHandle();
// The registry.c(T) will return MinecraftKey, and the toString() returns the "$mod:$name", so "minecraft:stone"
final IBlockData blockState = world.getType(((CraftBlock) block).getPosition());
// Sadly, Mojang doesn't store the string id onto blocks, states, or any of their types, they just call the registry.
final MinecraftKey key = BLOCK_REGISTRY.getKey(blockState.getBlock());
// Sometimes, there's a rare case with mods where the key is going to be null, but should never happen in bukkit/spigot.
return key == null ? "minecraft:air" : key.toString();
}
@Override
public String getIdFor(Entity entity) {
// Every entity knows it's "type". Here, we just use the right method getter to get the EntityTypes instance for that entity
final EntityTypes<?> entityType = ((CraftEntity) entity).getHandle().P();
// And then... well. we get the string id from the registry!
final MinecraftKey key = ENTITY_REGISTRY.getKey(entityType);
// If the key is null, well, we've got bigger problems...
return key == null ? "minecraft:slime" : key.toString();
}
@SuppressWarnings("Duplicates")
@Override
public String getIdFor(BlockState block) {
// Much like #getIdFor(Block) except here we have the "state" by numerical id. So.. we have to grab it from
// the world.
final CraftBlockState craftState = (CraftBlockState) block;
final IBlockData nmsState = craftState.getHandle();
final net.minecraft.server.v1_13_R2.Block nmsBlock = nmsState.getBlock();
final MinecraftKey blockKey = BLOCK_REGISTRY.getKey(nmsBlock);
// Now we can check if our blockstate registry actually has the block state.
final MinecraftKey stateKey = BLOCK_STATE_REGISTRY.getKey(nmsState);
if (stateKey != null) { // If the state has been registered by the handler, then by all means.
return stateKey.toString();
}
// If not, well, it needs to have a key generated and registered.
final String nameSpace = blockKey.getKey();
StringBuilder builder = new StringBuilder();
builder.append(nameSpace); // We only want to get the block id, not the domain id, since that's going to be appended later
// Get the full Property -> Value mapping for the block state
final ImmutableMap<IBlockState<?>, Comparable<?>> properties = nmsState.getStateMap();
if (!properties.isEmpty()) {
builder.append('[');
Joiner joiner = Joiner.on(',');
List<String> propertyValues = new ArrayList<>();
// Yadadadada, go through all property entries and add each as a string for the "propertyName=value" (like "variant=oak")
for (Map.Entry<IBlockState<?>, Comparable<?>> entry : properties.entrySet()) {
// a() gets the inputted "name" for the state, the value, well, that gets the value, which is always toStringable.
propertyValues.add(entry.getKey().a() + "=" + entry.getValue());
}
builder.append(joiner.join(propertyValues));
builder.append(']');
}
// Now we can make the MinecraftKey...
final MinecraftKey newKey = new MinecraftKey(builder.toString());
BLOCK_STATE_REGISTRY.a(newKey, nmsState);
return newKey.toString();
}
}

View File

@@ -0,0 +1,23 @@
import Config.Libs.Bukkit.`1_8` as Bukkit
plugins {
java
}
/*
Dependency inheritance is as follows
- ":core", which provides
configurate, tomcat jdbc/juli, and flowmath. It excludes sub
dependencies like guava and apache commons lang.
- ":bukkit", which provides nothing on it's own, except the
core bukkit classes that can be built on 1.13.2 API (which may change).
It also defines all subprojects to depend on ":core", and ":bukkit",
and bstats-bukkit.
*/
dependencies {
compileOnly(Bukkit.api) // Bukkit API for 1.8.8 - Defined in <root>/buildSrc/src/main/java/Config.kt
compileOnly(Bukkit.nms) // CraftBukkit-1.8.8-R0.3-SNAPSHOT - Defined in <root>/buildSrc/src/main/java/Config.kt
compileOnly(Bukkit.wgLegacy) // Old worldguard - Defined in <root>/buildSrc/src/main/java/Config.kt
}

View File

@@ -0,0 +1,93 @@
package com.gmail.nossr50.bukkit.v1_8;
import com.gmail.nossr50.VersionedHandler;
import com.gmail.nossr50.mcMMO;
import com.google.common.base.Joiner;
import com.google.common.collect.ImmutableMap;
import net.minecraft.server.v1_8_R3.Blocks;
import net.minecraft.server.v1_8_R3.EntityTypes;
import net.minecraft.server.v1_8_R3.IBlockData;
import net.minecraft.server.v1_8_R3.IBlockState;
import net.minecraft.server.v1_8_R3.MinecraftKey;
import net.minecraft.server.v1_8_R3.RegistryBlocks;
import org.bukkit.block.Block;
import org.bukkit.block.BlockState;
import org.bukkit.craftbukkit.v1_8_R3.entity.CraftEntity;
import org.bukkit.craftbukkit.v1_8_R3.util.CraftMagicNumbers;
import org.bukkit.entity.Entity;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
@SuppressWarnings({"unused", "Duplicates"}) // We use reflection to load this handler on 1.8 versions
public class NmsHandler extends VersionedHandler {
/**
* Static reference to the block registry. Don't really care about the fact that
* it is being stored as a reference here, but for imports reasons, it's smaller
* line length makes it optimal to read for method usages.
*/
private static final RegistryBlocks<MinecraftKey, net.minecraft.server.v1_8_R3.Block> BLOCK_REGISTRY = net.minecraft.server.v1_8_R3.Block.REGISTRY;
/**
* We can keep track of block state id's by generating them on demand, i.e., when
* they're being requested from Blocks, or BlockDatas.
*/
private static final RegistryBlocks<MinecraftKey, IBlockData> BLOCK_STATE_REGISTRY = new RegistryBlocks<>(BLOCK_REGISTRY.c(Blocks.AIR)); // Default to AIR
NmsHandler(mcMMO plugin) {
super(plugin);
}
@Override
public String getIdFor(Block block) {
// We have to get the underlying nms block by the block, which might as well just be the type id.
final net.minecraft.server.v1_8_R3.Block block1 = CraftMagicNumbers.getBlock(block);
// The registry.c(T) will return MinecraftKey, and the toString() returns the "$mod:$name", so "minecraft:stone"
final MinecraftKey key = BLOCK_REGISTRY.c(block1);
return key.toString();
}
@Override
public String getIdFor(Entity entity) {
// EntityTypes maintains the maps of Class<? extends nms.Entity> to String for id's and to numerical id numbers.
// We of course are using the method that gets us the String id of the entity, such as "minecraft:creeper"
return EntityTypes.b(((CraftEntity) entity).getHandle());
}
@Override
public String getIdFor(BlockState block) {
// Much like #getIdFor(Block) except here we have the "state" by numerical id. So.. we have to grab it from
// the world.
final net.minecraft.server.v1_8_R3.Block nmsBlock = net.minecraft.server.v1_8_R3.Block.REGISTRY.a(block.getTypeId());
final MinecraftKey blockKey = net.minecraft.server.v1_8_R3.Block.REGISTRY.c(nmsBlock);
final IBlockData blockState = nmsBlock.fromLegacyData(block.getRawData());
// Now we can check if our blockstate registry actually has the block state.
final MinecraftKey stateKey = BLOCK_STATE_REGISTRY.c(blockState);
if (stateKey != null) { // If the state has been registered by the handler, then by all means.
return stateKey.toString();
}
// If not, well, it needs to have a key generated and registered.
final String nameSpace = blockKey.a();
StringBuilder builder = new StringBuilder();
builder.append(blockKey.a()); // We only want to get the block id, not the domain id, since that's going to be appended later
// Get the full Property -> Value mapping for the block state
final ImmutableMap<IBlockState, Comparable> properties = blockState.b();
if (!properties.isEmpty()) {
builder.append('[');
Joiner joiner = Joiner.on(',');
List<String> propertyValues = new ArrayList<>();
for (Map.Entry<IBlockState, Comparable> entry : properties.entrySet()) {
// a() gets the inputted "name" for the state, the value, well, that gets the value, which is always toStringable.
propertyValues.add(entry.getKey().a() + "=" + entry.getValue());
}
builder.append(joiner.join(propertyValues));
builder.append(']');
}
// Now we can make the MinecraftKey...
final MinecraftKey newKey = new MinecraftKey(builder.toString());
BLOCK_STATE_REGISTRY.a(newKey, blockState);
return newKey.toString();
}
}

View File

@@ -0,0 +1,12 @@
package com.gmail.nossr50.platform.bukkit;
import org.bukkit.Material;
import org.bukkit.craftbukkit.v1_8_R3.block.CraftBlock;
public class Testing18 {
Material material;
CraftBlock block;
}

77
bukkit/build.gradle.kts Normal file
View File

@@ -0,0 +1,77 @@
import com.github.jengelman.gradle.plugins.shadow.tasks.ShadowJar
import Config.Libs.Bukkit as Bukkit
// Config is located in <root>/buildSrc/src/main/java/Config.kt
// It provides a bunch of constant values we use as dependency
// strings, so we don't have to duplicate a bunch of them in
// various scripts. The import as allows for shorthand.
val bukkit: Project = Projects.bukkit!! // Static project references
val core: Project = Projects.core!! // Stored by Config.kt and created in <root>/build.gradle.kts
/* This configures ":bukkit" and it's dependent projects:
- ":bukkit:1_8_8"
- ":bukkit:1_12"
- ":bukkit:1_13"
Basically sets up all projects to depend on ":core" and
bstats-bukkit. Also sets up shadow to relocate bukkit related
packages to limit platform interference
*/
allprojects {
dependencies {
compile(core) // includes junit for tests
implementation(Bukkit.bstats) // Bukkit bstats
}
// TODO dunno if this works yet... project needs to compile.
val shadowJar by tasks.getting(ShadowJar::class) {
// Relocate bstats for bukkit, as per requirement for bstats
relocate(Shadow.Origin.bstatsBukkit, Shadow.Target.bstatsBukkit)
// Relocate the bukkit platform classes of mcmmo so we don't
// interfere with other platform classes (or core)
relocate(Deps.Groups.nossr, "${Deps.Groups.nossr}.bukkit") {
exclude("${Deps.Groups.nossr}.core")
}
}
}
// Tells all subprojects of ":bukkit" (":bukkit:1_8_8", ":bukkit:1_12",etc.)
// to depend on this project (":bukkit") to inherit the dependencies, and
// does NOT inherit the same configurations (anything configured outside
// here does not persist to child projects).
subprojects {
dependencies {
// Provide the base bukkit plugin dependency for plugin classloading.
// All "versioned" implementations will be properly classloaded by the bukkit parent
compileOnly(bukkit)
}
}
plugins {
`java-library` // This is already provided, but for static compilation,
// we declare it here so we can use the IDE static type references
}
dependencies {
// Temporary dependencies while things are being moved.
compileOnly(Bukkit.`1_13`.spigotApi) { // Spigot API for generic usage. Based on 1.13.2
isTransitive = true // We don't want the dependencies
}
compileOnly(Bukkit.`1_13`.api) { // Bukkit API for generic usage. Based on 1.13.2
isTransitive = true // We don't want the dependencies
}
compileOnly(Bukkit.`1_13`.wgCore) { // WorldGuard dependency, again, for 1.13.2
isTransitive = true // We don't want the dependencies
exclude(group = Shadow.Exclude.sk89q)
exclude(group = Shadow.Exclude.intake, module = "intake")
exclude(group = Shadow.Exclude.sk89q, module = "squirrelid")
exclude(group = Shadow.Exclude.flyway)
exclude(group = Shadow.Exclude.khelekore)
exclude(group = Shadow.Exclude.findbugs)
}
compileOnly(Bukkit.`1_13`.wgLegacy) {
isTransitive = true // We don't want the dependencies
exclude(group = Shadow.Exclude.bukkit)
exclude(group = Shadow.Exclude.sk89q, module = "commandbook")
exclude(group = Shadow.Exclude.bstats)
}
}

View File

@@ -0,0 +1,12 @@
package com.gmail.nossr50;
import org.bukkit.Material;
import org.bukkit.block.data.BlockData;
public class BukkitBlockType {
private Material material;
private BlockData blockData;
}

View File

@@ -0,0 +1,74 @@
package com.gmail.nossr50;
import com.sk89q.worldedit.extension.platform.NoCapablePlatformException;
import org.bukkit.block.Block;
import org.bukkit.block.BlockState;
import org.bukkit.entity.Entity;
public abstract class VersionedHandler {
private static VersionedHandler instance;
private final mcMMO plugin;
protected VersionedHandler(mcMMO plugin) {
this.plugin = plugin;
}
/**
* Gets the string value id of the BlockType, note that this is not the
* blockstate.
*
* Examples include: "minecraft:stone", "minecraft:chest", "thaumcraft:log2"
* BlockStates are more specific like "minecraft:log[variant=oak,axis=x]"
*
* This should be casting down and retrieving the id from the block registry maintained by vanilla.
*
* @param block The block instance (holds byte/numerical id or sometimes block state in newer versions)
* @return The string id of the block type
*/
public abstract String getIdFor(Block block);
/**
* Gets the string value id of the Entity, much like blocks, this is not
* the full string representation of the entity, just the string id of the
* TYPE.
*
* Examples include: "minecraft:creeeper", "minecraft:sheep", "thaumcraft:wisp"
*
* @param entity The entity instance
* @return The string id of the entity's registered type.
*/
public abstract String getIdFor(Entity entity);
// Technically can be TileEntity snapshot references as well.
public abstract String getIdFor(BlockState block);
/**
* Gets the {@link VersionedHandler} instance for this running platform.
* Note that all the handler does is perform various operations necessitated
* by either a lack of, or bridging an implementation of some API/core aspects
* that are not available through Bukkit API (like getting BlockType id's, or
* BlockState id's).
*
* @param plugin The mcmmo plugin
* @return The version handler instance
*/
public VersionedHandler getInstance(mcMMO plugin) {
if (instance == null) {
final String serverPackage = mcMMO.p.getServer().getClass().getPackage().getName();
final String serverVersion = serverPackage.substring(serverPackage.lastIndexOf(".") + 1);
try {
final Class<?> clazz = Class.forName("com.gmail.nossr50.bukkit." + serverVersion + ".NmsHandler");
if (VersionedHandler.class.isAssignableFrom(clazz)) {
instance = (VersionedHandler) clazz.getConstructor(mcMMO.class).newInstance(plugin);
}
} catch (Exception e) {
e.printStackTrace();
throw new NoCapablePlatformException("Could not discover a valid mcMMO VersionedHandler for version:" + serverVersion);
}
}
return instance;
}
}

View File

@@ -0,0 +1,45 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.data.database.FlatfileDatabaseManager;
import com.gmail.nossr50.core.data.database.SQLDatabaseManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import java.util.List;
public class MHDCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (mcMMO.getDatabaseManager() instanceof SQLDatabaseManager) {
SQLDatabaseManager m = (SQLDatabaseManager) mcMMO.getDatabaseManager();
m.resetMobHealthSettings();
for (McMMOPlayer player : UserManager.getPlayers()) {
player.getProfile().setMobHealthbarType(MainConfig.getInstance().getMobHealthbarDefault());
}
sender.sendMessage("Mob health reset");
return true;
}
if (mcMMO.getDatabaseManager() instanceof FlatfileDatabaseManager) {
FlatfileDatabaseManager m = (FlatfileDatabaseManager) mcMMO.getDatabaseManager();
m.resetMobHealthSettings();
for (McMMOPlayer player : UserManager.getPlayers()) {
player.getProfile().setMobHealthbarType(MainConfig.getInstance().getMobHealthbarDefault());
}
sender.sendMessage("Mob health reset");
return true;
}
return false;
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
return ImmutableList.of();
}
}

View File

@@ -0,0 +1,325 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.core.skills.ModConfigType;
import com.gmail.nossr50.core.util.Misc;
import com.gmail.nossr50.mcMMO;
import org.bukkit.Material;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import java.io.*;
import java.util.ArrayList;
import java.util.HashMap;
public class McImportCommand implements CommandExecutor {
int fileAmount;
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 0:
importModConfig();
return true;
default:
return false;
}
}
public boolean importModConfig() {
String importFilePath = mcMMO.getModDirectory() + File.separator + "import";
File importFile = new File(importFilePath, "import.log");
mcMMO.p.getLogger().info("Starting import of mod materials...");
fileAmount = 0;
HashMap<ModConfigType, ArrayList<String>> materialNames = new HashMap<ModConfigType, ArrayList<String>>();
BufferedReader in = null;
try {
// Open the file
in = new BufferedReader(new FileReader(importFile));
String line;
String materialName;
String modName;
// While not at the end of the file
while ((line = in.readLine()) != null) {
String[] split1 = line.split("material ");
if (split1.length != 2) {
continue;
}
String[] split2 = split1[1].split(" with");
if (split2.length != 2) {
continue;
}
materialName = split2[0];
// Categorise each material under a mod config type
ModConfigType type = ModConfigType.getModConfigType(materialName);
if (!materialNames.containsKey(type)) {
materialNames.put(type, new ArrayList<String>());
}
materialNames.get(type).add(materialName);
continue;
}
} catch (FileNotFoundException e) {
mcMMO.p.getLogger().warning("Could not find " + importFile.getAbsolutePath() + " ! (No such file or directory)");
mcMMO.p.getLogger().warning("Copy and paste latest.log to " + importFile.getParentFile().getAbsolutePath() + " and rename it to import.log");
return false;
} catch (Exception e) {
e.printStackTrace();
return false;
} finally {
tryClose(in);
}
createOutput(materialNames);
mcMMO.p.getLogger().info("Import finished! Created " + fileAmount + " files!");
return true;
}
private void createOutput(HashMap<ModConfigType, ArrayList<String>> materialNames) {
for (ModConfigType modConfigType : materialNames.keySet()) {
HashMap<String, ArrayList<String>> materialNamesType = new HashMap<String, ArrayList<String>>();
for (String materialName : materialNames.get(modConfigType)) {
String modName = Misc.getModName(materialName);
if (!materialNamesType.containsKey(modName)) {
materialNamesType.put(modName, new ArrayList<String>());
}
materialNamesType.get(modName).add(materialName);
}
createOutput(modConfigType, materialNamesType);
}
}
private void tryClose(Closeable c) {
if (c == null) {
return;
}
try {
c.close();
} catch (IOException e) {
e.printStackTrace();
}
}
private void createOutput(ModConfigType modConfigType, HashMap<String, ArrayList<String>> materialNames) {
File outputFilePath = new File(mcMMO.getModDirectory() + File.separator + "output");
if (!outputFilePath.exists() && !outputFilePath.mkdirs()) {
mcMMO.p.getLogger().severe("Could not create output directory! " + outputFilePath.getAbsolutePath());
}
FileWriter out = null;
String type = modConfigType.name().toLowerCase();
for (String modName : materialNames.keySet()) {
File outputFile = new File(outputFilePath, modName + "." + type + ".yml");
mcMMO.p.getLogger().info("Creating " + outputFile.getName());
try {
if (outputFile.exists() && !outputFile.delete()) {
mcMMO.p.getLogger().severe("Not able to delete old output file! " + outputFile.getAbsolutePath());
}
if (!outputFile.createNewFile()) {
mcMMO.p.getLogger().severe("Could not create output file! " + outputFile.getAbsolutePath());
continue;
}
StringBuilder writer = new StringBuilder();
HashMap<String, ArrayList<String>> configSections = getConfigSections(modConfigType, modName, materialNames);
if (configSections == null) {
mcMMO.p.getLogger().severe("Something went wrong!! type is " + type);
return;
}
// Write the file, go through each skill and write all the materials
for (String configSection : configSections.keySet()) {
if (configSection.equals("UNIDENTIFIED")) {
writer.append("# This isn't a valid config section and all materials in this category need to be").append("\r\n");
writer.append("# copy and pasted to a valid section of this config file.").append("\r\n");
}
writer.append(configSection).append(":").append("\r\n");
for (String line : configSections.get(configSection)) {
writer.append(line).append("\r\n");
}
writer.append("\r\n");
}
out = new FileWriter(outputFile);
out.write(writer.toString());
} catch (IOException e) {
e.printStackTrace();
return;
} catch (Exception e) {
e.printStackTrace();
return;
} finally {
tryClose(out);
fileAmount++;
}
}
}
private HashMap<String, ArrayList<String>> getConfigSections(ModConfigType type, String modName, HashMap<String, ArrayList<String>> materialNames) {
switch (type) {
case BLOCKS:
return getConfigSectionsBlocks(modName, materialNames);
case TOOLS:
return getConfigSectionsTools(modName, materialNames);
case ARMOR:
return getConfigSectionsArmor(modName, materialNames);
case UNKNOWN:
return getConfigSectionsUnknown(modName, materialNames);
}
return null;
}
private HashMap<String, ArrayList<String>> getConfigSectionsBlocks(String modName, HashMap<String, ArrayList<String>> materialNames) {
HashMap<String, ArrayList<String>> configSections = new HashMap<String, ArrayList<String>>();
// Go through all the materials and categorise them under a skill
for (String materialName : materialNames.get(modName)) {
String skillName = "UNIDENTIFIED";
if (materialName.contains("ORE")) {
skillName = "Mining";
} else if (materialName.contains("LOG") || materialName.contains("LEAVES")) {
skillName = "Woodcutting";
} else if (materialName.contains("GRASS") || materialName.contains("FLOWER") || materialName.contains("CROP")) {
skillName = "Herbalism";
} else if (materialName.contains("DIRT") || materialName.contains("SAND")) {
skillName = "Excavation";
}
if (!configSections.containsKey(skillName)) {
configSections.put(skillName, new ArrayList<String>());
}
ArrayList<String> skillContents = configSections.get(skillName);
skillContents.add(" " + materialName + "|0:");
skillContents.add(" " + " " + "XP_Gain: 99");
skillContents.add(" " + " " + "Double_Drops_Enabled: true");
if (skillName.equals("Mining")) {
skillContents.add(" " + " " + "Smelting_XP_Gain: 9");
} else if (skillName.equals("Woodcutting")) {
skillContents.add(" " + " " + "Is_Log: " + materialName.contains("LOG"));
}
}
return configSections;
}
private HashMap<String, ArrayList<String>> getConfigSectionsTools(String modName, HashMap<String, ArrayList<String>> materialNames) {
HashMap<String, ArrayList<String>> configSections = new HashMap<String, ArrayList<String>>();
// Go through all the materials and categorise them under a tool type
for (String materialName : materialNames.get(modName)) {
String toolType = "UNIDENTIFIED";
if (materialName.contains("PICKAXE")) {
toolType = "Pickaxes";
} else if (materialName.contains("AXE")) {
toolType = "Axes";
} else if (materialName.contains("BOW")) {
toolType = "Bows";
} else if (materialName.contains("HOE")) {
toolType = "Hoes";
} else if (materialName.contains("SHOVEL") || materialName.contains("SPADE")) {
toolType = "Shovels";
} else if (materialName.contains("SWORD")) {
toolType = "Swords";
}
if (!configSections.containsKey(toolType)) {
configSections.put(toolType, new ArrayList<String>());
}
ArrayList<String> skillContents = configSections.get(toolType);
skillContents.add(" " + materialName + ":");
skillContents.add(" " + " " + "XP_Modifier: 1.0");
skillContents.add(" " + " " + "Tier: 1");
skillContents.add(" " + " " + "Ability_Enabled: true");
addRepairableLines(materialName, skillContents);
}
return configSections;
}
private HashMap<String, ArrayList<String>> getConfigSectionsArmor(String modName, HashMap<String, ArrayList<String>> materialNames) {
HashMap<String, ArrayList<String>> configSections = new HashMap<String, ArrayList<String>>();
// Go through all the materials and categorise them under an armor type
for (String materialName : materialNames.get(modName)) {
String toolType = "UNIDENTIFIED";
if (materialName.contains("BOOT") || materialName.contains("SHOE")) {
toolType = "Boots";
} else if (materialName.contains("CHESTPLATE") || materialName.contains("CHEST")) {
toolType = "Chestplates";
} else if (materialName.contains("HELM") || materialName.contains("HAT")) {
toolType = "Helmets";
} else if (materialName.contains("LEGGINGS") || materialName.contains("LEGS") || materialName.contains("PANTS")) {
toolType = "Leggings";
}
if (!configSections.containsKey(toolType)) {
configSections.put(toolType, new ArrayList<String>());
}
ArrayList<String> skillContents = configSections.get(toolType);
skillContents.add(" " + materialName + ":");
addRepairableLines(materialName, skillContents);
}
return configSections;
}
private void addRepairableLines(String materialName, ArrayList<String> skillContents) {
skillContents.add(" " + " " + "Repairable: true");
skillContents.add(" " + " " + "Repair_Material: REPAIR_MATERIAL_NAME");
skillContents.add(" " + " " + "Repair_Material_Data_Value: 0");
skillContents.add(" " + " " + "Repair_Material_Quantity: 9");
skillContents.add(" " + " " + "Repair_Material_Pretty_Name: Repair Item Name");
skillContents.add(" " + " " + "Repair_MinimumLevel: 0");
skillContents.add(" " + " " + "Repair_XpMultiplier: 1.0");
Material material = Material.matchMaterial(materialName);
short durability = (material == null) ? (short) 9999 : material.getMaxDurability();
skillContents.add(" " + " " + "Durability: " + ((durability > 0) ? durability : (short) 9999));
}
private HashMap<String, ArrayList<String>> getConfigSectionsUnknown(String modName, HashMap<String, ArrayList<String>> materialNames) {
HashMap<String, ArrayList<String>> configSections = new HashMap<String, ArrayList<String>>();
// Go through all the materials and print them
for (String materialName : materialNames.get(modName)) {
String configKey = "UNIDENTIFIED";
if (!configSections.containsKey(configKey)) {
configSections.put(configKey, new ArrayList<String>());
}
ArrayList<String> skillContents = configSections.get(configKey);
skillContents.add(" " + materialName);
}
return configSections;
}
}

View File

@@ -0,0 +1,29 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import org.bukkit.command.CommandSender;
public class McabilityCommand extends ToggleCommand {
@Override
protected boolean hasOtherPermission(CommandSender sender) {
return Permissions.mcabilityOthers(sender);
}
@Override
protected boolean hasSelfPermission(CommandSender sender) {
return Permissions.mcability(sender);
}
@Override
protected void applyCommandAction(McMMOPlayer mcMMOPlayer) {
mcMMOPlayer.getPlayer().sendMessage(LocaleLoader.getString("Commands.Ability." + (mcMMOPlayer.getAbilityUse() ? "Off" : "On")));
mcMMOPlayer.toggleAbilityUse();
}
@Override
protected void sendSuccessMessage(CommandSender sender, String playerName) {
sender.sendMessage(LocaleLoader.getString("Commands.Ability.Toggle", playerName));
}
}

View File

@@ -0,0 +1,90 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.commands.database.ConvertDatabaseCommand;
import com.gmail.nossr50.commands.experience.ConvertExperienceCommand;
import com.gmail.nossr50.core.data.database.DatabaseManagerFactory;
import com.gmail.nossr50.core.datatypes.database.DatabaseType;
import com.gmail.nossr50.core.datatypes.experience.FormulaType;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
public class McconvertCommand implements TabExecutor {
private static final List<String> FORMULA_TYPES;
private static final List<String> DATABASE_TYPES;
private static final List<String> SUBCOMMANDS = ImmutableList.of("database", "experience");
static {
ArrayList<String> formulaTypes = new ArrayList<String>();
ArrayList<String> databaseTypes = new ArrayList<String>();
for (FormulaType type : FormulaType.values()) {
formulaTypes.add(type.toString());
}
for (DatabaseType type : DatabaseType.values()) {
databaseTypes.add(type.toString());
}
// Custom stuff
databaseTypes.remove(DatabaseType.CUSTOM.toString());
if (mcMMO.getDatabaseManager().getDatabaseType() == DatabaseType.CUSTOM) {
databaseTypes.add(DatabaseManagerFactory.getCustomDatabaseManagerClass().getName());
}
Collections.sort(formulaTypes);
Collections.sort(databaseTypes);
FORMULA_TYPES = ImmutableList.copyOf(formulaTypes);
DATABASE_TYPES = ImmutableList.copyOf(databaseTypes);
}
private CommandExecutor databaseConvertCommand = new ConvertDatabaseCommand();
private CommandExecutor experienceConvertCommand = new ConvertExperienceCommand();
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
if (args[0].equalsIgnoreCase("database") || args[0].equalsIgnoreCase("db")) {
return databaseConvertCommand.onCommand(sender, command, label, args);
} else if (args[0].equalsIgnoreCase("experience") || args[0].equalsIgnoreCase("xp") || args[1].equalsIgnoreCase("exp")) {
return experienceConvertCommand.onCommand(sender, command, label, args);
}
return false;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
return StringUtil.copyPartialMatches(args[0], SUBCOMMANDS, new ArrayList<String>(SUBCOMMANDS.size()));
case 2:
if (args[0].equalsIgnoreCase("database") || args[0].equalsIgnoreCase("db")) {
return StringUtil.copyPartialMatches(args[0], DATABASE_TYPES, new ArrayList<String>(DATABASE_TYPES.size()));
}
if (args[0].equalsIgnoreCase("experience") || args[0].equalsIgnoreCase("xp") || args[0].equalsIgnoreCase("exp")) {
return StringUtil.copyPartialMatches(args[0], FORMULA_TYPES, new ArrayList<String>(FORMULA_TYPES.size()));
}
return ImmutableList.of();
default:
return ImmutableList.of();
}
}
}

View File

@@ -0,0 +1,29 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import org.bukkit.command.CommandSender;
public class McgodCommand extends ToggleCommand {
@Override
protected boolean hasOtherPermission(CommandSender sender) {
return Permissions.mcgodOthers(sender);
}
@Override
protected boolean hasSelfPermission(CommandSender sender) {
return Permissions.mcgod(sender);
}
@Override
protected void applyCommandAction(McMMOPlayer mcMMOPlayer) {
mcMMOPlayer.getPlayer().sendMessage(LocaleLoader.getString("Commands.GodMode." + (mcMMOPlayer.getGodMode() ? "Disabled" : "Enabled")));
mcMMOPlayer.toggleGodMode();
}
@Override
protected void sendSuccessMessage(CommandSender sender, String playerName) {
sender.sendMessage(LocaleLoader.getString("Commands.GodMode.Toggle", playerName));
}
}

View File

@@ -0,0 +1,115 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.commands.party.PartySubcommandType;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.mcMMO;
import org.bukkit.ChatColor;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
public class McmmoCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 0:
if (!Permissions.mcmmoDescription(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
String description = LocaleLoader.getString("mcMMO.Description");
String[] mcSplit = description.split(",");
sender.sendMessage(mcSplit);
if (MainConfig.getInstance().getDonateMessageEnabled()) {
sender.sendMessage(LocaleLoader.getString("MOTD.Donate"));
sender.sendMessage(ChatColor.GOLD + " - " + ChatColor.GREEN + "com.gmail.nossr50@com.gmail.com" + ChatColor.GOLD + " Paypal");
}
if (Permissions.showversion(sender)) {
sender.sendMessage(LocaleLoader.getString("MOTD.Version", mcMMO.p.getDescription().getVersion()));
}
mcMMO.getHolidayManager().anniversaryCheck(sender);
return true;
case 1:
if (args[0].equalsIgnoreCase("?") || args[0].equalsIgnoreCase("help") || args[0].equalsIgnoreCase("commands")) {
if (!Permissions.mcmmoHelp(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
sender.sendMessage(LocaleLoader.getString("Commands.mcc.Header"));
displayGeneralCommands(sender);
displayOtherCommands(sender);
displayPartyCommands(sender);
}
return true;
default:
return false;
}
}
private void displayGeneralCommands(CommandSender sender) {
sender.sendMessage(ChatColor.DARK_AQUA + " /mcstats " + LocaleLoader.getString("Commands.Stats"));
sender.sendMessage(ChatColor.DARK_AQUA + " /<skill>" + LocaleLoader.getString("Commands.SkillInfo"));
sender.sendMessage(ChatColor.DARK_AQUA + " /mctop " + LocaleLoader.getString("Commands.Leaderboards"));
if (Permissions.inspect(sender)) {
sender.sendMessage(ChatColor.DARK_AQUA + " /inspect " + LocaleLoader.getString("Commands.Inspect"));
}
if (Permissions.mcability(sender)) {
sender.sendMessage(ChatColor.DARK_AQUA + " /mcability " + LocaleLoader.getString("Commands.ToggleAbility"));
}
}
private void displayOtherCommands(CommandSender sender) {
//Don't show them this category if they have none of the permissions
if (!Permissions.skillreset(sender) && !Permissions.mmoedit(sender) && !Permissions.adminChat(sender) && !Permissions.mcgod(sender))
return;
sender.sendMessage(LocaleLoader.getString("Commands.Other"));
if (Permissions.skillreset(sender)) {
sender.sendMessage(ChatColor.DARK_AQUA + " /skillreset <skill|all> " + LocaleLoader.getString("Commands.Reset"));
}
if (Permissions.mmoedit(sender)) {
sender.sendMessage(ChatColor.DARK_AQUA + " /mmoedit " + LocaleLoader.getString("Commands.mmoedit"));
}
if (Permissions.adminChat(sender)) {
sender.sendMessage(ChatColor.DARK_AQUA + " /adminchat " + LocaleLoader.getString("Commands.AdminToggle"));
}
if (Permissions.mcgod(sender)) {
sender.sendMessage(ChatColor.DARK_AQUA + " /mcgod " + LocaleLoader.getString("Commands.mcgod"));
}
}
private void displayPartyCommands(CommandSender sender) {
if (Permissions.party(sender)) {
sender.sendMessage(LocaleLoader.getString("Commands.Party.Commands"));
sender.sendMessage(ChatColor.DARK_AQUA + " /party create <" + LocaleLoader.getString("Commands.Usage.PartyName") + "> " + LocaleLoader.getString("Commands.Party1"));
sender.sendMessage(ChatColor.DARK_AQUA + " /party join <" + LocaleLoader.getString("Commands.Usage.Player") + "> " + LocaleLoader.getString("Commands.Party2"));
sender.sendMessage(ChatColor.DARK_AQUA + " /party quit " + LocaleLoader.getString("Commands.Party.Quit"));
if (Permissions.partyChat(sender)) {
sender.sendMessage(ChatColor.DARK_AQUA + " /party chat " + LocaleLoader.getString("Commands.Party.Toggle"));
}
sender.sendMessage(ChatColor.DARK_AQUA + " /party invite <" + LocaleLoader.getString("Commands.Usage.Player") + "> " + LocaleLoader.getString("Commands.Party.Invite"));
sender.sendMessage(ChatColor.DARK_AQUA + " /party accept " + LocaleLoader.getString("Commands.Party.Accept"));
if (Permissions.partySubcommand(sender, PartySubcommandType.TELEPORT)) {
sender.sendMessage(ChatColor.DARK_AQUA + " /party teleport <" + LocaleLoader.getString("Commands.Usage.Player") + "> " + LocaleLoader.getString("Commands.Party.Teleport"));
}
}
}
}

View File

@@ -0,0 +1,34 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import java.util.List;
public class McnotifyCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 0:
McMMOPlayer mcMMOPlayer = UserManager.getPlayer((Player) sender);
sender.sendMessage(LocaleLoader.getString("Commands.Notifications." + (mcMMOPlayer.useChatNotifications() ? "Off" : "On")));
mcMMOPlayer.toggleChatNotifications();
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
return ImmutableList.of();
}
}

View File

@@ -0,0 +1,33 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import org.bukkit.command.CommandSender;
public class McrefreshCommand extends ToggleCommand {
@Override
protected boolean hasOtherPermission(CommandSender sender) {
return Permissions.mcrefreshOthers(sender);
}
@Override
protected boolean hasSelfPermission(CommandSender sender) {
return Permissions.mcrefresh(sender);
}
@Override
protected void applyCommandAction(McMMOPlayer mcMMOPlayer) {
mcMMOPlayer.setRecentlyHurt(0);
mcMMOPlayer.resetCooldowns();
mcMMOPlayer.resetToolPrepMode();
mcMMOPlayer.resetAbilityMode();
mcMMOPlayer.getPlayer().sendMessage(LocaleLoader.getString("Ability.Generic.Refresh"));
}
@Override
protected void sendSuccessMessage(CommandSender sender, String playerName) {
sender.sendMessage(LocaleLoader.getString("Commands.mcrefresh.Success", playerName));
}
}

View File

@@ -0,0 +1,88 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.core.util.scoreboards.ScoreboardManager;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public class McscoreboardCommand implements TabExecutor {
private static final List<String> FIRST_ARGS = ImmutableList.of("keep", "time", "clear");
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
switch (args.length) {
case 1:
if (args[0].equalsIgnoreCase("clear") || args[0].equalsIgnoreCase("reset")) {
ScoreboardManager.clearBoard(sender.getName());
sender.sendMessage(LocaleLoader.getString("Commands.Scoreboard.Clear"));
return true;
}
if (args[0].equalsIgnoreCase("keep")) {
if (!MainConfig.getInstance().getAllowKeepBoard() || !MainConfig.getInstance().getScoreboardsEnabled()) {
sender.sendMessage(LocaleLoader.getString("Commands.Disabled"));
return true;
}
if (!ScoreboardManager.isBoardShown(sender.getName())) {
sender.sendMessage(LocaleLoader.getString("Commands.Scoreboard.NoBoard"));
return true;
}
ScoreboardManager.keepBoard(sender.getName());
sender.sendMessage(LocaleLoader.getString("Commands.Scoreboard.Keep"));
return true;
}
return help(sender);
case 2:
if (args[0].equalsIgnoreCase("time") || args[0].equalsIgnoreCase("timer")) {
if (CommandUtils.isInvalidInteger(sender, args[1])) {
return true;
}
int time = Math.abs(Integer.parseInt(args[1]));
ScoreboardManager.setRevertTimer(sender.getName(), time);
sender.sendMessage(LocaleLoader.getString("Commands.Scoreboard.Timer", time));
return true;
}
return help(sender);
default:
return help(sender);
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
return StringUtil.copyPartialMatches(args[0], FIRST_ARGS, new ArrayList<String>(FIRST_ARGS.size()));
default:
return ImmutableList.of();
}
}
private boolean help(CommandSender sender) {
sender.sendMessage(LocaleLoader.getString("Commands.Scoreboard.Help.0"));
sender.sendMessage(LocaleLoader.getString("Commands.Scoreboard.Help.1"));
sender.sendMessage(LocaleLoader.getString("Commands.Scoreboard.Help.2"));
sender.sendMessage(LocaleLoader.getString("Commands.Scoreboard.Help.3"));
return true;
}
}

View File

@@ -0,0 +1,80 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public abstract class ToggleCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 0:
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
if (!hasSelfPermission(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (!CommandUtils.hasPlayerDataKey(sender)) {
return true;
}
applyCommandAction(UserManager.getPlayer(sender.getName()));
return true;
case 1:
if (!hasOtherPermission(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
String playerName = CommandUtils.getMatchedPlayerName(args[0]);
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(playerName);
if (!CommandUtils.checkPlayerExistence(sender, playerName, mcMMOPlayer)) {
return true;
}
if (CommandUtils.isOffline(sender, mcMMOPlayer.getPlayer())) {
return true;
}
applyCommandAction(mcMMOPlayer);
sendSuccessMessage(sender, playerName);
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
List<String> playerNames = CommandUtils.getOnlinePlayerNames(sender);
return StringUtil.copyPartialMatches(args[0], playerNames, new ArrayList<String>(playerNames.size()));
default:
return ImmutableList.of();
}
}
protected abstract boolean hasOtherPermission(CommandSender sender);
protected abstract boolean hasSelfPermission(CommandSender sender);
protected abstract void applyCommandAction(McMMOPlayer mcMMOPlayer);
protected abstract void sendSuccessMessage(CommandSender sender, String playerName);
}

View File

@@ -0,0 +1,117 @@
package com.gmail.nossr50.commands;
import com.gmail.nossr50.config.experience.ExperienceConfig;
import com.gmail.nossr50.core.config.AdvancedConfig;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.StringUtils;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.core.util.player.NotificationManager;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.ChatColor;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public class XprateCommand implements TabExecutor {
private final double ORIGINAL_XP_RATE = ExperienceConfig.getInstance().getExperienceGainsGlobalMultiplier();
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 1:
if (!args[0].equalsIgnoreCase("reset") && !args[0].equalsIgnoreCase("clear")) {
return false;
}
if (!Permissions.xprateReset(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (mcMMO.p.isXPEventEnabled()) {
if (AdvancedConfig.getInstance().useTitlesForXPEvent()) {
NotificationManager.broadcastTitle(mcMMO.p.getServer(),
LocaleLoader.getString("Commands.Event.Stop"),
LocaleLoader.getString("Commands.Event.Stop.Subtitle"),
10, 10 * 20, 20);
}
mcMMO.p.getServer().broadcastMessage(LocaleLoader.getString("Commands.Event.Stop"));
mcMMO.p.getServer().broadcastMessage(LocaleLoader.getString("Commands.Event.Stop.Subtitle"));
mcMMO.p.toggleXpEventEnabled();
}
ExperienceConfig.getInstance().setExperienceGainsGlobalMultiplier(ORIGINAL_XP_RATE);
return true;
case 2:
if (CommandUtils.isInvalidInteger(sender, args[0])) {
return true;
}
if (!Permissions.xprateSet(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (CommandUtils.shouldDisableToggle(args[1])) {
mcMMO.p.setXPEventEnabled(false);
} else if (CommandUtils.shouldEnableToggle(args[1])) {
mcMMO.p.setXPEventEnabled(true);
} else {
return false;
}
int newXpRate = Integer.parseInt(args[0]);
if (newXpRate < 0) {
sender.sendMessage(ChatColor.RED + LocaleLoader.getString("Commands.NegativeNumberWarn"));
return true;
}
ExperienceConfig.getInstance().setExperienceGainsGlobalMultiplier(newXpRate);
if (mcMMO.p.isXPEventEnabled()) {
if (AdvancedConfig.getInstance().useTitlesForXPEvent()) {
NotificationManager.broadcastTitle(mcMMO.p.getServer(),
LocaleLoader.getString("Commands.Event.Start"),
LocaleLoader.getString("Commands.Event.XP", newXpRate),
10, 10 * 20, 20);
}
mcMMO.p.getServer().broadcastMessage(LocaleLoader.getString("Commands.Event.Start"));
mcMMO.p.getServer().broadcastMessage(LocaleLoader.getString("Commands.Event.XP", newXpRate));
} else {
sender.sendMessage(LocaleLoader.getString("Commands.xprate.modified", newXpRate));
}
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
if (StringUtils.isInt(args[0])) {
return ImmutableList.of();
}
return StringUtil.copyPartialMatches(args[0], CommandUtils.RESET_OPTIONS, new ArrayList<String>(CommandUtils.RESET_OPTIONS.size()));
case 2:
return StringUtil.copyPartialMatches(args[1], CommandUtils.TRUE_FALSE_OPTIONS, new ArrayList<String>(CommandUtils.TRUE_FALSE_OPTIONS.size()));
default:
return ImmutableList.of();
}
}
}

View File

@@ -0,0 +1,15 @@
package com.gmail.nossr50.commands.chat;
import com.gmail.nossr50.core.datatypes.chat.ChatMode;
import org.bukkit.command.CommandSender;
public class AdminChatCommand extends ChatCommand {
public AdminChatCommand() {
super(ChatMode.ADMIN);
}
@Override
protected void handleChatSending(CommandSender sender, String[] args) {
chatManager.handleChat(sender.getName(), getDisplayName(sender), buildChatMessage(args, 0));
}
}

View File

@@ -0,0 +1,139 @@
package com.gmail.nossr50.commands.chat;
import com.gmail.nossr50.core.chat.ChatManager;
import com.gmail.nossr50.core.chat.ChatManagerFactory;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.chat.ChatMode;
import com.gmail.nossr50.core.datatypes.party.PartyFeature;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public abstract class ChatCommand implements TabExecutor {
protected ChatManager chatManager;
private ChatMode chatMode;
public ChatCommand(ChatMode chatMode) {
this.chatMode = chatMode;
this.chatManager = ChatManagerFactory.getChatManager(mcMMO.p, chatMode);
}
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
McMMOPlayer mcMMOPlayer;
switch (args.length) {
case 0:
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
if (!CommandUtils.hasPlayerDataKey(sender)) {
return true;
}
mcMMOPlayer = UserManager.getPlayer(sender.getName());
if (mcMMOPlayer.isChatEnabled(chatMode)) {
disableChatMode(mcMMOPlayer, sender);
} else {
enableChatMode(mcMMOPlayer, sender);
}
return true;
case 1:
if (!CommandUtils.hasPlayerDataKey(sender)) {
return true;
}
if (CommandUtils.shouldEnableToggle(args[0])) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
enableChatMode(UserManager.getPlayer(sender.getName()), sender);
return true;
}
if (CommandUtils.shouldDisableToggle(args[0])) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
disableChatMode(UserManager.getPlayer(sender.getName()), sender);
return true;
}
// Fallthrough
default:
handleChatSending(sender, args);
return true;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
return StringUtil.copyPartialMatches(args[0], CommandUtils.TRUE_FALSE_OPTIONS, new ArrayList<String>(CommandUtils.TRUE_FALSE_OPTIONS.size()));
default:
return ImmutableList.of();
}
}
protected String buildChatMessage(String[] args, int index) {
StringBuilder builder = new StringBuilder();
builder.append(args[index]);
for (int i = index + 1; i < args.length; i++) {
builder.append(" ");
builder.append(args[i]);
}
return builder.toString();
}
protected String getDisplayName(CommandSender sender) {
return (sender instanceof Player) ? ((Player) sender).getDisplayName() : LocaleLoader.getString("Commands.Chat.Console");
}
protected abstract void handleChatSending(CommandSender sender, String[] args);
private void enableChatMode(McMMOPlayer mcMMOPlayer, CommandSender sender) {
if (chatMode == ChatMode.PARTY && mcMMOPlayer.getParty() == null) {
sender.sendMessage(LocaleLoader.getString("Commands.Party.None"));
return;
}
if (chatMode == ChatMode.PARTY && (mcMMOPlayer.getParty().getLevel() < MainConfig.getInstance().getPartyFeatureUnlockLevel(PartyFeature.CHAT))) {
sender.sendMessage(LocaleLoader.getString("Party.Feature.Disabled.1"));
return;
}
mcMMOPlayer.enableChat(chatMode);
sender.sendMessage(chatMode.getEnabledMessage());
}
private void disableChatMode(McMMOPlayer mcMMOPlayer, CommandSender sender) {
if (chatMode == ChatMode.PARTY && mcMMOPlayer.getParty() == null) {
sender.sendMessage(LocaleLoader.getString("Commands.Party.None"));
return;
}
mcMMOPlayer.disableChat(chatMode);
sender.sendMessage(chatMode.getDisabledMessage());
}
}

View File

@@ -0,0 +1,30 @@
package com.gmail.nossr50.commands.chat;
import com.gmail.nossr50.commands.ToggleCommand;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import org.bukkit.command.CommandSender;
public class McChatSpy extends ToggleCommand {
@Override
protected boolean hasOtherPermission(CommandSender sender) {
return Permissions.adminChatSpyOthers(sender);
}
@Override
protected boolean hasSelfPermission(CommandSender sender) {
return Permissions.adminChatSpy(sender);
}
@Override
protected void applyCommandAction(McMMOPlayer mcMMOPlayer) {
mcMMOPlayer.getPlayer().sendMessage(LocaleLoader.getString("Commands.AdminChatSpy." + (mcMMOPlayer.isPartyChatSpying() ? "Disabled" : "Enabled")));
mcMMOPlayer.togglePartyChatSpying();
}
@Override
protected void sendSuccessMessage(CommandSender sender, String playerName) {
sender.sendMessage(LocaleLoader.getString("Commands.AdminChatSpy.Toggle", playerName));
}
}

View File

@@ -0,0 +1,57 @@
package com.gmail.nossr50.commands.chat;
import com.gmail.nossr50.core.chat.PartyChatManager;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.chat.ChatMode;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.party.PartyFeature;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class PartyChatCommand extends ChatCommand {
public PartyChatCommand() {
super(ChatMode.PARTY);
}
@Override
protected void handleChatSending(CommandSender sender, String[] args) {
Party party;
String message;
if (sender instanceof Player) {
party = UserManager.getPlayer((Player) sender).getParty();
if (party == null) {
sender.sendMessage(LocaleLoader.getString("Commands.Party.None"));
return;
}
if (party.getLevel() < MainConfig.getInstance().getPartyFeatureUnlockLevel(PartyFeature.CHAT)) {
sender.sendMessage(LocaleLoader.getString("Party.Feature.Disabled.1"));
return;
}
message = buildChatMessage(args, 0);
} else {
if (args.length < 2) {
sender.sendMessage(LocaleLoader.getString("Party.Specify"));
return;
}
party = PartyManager.getParty(args[0]);
if (party == null) {
sender.sendMessage(LocaleLoader.getString("Party.InvalidName"));
return;
}
message = buildChatMessage(args, 1);
}
((PartyChatManager) chatManager).setParty(party);
chatManager.handleChat(sender.getName(), getDisplayName(sender), message);
}
}

View File

@@ -0,0 +1,73 @@
package com.gmail.nossr50.commands.database;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.data.database.DatabaseManager;
import com.gmail.nossr50.core.data.database.DatabaseManagerFactory;
import com.gmail.nossr50.core.datatypes.database.DatabaseType;
import com.gmail.nossr50.core.datatypes.player.PlayerProfile;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.runnables.database.DatabaseConversionTask;
import com.gmail.nossr50.core.runnables.player.PlayerProfileLoadingTask;
import com.gmail.nossr50.mcMMO;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class ConvertDatabaseCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
DatabaseType previousType = DatabaseType.getDatabaseType(args[1]);
DatabaseType newType = mcMMO.getDatabaseManager().getDatabaseType();
if (previousType == newType || (newType == DatabaseType.CUSTOM && DatabaseManagerFactory.getCustomDatabaseManagerClass().getSimpleName().equalsIgnoreCase(args[1]))) {
sender.sendMessage(LocaleLoader.getString("Commands.mcconvert.Database.Same", newType.toString()));
return true;
}
DatabaseManager oldDatabase = DatabaseManagerFactory.createDatabaseManager(previousType);
if (previousType == DatabaseType.CUSTOM) {
Class<?> clazz;
try {
clazz = Class.forName(args[1]);
if (!DatabaseManager.class.isAssignableFrom(clazz)) {
sender.sendMessage(LocaleLoader.getString("Commands.mcconvert.Database.InvalidType", args[1]));
return true;
}
oldDatabase = DatabaseManagerFactory.createCustomDatabaseManager((Class<? extends DatabaseManager>) clazz);
} catch (Throwable e) {
e.printStackTrace();
sender.sendMessage(LocaleLoader.getString("Commands.mcconvert.Database.InvalidType", args[1]));
return true;
}
}
sender.sendMessage(LocaleLoader.getString("Commands.mcconvert.Database.Start", previousType.toString(), newType.toString()));
UserManager.saveAll();
UserManager.clearAll();
for (Player player : mcMMO.p.getServer().getOnlinePlayers()) {
PlayerProfile profile = oldDatabase.loadPlayerProfile(player.getUniqueId());
if (profile.isLoaded()) {
mcMMO.getDatabaseManager().saveUser(profile);
}
new PlayerProfileLoadingTask(player).runTaskLaterAsynchronously(mcMMO.p, 1); // 1 Tick delay to ensure the player is marked as online before we begin loading
}
new DatabaseConversionTask(oldDatabase, sender, previousType.toString(), newType.toString()).runTaskAsynchronously(mcMMO.p);
return true;
default:
return false;
}
}
}

View File

@@ -0,0 +1,36 @@
package com.gmail.nossr50.commands.database;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import java.util.List;
public class McpurgeCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 0:
mcMMO.getDatabaseManager().purgePowerlessUsers();
if (MainConfig.getInstance().getOldUsersCutoff() != -1) {
mcMMO.getDatabaseManager().purgeOldUsers();
}
sender.sendMessage(LocaleLoader.getString("Commands.mcpurge.Success"));
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
return ImmutableList.of();
}
}

View File

@@ -0,0 +1,50 @@
package com.gmail.nossr50.commands.database;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public class McremoveCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 1:
String playerName = CommandUtils.getMatchedPlayerName(args[0]);
if (UserManager.getOfflinePlayer(playerName) == null && CommandUtils.unloadedProfile(sender, mcMMO.getDatabaseManager().loadPlayerProfile(playerName, false))) {
return true;
}
if (mcMMO.getDatabaseManager().removeUser(playerName)) {
sender.sendMessage(LocaleLoader.getString("Commands.mcremove.Success", playerName));
} else {
sender.sendMessage(playerName + " could not be removed from the database."); // Pretty sure this should NEVER happen.
}
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
List<String> playerNames = CommandUtils.getOnlinePlayerNames(sender);
return StringUtil.copyPartialMatches(args[0], playerNames, new ArrayList<String>(playerNames.size()));
default:
return ImmutableList.of();
}
}
}

View File

@@ -0,0 +1,37 @@
package com.gmail.nossr50.commands.database;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.database.DatabaseManagerFactory;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import java.util.List;
public class MmoshowdbCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 0:
Class<?> clazz = DatabaseManagerFactory.getCustomDatabaseManagerClass();
if (clazz != null) {
sender.sendMessage(LocaleLoader.getString("Commands.mmoshowdb", clazz.getName()));
return true;
}
sender.sendMessage(LocaleLoader.getString("Commands.mmoshowdb", (MainConfig.getInstance().getUseMySQL() ? "sql" : "flatfile")));
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
return ImmutableList.of();
}
}

View File

@@ -0,0 +1,45 @@
package com.gmail.nossr50.commands.experience;
import com.gmail.nossr50.core.datatypes.experience.XPGainReason;
import com.gmail.nossr50.core.datatypes.player.PlayerProfile;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.EventUtils;
import com.gmail.nossr50.core.util.Permissions;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class AddlevelsCommand extends ExperienceCommand {
@Override
protected boolean permissionsCheckSelf(CommandSender sender) {
return Permissions.addlevels(sender);
}
@Override
protected boolean permissionsCheckOthers(CommandSender sender) {
return Permissions.addlevelsOthers(sender);
}
@Override
protected void handleCommand(Player player, PlayerProfile profile, PrimarySkillType skill, int value) {
float xpRemoved = profile.getSkillXpLevelRaw(skill);
profile.addLevels(skill, value);
if (player == null) {
profile.scheduleAsyncSave();
return;
}
EventUtils.handleLevelChangeEvent(player, skill, value, xpRemoved, true, XPGainReason.COMMAND);
}
@Override
protected void handlePlayerMessageAll(Player player, int value) {
player.sendMessage(LocaleLoader.getString("Commands.addlevels.AwardAll.1", value));
}
@Override
protected void handlePlayerMessageSkill(Player player, int value, PrimarySkillType skill) {
player.sendMessage(LocaleLoader.getString("Commands.addlevels.AwardSkill.1", value, skill.getName()));
}
}

View File

@@ -0,0 +1,43 @@
package com.gmail.nossr50.commands.experience;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.experience.XPGainReason;
import com.gmail.nossr50.core.datatypes.experience.XPGainSource;
import com.gmail.nossr50.core.datatypes.player.PlayerProfile;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.Permissions;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class AddxpCommand extends ExperienceCommand {
@Override
protected boolean permissionsCheckSelf(CommandSender sender) {
return Permissions.addxp(sender);
}
@Override
protected boolean permissionsCheckOthers(CommandSender sender) {
return Permissions.addxpOthers(sender);
}
@Override
protected void handleCommand(Player player, PlayerProfile profile, PrimarySkillType skill, int value) {
if (player != null) {
UserManager.getPlayer(player).applyXpGain(skill, value, XPGainReason.COMMAND, XPGainSource.COMMAND);
} else {
profile.addXp(skill, value);
profile.scheduleAsyncSave();
}
}
@Override
protected void handlePlayerMessageAll(Player player, int value) {
player.sendMessage(LocaleLoader.getString("Commands.addxp.AwardAll", value));
}
@Override
protected void handlePlayerMessageSkill(Player player, int value, PrimarySkillType skill) {
player.sendMessage(LocaleLoader.getString("Commands.addxp.AwardSkill", value, skill.getName()));
}
}

View File

@@ -0,0 +1,49 @@
package com.gmail.nossr50.commands.experience;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.experience.FormulaType;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.runnables.database.FormulaConversionTask;
import com.gmail.nossr50.core.runnables.player.PlayerProfileLoadingTask;
import com.gmail.nossr50.mcMMO;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class ConvertExperienceCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
FormulaType previousType = mcMMO.getFormulaManager().getPreviousFormulaType();
FormulaType newType = FormulaType.getFormulaType(args[1].toUpperCase());
if (newType == FormulaType.UNKNOWN) {
sender.sendMessage(LocaleLoader.getString("Commands.mcconvert.Experience.Invalid"));
return true;
}
if (previousType == newType) {
sender.sendMessage(LocaleLoader.getString("Commands.mcconvert.Experience.Same", newType.toString()));
return true;
}
sender.sendMessage(LocaleLoader.getString("Commands.mcconvert.Experience.Start", previousType.toString(), newType.toString()));
UserManager.saveAll();
UserManager.clearAll();
new FormulaConversionTask(sender, newType).runTaskLater(mcMMO.p, 1);
for (Player player : mcMMO.p.getServer().getOnlinePlayers()) {
new PlayerProfileLoadingTask(player).runTaskLaterAsynchronously(mcMMO.p, 1); // 1 Tick delay to ensure the player is marked as online before we begin loading
}
return true;
default:
return false;
}
}
}

View File

@@ -0,0 +1,160 @@
package com.gmail.nossr50.commands.experience;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.datatypes.player.PlayerProfile;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.OfflinePlayer;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;
public abstract class ExperienceCommand implements TabExecutor {
protected static void handleSenderMessage(CommandSender sender, String playerName, PrimarySkillType skill) {
if (skill == null) {
sender.sendMessage(LocaleLoader.getString("Commands.addlevels.AwardAll.2", playerName));
} else {
sender.sendMessage(LocaleLoader.getString("Commands.addlevels.AwardSkill.2", skill.getName(), playerName));
}
}
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
PrimarySkillType skill;
switch (args.length) {
case 2:
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
if (!permissionsCheckSelf(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (!validateArguments(sender, args[0], args[1])) {
return true;
}
skill = PrimarySkillType.getSkill(args[0]);
if (args[1].equalsIgnoreCase("all")) {
skill = null;
}
if (skill != null && skill.isChildSkill()) {
sender.sendMessage(LocaleLoader.getString("Commands.Skill.ChildSkill"));
return true;
}
editValues((Player) sender, UserManager.getPlayer(sender.getName()).getProfile(), skill, Integer.parseInt(args[1]));
return true;
case 3:
if (!permissionsCheckOthers(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (!validateArguments(sender, args[1], args[2])) {
return true;
}
skill = PrimarySkillType.getSkill(args[1]);
if (args[1].equalsIgnoreCase("all")) {
skill = null;
}
if (skill != null && skill.isChildSkill()) {
sender.sendMessage(LocaleLoader.getString("Commands.Skill.ChildSkill"));
return true;
}
int value = Integer.parseInt(args[2]);
String playerName = CommandUtils.getMatchedPlayerName(args[0]);
McMMOPlayer mcMMOPlayer = UserManager.getOfflinePlayer(playerName);
// If the mcMMOPlayer doesn't exist, create a temporary profile and check if it's present in the database. If it's not, abort the process.
if (mcMMOPlayer == null) {
UUID uuid = null;
OfflinePlayer player = mcMMO.p.getServer().getOfflinePlayer(playerName);
if (player != null) {
uuid = player.getUniqueId();
}
PlayerProfile profile = mcMMO.getDatabaseManager().loadPlayerProfile(playerName, uuid, false);
if (CommandUtils.unloadedProfile(sender, profile)) {
return true;
}
editValues(null, profile, skill, value);
} else {
editValues(mcMMOPlayer.getPlayer(), mcMMOPlayer.getProfile(), skill, value);
}
handleSenderMessage(sender, playerName, skill);
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
List<String> playerNames = CommandUtils.getOnlinePlayerNames(sender);
return StringUtil.copyPartialMatches(args[0], playerNames, new ArrayList<String>(playerNames.size()));
case 2:
return StringUtil.copyPartialMatches(args[1], PrimarySkillType.SKILL_NAMES, new ArrayList<String>(PrimarySkillType.SKILL_NAMES.size()));
default:
return ImmutableList.of();
}
}
protected abstract boolean permissionsCheckSelf(CommandSender sender);
protected abstract boolean permissionsCheckOthers(CommandSender sender);
protected abstract void handleCommand(Player player, PlayerProfile profile, PrimarySkillType skill, int value);
protected abstract void handlePlayerMessageAll(Player player, int value);
protected abstract void handlePlayerMessageSkill(Player player, int value, PrimarySkillType skill);
private boolean validateArguments(CommandSender sender, String skillName, String value) {
return !(CommandUtils.isInvalidInteger(sender, value) || (!skillName.equalsIgnoreCase("all") && CommandUtils.isInvalidSkill(sender, skillName)));
}
protected void editValues(Player player, PlayerProfile profile, PrimarySkillType skill, int value) {
if (skill == null) {
for (PrimarySkillType primarySkillType : PrimarySkillType.NON_CHILD_SKILLS) {
handleCommand(player, profile, primarySkillType, value);
}
if (player != null) {
handlePlayerMessageAll(player, value);
}
} else {
handleCommand(player, profile, skill, value);
if (player != null) {
handlePlayerMessageSkill(player, value, skill);
}
}
}
}

View File

@@ -0,0 +1,51 @@
package com.gmail.nossr50.commands.experience;
import com.gmail.nossr50.core.datatypes.experience.XPGainReason;
import com.gmail.nossr50.core.datatypes.player.PlayerProfile;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.EventUtils;
import com.gmail.nossr50.core.util.Permissions;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class MmoeditCommand extends ExperienceCommand {
@Override
protected boolean permissionsCheckSelf(CommandSender sender) {
return Permissions.mmoedit(sender);
}
@Override
protected boolean permissionsCheckOthers(CommandSender sender) {
return Permissions.mmoeditOthers(sender);
}
@Override
protected void handleCommand(Player player, PlayerProfile profile, PrimarySkillType skill, int value) {
int skillLevel = profile.getSkillLevel(skill);
float xpRemoved = profile.getSkillXpLevelRaw(skill);
profile.modifySkill(skill, value);
if (player == null) {
profile.scheduleAsyncSave();
return;
}
if (value == skillLevel) {
return;
}
EventUtils.handleLevelChangeEvent(player, skill, value, xpRemoved, value > skillLevel, XPGainReason.COMMAND);
}
@Override
protected void handlePlayerMessageAll(Player player, int value) {
player.sendMessage(LocaleLoader.getString("Commands.mmoedit.AllSkills.1", value));
}
@Override
protected void handlePlayerMessageSkill(Player player, int value, PrimarySkillType skill) {
player.sendMessage(LocaleLoader.getString("Commands.mmoedit.Modified.1", skill.getName(), value));
}
}

View File

@@ -0,0 +1,174 @@
package com.gmail.nossr50.commands.experience;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.experience.XPGainReason;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.datatypes.player.PlayerProfile;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.EventUtils;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.OfflinePlayer;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;
/**
* This class mirrors the structure of ExperienceCommand, except the
* value/quantity argument is removed.
*/
public class SkillresetCommand implements TabExecutor {
protected static void handleSenderMessage(CommandSender sender, String playerName, PrimarySkillType skill) {
if (skill == null) {
sender.sendMessage(LocaleLoader.getString("Commands.addlevels.AwardAll.2", playerName));
} else {
sender.sendMessage(LocaleLoader.getString("Commands.addlevels.AwardSkill.2", skill.getName(), playerName));
}
}
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
PrimarySkillType skill;
switch (args.length) {
case 1:
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
if (!permissionsCheckSelf(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (!validateArguments(sender, args[0])) {
return true;
}
if (args[0].equalsIgnoreCase("all")) {
skill = null;
} else {
skill = PrimarySkillType.getSkill(args[1]);
}
editValues((Player) sender, UserManager.getPlayer(sender.getName()).getProfile(), skill);
return true;
case 2:
if (!permissionsCheckOthers(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (!validateArguments(sender, args[1])) {
return true;
}
if (args[1].equalsIgnoreCase("all")) {
skill = null;
} else {
skill = PrimarySkillType.getSkill(args[1]);
}
String playerName = CommandUtils.getMatchedPlayerName(args[0]);
McMMOPlayer mcMMOPlayer = UserManager.getOfflinePlayer(playerName);
// If the mcMMOPlayer doesn't exist, create a temporary profile and check if it's present in the database. If it's not, abort the process.
if (mcMMOPlayer == null) {
UUID uuid = null;
OfflinePlayer player = mcMMO.p.getServer().getOfflinePlayer(playerName);
if (player != null) {
uuid = player.getUniqueId();
}
PlayerProfile profile = mcMMO.getDatabaseManager().loadPlayerProfile(playerName, uuid, false);
if (CommandUtils.unloadedProfile(sender, profile)) {
return true;
}
editValues(null, profile, skill);
} else {
editValues(mcMMOPlayer.getPlayer(), mcMMOPlayer.getProfile(), skill);
}
handleSenderMessage(sender, playerName, skill);
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
List<String> playerNames = CommandUtils.getOnlinePlayerNames(sender);
return StringUtil.copyPartialMatches(args[0], playerNames, new ArrayList<String>(playerNames.size()));
case 2:
return StringUtil.copyPartialMatches(args[1], PrimarySkillType.SKILL_NAMES, new ArrayList<String>(PrimarySkillType.SKILL_NAMES.size()));
default:
return ImmutableList.of();
}
}
protected void handleCommand(Player player, PlayerProfile profile, PrimarySkillType skill) {
int levelsRemoved = profile.getSkillLevel(skill);
float xpRemoved = profile.getSkillXpLevelRaw(skill);
profile.modifySkill(skill, 0);
if (player == null) {
profile.scheduleAsyncSave();
return;
}
EventUtils.handleLevelChangeEvent(player, skill, levelsRemoved, xpRemoved, false, XPGainReason.COMMAND);
}
protected boolean permissionsCheckSelf(CommandSender sender) {
return Permissions.skillreset(sender);
}
protected boolean permissionsCheckOthers(CommandSender sender) {
return Permissions.skillresetOthers(sender);
}
protected void handlePlayerMessageAll(Player player) {
player.sendMessage(LocaleLoader.getString("Commands.Reset.All"));
}
protected void handlePlayerMessageSkill(Player player, PrimarySkillType skill) {
player.sendMessage(LocaleLoader.getString("Commands.Reset.Single", skill.getName()));
}
private boolean validateArguments(CommandSender sender, String skillName) {
return skillName.equalsIgnoreCase("all") || !CommandUtils.isInvalidSkill(sender, skillName);
}
protected void editValues(Player player, PlayerProfile profile, PrimarySkillType skill) {
if (skill == null) {
for (PrimarySkillType primarySkillType : PrimarySkillType.NON_CHILD_SKILLS) {
handleCommand(player, profile, primarySkillType);
}
if (player != null) {
handlePlayerMessageAll(player);
}
} else {
handleCommand(player, profile, skill);
if (player != null) {
handlePlayerMessageSkill(player, skill);
}
}
}
}

View File

@@ -0,0 +1,63 @@
package com.gmail.nossr50.commands.hardcore;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.mcMMO;
import org.bukkit.command.CommandSender;
public class HardcoreCommand extends HardcoreModeCommand {
@Override
protected boolean checkTogglePermissions(CommandSender sender) {
return Permissions.hardcoreToggle(sender);
}
@Override
protected boolean checkModifyPermissions(CommandSender sender) {
return Permissions.hardcoreModify(sender);
}
@Override
protected boolean checkEnabled(PrimarySkillType skill) {
if (skill == null) {
for (PrimarySkillType primarySkillType : PrimarySkillType.values()) {
if (!primarySkillType.getHardcoreStatLossEnabled()) {
return false;
}
}
return true;
}
return skill.getHardcoreStatLossEnabled();
}
@Override
protected void enable(PrimarySkillType skill) {
toggle(true, skill);
}
@Override
protected void disable(PrimarySkillType skill) {
toggle(false, skill);
}
@Override
protected void modify(CommandSender sender, double newPercentage) {
MainConfig.getInstance().setHardcoreDeathStatPenaltyPercentage(newPercentage);
sender.sendMessage(LocaleLoader.getString("Hardcore.DeathStatLoss.PercentageChanged", percent.format(newPercentage / 100.0D)));
}
private void toggle(boolean enable, PrimarySkillType skill) {
if (skill == null) {
for (PrimarySkillType primarySkillType : PrimarySkillType.NON_CHILD_SKILLS) {
primarySkillType.setHardcoreStatLossEnabled(enable);
}
} else {
skill.setHardcoreStatLossEnabled(enable);
}
mcMMO.p.getServer().broadcastMessage(LocaleLoader.getString("Hardcore.Mode." + (enable ? "Enabled" : "Disabled"), LocaleLoader.getString("Hardcore.DeathStatLoss.Name"), (skill == null ? "all skills" : skill.getName())));
}
}

View File

@@ -0,0 +1,134 @@
package com.gmail.nossr50.commands.hardcore;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.StringUtils;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.util.StringUtil;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.List;
public abstract class HardcoreModeCommand implements TabExecutor {
protected final DecimalFormat percent = new DecimalFormat("##0.00%");
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 0:
if (!checkTogglePermissions(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (checkEnabled(null)) {
disable(null);
} else {
enable(null);
}
return true;
case 1:
if (CommandUtils.shouldEnableToggle(args[0])) {
if (!Permissions.hardcoreToggle(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
enable(null);
return true;
}
if (CommandUtils.shouldDisableToggle(args[0])) {
if (!Permissions.hardcoreToggle(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
disable(null);
return true;
}
if (CommandUtils.isInvalidDouble(sender, args[0])) {
return true;
}
if (!Permissions.hardcoreModify(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
modify(sender, Double.parseDouble(args[0]));
return true;
case 2:
if (CommandUtils.isInvalidSkill(sender, args[0])) {
return true;
}
PrimarySkillType skill = PrimarySkillType.getSkill(args[0]);
if (!CommandUtils.isChildSkill(sender, skill)) {
return true;
}
if (CommandUtils.shouldEnableToggle(args[1])) {
if (!Permissions.hardcoreToggle(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
enable(skill);
return true;
}
if (CommandUtils.shouldDisableToggle(args[1])) {
if (!Permissions.hardcoreToggle(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
enable(skill);
return true;
}
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
if (StringUtils.isDouble(args[0])) {
return ImmutableList.of();
}
return StringUtil.copyPartialMatches(args[0], CommandUtils.TRUE_FALSE_OPTIONS, new ArrayList<String>(CommandUtils.TRUE_FALSE_OPTIONS.size()));
default:
return ImmutableList.of();
}
}
protected abstract boolean checkTogglePermissions(CommandSender sender);
protected abstract boolean checkModifyPermissions(CommandSender sender);
protected abstract boolean checkEnabled(PrimarySkillType skill);
protected abstract void enable(PrimarySkillType skill);
protected abstract void disable(PrimarySkillType skill);
protected abstract void modify(CommandSender sender, double newPercentage);
}

View File

@@ -0,0 +1,63 @@
package com.gmail.nossr50.commands.hardcore;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.mcMMO;
import org.bukkit.command.CommandSender;
public class VampirismCommand extends HardcoreModeCommand {
@Override
protected boolean checkTogglePermissions(CommandSender sender) {
return Permissions.vampirismToggle(sender);
}
@Override
protected boolean checkModifyPermissions(CommandSender sender) {
return Permissions.vampirismModify(sender);
}
@Override
protected boolean checkEnabled(PrimarySkillType skill) {
if (skill == null) {
for (PrimarySkillType primarySkillType : PrimarySkillType.values()) {
if (!primarySkillType.getHardcoreVampirismEnabled()) {
return false;
}
}
return true;
}
return skill.getHardcoreVampirismEnabled();
}
@Override
protected void enable(PrimarySkillType skill) {
toggle(true, skill);
}
@Override
protected void disable(PrimarySkillType skill) {
toggle(false, skill);
}
@Override
protected void modify(CommandSender sender, double newPercentage) {
MainConfig.getInstance().setHardcoreVampirismStatLeechPercentage(newPercentage);
sender.sendMessage(LocaleLoader.getString("Hardcore.Vampirism.PercentageChanged", percent.format(newPercentage / 100.0D)));
}
private void toggle(boolean enable, PrimarySkillType skill) {
if (skill == null) {
for (PrimarySkillType primarySkillType : PrimarySkillType.NON_CHILD_SKILLS) {
primarySkillType.setHardcoreVampirismEnabled(enable);
}
} else {
skill.setHardcoreVampirismEnabled(enable);
}
mcMMO.p.getServer().broadcastMessage(LocaleLoader.getString("Hardcore.Mode." + (enable ? "Enabled" : "Disabled"), LocaleLoader.getString("Hardcore.Vampirism.Name"), (skill == null ? "all skills" : skill)));
}
}

View File

@@ -1,22 +1,21 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import com.gmail.nossr50.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.party.PartyManager;
import com.gmail.nossr50.util.player.UserManager;
public class PartyAcceptCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 1:
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(sender.getName());
Player player = mcMMOPlayer.getPlayer();
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
if (!mcMMOPlayer.hasPartyInvite()) {
sender.sendMessage(LocaleLoader.getString("mcMMO.NoInvites"));
@@ -24,11 +23,11 @@ public class PartyAcceptCommand implements CommandExecutor {
}
// Changing parties
if (!PartyManager.changeOrJoinParty(mcMMOPlayer, player, mcMMOPlayer.getParty(), mcMMOPlayer.getPartyInvite().getName())) {
if (!PartyManager.changeOrJoinParty(mcMMOPlayer, mcMMOPlayer.getPartyInvite().getName())) {
return true;
}
PartyManager.joinInvitedParty(player, mcMMOPlayer);
PartyManager.joinInvitedParty(mcMMOPlayer);
return true;
default:

View File

@@ -1,28 +1,32 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.mcMMO;
import org.bukkit.OfflinePlayer;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import com.gmail.nossr50.mcMMO;
import com.gmail.nossr50.datatypes.party.Party;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.party.PartyManager;
import com.gmail.nossr50.util.player.UserManager;
import org.bukkit.entity.Player;
public class PartyChangeOwnerCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
Party playerParty = UserManager.getPlayer(sender.getName()).getParty();
Party playerParty = UserManager.getPlayer((Player) sender).getParty();
String targetName = CommandUtils.getMatchedPlayerName(args[1]);
OfflinePlayer target = mcMMO.p.getServer().getOfflinePlayer(targetName);
if (!playerParty.getMembers().contains(mcMMO.p.getServer().getOfflinePlayer(args[1]))) {
sender.sendMessage(LocaleLoader.getString("Party.NotInYourParty", args[1]));
if (!playerParty.hasMember(target.getUniqueId())) {
sender.sendMessage(LocaleLoader.getString("Party.NotInYourParty", targetName));
return true;
}
PartyManager.setPartyLeader(args[1], playerParty);
PartyManager.setPartyLeader(target.getUniqueId(), playerParty);
return true;
default:

View File

@@ -1,32 +1,30 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.locale.LocaleLoader;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import com.gmail.nossr50.datatypes.party.Party;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.util.player.UserManager;
import org.bukkit.entity.Player;
public class PartyChangePasswordCommand implements CommandExecutor {
private Party playerParty;
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
playerParty = UserManager.getPlayer(sender.getName()).getParty();
Party party = UserManager.getPlayer((Player) sender).getParty();
switch (args.length) {
case 1:
unprotectParty(sender);
unprotectParty(party, sender);
return true;
case 2:
if (args[1].equalsIgnoreCase("clear") || args[1].equalsIgnoreCase("reset")) {
unprotectParty(sender);
unprotectParty(party, sender);
return true;
}
protectParty(sender, args[1]);
protectParty(party, sender, args[1]);
return true;
default:
@@ -36,15 +34,15 @@ public class PartyChangePasswordCommand implements CommandExecutor {
}
}
private void unprotectParty(CommandSender sender) {
playerParty.setLocked(true);
playerParty.setPassword(null);
private void unprotectParty(Party party, CommandSender sender) {
party.setLocked(true);
party.setPassword(null);
sender.sendMessage(LocaleLoader.getString("Party.Password.Removed"));
}
private void protectParty(CommandSender sender, String password) {
playerParty.setLocked(true);
playerParty.setPassword(password);
private void protectParty(Party party, CommandSender sender, String password) {
party.setLocked(true);
party.setPassword(password);
sender.sendMessage(LocaleLoader.getString("Party.Password.Set", password));
}
}

View File

@@ -0,0 +1,236 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.commands.chat.PartyChatCommand;
import com.gmail.nossr50.commands.party.alliance.PartyAllianceCommand;
import com.gmail.nossr50.commands.party.teleport.PtpCommand;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
public class PartyCommand implements TabExecutor {
private static final List<String> PARTY_SUBCOMMANDS;
private static final List<String> XPSHARE_COMPLETIONS = ImmutableList.of("none", "equal");
private static final List<String> ITEMSHARE_COMPLETIONS = ImmutableList.of("none", "equal", "random", "loot", "mining", "herbalism", "woodcutting", "misc");
static {
ArrayList<String> subcommands = new ArrayList<String>();
for (PartySubcommandType subcommand : PartySubcommandType.values()) {
subcommands.add(subcommand.toString());
}
Collections.sort(subcommands);
PARTY_SUBCOMMANDS = ImmutableList.copyOf(subcommands);
}
private CommandExecutor partyJoinCommand = new PartyJoinCommand();
private CommandExecutor partyAcceptCommand = new PartyAcceptCommand();
private CommandExecutor partyCreateCommand = new PartyCreateCommand();
private CommandExecutor partyQuitCommand = new PartyQuitCommand();
private CommandExecutor partyXpShareCommand = new PartyXpShareCommand();
private CommandExecutor partyItemShareCommand = new PartyItemShareCommand();
private CommandExecutor partyInviteCommand = new PartyInviteCommand();
private CommandExecutor partyKickCommand = new PartyKickCommand();
private CommandExecutor partyDisbandCommand = new PartyDisbandCommand();
private CommandExecutor partyChangeOwnerCommand = new PartyChangeOwnerCommand();
private CommandExecutor partyLockCommand = new PartyLockCommand();
private CommandExecutor partyChangePasswordCommand = new PartyChangePasswordCommand();
private CommandExecutor partyRenameCommand = new PartyRenameCommand();
private CommandExecutor partyInfoCommand = new PartyInfoCommand();
private CommandExecutor partyHelpCommand = new PartyHelpCommand();
private CommandExecutor partyTeleportCommand = new PtpCommand();
private CommandExecutor partyChatCommand = new PartyChatCommand();
private CommandExecutor partyAllianceCommand = new PartyAllianceCommand();
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
if (!Permissions.party(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
Player player = (Player) sender;
if (!UserManager.hasPlayerDataKey(player)) {
return true;
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
if (args.length < 1) {
if (!mcMMOPlayer.inParty()) {
sender.sendMessage(LocaleLoader.getString("Commands.Party.None"));
return printUsage(player);
}
return partyInfoCommand.onCommand(sender, command, label, args);
}
PartySubcommandType subcommand = PartySubcommandType.getSubcommand(args[0]);
if (subcommand == null) {
return printUsage(player);
}
// Can't use this for lock/unlock since they're handled by the same command
if (subcommand != PartySubcommandType.LOCK && subcommand != PartySubcommandType.UNLOCK && !Permissions.partySubcommand(sender, subcommand)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
switch (subcommand) {
case JOIN:
return partyJoinCommand.onCommand(sender, command, label, args);
case ACCEPT:
return partyAcceptCommand.onCommand(sender, command, label, args);
case CREATE:
return partyCreateCommand.onCommand(sender, command, label, args);
case HELP:
return partyHelpCommand.onCommand(sender, command, label, args);
default:
break;
}
// Party member commands
if (!mcMMOPlayer.inParty()) {
sender.sendMessage(LocaleLoader.getString("Commands.Party.None"));
return printUsage(player);
}
switch (subcommand) {
case INFO:
return partyInfoCommand.onCommand(sender, command, label, args);
case QUIT:
return partyQuitCommand.onCommand(sender, command, label, args);
case INVITE:
return partyInviteCommand.onCommand(sender, command, label, args);
case TELEPORT:
return partyTeleportCommand.onCommand(sender, command, label, extractArgs(args));
case CHAT:
return partyChatCommand.onCommand(sender, command, label, extractArgs(args));
default:
break;
}
// Party leader commands
if (!mcMMOPlayer.getParty().getLeader().getUniqueId().equals(player.getUniqueId())) {
sender.sendMessage(LocaleLoader.getString("Party.NotOwner"));
return true;
}
switch (subcommand) {
case XPSHARE:
return partyXpShareCommand.onCommand(sender, command, label, args);
case ITEMSHARE:
return partyItemShareCommand.onCommand(sender, command, label, args);
case KICK:
return partyKickCommand.onCommand(sender, command, label, args);
case DISBAND:
return partyDisbandCommand.onCommand(sender, command, label, args);
case OWNER:
return partyChangeOwnerCommand.onCommand(sender, command, label, args);
case LOCK:
case UNLOCK:
return partyLockCommand.onCommand(sender, command, label, args);
case PASSWORD:
return partyChangePasswordCommand.onCommand(sender, command, label, args);
case RENAME:
return partyRenameCommand.onCommand(sender, command, label, args);
case ALLIANCE:
return partyAllianceCommand.onCommand(sender, command, label, args);
default:
break;
}
return true;
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
return StringUtil.copyPartialMatches(args[0], PARTY_SUBCOMMANDS, new ArrayList<String>(PARTY_SUBCOMMANDS.size()));
case 2:
PartySubcommandType subcommand = PartySubcommandType.getSubcommand(args[0]);
if (subcommand == null) {
return ImmutableList.of();
}
switch (subcommand) {
case JOIN:
case INVITE:
case KICK:
case OWNER:
List<String> playerNames = CommandUtils.getOnlinePlayerNames(sender);
return StringUtil.copyPartialMatches(args[1], playerNames, new ArrayList<String>(playerNames.size()));
case XPSHARE:
return StringUtil.copyPartialMatches(args[1], XPSHARE_COMPLETIONS, new ArrayList<String>(XPSHARE_COMPLETIONS.size()));
case ITEMSHARE:
return StringUtil.copyPartialMatches(args[1], ITEMSHARE_COMPLETIONS, new ArrayList<String>(ITEMSHARE_COMPLETIONS.size()));
case LOCK:
case CHAT:
return StringUtil.copyPartialMatches(args[1], CommandUtils.TRUE_FALSE_OPTIONS, new ArrayList<String>(CommandUtils.TRUE_FALSE_OPTIONS.size()));
case PASSWORD:
return StringUtil.copyPartialMatches(args[1], CommandUtils.RESET_OPTIONS, new ArrayList<String>(CommandUtils.RESET_OPTIONS.size()));
case TELEPORT:
List<String> matches = StringUtil.copyPartialMatches(args[1], PtpCommand.TELEPORT_SUBCOMMANDS, new ArrayList<String>(PtpCommand.TELEPORT_SUBCOMMANDS.size()));
if (matches.size() == 0) {
Player player = (Player) sender;
Party party = UserManager.getPlayer(player).getParty();
playerNames = party.getOnlinePlayerNames(player);
return StringUtil.copyPartialMatches(args[1], playerNames, new ArrayList<String>(playerNames.size()));
}
return matches;
default:
return ImmutableList.of();
}
case 3:
if (PartySubcommandType.getSubcommand(args[0]) == PartySubcommandType.ITEMSHARE && isItemShareCategory(args[1])) {
return StringUtil.copyPartialMatches(args[2], CommandUtils.TRUE_FALSE_OPTIONS, new ArrayList<String>(CommandUtils.TRUE_FALSE_OPTIONS.size()));
}
return ImmutableList.of();
default:
return ImmutableList.of();
}
}
private boolean printUsage(Player player) {
player.sendMessage(LocaleLoader.getString("Party.Help.0", "/party join"));
player.sendMessage(LocaleLoader.getString("Party.Help.1", "/party create"));
player.sendMessage(LocaleLoader.getString("Party.Help.2", "/party ?"));
return true;
}
private String[] extractArgs(String[] args) {
return Arrays.copyOfRange(args, 1, args.length);
}
private boolean isItemShareCategory(String category) {
return category.equalsIgnoreCase("loot") || category.equalsIgnoreCase("mining") || category.equalsIgnoreCase("herbalism") || category.equalsIgnoreCase("woodcutting") || category.equalsIgnoreCase("misc");
}
}

View File

@@ -1,38 +1,34 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import com.gmail.nossr50.datatypes.party.Party;
import com.gmail.nossr50.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.party.PartyManager;
import com.gmail.nossr50.util.player.UserManager;
public class PartyCreateCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
case 3:
Party newParty = PartyManager.getParty(args[1]);
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(sender.getName());
Player player = mcMMOPlayer.getPlayer();
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
// Check to see if the party exists, and if it does cancel creating a new party
if (PartyManager.checkPartyExistence(player, newParty, args[1])) {
if (PartyManager.checkPartyExistence(player, args[1])) {
return true;
}
// Changing parties
if (!PartyManager.changeOrJoinParty(mcMMOPlayer, player, mcMMOPlayer.getParty(), args[1])) {
if (!PartyManager.changeOrJoinParty(mcMMOPlayer, args[1])) {
return true;
}
PartyManager.createParty(player, mcMMOPlayer, args[1], getPassword(args));
PartyManager.createParty(mcMMOPlayer, args[1], getPassword(args));
return true;
default:

View File

@@ -1,22 +1,21 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.events.party.McMMOPartyChangeEvent.EventReason;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import com.gmail.nossr50.datatypes.party.Party;
import com.gmail.nossr50.events.party.McMMOPartyChangeEvent.EventReason;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.party.PartyManager;
import com.gmail.nossr50.util.player.UserManager;
public class PartyDisbandCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 1:
Party playerParty = UserManager.getPlayer(sender.getName()).getParty();
Party playerParty = UserManager.getPlayer((Player) sender).getParty();
String partyName = playerParty.getName();
for (Player member : playerParty.getOnlineMembers()) {

View File

@@ -1,11 +1,10 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.locale.LocaleLoader;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import com.gmail.nossr50.locale.LocaleLoader;
public class PartyHelpCommand implements CommandExecutor {
@Override
@@ -19,6 +18,8 @@ public class PartyHelpCommand implements CommandExecutor {
sender.sendMessage(LocaleLoader.getString("Party.Help.6", "/party kick"));
sender.sendMessage(LocaleLoader.getString("Party.Help.7", "/party leader"));
sender.sendMessage(LocaleLoader.getString("Party.Help.8", "/party disband"));
sender.sendMessage(LocaleLoader.getString("Party.Help.9", "/party itemshare"));
sender.sendMessage(LocaleLoader.getString("Party.Help.10", "/party xpshare"));
return true;
default:

View File

@@ -0,0 +1,128 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.party.PartyFeature;
import com.gmail.nossr50.core.datatypes.party.ShareMode;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import org.bukkit.ChatColor;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class PartyInfoCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 0:
case 1:
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
Party party = mcMMOPlayer.getParty();
displayPartyHeader(player, party);
displayShareModeInfo(player, party);
displayPartyFeatures(player, party);
displayMemberInfo(player, mcMMOPlayer, party);
return true;
default:
sender.sendMessage(LocaleLoader.getString("Commands.Usage.1", "party", "info"));
return true;
}
}
private void displayPartyHeader(Player player, Party party) {
player.sendMessage(LocaleLoader.getString("Commands.Party.Header"));
StringBuilder status = new StringBuilder();
status.append(LocaleLoader.getString("Commands.Party.Status", party.getName(), LocaleLoader.getString("Party.Status." + (party.isLocked() ? "Locked" : "Unlocked")), party.getLevel()));
if (!party.hasReachedLevelCap()) {
status.append(" (").append(party.getXpToLevelPercentage()).append(")");
}
player.sendMessage(status.toString());
}
private void displayPartyFeatures(Player player, Party party) {
player.sendMessage(LocaleLoader.getString("Commands.Party.Features.Header"));
List<String> unlockedPartyFeatures = new ArrayList<String>();
List<String> lockedPartyFeatures = new ArrayList<String>();
for (PartyFeature partyFeature : PartyFeature.values()) {
if (!partyFeature.hasPermission(player)) {
continue;
}
if (isUnlockedFeature(party, partyFeature)) {
unlockedPartyFeatures.add(partyFeature.getLocaleString());
} else {
lockedPartyFeatures.add(partyFeature.getFeatureLockedLocaleString());
}
}
player.sendMessage(LocaleLoader.getString("Commands.Party.UnlockedFeatures", unlockedPartyFeatures.isEmpty() ? "None" : unlockedPartyFeatures));
for (String message : lockedPartyFeatures) {
player.sendMessage(message);
}
}
private boolean isUnlockedFeature(Party party, PartyFeature partyFeature) {
return party.getLevel() >= MainConfig.getInstance().getPartyFeatureUnlockLevel(partyFeature);
}
private void displayShareModeInfo(Player player, Party party) {
boolean xpShareEnabled = isUnlockedFeature(party, PartyFeature.XP_SHARE);
boolean itemShareEnabled = isUnlockedFeature(party, PartyFeature.ITEM_SHARE);
boolean itemSharingActive = (party.getItemShareMode() != ShareMode.NONE);
if (!xpShareEnabled && !itemShareEnabled) {
return;
}
String expShareInfo = "";
String itemShareInfo = "";
String separator = "";
if (xpShareEnabled) {
expShareInfo = LocaleLoader.getString("Commands.Party.ExpShare", party.getXpShareMode().toString());
}
if (itemShareEnabled) {
itemShareInfo = LocaleLoader.getString("Commands.Party.ItemShare", party.getItemShareMode().toString());
}
if (xpShareEnabled && itemShareEnabled) {
separator = ChatColor.DARK_GRAY + " || ";
}
player.sendMessage(LocaleLoader.getString("Commands.Party.ShareMode") + expShareInfo + separator + itemShareInfo);
if (itemSharingActive) {
player.sendMessage(LocaleLoader.getString("Commands.Party.ItemShareCategories", party.getItemShareCategories()));
}
}
private void displayMemberInfo(Player player, McMMOPlayer mcMMOPlayer, Party party) {
/*
* Only show members of the party that this member can see
*/
List<Player> nearMembers = PartyManager.getNearVisibleMembers(mcMMOPlayer);
int membersOnline = party.getVisibleMembers(player).size();
player.sendMessage(LocaleLoader.getString("Commands.Party.Members.Header"));
player.sendMessage(LocaleLoader.getString("Commands.Party.MembersNear", nearMembers.size() + 1, membersOnline));
player.sendMessage(party.createMembersList(player));
}
}

View File

@@ -1,31 +1,33 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import com.gmail.nossr50.datatypes.party.Party;
import com.gmail.nossr50.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.party.PartyManager;
import com.gmail.nossr50.util.commands.CommandUtils;
import com.gmail.nossr50.util.player.UserManager;
public class PartyInviteCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
McMMOPlayer mcMMOTarget = UserManager.getPlayer(args[1]);
String targetName = CommandUtils.getMatchedPlayerName(args[1]);
McMMOPlayer mcMMOTarget = UserManager.getOfflinePlayer(targetName);
if (!CommandUtils.checkPlayerExistence(sender, args[1], mcMMOTarget)) {
if (!CommandUtils.checkPlayerExistence(sender, targetName, mcMMOTarget)) {
return false;
}
Player target = mcMMOTarget.getPlayer();
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(sender.getName());
Player player = mcMMOPlayer.getPlayer();
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
String playerName = player.getName();
if (player.equals(target)) {
sender.sendMessage(LocaleLoader.getString("Party.Invite.Self"));
@@ -33,21 +35,26 @@ public class PartyInviteCommand implements CommandExecutor {
}
if (PartyManager.inSameParty(player, target)) {
sender.sendMessage(LocaleLoader.getString("Party.Player.InSameParty", target.getName()));
sender.sendMessage(LocaleLoader.getString("Party.Player.InSameParty", targetName));
return true;
}
if (!PartyManager.canInvite(mcMMOPlayer)) {
player.sendMessage(LocaleLoader.getString("Party.Locked"));
return true;
}
Party playerParty = mcMMOPlayer.getParty();
if (!PartyManager.canInvite(player, playerParty)) {
player.sendMessage(LocaleLoader.getString("Party.Locked"));
if (PartyManager.isPartyFull(target, playerParty)) {
player.sendMessage(LocaleLoader.getString("Commands.Party.PartyFull.Invite", target.getName(), playerParty.toString(), MainConfig.getInstance().getPartyMaxSize()));
return true;
}
mcMMOTarget.setPartyInvite(playerParty);
sender.sendMessage(LocaleLoader.getString("Commands.Invite.Success"));
target.sendMessage(LocaleLoader.getString("Commands.Party.Invite.0", playerParty.getName(), player.getName()));
target.sendMessage(LocaleLoader.getString("Commands.Party.Invite.0", playerParty.getName(), playerName));
target.sendMessage(LocaleLoader.getString("Commands.Party.Invite.1"));
return true;

View File

@@ -0,0 +1,85 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.ItemShareType;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.party.PartyFeature;
import com.gmail.nossr50.core.datatypes.party.ShareMode;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.StringUtils;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class PartyItemShareCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
Party party = UserManager.getPlayer((Player) sender).getParty();
if (party.getLevel() < MainConfig.getInstance().getPartyFeatureUnlockLevel(PartyFeature.ITEM_SHARE)) {
sender.sendMessage(LocaleLoader.getString("Party.Feature.Disabled.4"));
return true;
}
switch (args.length) {
case 2:
ShareMode mode = ShareMode.getShareMode(args[1].toUpperCase());
if (mode == null) {
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "itemshare", "<NONE | EQUAL | RANDOM>"));
return true;
}
handleChangingShareMode(party, mode);
return true;
case 3:
boolean toggle;
if (CommandUtils.shouldEnableToggle(args[2])) {
toggle = true;
} else if (CommandUtils.shouldDisableToggle(args[2])) {
toggle = false;
} else {
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "itemshare", "<loot | mining | herbalism | woodcutting | misc> <true | false>"));
return true;
}
try {
handleToggleItemShareCategory(party, ItemShareType.valueOf(args[1].toUpperCase()), toggle);
} catch (IllegalArgumentException ex) {
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "itemshare", "<loot | mining | herbalism | woodcutting | misc> <true | false>"));
}
return true;
default:
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "itemshare", "<NONE | EQUAL | RANDOM>"));
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "itemshare", "<loot | mining | herbalism | woodcutting | misc> <true | false>"));
return true;
}
}
private void handleChangingShareMode(Party party, ShareMode mode) {
party.setItemShareMode(mode);
String changeModeMessage = LocaleLoader.getString("Commands.Party.SetSharing", LocaleLoader.getString("Party.ShareType.Item"), LocaleLoader.getString("Party.ShareMode." + StringUtils.getCapitalized(mode.toString())));
for (Player member : party.getOnlineMembers()) {
member.sendMessage(changeModeMessage);
}
}
private void handleToggleItemShareCategory(Party party, ItemShareType type, boolean toggle) {
party.setSharingDrops(type, toggle);
String toggleMessage = LocaleLoader.getString("Commands.Party.ToggleShareCategory", StringUtils.getCapitalized(type.toString()), toggle ? "enabled" : "disabled");
for (Player member : party.getOnlineMembers()) {
member.sendMessage(toggleMessage);
}
}
}

View File

@@ -0,0 +1,79 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class PartyJoinCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
case 3:
String targetName = CommandUtils.getMatchedPlayerName(args[1]);
McMMOPlayer mcMMOTarget = UserManager.getPlayer(targetName);
if (!CommandUtils.checkPlayerExistence(sender, targetName, mcMMOTarget)) {
return true;
}
Player target = mcMMOTarget.getPlayer();
if (!mcMMOTarget.inParty()) {
sender.sendMessage(LocaleLoader.getString("Party.PlayerNotInParty", targetName));
return true;
}
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
Party targetParty = mcMMOTarget.getParty();
if (player.equals(target) || (mcMMOPlayer.inParty() && mcMMOPlayer.getParty().equals(targetParty))) {
sender.sendMessage(LocaleLoader.getString("Party.Join.Self"));
return true;
}
String password = getPassword(args);
// Make sure party passwords match
if (!PartyManager.checkPartyPassword(player, targetParty, password)) {
return true;
}
String partyName = targetParty.getName();
// Changing parties
if (!PartyManager.changeOrJoinParty(mcMMOPlayer, partyName)) {
return true;
}
if (PartyManager.isPartyFull(player, targetParty)) {
player.sendMessage(LocaleLoader.getString("Commands.Party.PartyFull", targetParty.toString()));
return true;
}
player.sendMessage(LocaleLoader.getString("Commands.Party.Join", partyName));
PartyManager.addToParty(mcMMOPlayer, targetParty);
return true;
default:
sender.sendMessage(LocaleLoader.getString("Commands.Usage.3", "party", "join", "<" + LocaleLoader.getString("Commands.Usage.Player") + ">", "[" + LocaleLoader.getString("Commands.Usage.Password") + "]"));
return true;
}
}
private String getPassword(String[] args) {
if (args.length == 3) {
return args[2];
}
return null;
}
}

View File

@@ -1,31 +1,33 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.core.events.party.McMMOPartyChangeEvent.EventReason;
import com.gmail.nossr50.mcMMO;
import org.bukkit.OfflinePlayer;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import com.gmail.nossr50.mcMMO;
import com.gmail.nossr50.datatypes.party.Party;
import com.gmail.nossr50.events.party.McMMOPartyChangeEvent.EventReason;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.party.PartyManager;
import com.gmail.nossr50.util.player.UserManager;
public class PartyKickCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
Party playerParty = UserManager.getPlayer(sender.getName()).getParty();
OfflinePlayer target = mcMMO.p.getServer().getOfflinePlayer(args[1]);
Party playerParty = UserManager.getPlayer((Player) sender).getParty();
String targetName = CommandUtils.getMatchedPlayerName(args[1]);
if (!playerParty.getMembers().contains(target)) {
sender.sendMessage(LocaleLoader.getString("Party.NotInYourParty", args[1]));
if (!playerParty.hasMember(targetName)) {
sender.sendMessage(LocaleLoader.getString("Party.NotInYourParty", targetName));
return true;
}
OfflinePlayer target = mcMMO.p.getServer().getOfflinePlayer(targetName);
if (target.isOnline()) {
Player onlineTarget = target.getPlayer();
String partyName = playerParty.getName();
@@ -34,6 +36,7 @@ public class PartyKickCommand implements CommandExecutor {
return true;
}
PartyManager.processPartyLeaving(UserManager.getPlayer(onlineTarget));
onlineTarget.sendMessage(LocaleLoader.getString("Commands.Party.Kick", partyName));
}

View File

@@ -0,0 +1,69 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class PartyLockCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 1:
if (args[0].equalsIgnoreCase("lock")) {
togglePartyLock(sender, true);
} else if (args[0].equalsIgnoreCase("unlock")) {
togglePartyLock(sender, false);
}
return true;
case 2:
if (!args[0].equalsIgnoreCase("lock")) {
sendUsageStrings(sender);
return true;
}
if (CommandUtils.shouldEnableToggle(args[1])) {
togglePartyLock(sender, true);
} else if (CommandUtils.shouldDisableToggle(args[1])) {
togglePartyLock(sender, false);
} else {
sendUsageStrings(sender);
}
return true;
default:
sendUsageStrings(sender);
return true;
}
}
private void sendUsageStrings(CommandSender sender) {
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "lock", "[on|off]"));
sender.sendMessage(LocaleLoader.getString("Commands.Usage.1", "party", "unlock"));
}
private void togglePartyLock(CommandSender sender, boolean lock) {
Party party = UserManager.getPlayer((Player) sender).getParty();
if (!Permissions.partySubcommand(sender, lock ? PartySubcommandType.LOCK : PartySubcommandType.UNLOCK)) {
sender.sendMessage(LocaleLoader.getString("mcMMO.NoPermission"));
return;
}
if (lock ? party.isLocked() : !party.isLocked()) {
sender.sendMessage(LocaleLoader.getString("Party." + (lock ? "IsLocked" : "IsntLocked")));
return;
}
party.setLocked(lock);
sender.sendMessage(LocaleLoader.getString("Party." + (lock ? "Locked" : "Unlocked")));
}
}

View File

@@ -1,29 +1,30 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.events.party.McMMOPartyChangeEvent.EventReason;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import com.gmail.nossr50.datatypes.party.Party;
import com.gmail.nossr50.events.party.McMMOPartyChangeEvent.EventReason;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.party.PartyManager;
import com.gmail.nossr50.util.player.UserManager;
public class PartyQuitCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 1:
Player player = (Player) sender;
Party playerParty = UserManager.getPlayer(player).getParty();
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
Party playerParty = mcMMOPlayer.getParty();
if (!PartyManager.handlePartyChangeEvent(player, playerParty.getName(), null, EventReason.LEFT_PARTY)) {
return true;
}
PartyManager.removeFromParty(player, playerParty);
PartyManager.removeFromParty(mcMMOPlayer);
sender.sendMessage(LocaleLoader.getString("Commands.Party.Leave"));
return true;

View File

@@ -1,23 +1,22 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.events.party.McMMOPartyChangeEvent.EventReason;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import com.gmail.nossr50.datatypes.party.Party;
import com.gmail.nossr50.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.events.party.McMMOPartyChangeEvent.EventReason;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.party.PartyManager;
import com.gmail.nossr50.util.player.UserManager;
public class PartyRenameCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(sender.getName());
McMMOPlayer mcMMOPlayer = UserManager.getPlayer((Player) sender);
Party playerParty = mcMMOPlayer.getParty();
String oldPartyName = playerParty.getName();
@@ -30,14 +29,13 @@ public class PartyRenameCommand implements CommandExecutor {
}
Player player = mcMMOPlayer.getPlayer();
Party newParty = PartyManager.getParty(newPartyName);
// Check to see if the party exists, and if it does cancel renaming the party
if (PartyManager.checkPartyExistence(player, newParty, newPartyName)) {
if (PartyManager.checkPartyExistence(player, newPartyName)) {
return true;
}
String leaderName = playerParty.getLeader();
String leaderName = playerParty.getLeader().getPlayerName();
for (Player member : playerParty.getOnlineMembers()) {
if (!PartyManager.handlePartyChangeEvent(member, oldPartyName, newPartyName, EventReason.CHANGED_PARTIES)) {

View File

@@ -7,7 +7,7 @@ public enum PartySubcommandType {
HELP,
INFO,
QUIT,
EXPSHARE,
XPSHARE,
ITEMSHARE,
INVITE,
KICK,
@@ -18,7 +18,8 @@ public enum PartySubcommandType {
PASSWORD,
RENAME,
TELEPORT,
CHAT;
CHAT,
ALLIANCE;
public static PartySubcommandType getSubcommand(String commandName) {
for (PartySubcommandType command : values()) {
@@ -29,18 +30,16 @@ public enum PartySubcommandType {
if (commandName.equalsIgnoreCase("?")) {
return HELP;
}
else if (commandName.equalsIgnoreCase("q") || commandName.equalsIgnoreCase("leave")) {
} else if (commandName.equalsIgnoreCase("q") || commandName.equalsIgnoreCase("leave")) {
return QUIT;
}
else if (commandName.equalsIgnoreCase("leader")) {
} else if (commandName.equalsIgnoreCase("leader")) {
return OWNER;
}
else if (commandName.equalsIgnoreCase("xpshare") || commandName.equalsIgnoreCase("shareexp") || commandName.equalsIgnoreCase("sharexp")) {
return EXPSHARE;
}
else if (commandName.equalsIgnoreCase("shareitem") || commandName.equalsIgnoreCase("shareitems")) {
} else if (commandName.equalsIgnoreCase("xpshare") || commandName.equalsIgnoreCase("shareexp") || commandName.equalsIgnoreCase("sharexp")) {
return XPSHARE;
} else if (commandName.equalsIgnoreCase("shareitem") || commandName.equalsIgnoreCase("shareitems")) {
return ITEMSHARE;
} else if (commandName.equalsIgnoreCase("ally")) {
return ALLIANCE;
}
return null;

View File

@@ -0,0 +1,53 @@
package com.gmail.nossr50.commands.party;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.party.PartyFeature;
import com.gmail.nossr50.core.datatypes.party.ShareMode;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.StringUtils;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class PartyXpShareCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
Party party = UserManager.getPlayer((Player) sender).getParty();
if (party.getLevel() < MainConfig.getInstance().getPartyFeatureUnlockLevel(PartyFeature.XP_SHARE)) {
sender.sendMessage(LocaleLoader.getString("Party.Feature.Disabled.5"));
return true;
}
switch (args.length) {
case 2:
if (args[1].equalsIgnoreCase("none") || CommandUtils.shouldDisableToggle(args[1])) {
handleChangingShareMode(party, ShareMode.NONE);
} else if (args[1].equalsIgnoreCase("equal") || args[1].equalsIgnoreCase("even") || CommandUtils.shouldEnableToggle(args[1])) {
handleChangingShareMode(party, ShareMode.EQUAL);
} else {
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "xpshare", "<NONE | EQUAL>"));
}
return true;
default:
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "xpshare", "<NONE | EQUAL>"));
return true;
}
}
private void handleChangingShareMode(Party party, ShareMode mode) {
party.setXpShareMode(mode);
String changeModeMessage = LocaleLoader.getString("Commands.Party.SetSharing", LocaleLoader.getString("Party.ShareType.Xp"), LocaleLoader.getString("Party.ShareMode." + StringUtils.getCapitalized(mode.toString())));
for (Player member : party.getOnlineMembers()) {
member.sendMessage(changeModeMessage);
}
}
}

View File

@@ -0,0 +1,38 @@
package com.gmail.nossr50.commands.party.alliance;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class PartyAllianceAcceptCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
if (!mcMMOPlayer.hasPartyAllianceInvite()) {
sender.sendMessage(LocaleLoader.getString("mcMMO.NoInvites"));
return true;
}
if (mcMMOPlayer.getParty().getAlly() != null) {
player.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.AlreadyAllies"));
return true;
}
PartyManager.acceptAllianceInvite(mcMMOPlayer);
return true;
default:
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "alliance", "accept"));
return true;
}
}
}

View File

@@ -0,0 +1,131 @@
package com.gmail.nossr50.commands.party.alliance;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.party.PartyFeature;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.google.common.collect.ImmutableList;
import org.bukkit.ChatColor;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public class PartyAllianceCommand implements TabExecutor {
public static final List<String> ALLIANCE_SUBCOMMANDS = ImmutableList.of("invite", "accept", "disband");
private Player player;
private Party playerParty;
private Party targetParty;
private CommandExecutor partyAllianceInviteCommand = new PartyAllianceInviteCommand();
private CommandExecutor partyAllianceAcceptCommand = new PartyAllianceAcceptCommand();
private CommandExecutor partyAllianceDisbandCommand = new PartyAllianceDisbandCommand();
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
playerParty = mcMMOPlayer.getParty();
switch (args.length) {
case 1:
if (playerParty.getLevel() < MainConfig.getInstance().getPartyFeatureUnlockLevel(PartyFeature.ALLIANCE)) {
sender.sendMessage(LocaleLoader.getString("Party.Feature.Disabled.3"));
return true;
}
if (playerParty.getAlly() == null) {
printUsage();
return true;
}
targetParty = playerParty.getAlly();
displayPartyHeader();
displayMemberInfo(mcMMOPlayer);
return true;
case 2:
case 3:
if (playerParty.getLevel() < MainConfig.getInstance().getPartyFeatureUnlockLevel(PartyFeature.ALLIANCE)) {
sender.sendMessage(LocaleLoader.getString("Party.Feature.Disabled.3"));
return true;
}
if (args[1].equalsIgnoreCase("invite")) {
return partyAllianceInviteCommand.onCommand(sender, command, label, args);
}
if (args[1].equalsIgnoreCase("accept")) {
return partyAllianceAcceptCommand.onCommand(sender, command, label, args);
}
if (args[1].equalsIgnoreCase("disband")) {
return partyAllianceDisbandCommand.onCommand(sender, command, label, args);
}
if (playerParty.getAlly() == null) {
printUsage();
return true;
}
targetParty = playerParty.getAlly();
displayPartyHeader();
displayMemberInfo(mcMMOPlayer);
return true;
default:
return false;
}
}
private boolean printUsage() {
player.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.Help.0"));
player.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.Help.1"));
return true;
}
@Override
public List<String> onTabComplete(CommandSender commandSender, Command command, String label, String[] args) {
switch (args.length) {
case 1:
List<String> matches = StringUtil.copyPartialMatches(args[0], ALLIANCE_SUBCOMMANDS, new ArrayList<String>(ALLIANCE_SUBCOMMANDS.size()));
if (matches.size() == 0) {
List<String> playerNames = CommandUtils.getOnlinePlayerNames(commandSender);
return StringUtil.copyPartialMatches(args[0], playerNames, new ArrayList<String>(playerNames.size()));
}
return matches;
default:
return ImmutableList.of();
}
}
private void displayPartyHeader() {
player.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.Header"));
player.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.Ally", playerParty.getName(), targetParty.getName()));
}
private void displayMemberInfo(McMMOPlayer mcMMOPlayer) {
List<Player> nearMembers = PartyManager.getNearMembers(mcMMOPlayer);
player.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.Members.Header"));
player.sendMessage(playerParty.createMembersList(player));
player.sendMessage(ChatColor.DARK_GRAY + "----------------------------");
player.sendMessage(targetParty.createMembersList(player));
}
}

View File

@@ -0,0 +1,35 @@
package com.gmail.nossr50.commands.party.alliance;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class PartyAllianceDisbandCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 2:
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
Party party = mcMMOPlayer.getParty();
if (party.getAlly() == null) {
sender.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.None"));
return true;
}
PartyManager.disbandAlliance(player, party, party.getAlly());
return true;
default:
sender.sendMessage(LocaleLoader.getString("Commands.Usage.2", "party", "alliance", "disband"));
return true;
}
}
}

View File

@@ -0,0 +1,70 @@
package com.gmail.nossr50.commands.party.alliance;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
public class PartyAllianceInviteCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 3:
String targetName = CommandUtils.getMatchedPlayerName(args[2]);
McMMOPlayer mcMMOTarget = UserManager.getOfflinePlayer(targetName);
if (!CommandUtils.checkPlayerExistence(sender, targetName, mcMMOTarget)) {
return false;
}
Player target = mcMMOTarget.getPlayer();
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
String playerName = player.getName();
if (player.equals(target)) {
sender.sendMessage(LocaleLoader.getString("Party.Invite.Self"));
return true;
}
if (!mcMMOTarget.inParty()) {
player.sendMessage(LocaleLoader.getString("Party.PlayerNotInParty", targetName));
return true;
}
if (PartyManager.inSameParty(player, target)) {
sender.sendMessage(LocaleLoader.getString("Party.Player.InSameParty", targetName));
return true;
}
if (!mcMMOTarget.getParty().getLeader().getUniqueId().equals(target.getUniqueId())) {
player.sendMessage(LocaleLoader.getString("Party.Target.NotOwner", targetName));
return true;
}
Party playerParty = mcMMOPlayer.getParty();
if (playerParty.getAlly() != null) {
player.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.AlreadyAllies"));
return true;
}
mcMMOTarget.setPartyAllianceInvite(playerParty);
sender.sendMessage(LocaleLoader.getString("Commands.Invite.Success"));
target.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.Invite.0", playerParty.getName(), playerName));
target.sendMessage(LocaleLoader.getString("Commands.Party.Alliance.Invite.1"));
return true;
default:
sender.sendMessage(LocaleLoader.getString("Commands.Usage.3", "party", "alliance", "invite", "<" + LocaleLoader.getString("Commands.Usage.Player") + ">"));
return true;
}
}
}

View File

@@ -0,0 +1,30 @@
package com.gmail.nossr50.commands.party.teleport;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.PartyTeleportRecord;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
public class PtpAcceptAnyCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (!Permissions.partyTeleportAcceptAll(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
PartyTeleportRecord ptpRecord = UserManager.getPlayer(sender.getName()).getPartyTeleportRecord();
if (ptpRecord.isConfirmRequired()) {
sender.sendMessage(LocaleLoader.getString("Commands.ptp.AcceptAny.Disabled"));
} else {
sender.sendMessage(LocaleLoader.getString("Commands.ptp.AcceptAny.Enabled"));
}
ptpRecord.toggleConfirmRequired();
return true;
}
}

View File

@@ -1,18 +1,17 @@
package com.gmail.nossr50.commands.party.teleport;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.PartyTeleportRecord;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.skills.SkillUtils;
import org.bukkit.World;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import com.gmail.nossr50.config.Config;
import com.gmail.nossr50.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.util.Misc;
import com.gmail.nossr50.util.Permissions;
import com.gmail.nossr50.util.player.UserManager;
public class PtpAcceptCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
@@ -21,28 +20,28 @@ public class PtpAcceptCommand implements CommandExecutor {
return true;
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(sender.getName());
Player player = mcMMOPlayer.getPlayer();
Player player = (Player) sender;
PartyTeleportRecord ptpRecord = UserManager.getPlayer(player).getPartyTeleportRecord();
if (!mcMMOPlayer.hasPtpRequest()) {
if (!ptpRecord.hasRequest()) {
player.sendMessage(LocaleLoader.getString("Commands.ptp.NoRequests"));
return true;
}
if ((mcMMOPlayer.getPtpTimeout() + Config.getInstance().getPTPCommandTimeout()) * Misc.TIME_CONVERSION_FACTOR < System.currentTimeMillis()) {
mcMMOPlayer.removePtpRequest();
if (SkillUtils.cooldownExpired(ptpRecord.getTimeout(), MainConfig.getInstance().getPTPCommandTimeout())) {
ptpRecord.removeRequest();
player.sendMessage(LocaleLoader.getString("Commands.ptp.RequestExpired"));
return true;
}
Player target = mcMMOPlayer.getPtpRequest();
mcMMOPlayer.removePtpRequest();
Player target = ptpRecord.getRequestor();
ptpRecord.removeRequest();
if (!PtpCommand.canTeleport(sender, player, target.getName())) {
return true;
}
if (Config.getInstance().getPTPCommandWorldPermissions()) {
if (MainConfig.getInstance().getPTPCommandWorldPermissions()) {
World targetWorld = target.getWorld();
World playerWorld = player.getWorld();
@@ -50,15 +49,14 @@ public class PtpAcceptCommand implements CommandExecutor {
if (!Permissions.partyTeleportWorld(target, targetWorld)) {
target.sendMessage(LocaleLoader.getString("Commands.ptp.NoWorldPermissions", targetWorld.getName()));
return true;
}
else if (targetWorld != playerWorld && !Permissions.partyTeleportWorld(target, playerWorld)) {
} else if (targetWorld != playerWorld && !Permissions.partyTeleportWorld(target, playerWorld)) {
target.sendMessage(LocaleLoader.getString("Commands.ptp.NoWorldPermissions", playerWorld.getName()));
return true;
}
}
}
PtpCommand.handlePartyTeleportEvent(target, player);
PtpCommand.handleTeleportWarmup(target, player);
return true;
}
}

View File

@@ -0,0 +1,221 @@
package com.gmail.nossr50.commands.party.teleport;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.config.WorldBlacklist;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.Party;
import com.gmail.nossr50.core.datatypes.party.PartyFeature;
import com.gmail.nossr50.core.datatypes.party.PartyTeleportRecord;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.runnables.items.TeleportationWarmup;
import com.gmail.nossr50.core.util.EventUtils;
import com.gmail.nossr50.core.util.Misc;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.core.util.skills.SkillUtils;
import com.gmail.nossr50.core.worldguard.WorldGuardManager;
import com.gmail.nossr50.core.worldguard.WorldGuardUtils;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public class PtpCommand implements TabExecutor {
public static final List<String> TELEPORT_SUBCOMMANDS = ImmutableList.of("toggle", "accept", "acceptany", "acceptall");
private CommandExecutor ptpToggleCommand = new PtpToggleCommand();
private CommandExecutor ptpAcceptAnyCommand = new PtpAcceptAnyCommand();
private CommandExecutor ptpAcceptCommand = new PtpAcceptCommand();
protected static boolean canTeleport(CommandSender sender, Player player, String targetName) {
McMMOPlayer mcMMOTarget = UserManager.getPlayer(targetName);
if (!CommandUtils.checkPlayerExistence(sender, targetName, mcMMOTarget)) {
return false;
}
Player target = mcMMOTarget.getPlayer();
if (player.equals(target)) {
player.sendMessage(LocaleLoader.getString("Party.Teleport.Self"));
return false;
}
if (!PartyManager.inSameParty(player, target)) {
player.sendMessage(LocaleLoader.getString("Party.NotInYourParty", targetName));
return false;
}
if (!mcMMOTarget.getPartyTeleportRecord().isEnabled()) {
player.sendMessage(LocaleLoader.getString("Party.Teleport.Disabled", targetName));
return false;
}
if (!target.isValid()) {
player.sendMessage(LocaleLoader.getString("Party.Teleport.Dead"));
return false;
}
return true;
}
protected static void handleTeleportWarmup(Player teleportingPlayer, Player targetPlayer) {
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(teleportingPlayer);
McMMOPlayer mcMMOTarget = UserManager.getPlayer(targetPlayer);
long warmup = MainConfig.getInstance().getPTPCommandWarmup();
mcMMOPlayer.actualizeTeleportCommenceLocation(teleportingPlayer);
if (warmup > 0) {
teleportingPlayer.sendMessage(LocaleLoader.getString("Teleport.Commencing", warmup));
new TeleportationWarmup(mcMMOPlayer, mcMMOTarget).runTaskLater(mcMMO.p, 20 * warmup);
} else {
EventUtils.handlePartyTeleportEvent(teleportingPlayer, targetPlayer);
}
}
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
Player player = (Player) sender;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return true;
}
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(player.getWorld()))
return true;
if (!UserManager.hasPlayerDataKey(player)) {
return true;
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
if (!mcMMOPlayer.inParty()) {
sender.sendMessage(LocaleLoader.getString("Commands.Party.None"));
return true;
}
Party party = mcMMOPlayer.getParty();
if (party.getLevel() < MainConfig.getInstance().getPartyFeatureUnlockLevel(PartyFeature.TELEPORT)) {
sender.sendMessage(LocaleLoader.getString("Party.Feature.Disabled.2"));
return true;
}
switch (args.length) {
case 1:
if (args[0].equalsIgnoreCase("toggle")) {
return ptpToggleCommand.onCommand(sender, command, label, args);
}
if (args[0].equalsIgnoreCase("acceptany") || args[0].equalsIgnoreCase("acceptall")) {
return ptpAcceptAnyCommand.onCommand(sender, command, label, args);
}
long recentlyHurt = mcMMOPlayer.getRecentlyHurt();
int hurtCooldown = MainConfig.getInstance().getPTPCommandRecentlyHurtCooldown();
if (hurtCooldown > 0) {
int timeRemaining = SkillUtils.calculateTimeLeft(recentlyHurt * Misc.TIME_CONVERSION_FACTOR, hurtCooldown, player);
if (timeRemaining > 0) {
player.sendMessage(LocaleLoader.getString("Item.Injured.Wait", timeRemaining));
return true;
}
}
if (args[0].equalsIgnoreCase("accept")) {
return ptpAcceptCommand.onCommand(sender, command, label, args);
}
if (!Permissions.partyTeleportSend(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
int ptpCooldown = MainConfig.getInstance().getPTPCommandCooldown();
long ptpLastUse = mcMMOPlayer.getPartyTeleportRecord().getLastUse();
if (ptpCooldown > 0) {
int timeRemaining = SkillUtils.calculateTimeLeft(ptpLastUse * Misc.TIME_CONVERSION_FACTOR, ptpCooldown, player);
if (timeRemaining > 0) {
player.sendMessage(LocaleLoader.getString("Item.Generic.Wait", timeRemaining));
return true;
}
}
sendTeleportRequest(sender, player, CommandUtils.getMatchedPlayerName(args[0]));
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
List<String> matches = StringUtil.copyPartialMatches(args[0], TELEPORT_SUBCOMMANDS, new ArrayList<String>(TELEPORT_SUBCOMMANDS.size()));
if (matches.size() == 0) {
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
if (!mcMMOPlayer.inParty()) {
return ImmutableList.of();
}
List<String> playerNames = mcMMOPlayer.getParty().getOnlinePlayerNames(player);
return StringUtil.copyPartialMatches(args[0], playerNames, new ArrayList<String>(playerNames.size()));
}
return matches;
default:
return ImmutableList.of();
}
}
private void sendTeleportRequest(CommandSender sender, Player player, String targetName) {
if (!canTeleport(sender, player, targetName)) {
return;
}
McMMOPlayer mcMMOTarget = UserManager.getPlayer(targetName);
Player target = mcMMOTarget.getPlayer();
PartyTeleportRecord ptpRecord = mcMMOTarget.getPartyTeleportRecord();
if (!ptpRecord.isConfirmRequired()) {
handleTeleportWarmup(player, target);
return;
}
ptpRecord.setRequestor(player);
ptpRecord.actualizeTimeout();
player.sendMessage(LocaleLoader.getString("Commands.Invite.Success"));
target.sendMessage(LocaleLoader.getString("Commands.ptp.Request1", player.getName()));
target.sendMessage(LocaleLoader.getString("Commands.ptp.Request2", MainConfig.getInstance().getPTPCommandTimeout()));
}
}

View File

@@ -0,0 +1,30 @@
package com.gmail.nossr50.commands.party.teleport;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.party.PartyTeleportRecord;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.Permissions;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
public class PtpToggleCommand implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (!Permissions.partyTeleportToggle(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
PartyTeleportRecord ptpRecord = UserManager.getPlayer(sender.getName()).getPartyTeleportRecord();
if (ptpRecord.isEnabled()) {
sender.sendMessage(LocaleLoader.getString("Commands.ptp.Disabled"));
} else {
sender.sendMessage(LocaleLoader.getString("Commands.ptp.Enabled"));
}
ptpRecord.toggleEnabled();
return true;
}
}

View File

@@ -0,0 +1,112 @@
package com.gmail.nossr50.commands.player;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.datatypes.player.PlayerProfile;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.core.util.scoreboards.ScoreboardManager;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public class InspectCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 1:
String playerName = CommandUtils.getMatchedPlayerName(args[0]);
McMMOPlayer mcMMOPlayer = UserManager.getOfflinePlayer(playerName);
// If the mcMMOPlayer doesn't exist, create a temporary profile and check if it's present in the database. If it's not, abort the process.
if (mcMMOPlayer == null) {
PlayerProfile profile = mcMMO.getDatabaseManager().loadPlayerProfile(playerName, false); // Temporary Profile
if (!CommandUtils.isLoaded(sender, profile)) {
return true;
}
if (CommandUtils.inspectOffline(sender, profile, Permissions.inspectOffline(sender))) {
return true;
}
if (MainConfig.getInstance().getScoreboardsEnabled() && sender instanceof Player && MainConfig.getInstance().getInspectUseBoard()) {
ScoreboardManager.enablePlayerInspectScoreboard((Player) sender, profile);
if (!MainConfig.getInstance().getInspectUseChat()) {
return true;
}
}
sender.sendMessage(LocaleLoader.getString("Inspect.OfflineStats", playerName));
sender.sendMessage(LocaleLoader.getString("Stats.Header.Gathering"));
for (PrimarySkillType skill : PrimarySkillType.GATHERING_SKILLS) {
sender.sendMessage(CommandUtils.displaySkill(profile, skill));
}
sender.sendMessage(LocaleLoader.getString("Stats.Header.Combat"));
for (PrimarySkillType skill : PrimarySkillType.COMBAT_SKILLS) {
sender.sendMessage(CommandUtils.displaySkill(profile, skill));
}
sender.sendMessage(LocaleLoader.getString("Stats.Header.Misc"));
for (PrimarySkillType skill : PrimarySkillType.MISC_SKILLS) {
sender.sendMessage(CommandUtils.displaySkill(profile, skill));
}
} else {
Player target = mcMMOPlayer.getPlayer();
if (CommandUtils.hidden(sender, target, Permissions.inspectHidden(sender))) {
if (!Permissions.inspectOffline(sender)) {
sender.sendMessage(LocaleLoader.getString("Inspect.Offline"));
return true;
}
} else if (CommandUtils.tooFar(sender, target, Permissions.inspectFar(sender))) {
return true;
}
if (MainConfig.getInstance().getScoreboardsEnabled() && sender instanceof Player && MainConfig.getInstance().getInspectUseBoard()) {
ScoreboardManager.enablePlayerInspectScoreboard((Player) sender, mcMMOPlayer.getProfile());
if (!MainConfig.getInstance().getInspectUseChat()) {
return true;
}
}
sender.sendMessage(LocaleLoader.getString("Inspect.Stats", target.getName()));
CommandUtils.printGatheringSkills(target, sender);
CommandUtils.printCombatSkills(target, sender);
CommandUtils.printMiscSkills(target, sender);
sender.sendMessage(LocaleLoader.getString("Commands.PowerLevel", mcMMOPlayer.getPowerLevel()));
}
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
List<String> playerNames = CommandUtils.getOnlinePlayerNames(sender);
return StringUtil.copyPartialMatches(args[0], playerNames, new ArrayList<String>(playerNames.size()));
default:
return ImmutableList.of();
}
}
}

View File

@@ -0,0 +1,71 @@
package com.gmail.nossr50.commands.player;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.SuperAbilityType;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.core.util.scoreboards.ScoreboardManager;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import java.util.List;
public class MccooldownCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
if (!CommandUtils.hasPlayerDataKey(sender)) {
return true;
}
switch (args.length) {
case 0:
Player player = (Player) sender;
if (MainConfig.getInstance().getScoreboardsEnabled() && MainConfig.getInstance().getCooldownUseBoard()) {
ScoreboardManager.enablePlayerCooldownScoreboard(player);
if (!MainConfig.getInstance().getCooldownUseChat()) {
return true;
}
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
player.sendMessage(LocaleLoader.getString("Commands.Cooldowns.Header"));
player.sendMessage(LocaleLoader.getString("mcMMO.NoSkillNote"));
for (SuperAbilityType ability : SuperAbilityType.values()) {
if (!ability.getPermissions(player)) {
continue;
}
int seconds = mcMMOPlayer.calculateTimeRemaining(ability);
if (seconds <= 0) {
player.sendMessage(LocaleLoader.getString("Commands.Cooldowns.Row.Y", ability.getName()));
} else {
player.sendMessage(LocaleLoader.getString("Commands.Cooldowns.Row.N", ability.getName(), seconds));
}
}
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
return ImmutableList.of();
}
}

View File

@@ -0,0 +1,112 @@
package com.gmail.nossr50.commands.player;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.runnables.commands.McrankCommandAsyncTask;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.metadata.FixedMetadataValue;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public class McrankCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
switch (args.length) {
case 0:
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
if (!Permissions.mcrank(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (!CommandUtils.hasPlayerDataKey(sender)) {
return true;
}
display(sender, sender.getName());
return true;
case 1:
if (!Permissions.mcrankOthers(sender)) {
sender.sendMessage(command.getPermissionMessage());
return true;
}
if (!CommandUtils.hasPlayerDataKey(sender)) {
return true;
}
String playerName = CommandUtils.getMatchedPlayerName(args[0]);
McMMOPlayer mcMMOPlayer = UserManager.getOfflinePlayer(playerName);
if (mcMMOPlayer != null) {
Player player = mcMMOPlayer.getPlayer();
playerName = player.getName();
if (CommandUtils.tooFar(sender, player, Permissions.mcrankFar(sender))) {
return true;
}
} else if (CommandUtils.inspectOffline(sender, mcMMO.getDatabaseManager().loadPlayerProfile(playerName, false), Permissions.mcrankOffline(sender))) {
return true;
}
display(sender, playerName);
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
List<String> playerNames = CommandUtils.getOnlinePlayerNames(sender);
return StringUtil.copyPartialMatches(args[0], playerNames, new ArrayList<String>(playerNames.size()));
default:
return ImmutableList.of();
}
}
private void display(CommandSender sender, String playerName) {
if (sender instanceof Player) {
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(sender.getName());
long cooldownMillis = Math.max(MainConfig.getInstance().getDatabasePlayerCooldown(), 1750);
if (mcMMOPlayer.getDatabaseATS() + cooldownMillis > System.currentTimeMillis()) {
sender.sendMessage(LocaleLoader.getString("Commands.Database.Cooldown"));
return;
}
if (((Player) sender).hasMetadata(mcMMO.databaseCommandKey)) {
sender.sendMessage(LocaleLoader.getString("Commands.Database.Processing"));
return;
} else {
((Player) sender).setMetadata(mcMMO.databaseCommandKey, new FixedMetadataValue(mcMMO.p, null));
}
mcMMOPlayer.actualizeDatabaseATS();
}
boolean useBoard = MainConfig.getInstance().getScoreboardsEnabled() && (sender instanceof Player) && (MainConfig.getInstance().getRankUseBoard());
boolean useChat = !useBoard || MainConfig.getInstance().getRankUseChat();
new McrankCommandAsyncTask(playerName, sender, useBoard, useChat).runTaskAsynchronously(mcMMO.p);
}
}

View File

@@ -1,27 +1,40 @@
package com.gmail.nossr50.commands.player;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.core.util.scoreboards.ScoreboardManager;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import com.gmail.nossr50.config.Config;
import com.gmail.nossr50.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.util.commands.CommandUtils;
import com.gmail.nossr50.util.player.UserManager;
import java.util.List;
public class McstatsCommand implements CommandExecutor {
public class McstatsCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
if (!CommandUtils.hasPlayerDataKey(sender)) {
return true;
}
switch (args.length) {
case 0:
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(sender.getName());
Player player = mcMMOPlayer.getPlayer();
Player player = (Player) sender;
if (MainConfig.getInstance().getStatsUseBoard() && MainConfig.getInstance().getScoreboardsEnabled()) {
ScoreboardManager.enablePlayerStatsScoreboard(player);
if (!MainConfig.getInstance().getStatsUseChat()) {
return true;
}
}
player.sendMessage(LocaleLoader.getString("Stats.Own.Stats"));
player.sendMessage(LocaleLoader.getString("mcMMO.NoSkillNote"));
@@ -30,12 +43,11 @@ public class McstatsCommand implements CommandExecutor {
CommandUtils.printCombatSkills(player);
CommandUtils.printMiscSkills(player);
int powerLevelCap = Config.getInstance().getPowerLevelCap();
int powerLevelCap = MainConfig.getInstance().getPowerLevelCap();
if (powerLevelCap != Integer.MAX_VALUE) {
player.sendMessage(LocaleLoader.getString("Commands.PowerLevel.Capped", UserManager.getPlayer(player).getPowerLevel(), powerLevelCap));
}
else {
} else {
player.sendMessage(LocaleLoader.getString("Commands.PowerLevel", UserManager.getPlayer(player).getPowerLevel()));
}
@@ -45,4 +57,9 @@ public class McstatsCommand implements CommandExecutor {
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
return ImmutableList.of();
}
}

View File

@@ -0,0 +1,135 @@
package com.gmail.nossr50.commands.player;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.runnables.commands.MctopCommandAsyncTask;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.StringUtils;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.mcMMO;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.metadata.FixedMetadataValue;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
public class MctopCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
PrimarySkillType skill = null;
switch (args.length) {
case 0:
display(1, skill, sender, command);
return true;
case 1:
if (StringUtils.isInt(args[0])) {
display(Math.abs(Integer.parseInt(args[0])), skill, sender, command);
return true;
}
skill = extractSkill(sender, args[0]);
if (skill == null) {
return true;
}
display(1, skill, sender, command);
return true;
case 2:
if (CommandUtils.isInvalidInteger(sender, args[1])) {
return true;
}
skill = extractSkill(sender, args[0]);
if (skill == null) {
return true;
}
display(Math.abs(Integer.parseInt(args[1])), skill, sender, command);
return true;
default:
return false;
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
return StringUtil.copyPartialMatches(args[0], PrimarySkillType.SKILL_NAMES, new ArrayList<String>(PrimarySkillType.SKILL_NAMES.size()));
default:
return ImmutableList.of();
}
}
private void display(int page, PrimarySkillType skill, CommandSender sender, Command command) {
if (skill != null && !Permissions.mctop(sender, skill)) {
sender.sendMessage(command.getPermissionMessage());
return;
}
if (sender instanceof Player) {
if (!CommandUtils.hasPlayerDataKey(sender)) {
return;
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(sender.getName());
long cooldownMillis = Math.max(MainConfig.getInstance().getDatabasePlayerCooldown(), 1750);
if (mcMMOPlayer.getDatabaseATS() + cooldownMillis > System.currentTimeMillis()) {
double seconds = ((mcMMOPlayer.getDatabaseATS() + cooldownMillis) - System.currentTimeMillis()) / 1000;
if (seconds < 1) {
seconds = 1;
}
sender.sendMessage(LocaleLoader.formatString(LocaleLoader.getString("Commands.Database.Cooldown"), seconds));
return;
}
if (((Player) sender).hasMetadata(mcMMO.databaseCommandKey)) {
sender.sendMessage(LocaleLoader.getString("Commands.Database.Processing"));
return;
} else {
((Player) sender).setMetadata(mcMMO.databaseCommandKey, new FixedMetadataValue(mcMMO.p, null));
}
mcMMOPlayer.actualizeDatabaseATS();
}
display(page, skill, sender);
}
private void display(int page, PrimarySkillType skill, CommandSender sender) {
boolean useBoard = (sender instanceof Player) && (MainConfig.getInstance().getTopUseBoard());
boolean useChat = !useBoard || MainConfig.getInstance().getTopUseChat();
new MctopCommandAsyncTask(page, skill, sender, useBoard, useChat).runTaskAsynchronously(mcMMO.p);
}
private PrimarySkillType extractSkill(CommandSender sender, String skillName) {
if (CommandUtils.isInvalidSkill(sender, skillName)) {
return null;
}
PrimarySkillType skill = PrimarySkillType.getSkill(skillName);
if (CommandUtils.isChildSkill(sender, skill)) {
return null;
}
return skill;
}
}

View File

@@ -0,0 +1,15 @@
package com.gmail.nossr50.commands.server;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
/**
* This command facilitates switching the skill system scale between classic and modern scale
*/
public class Mcmmoupgrade implements CommandExecutor {
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
return false;
}
}

View File

@@ -0,0 +1,98 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.subskills.AbstractSubSkill;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.random.RandomChanceSkill;
import com.gmail.nossr50.core.util.random.RandomChanceUtil;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import com.gmail.nossr50.listeners.InteractionManager;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class AcrobaticsCommand extends SkillCommand {
private String dodgeChance;
private String dodgeChanceLucky;
private boolean canDodge;
private boolean canRoll;
public AcrobaticsCommand() {
super(PrimarySkillType.ACROBATICS);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// ACROBATICS_DODGE
if (canDodge) {
String[] dodgeStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.ACROBATICS_DODGE);
dodgeChance = dodgeStrings[0];
dodgeChanceLucky = dodgeStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
canDodge = canUseSubskill(player, SubSkillType.ACROBATICS_DODGE);
canRoll = canUseSubskill(player, SubSkillType.ACROBATICS_ROLL);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canDodge) {
messages.add(getStatMessage(SubSkillType.ACROBATICS_DODGE, dodgeChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", dodgeChanceLucky) : ""));
}
if (canRoll) {
AbstractSubSkill abstractSubSkill = InteractionManager.getAbstractByName("Roll");
if (abstractSubSkill != null) {
double rollChance, graceChance;
//Chance to roll at half
RandomChanceSkill roll_rcs = new RandomChanceSkill(player, SubSkillType.ACROBATICS_ROLL);
//Chance to graceful roll
RandomChanceSkill grace_rcs = new RandomChanceSkill(player, SubSkillType.ACROBATICS_ROLL);
grace_rcs.setSkillLevel(grace_rcs.getSkillLevel() * 2); //Double Odds
//Chance Stat Calculations
rollChance = RandomChanceUtil.getRandomChanceExecutionChance(roll_rcs);
graceChance = RandomChanceUtil.getRandomChanceExecutionChance(grace_rcs);
//damageThreshold = AdvancedConfig.getInstance().getRollDamageThreshold();
String rollStrings[] = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.ACROBATICS_ROLL);
//Format
double rollChanceLucky = rollChance * 1.333D;
double graceChanceLucky = graceChance * 1.333D;
messages.add(getStatMessage(SubSkillType.ACROBATICS_ROLL, rollStrings[0])
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", rollStrings[1]) : ""));
/*messages.add(getStatMessage(true, false, SubSkillType.ACROBATICS_ROLL, String.valueOf(graceChance))
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", String.valueOf(graceChanceLucky)) : ""));*/
}
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.ACROBATICS);
return textComponents;
}
}

View File

@@ -0,0 +1,96 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.primary.alchemy.AlchemyManager;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class AlchemyCommand extends SkillCommand {
private String brewSpeed;
private String brewSpeedLucky;
private int tier;
private int ingredientCount;
private String ingredientList;
private boolean canCatalysis;
private boolean canConcoctions;
public AlchemyCommand() {
super(PrimarySkillType.ALCHEMY);
}
protected String[] calculateAbilityDisplayValues(Player player) {
AlchemyManager alchemyManager = UserManager.getPlayer(player).getAlchemyManager();
String[] displayValues = new String[2];
boolean isLucky = Permissions.lucky(player, PrimarySkillType.ALCHEMY);
displayValues[0] = decimal.format(alchemyManager.calculateBrewSpeed(false)) + "x";
displayValues[1] = isLucky ? decimal.format(alchemyManager.calculateBrewSpeed(true)) + "x" : null;
return displayValues;
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// ALCHEMY_CATALYSIS
if (canCatalysis) {
String[] catalysisStrings = calculateAbilityDisplayValues(player);
brewSpeed = catalysisStrings[0];
brewSpeedLucky = catalysisStrings[1];
}
// ALCHEMY_CONCOCTIONS
if (canConcoctions) {
AlchemyManager alchemyManager = UserManager.getPlayer(player).getAlchemyManager();
tier = alchemyManager.getTier();
ingredientCount = alchemyManager.getIngredients().size();
ingredientList = alchemyManager.getIngredientList();
}
}
@Override
protected void permissionsCheck(Player player) {
canCatalysis = canUseSubskill(player, SubSkillType.ALCHEMY_CATALYSIS);
canConcoctions = canUseSubskill(player, SubSkillType.ALCHEMY_CONCOCTIONS);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canCatalysis) {
messages.add(getStatMessage(SubSkillType.ALCHEMY_CATALYSIS, brewSpeed)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", brewSpeedLucky) : ""));
}
if (canConcoctions) {
messages.add(getStatMessage(false, true, SubSkillType.ALCHEMY_CONCOCTIONS, String.valueOf(tier), String.valueOf(RankUtils.getHighestRank(SubSkillType.ALCHEMY_CONCOCTIONS))));
messages.add(getStatMessage(true, true, SubSkillType.ALCHEMY_CONCOCTIONS, String.valueOf(ingredientCount), ingredientList));
//messages.add(LocaleLoader.getString("Alchemy.Concoctions.Rank", tier, RankUtils.getHighestRank(SubSkillType.ALCHEMY_CONCOCTIONS)));
//messages.add(LocaleLoader.getString("Alchemy.Concoctions.Ingredients", ingredientCount, ingredientList));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.ALCHEMY);
return textComponents;
}
}

View File

@@ -0,0 +1,202 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.util.HolidayManager.FakeSkillType;
import com.gmail.nossr50.core.util.Misc;
import com.gmail.nossr50.core.util.StringUtils;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.List;
public class AprilCommand implements TabExecutor {
protected DecimalFormat percent = new DecimalFormat("##0.00%");
protected DecimalFormat decimal = new DecimalFormat("##0.00");
private String skillName;
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
skillName = StringUtils.getCapitalized(label);
switch (args.length) {
case 0:
Player player = (Player) sender;
FakeSkillType fakeSkillType = FakeSkillType.getByName(skillName);
float skillValue = Misc.getRandom().nextInt(99);
player.sendMessage(LocaleLoader.getString("Skills.Header", skillName));
player.sendMessage(LocaleLoader.getString("Commands.XPGain", getXPGainString(fakeSkillType)));
player.sendMessage(LocaleLoader.getString("Effects.Level", (int) skillValue, Misc.getRandom().nextInt(1000), 1000 + Misc.getRandom().nextInt(1000)));
List<String> effectMessages = effectsDisplay(fakeSkillType);
if (!effectMessages.isEmpty()) {
player.sendMessage(LocaleLoader.getString("Skills.Header", LocaleLoader.getString("Effects.Effects")));
for (String message : effectMessages) {
player.sendMessage(message);
}
}
List<String> statsMessages = statsDisplay(fakeSkillType);
if (!statsMessages.isEmpty()) {
player.sendMessage(LocaleLoader.getString("Skills.Header", LocaleLoader.getString("Commands.Stats.Self")));
for (String message : statsMessages) {
player.sendMessage(message);
}
}
player.sendMessage(LocaleLoader.formatString("[[DARK_AQUA]]Guide for {0} available - type /APRIL FOOLS ! :D", skillName));
return true;
default:
return true;
}
}
private String getXPGainString(FakeSkillType fakeSkillType) {
switch (fakeSkillType) {
case MACHO:
return "Get beaten up";
case JUMPING:
return "Kris Kross will make ya Jump Jump";
case THROWING:
return "Chuck your items on the floor";
case WRECKING:
return "I'M GONNA WRECK IT!";
case CRAFTING:
return "Craft apple pies";
case WALKING:
return "Walk around the park";
case SWIMMING:
return "Like a fish on a bicycle";
case FALLING:
return "Faceplant the floor, headbutt the ground";
case CLIMBING:
return "Climb the highest mountain";
case FLYING:
return "I believe I can fly";
case DIVING:
return "Scuba club 4000";
case PIGGY:
return "OINK! OINK!";
default:
return "Sit and wait?";
}
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
return ImmutableList.of("?");
default:
return ImmutableList.of();
}
}
private List<String> effectsDisplay(FakeSkillType fakeSkillType) {
List<String> messages = new ArrayList<String>();
switch (fakeSkillType) {
case MACHO:
messages.add(LocaleLoader.getString("Effects.Template", "Punching bag", "Absorb damage, like a bag of sand"));
break;
case JUMPING:
messages.add(LocaleLoader.getString("Effects.Template", "Jump", "PRESS SPACE TO JUMP"));
messages.add(LocaleLoader.getString("Effects.Template", "Jump Twice", "PRESS SPACE TWICE TO JUMP TWICE"));
break;
case THROWING:
messages.add(LocaleLoader.getString("Effects.Template", "Drop Item", "Randomly drop items, at random"));
break;
case WRECKING:
messages.add(LocaleLoader.getString("Effects.Template", "Ralphinator", "Smash windows with your fists"));
break;
case CRAFTING:
messages.add(LocaleLoader.getString("Effects.Template", "Crafting", "Chance of successful craft"));
break;
case WALKING:
messages.add(LocaleLoader.getString("Effects.Template", "Walk", "Traveling gracefully by foot"));
break;
case SWIMMING:
messages.add(LocaleLoader.getString("Effects.Template", "Swim", "Just keep swimming, swimming, swimming"));
break;
case FALLING:
messages.add(LocaleLoader.getString("Effects.Template", "Skydiving", "Go jump of a cliff. No, seriously."));
break;
case CLIMBING:
messages.add(LocaleLoader.getString("Effects.Template", "Rock Climber", "Use string to climb mountains faster"));
break;
case FLYING:
messages.add(LocaleLoader.getString("Effects.Template", "Fly", "Throw yourself at the ground and miss"));
break;
case DIVING:
messages.add(LocaleLoader.getString("Effects.Template", "Hold Breath", "Press shift to hold your breath longer"));
break;
case PIGGY:
messages.add(LocaleLoader.getString("Effects.Template", "Carrot Turbo", "Supercharge your pigs with carrots"));
break;
}
return messages;
}
private List<String> statsDisplay(FakeSkillType fakeSkillType) {
List<String> messages = new ArrayList<String>();
switch (fakeSkillType) {
case MACHO:
messages.add(LocaleLoader.formatString("[[RED]]Damage Taken: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(77))));
break;
case JUMPING:
messages.add(LocaleLoader.formatString("[[RED]]Double Jump Chance: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(27))));
break;
case THROWING:
messages.add(LocaleLoader.formatString("[[RED]]Drop Item Chance: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(87))));
break;
case WRECKING:
messages.add(LocaleLoader.formatString("[[RED]]Wrecking Chance: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(14))));
break;
case CRAFTING:
messages.add(LocaleLoader.formatString("[[RED]]Crafting Success: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(27))));
break;
case WALKING:
messages.add(LocaleLoader.formatString("[[RED]]Walk Chance: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(27))));
break;
case SWIMMING:
messages.add(LocaleLoader.formatString("[[RED]]Swim Chance: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(27))));
break;
case FALLING:
messages.add(LocaleLoader.formatString("[[RED]]Skydiving Success: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(37))));
break;
case CLIMBING:
messages.add(LocaleLoader.formatString("[[RED]]Rock Climber Chance: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(27))));
break;
case FLYING:
messages.add(LocaleLoader.formatString("[[RED]]Fly Chance: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(27))));
break;
case DIVING:
messages.add(LocaleLoader.formatString("[[RED]]Hold Breath Chance: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(27))));
break;
case PIGGY:
messages.add(LocaleLoader.formatString("[[RED]]Carrot Turbo Boost: [[YELLOW]]{0}%", decimal.format(Misc.getRandom().nextInt(80)) + 10));
break;
}
return messages;
}
}

View File

@@ -0,0 +1,88 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.primary.archery.Archery;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class ArcheryCommand extends SkillCommand {
private String skillShotBonus;
private String dazeChance;
private String dazeChanceLucky;
private String retrieveChance;
private String retrieveChanceLucky;
private boolean canSkillShot;
private boolean canDaze;
private boolean canRetrieve;
public ArcheryCommand() {
super(PrimarySkillType.ARCHERY);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// ARCHERY_ARROW_RETRIEVAL
if (canRetrieve) {
String[] retrieveStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.ARCHERY_ARROW_RETRIEVAL);
retrieveChance = retrieveStrings[0];
retrieveChanceLucky = retrieveStrings[1];
}
// ARCHERY_DAZE
if (canDaze) {
String[] dazeStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.ARCHERY_DAZE);
dazeChance = dazeStrings[0];
dazeChanceLucky = dazeStrings[1];
}
// SKILL SHOT
if (canSkillShot) {
skillShotBonus = percent.format(Archery.getDamageBonusPercent(player));
}
}
@Override
protected void permissionsCheck(Player player) {
canSkillShot = canUseSubskill(player, SubSkillType.ARCHERY_SKILL_SHOT);
canDaze = canUseSubskill(player, SubSkillType.ARCHERY_DAZE);
canRetrieve = canUseSubskill(player, SubSkillType.ARCHERY_ARROW_RETRIEVAL);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canRetrieve) {
messages.add(getStatMessage(SubSkillType.ARCHERY_ARROW_RETRIEVAL, retrieveChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", retrieveChanceLucky) : ""));
}
if (canDaze) {
messages.add(getStatMessage(SubSkillType.ARCHERY_DAZE, dazeChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", dazeChanceLucky) : ""));
}
if (canSkillShot) {
messages.add(getStatMessage(SubSkillType.ARCHERY_SKILL_SHOT, skillShotBonus));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.ARCHERY);
return textComponents;
}
}

View File

@@ -0,0 +1,109 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.primary.axes.Axes;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class AxesCommand extends SkillCommand {
private String critChance;
private String critChanceLucky;
private double axeMasteryDamage;
private double impactDamage;
private String skullSplitterLength;
private String skullSplitterLengthEndurance;
private boolean canSkullSplitter;
private boolean canCritical;
private boolean canAxeMastery;
private boolean canImpact;
private boolean canGreaterImpact;
public AxesCommand() {
super(PrimarySkillType.AXES);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// ARMOR IMPACT
if (canImpact) {
impactDamage = UserManager.getPlayer(player).getAxesManager().getImpactDurabilityDamage();
}
// AXE MASTERY
if (canAxeMastery) {
axeMasteryDamage = Axes.getAxeMasteryBonusDamage(player);
}
// CRITICAL HIT
if (canCritical) {
String[] criticalHitStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.AXES_CRITICAL_STRIKES);
critChance = criticalHitStrings[0];
critChanceLucky = criticalHitStrings[1];
}
// SKULL SPLITTER
if (canSkullSplitter) {
String[] skullSplitterStrings = calculateLengthDisplayValues(player, skillValue);
skullSplitterLength = skullSplitterStrings[0];
skullSplitterLengthEndurance = skullSplitterStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
canSkullSplitter = Permissions.skullSplitter(player) && RankUtils.hasUnlockedSubskill(player, SubSkillType.AXES_SKULL_SPLITTER);
canCritical = canUseSubskill(player, SubSkillType.AXES_CRITICAL_STRIKES);
canAxeMastery = canUseSubskill(player, SubSkillType.AXES_AXE_MASTERY);
canImpact = canUseSubskill(player, SubSkillType.AXES_ARMOR_IMPACT);
canGreaterImpact = canUseSubskill(player, SubSkillType.AXES_GREATER_IMPACT);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canImpact) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Axes.Ability.Bonus.2"), LocaleLoader.getString("Axes.Ability.Bonus.3", impactDamage)));
}
if (canAxeMastery) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Axes.Ability.Bonus.0"), LocaleLoader.getString("Axes.Ability.Bonus.1", axeMasteryDamage)));
}
if (canCritical) {
messages.add(getStatMessage(SubSkillType.AXES_CRITICAL_STRIKES, critChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", critChanceLucky) : ""));
}
if (canGreaterImpact) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Axes.Ability.Bonus.4"), LocaleLoader.getString("Axes.Ability.Bonus.5", Axes.greaterImpactBonusDamage)));
}
if (canSkullSplitter) {
messages.add(getStatMessage(SubSkillType.AXES_SKULL_SPLITTER, skullSplitterLength)
+ (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", skullSplitterLengthEndurance) : ""));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.AXES);
return textComponents;
}
}

View File

@@ -0,0 +1,64 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class ExcavationCommand extends SkillCommand {
private String gigaDrillBreakerLength;
private String gigaDrillBreakerLengthEndurance;
private boolean canGigaDrill;
private boolean canTreasureHunt;
public ExcavationCommand() {
super(PrimarySkillType.EXCAVATION);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// GIGA DRILL BREAKER
if (canGigaDrill) {
String gigaDrillStrings[] = calculateLengthDisplayValues(player, skillValue);
gigaDrillBreakerLength = gigaDrillStrings[0];
gigaDrillBreakerLengthEndurance = gigaDrillStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
canGigaDrill = Permissions.gigaDrillBreaker(player) && RankUtils.hasUnlockedSubskill(player, SubSkillType.EXCAVATION_GIGA_DRILL_BREAKER);
canTreasureHunt = canUseSubskill(player, SubSkillType.EXCAVATION_ARCHAEOLOGY);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canGigaDrill) {
messages.add(getStatMessage(SubSkillType.EXCAVATION_GIGA_DRILL_BREAKER, gigaDrillBreakerLength)
+ (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", gigaDrillBreakerLengthEndurance) : ""));
//messages.add(LocaleLoader.getString("Excavation.Effect.Length", gigaDrillBreakerLength) + (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", gigaDrillBreakerLengthEndurance) : ""));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.EXCAVATION);
return textComponents;
}
}

View File

@@ -0,0 +1,177 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.config.AdvancedConfig;
import com.gmail.nossr50.core.config.treasure.TreasureConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.primary.fishing.Fishing;
import com.gmail.nossr50.core.skills.primary.fishing.FishingManager;
import com.gmail.nossr50.core.skills.treasure.Rarity;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.random.RandomChanceUtil;
import com.gmail.nossr50.core.util.skills.RankUtils;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.Location;
import org.bukkit.entity.EntityType;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class FishingCommand extends SkillCommand {
private int lootTier;
private String shakeChance;
private String shakeChanceLucky;
private int fishermansDietRank;
private String biteChance;
private String trapTreasure;
private String commonTreasure;
private String uncommonTreasure;
private String rareTreasure;
private String epicTreasure;
private String legendaryTreasure;
private String recordTreasure;
private String magicChance;
private boolean canTreasureHunt;
private boolean canMagicHunt;
private boolean canShake;
private boolean canFishermansDiet;
private boolean canMasterAngler;
private boolean canIceFish;
public FishingCommand() {
super(PrimarySkillType.FISHING);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
FishingManager fishingManager = UserManager.getPlayer(player).getFishingManager();
// TREASURE HUNTER
if (canTreasureHunt) {
lootTier = fishingManager.getLootTier();
// ItemStack drop rates
commonTreasure = percent.format(TreasureConfig.getInstance().getItemDropRate(lootTier, Rarity.COMMON) / 100.0);
uncommonTreasure = percent.format(TreasureConfig.getInstance().getItemDropRate(lootTier, Rarity.UNCOMMON) / 100.0);
rareTreasure = percent.format(TreasureConfig.getInstance().getItemDropRate(lootTier, Rarity.RARE) / 100.0);
epicTreasure = percent.format(TreasureConfig.getInstance().getItemDropRate(lootTier, Rarity.EPIC) / 100.0);
legendaryTreasure = percent.format(TreasureConfig.getInstance().getItemDropRate(lootTier, Rarity.LEGENDARY) / 100.0);
recordTreasure = percent.format(TreasureConfig.getInstance().getItemDropRate(lootTier, Rarity.RECORD) / 100.0);
// Magic hunter drop rates
double totalEnchantChance = 0;
for (Rarity rarity : Rarity.values()) {
if (rarity != Rarity.RECORD) {
totalEnchantChance += TreasureConfig.getInstance().getEnchantmentDropRate(lootTier, rarity);
}
}
if (totalEnchantChance >= 1)
magicChance = percent.format(totalEnchantChance / 100.0);
else
magicChance = percent.format(0);
}
// FISHING_SHAKE
if (canShake) {
String[] shakeStrings = RandomChanceUtil.calculateAbilityDisplayValuesStatic(player, PrimarySkillType.FISHING, fishingManager.getShakeChance());
shakeChance = shakeStrings[0];
shakeChanceLucky = shakeStrings[1];
}
// FISHERMAN'S DIET
if (canFishermansDiet) {
fishermansDietRank = calculateRank(skillValue, Fishing.fishermansDietMaxLevel, Fishing.fishermansDietRankLevel1);
}
// MASTER ANGLER
if (canMasterAngler) {
double rawBiteChance = 1.0 / (player.getWorld().hasStorm() ? 300 : 500);
Location location = fishingManager.getHookLocation();
if (location == null) {
location = player.getLocation();
}
if (Fishing.masterAnglerBiomes.contains(location.getBlock().getBiome())) {
rawBiteChance = rawBiteChance * AdvancedConfig.getInstance().getMasterAnglerBiomeModifier();
}
if (player.isInsideVehicle() && player.getVehicle().getType() == EntityType.BOAT) {
rawBiteChance = rawBiteChance * AdvancedConfig.getInstance().getMasterAnglerBoatModifier();
}
double luckyModifier = Permissions.lucky(player, PrimarySkillType.FISHING) ? 1.333D : 1.0D;
biteChance = percent.format((rawBiteChance * 100.0D) * luckyModifier);
}
}
@Override
protected void permissionsCheck(Player player) {
canTreasureHunt = canUseSubskill(player, SubSkillType.FISHING_TREASURE_HUNTER);
canMagicHunt = canUseSubskill(player, SubSkillType.FISHING_MAGIC_HUNTER) && canUseSubskill(player, SubSkillType.FISHING_TREASURE_HUNTER);
canShake = canUseSubskill(player, SubSkillType.FISHING_SHAKE);
canFishermansDiet = canUseSubskill(player, SubSkillType.FISHING_FISHERMANS_DIET);
canMasterAngler = canUseSubskill(player, SubSkillType.FISHING_MASTER_ANGLER);
canIceFish = canUseSubskill(player, SubSkillType.FISHING_ICE_FISHING);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canFishermansDiet) {
messages.add(getStatMessage(false, true, SubSkillType.FISHING_FISHERMANS_DIET, String.valueOf(fishermansDietRank)));
}
if (canIceFish) {
messages.add(getStatMessage(SubSkillType.FISHING_ICE_FISHING, SubSkillType.FISHING_ICE_FISHING.getLocaleStatDescription()));
}
if (canMagicHunt) {
messages.add(getStatMessage(SubSkillType.FISHING_MAGIC_HUNTER, magicChance));
}
if (canMasterAngler) {
//TODO: Update this with more details
messages.add(getStatMessage(false, true, SubSkillType.FISHING_MASTER_ANGLER, biteChance));
}
if (canShake) {
messages.add(getStatMessage(SubSkillType.FISHING_SHAKE, shakeChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", shakeChanceLucky) : ""));
}
if (canTreasureHunt) {
messages.add(getStatMessage(false, true, SubSkillType.FISHING_TREASURE_HUNTER, String.valueOf(lootTier), String.valueOf(RankUtils.getHighestRank(SubSkillType.FISHING_TREASURE_HUNTER))));
messages.add(getStatMessage(true, true, SubSkillType.FISHING_TREASURE_HUNTER,
String.valueOf(commonTreasure),
String.valueOf(uncommonTreasure),
String.valueOf(rareTreasure),
String.valueOf(epicTreasure),
String.valueOf(legendaryTreasure),
String.valueOf(recordTreasure)));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.FISHING);
return textComponents;
}
}

View File

@@ -0,0 +1,152 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.Material;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class HerbalismCommand extends SkillCommand {
private String greenTerraLength;
private String greenTerraLengthEndurance;
private String greenThumbChance;
private String greenThumbChanceLucky;
private int greenThumbStage;
private int farmersDietRank;
private String doubleDropChance;
private String doubleDropChanceLucky;
private String hylianLuckChance;
private String hylianLuckChanceLucky;
private String shroomThumbChance;
private String shroomThumbChanceLucky;
private boolean hasHylianLuck;
private boolean canGreenTerra;
private boolean canGreenThumbPlants;
private boolean canGreenThumbBlocks;
private boolean canFarmersDiet;
private boolean canDoubleDrop;
private boolean canShroomThumb;
public HerbalismCommand() {
super(PrimarySkillType.HERBALISM);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// DOUBLE DROPS
if (canDoubleDrop) {
String[] doubleDropStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.HERBALISM_DOUBLE_DROPS);
;
doubleDropChance = doubleDropStrings[0];
doubleDropChanceLucky = doubleDropStrings[1];
}
// FARMERS DIET
if (canFarmersDiet) {
farmersDietRank = RankUtils.getRank(player, SubSkillType.HERBALISM_FARMERS_DIET);
}
// GREEN TERRA
if (canGreenTerra) {
String[] greenTerraStrings = calculateLengthDisplayValues(player, skillValue);
greenTerraLength = greenTerraStrings[0];
greenTerraLengthEndurance = greenTerraStrings[1];
}
// GREEN THUMB
if (canGreenThumbBlocks || canGreenThumbPlants) {
greenThumbStage = RankUtils.getRank(player, SubSkillType.HERBALISM_GREEN_THUMB);
String[] greenThumbStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.HERBALISM_GREEN_THUMB);
greenThumbChance = greenThumbStrings[0];
greenThumbChanceLucky = greenThumbStrings[1];
}
// HYLIAN LUCK
if (hasHylianLuck) {
String[] hylianLuckStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.HERBALISM_HYLIAN_LUCK);
hylianLuckChance = hylianLuckStrings[0];
hylianLuckChanceLucky = hylianLuckStrings[1];
}
// SHROOM THUMB
if (canShroomThumb) {
String[] shroomThumbStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.HERBALISM_SHROOM_THUMB);
shroomThumbChance = shroomThumbStrings[0];
shroomThumbChanceLucky = shroomThumbStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
hasHylianLuck = canUseSubskill(player, SubSkillType.HERBALISM_HYLIAN_LUCK);
canGreenTerra = Permissions.greenTerra(player);
canGreenThumbPlants = RankUtils.hasUnlockedSubskill(player, SubSkillType.HERBALISM_GREEN_THUMB) && (Permissions.greenThumbPlant(player, Material.WHEAT) || Permissions.greenThumbPlant(player, Material.CARROT) || Permissions.greenThumbPlant(player, Material.POTATO) || Permissions.greenThumbPlant(player, Material.BEETROOT) || Permissions.greenThumbPlant(player, Material.NETHER_WART) || Permissions.greenThumbPlant(player, Material.COCOA));
canGreenThumbBlocks = RankUtils.hasUnlockedSubskill(player, SubSkillType.HERBALISM_GREEN_THUMB) && (Permissions.greenThumbBlock(player, Material.DIRT) || Permissions.greenThumbBlock(player, Material.COBBLESTONE) || Permissions.greenThumbBlock(player, Material.COBBLESTONE_WALL) || Permissions.greenThumbBlock(player, Material.STONE_BRICKS));
canFarmersDiet = canUseSubskill(player, SubSkillType.HERBALISM_FARMERS_DIET);
canDoubleDrop = canUseSubskill(player, SubSkillType.HERBALISM_DOUBLE_DROPS) && !skill.getDoubleDropsDisabled();
canShroomThumb = canUseSubskill(player, SubSkillType.HERBALISM_SHROOM_THUMB);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canDoubleDrop) {
messages.add(getStatMessage(SubSkillType.HERBALISM_DOUBLE_DROPS, doubleDropChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", doubleDropChanceLucky) : ""));
}
if (canFarmersDiet) {
messages.add(getStatMessage(false, true, SubSkillType.HERBALISM_FARMERS_DIET, String.valueOf(farmersDietRank)));
}
if (canGreenTerra) {
messages.add(getStatMessage(SubSkillType.HERBALISM_GREEN_TERRA, greenTerraLength)
+ (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", greenTerraLengthEndurance) : ""));
//messages.add(LocaleLoader.getString("Herbalism.Ability.GTe.Length", greenTerraLength) + (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", greenTerraLengthEndurance) : ""));
}
if (canGreenThumbBlocks || canGreenThumbPlants) {
messages.add(getStatMessage(SubSkillType.HERBALISM_GREEN_THUMB, greenThumbChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", greenThumbChanceLucky) : ""));
//messages.add(LocaleLoader.getString("Herbalism.Ability.GTh.Chance", greenThumbChance) + (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", greenThumbChanceLucky) : ""));
}
if (canGreenThumbPlants) {
messages.add(getStatMessage(true, true, SubSkillType.HERBALISM_GREEN_THUMB, String.valueOf(greenThumbStage)));
}
if (hasHylianLuck) {
messages.add(getStatMessage(SubSkillType.HERBALISM_HYLIAN_LUCK, hylianLuckChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", hylianLuckChanceLucky) : ""));
}
if (canShroomThumb) {
messages.add(getStatMessage(SubSkillType.HERBALISM_SHROOM_THUMB, shroomThumbChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", shroomThumbChanceLucky) : ""));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.HERBALISM);
return textComponents;
}
}

View File

@@ -0,0 +1,121 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.primary.mining.MiningManager;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class MiningCommand extends SkillCommand {
private String doubleDropChance;
private String doubleDropChanceLucky;
private String superBreakerLength;
private String superBreakerLengthEndurance;
private int blastMiningRank;
private int bonusTNTDrops;
private double blastRadiusIncrease;
private String oreBonus;
private String debrisReduction;
private String blastDamageDecrease;
private boolean canSuperBreaker;
private boolean canDoubleDrop;
private boolean canBlast;
private boolean canBiggerBombs;
private boolean canDemoExpert;
public MiningCommand() {
super(PrimarySkillType.MINING);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// BLAST MINING
if (canBlast || canDemoExpert || canBiggerBombs) {
MiningManager miningManager = UserManager.getPlayer(player).getMiningManager();
blastMiningRank = miningManager.getBlastMiningTier();
bonusTNTDrops = miningManager.getDropMultiplier();
oreBonus = percent.format(miningManager.getOreBonus() / 30.0D); // Base received in TNT is 30%
debrisReduction = percent.format(miningManager.getDebrisReduction() / 30.0D); // Base received in TNT is 30%
blastDamageDecrease = percent.format(miningManager.getBlastDamageModifier() / 100.0D);
blastRadiusIncrease = miningManager.getBlastRadiusModifier();
}
// DOUBLE DROPS
if (canDoubleDrop) {
String[] doubleDropStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.MINING_DOUBLE_DROPS);
doubleDropChance = doubleDropStrings[0];
doubleDropChanceLucky = doubleDropStrings[1];
}
// SUPER BREAKER
if (canSuperBreaker) {
String[] superBreakerStrings = calculateLengthDisplayValues(player, skillValue);
superBreakerLength = superBreakerStrings[0];
superBreakerLengthEndurance = superBreakerStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
canBiggerBombs = RankUtils.hasUnlockedSubskill(player, SubSkillType.MINING_BIGGER_BOMBS) && Permissions.biggerBombs(player);
canBlast = RankUtils.hasUnlockedSubskill(player, SubSkillType.MINING_BLAST_MINING) && Permissions.remoteDetonation(player);
canDemoExpert = RankUtils.hasUnlockedSubskill(player, SubSkillType.MINING_DEMOLITIONS_EXPERTISE) && Permissions.demolitionsExpertise(player);
canDoubleDrop = Permissions.isSubSkillEnabled(player, SubSkillType.MINING_DOUBLE_DROPS) && !skill.getDoubleDropsDisabled();
canSuperBreaker = RankUtils.hasUnlockedSubskill(player, SubSkillType.MINING_SUPER_BREAKER) && Permissions.superBreaker(player);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canBiggerBombs) {
messages.add(getStatMessage(true, true, SubSkillType.MINING_BLAST_MINING, String.valueOf(blastRadiusIncrease)));
//messages.add(LocaleLoader.getString("Mining.Blast.Radius.Increase", blastRadiusIncrease));
}
if (canBlast) {
messages.add(getStatMessage(false, true, SubSkillType.MINING_BLAST_MINING, String.valueOf(blastMiningRank), String.valueOf(RankUtils.getHighestRank(SubSkillType.MINING_BLAST_MINING)), LocaleLoader.getString("Mining.Blast.Effect", oreBonus, debrisReduction, bonusTNTDrops)));
//messages.add(LocaleLoader.getString("Mining.Blast.Rank", blastMiningRank, RankUtils.getHighestRank(SubSkillType.MINING_BLAST_MINING), LocaleLoader.getString("Mining.Blast.Effect", oreBonus, debrisReduction, bonusTNTDrops)));
}
if (canDemoExpert) {
messages.add(getStatMessage(SubSkillType.MINING_DEMOLITIONS_EXPERTISE, blastDamageDecrease));
//messages.add(LocaleLoader.getString("Mining.Effect.Decrease", blastDamageDecrease));
}
if (canDoubleDrop) {
messages.add(getStatMessage(SubSkillType.HERBALISM_DOUBLE_DROPS, doubleDropChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", doubleDropChanceLucky) : ""));
//messages.add(LocaleLoader.getString("Mining.Effect.DropChance", doubleDropChance) + (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", doubleDropChanceLucky) : ""));
}
if (canSuperBreaker) {
messages.add(getStatMessage(SubSkillType.MINING_SUPER_BREAKER, superBreakerLength)
+ (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", superBreakerLengthEndurance) : ""));
//messages.add(LocaleLoader.getString("Mining.Ability.Length", superBreakerLength) + (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", superBreakerLengthEndurance) : ""));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.MINING);
return textComponents;
}
}

View File

@@ -0,0 +1,94 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.subskills.AbstractSubSkill;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.listeners.InteractionManager;
import com.google.common.collect.ImmutableList;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import org.bukkit.util.StringUtil;
import java.util.ArrayList;
import java.util.List;
/**
* This is the command that retrieves data about skills from in-game sources
*/
public class MmoInfoCommand implements TabExecutor {
@Override
public boolean onCommand(CommandSender commandSender, Command command, String s, String[] args) {
/*
* Only allow players to use this command
*/
if (commandSender instanceof Player) {
if (args.length < 1)
return false;
Player player = (Player) commandSender;
if (Permissions.mmoinfo(player)) {
if (args == null || args[0] == null)
return false;
if (args[0].equalsIgnoreCase("???")) {
player.sendMessage(LocaleLoader.getString("Commands.MmoInfo.Header"));
player.sendMessage(LocaleLoader.getString("Commands.MmoInfo.SubSkillHeader", "???"));
player.sendMessage(LocaleLoader.getString("Commands.MmoInfo.DetailsHeader"));
player.sendMessage(LocaleLoader.getString("Commands.MmoInfo.Mystery"));
return true;
} else if (InteractionManager.getAbstractByName(args[0]) != null || PrimarySkillType.SUBSKILL_NAMES.contains(args[0])) {
displayInfo(player, args[0]);
return true;
}
//Not a real skill
player.sendMessage(LocaleLoader.getString("Commands.MmoInfo.NoMatch"));
return true;
}
}
return false;
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
return StringUtil.copyPartialMatches(args[0], PrimarySkillType.SUBSKILL_NAMES, new ArrayList<String>(PrimarySkillType.SUBSKILL_NAMES.size()));
default:
return ImmutableList.of();
}
}
private void displayInfo(Player player, String subSkillName) {
//Check to see if the skill exists in the new system
AbstractSubSkill abstractSubSkill = InteractionManager.getAbstractByName(subSkillName);
if (abstractSubSkill != null) {
/* New System Skills are programmable */
abstractSubSkill.printInfo(player);
//TextComponentFactory.sendPlayerUrlHeader(player);
} else {
/*
* Skill is only in the old system
*/
player.sendMessage(LocaleLoader.getString("Commands.MmoInfo.Header"));
player.sendMessage(LocaleLoader.getString("Commands.MmoInfo.SubSkillHeader", subSkillName));
player.sendMessage(LocaleLoader.getString("Commands.MmoInfo.DetailsHeader"));
player.sendMessage(LocaleLoader.getString("Commands.MmoInfo.OldSkill"));
}
for (SubSkillType subSkillType : SubSkillType.values()) {
if (subSkillType.getNiceNameNoSpaces(subSkillType).equalsIgnoreCase(subSkillName))
subSkillName = subSkillType.getWikiName(subSkillType.toString());
}
//Send Player Wiki Link
TextComponentFactory.sendPlayerSubSkillWikiLink(player, subSkillName);
}
}

View File

@@ -0,0 +1,131 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.MaterialType;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.primary.repair.ArcaneForging;
import com.gmail.nossr50.core.skills.primary.repair.Repair;
import com.gmail.nossr50.core.skills.primary.repair.RepairManager;
import com.gmail.nossr50.core.skills.primary.repair.repairables.Repairable;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import com.gmail.nossr50.mcMMO;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.Material;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class RepairCommand extends SkillCommand {
private String repairMasteryBonus;
private String superRepairChance;
private String superRepairChanceLucky;
private boolean canSuperRepair;
private boolean canMasterRepair;
private boolean canArcaneForge;
private boolean canRepairStone;
private boolean canRepairIron;
private boolean canRepairGold;
private boolean canRepairDiamond;
private boolean canRepairString;
private boolean canRepairLeather;
private boolean canRepairWood;
private boolean arcaneBypass;
private int diamondLevel;
private int goldLevel;
private int ironLevel;
private int stoneLevel;
public RepairCommand() {
super(PrimarySkillType.REPAIR);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// We're using pickaxes here, not the best but it works
Repairable diamondRepairable = mcMMO.getRepairableManager().getRepairable(Material.DIAMOND_PICKAXE);
Repairable goldRepairable = mcMMO.getRepairableManager().getRepairable(Material.GOLDEN_PICKAXE);
Repairable ironRepairable = mcMMO.getRepairableManager().getRepairable(Material.IRON_PICKAXE);
Repairable stoneRepairable = mcMMO.getRepairableManager().getRepairable(Material.STONE_PICKAXE);
// TODO: This isn't really accurate - if they don't have pickaxes loaded it doesn't always mean the repair level is 0
diamondLevel = (diamondRepairable == null) ? 0 : diamondRepairable.getMinimumLevel();
goldLevel = (goldRepairable == null) ? 0 : goldRepairable.getMinimumLevel();
ironLevel = (ironRepairable == null) ? 0 : ironRepairable.getMinimumLevel();
stoneLevel = (stoneRepairable == null) ? 0 : stoneRepairable.getMinimumLevel();
// REPAIR MASTERY
if (canMasterRepair) {
repairMasteryBonus = percent.format(Math.min(((Repair.repairMasteryMaxBonus / Repair.repairMasteryMaxBonusLevel) * skillValue), Repair.repairMasteryMaxBonus) / 100D);
}
// SUPER REPAIR
if (canSuperRepair) {
String[] superRepairStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.REPAIR_SUPER_REPAIR);
superRepairChance = superRepairStrings[0];
superRepairChanceLucky = superRepairStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
canSuperRepair = canUseSubskill(player, SubSkillType.REPAIR_SUPER_REPAIR);
canMasterRepair = canUseSubskill(player, SubSkillType.REPAIR_REPAIR_MASTERY);
canArcaneForge = canUseSubskill(player, SubSkillType.REPAIR_ARCANE_FORGING);
canRepairDiamond = Permissions.repairMaterialType(player, MaterialType.DIAMOND);
canRepairGold = Permissions.repairMaterialType(player, MaterialType.GOLD);
canRepairIron = Permissions.repairMaterialType(player, MaterialType.IRON);
canRepairStone = Permissions.repairMaterialType(player, MaterialType.STONE);
canRepairString = Permissions.repairMaterialType(player, MaterialType.STRING);
canRepairLeather = Permissions.repairMaterialType(player, MaterialType.LEATHER);
canRepairWood = Permissions.repairMaterialType(player, MaterialType.WOOD);
arcaneBypass = Permissions.arcaneBypass(player);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canArcaneForge) {
RepairManager repairManager = UserManager.getPlayer(player).getRepairManager();
messages.add(getStatMessage(false, true,
SubSkillType.REPAIR_ARCANE_FORGING,
String.valueOf(RankUtils.getRank(player, SubSkillType.REPAIR_ARCANE_FORGING)),
RankUtils.getHighestRankStr(SubSkillType.REPAIR_ARCANE_FORGING)));
if (ArcaneForging.arcaneForgingEnchantLoss || ArcaneForging.arcaneForgingDowngrades) {
messages.add(getStatMessage(true, true, SubSkillType.REPAIR_ARCANE_FORGING,
String.valueOf(arcaneBypass ? 100 : repairManager.getKeepEnchantChance()),
String.valueOf(arcaneBypass ? 0 : repairManager.getDowngradeEnchantChance()))); //Jesus those parentheses
}
}
if (canMasterRepair) {
messages.add(getStatMessage(false, true, SubSkillType.REPAIR_REPAIR_MASTERY, repairMasteryBonus));
}
if (canSuperRepair) {
messages.add(getStatMessage(SubSkillType.REPAIR_SUPER_REPAIR, superRepairChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", superRepairChanceLucky) : ""));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.REPAIR);
return textComponents;
}
}

View File

@@ -0,0 +1,72 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.child.salvage.Salvage;
import com.gmail.nossr50.core.skills.child.salvage.SalvageManager;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class SalvageCommand extends SkillCommand {
private boolean canAdvancedSalvage;
private boolean canArcaneSalvage;
public SalvageCommand() {
super(PrimarySkillType.SALVAGE);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// TODO Auto-generated method stub
}
@Override
protected void permissionsCheck(Player player) {
canAdvancedSalvage = canUseSubskill(player, SubSkillType.SALVAGE_ADVANCED_SALVAGE);
canArcaneSalvage = canUseSubskill(player, SubSkillType.SALVAGE_ARCANE_SALVAGE);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
SalvageManager salvageManager = UserManager.getPlayer(player).getSalvageManager();
if (canAdvancedSalvage) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Salvage.Ability.Bonus.0"),
LocaleLoader.getString("Salvage.Ability.Bonus.1", salvageManager.getSalvageableAmount())));
}
if (canArcaneSalvage) {
messages.add(getStatMessage(false, true, SubSkillType.SALVAGE_ARCANE_SALVAGE,
String.valueOf(salvageManager.getArcaneSalvageRank()),
String.valueOf(RankUtils.getHighestRank(SubSkillType.SALVAGE_ARCANE_SALVAGE))));
if (Salvage.arcaneSalvageEnchantLoss) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Salvage.Arcane.ExtractFull"), percent.format(salvageManager.getExtractFullEnchantChance() / 100)));
}
if (Salvage.arcaneSalvageDowngrades) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Salvage.Arcane.ExtractPartial"), percent.format(salvageManager.getExtractPartialEnchantChance() / 100)));
}
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.SALVAGE);
return textComponents;
}
}

View File

@@ -0,0 +1,290 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.config.AdvancedConfig;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.child.FamilyTree;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.StringUtils;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.commands.CommandUtils;
import com.gmail.nossr50.core.util.random.RandomChanceUtil;
import com.gmail.nossr50.core.util.scoreboards.ScoreboardManager;
import com.gmail.nossr50.core.util.skills.PerksUtils;
import com.gmail.nossr50.core.util.skills.RankUtils;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import com.google.common.collect.ImmutableList;
import net.md_5.bungee.api.ChatColor;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabExecutor;
import org.bukkit.entity.Player;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
public abstract class SkillCommand implements TabExecutor {
protected PrimarySkillType skill;
protected DecimalFormat percent = new DecimalFormat("##0.00%");
protected DecimalFormat decimal = new DecimalFormat("##0.00");
private String skillName;
private CommandExecutor skillGuideCommand;
public SkillCommand(PrimarySkillType skill) {
this.skill = skill;
skillName = skill.getName();
skillGuideCommand = new SkillGuideCommand(skill);
}
public static String[] addItemToFirstPositionOfArray(String itemToAdd, String... existingArray) {
String[] newArray = new String[existingArray.length + 1];
newArray[0] = itemToAdd;
System.arraycopy(existingArray, 0, newArray, 1, existingArray.length);
return newArray;
}
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (CommandUtils.noConsoleUsage(sender)) {
return true;
}
if (!CommandUtils.hasPlayerDataKey(sender)) {
return true;
}
switch (args.length) {
case 0:
Player player = (Player) sender;
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
boolean isLucky = Permissions.lucky(player, skill);
boolean hasEndurance = (PerksUtils.handleActivationPerks(player, 0, 0) != 0);
float skillValue = mcMMOPlayer.getSkillLevel(skill);
//Send the players a few blank lines to make finding the top of the skill command easier
if (AdvancedConfig.getInstance().doesSkillCommandSendBlankLines())
for (int i = 0; i < 2; i++) {
player.sendMessage("");
}
permissionsCheck(player);
dataCalculations(player, skillValue);
sendSkillCommandHeader(player, mcMMOPlayer, (int) skillValue);
//Make JSON text components
List<TextComponent> subskillTextComponents = getTextComponents(player);
//Subskills Header
player.sendMessage(LocaleLoader.getString("Skills.Overhaul.Header", LocaleLoader.getString("Effects.SubSkills.Overhaul")));
//Send JSON text components
TextComponentFactory.sendPlayerSubSkillList(player, subskillTextComponents);
/*for(TextComponent tc : subskillTextComponents)
{
player.spigot().sendMessage(new TextComponent[]{tc, new TextComponent(": TESTING")});
}*/
//Stats
getStatMessages(player, isLucky, hasEndurance, skillValue);
//Header
//Link Header
if (MainConfig.getInstance().getUrlLinksEnabled()) {
player.sendMessage(LocaleLoader.getString("Overhaul.mcMMO.Header"));
TextComponentFactory.sendPlayerUrlHeader(player);
}
if (MainConfig.getInstance().getScoreboardsEnabled() && MainConfig.getInstance().getSkillUseBoard()) {
ScoreboardManager.enablePlayerSkillScoreboard(player, skill);
}
return true;
default:
return skillGuideCommand.onCommand(sender, command, label, args);
}
}
private void getStatMessages(Player player, boolean isLucky, boolean hasEndurance, float skillValue) {
List<String> statsMessages = statsDisplay(player, skillValue, hasEndurance, isLucky);
if (!statsMessages.isEmpty()) {
player.sendMessage(LocaleLoader.getString("Skills.Overhaul.Header", LocaleLoader.getString("Commands.Stats.Self.Overhaul")));
for (String message : statsMessages) {
player.sendMessage(message);
}
}
player.sendMessage(LocaleLoader.getString("Guides.Available", skillName, skillName.toLowerCase()));
}
private void sendSkillCommandHeader(Player player, McMMOPlayer mcMMOPlayer, int skillValue) {
ChatColor hd1 = ChatColor.DARK_AQUA;
ChatColor c1 = ChatColor.GOLD;
ChatColor c2 = ChatColor.RED;
player.sendMessage(LocaleLoader.getString("Skills.Overhaul.Header", skillName));
if (!skill.isChildSkill()) {
/*
* NON-CHILD SKILLS
*/
//XP GAIN METHOD
player.sendMessage(LocaleLoader.getString("Commands.XPGain.Overhaul", LocaleLoader.getString("Commands.XPGain." + StringUtils.getCapitalized(skill.toString()))));
//LEVEL
player.sendMessage(LocaleLoader.getString("Effects.Level.Overhaul", skillValue, mcMMOPlayer.getSkillXpLevel(skill), mcMMOPlayer.getXpToLevel(skill)));
} else {
/*
* CHILD SKILLS
*/
Set<PrimarySkillType> parents = FamilyTree.getParents(skill);
ArrayList<PrimarySkillType> parentList = new ArrayList<>();
//TODO: Add JSON here
for (PrimarySkillType parent : parents) {
parentList.add(parent);
/*player.sendMessage(parent.getName() + " - " + LocaleLoader.getString("Effects.Level.Overhaul", mcMMOPlayer.getSkillLevel(parent), mcMMOPlayer.getSkillXpLevel(parent), mcMMOPlayer.getXpToLevel(parent)))*/
;
}
String parentMessage = "";
for (int i = 0; i < parentList.size(); i++) {
if (i + 1 < parentList.size()) {
parentMessage += LocaleLoader.getString("Effects.Child.ParentList", parentList.get(i).getName(), mcMMOPlayer.getSkillLevel(parentList.get(i)));
parentMessage += ChatColor.GRAY + ", ";
} else {
parentMessage += LocaleLoader.getString("Effects.Child.ParentList", parentList.get(i).getName(), mcMMOPlayer.getSkillLevel(parentList.get(i)));
}
}
//XP GAIN METHOD
player.sendMessage(LocaleLoader.getString("Commands.XPGain.Overhaul", LocaleLoader.getString("Commands.XPGain.Child")));
player.sendMessage(LocaleLoader.getString("Effects.Child.Overhaul", skillValue, parentMessage));
//LEVEL
//player.sendMessage(LocaleLoader.getString("Effects.Child.Overhaul", skillValue, skillValue));
}
/*
if (!skill.isChildSkill()) {
player.sendMessage(LocaleLoader.getString("Skills.Header", skillName));
player.sendMessage(LocaleLoader.getString("Commands.XPGain", LocaleLoader.getString("Commands.XPGain." + StringUtils.getCapitalized(skill.toString()))));
player.sendMessage(LocaleLoader.getString("Effects.Level", skillValue, mcMMOPlayer.getSkillXpLevel(skill), mcMMOPlayer.getXpToLevel(skill)));
} else {
player.sendMessage(LocaleLoader.getString("Skills.Header", skillName + " " + LocaleLoader.getString("Skills.Child")));
player.sendMessage(LocaleLoader.getString("Commands.XPGain", LocaleLoader.getString("Commands.XPGain.Child")));
player.sendMessage(LocaleLoader.getString("Effects.Child", skillValue));
player.sendMessage(LocaleLoader.getString("Skills.Header", LocaleLoader.getString("Skills.Parents")));
Set<PrimarySkillType> parents = FamilyTree.getParents(skill);
for (PrimarySkillType parent : parents) {
player.sendMessage(parent.getName() + " - " + LocaleLoader.getString("Effects.Level", mcMMOPlayer.getSkillLevel(parent), mcMMOPlayer.getSkillXpLevel(parent), mcMMOPlayer.getXpToLevel(parent)));
}
}
*/
}
@Override
public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
switch (args.length) {
case 1:
return ImmutableList.of("?");
default:
return ImmutableList.of();
}
}
protected int calculateRank(float skillValue, int maxLevel, int rankChangeLevel) {
return Math.min((int) skillValue, maxLevel) / rankChangeLevel;
}
protected String[] getAbilityDisplayValues(SkillActivationType skillActivationType, Player player, SubSkillType subSkill) {
return RandomChanceUtil.calculateAbilityDisplayValues(skillActivationType, player, subSkill);
}
protected String[] calculateLengthDisplayValues(Player player, float skillValue) {
int maxLength = skill.getAbility().getMaxLength();
int abilityLengthVar = AdvancedConfig.getInstance().getAbilityLength();
int abilityLengthCap = AdvancedConfig.getInstance().getAbilityLengthCap();
int length;
if (abilityLengthCap <= 0) {
length = 2 + (int) (skillValue / abilityLengthVar);
} else {
length = 2 + (int) (Math.min(abilityLengthCap, skillValue) / abilityLengthVar);
}
int enduranceLength = PerksUtils.handleActivationPerks(player, length, maxLength);
if (maxLength != 0) {
length = Math.min(length, maxLength);
}
return new String[]{String.valueOf(length), String.valueOf(enduranceLength)};
}
protected String getStatMessage(SubSkillType subSkillType, String... vars) {
return getStatMessage(false, false, subSkillType, vars);
}
protected String getStatMessage(boolean isExtra, boolean isCustom, SubSkillType subSkillType, String... vars) {
String templateKey = isCustom ? "Ability.Generic.Template.Custom" : "Ability.Generic.Template";
String statDescriptionKey = !isExtra ? subSkillType.getLocaleKeyStatDescription() : subSkillType.getLocaleKeyStatExtraDescription();
if (isCustom)
//Cast to Object[] to suppress warnings
return LocaleLoader.getString(templateKey, LocaleLoader.getString(statDescriptionKey, (Object[]) vars));
else {
String[] mergedList = addItemToFirstPositionOfArray(LocaleLoader.getString(statDescriptionKey), vars);
//Cast to Object[] to suppress warnings
return LocaleLoader.getString(templateKey, (Object[]) mergedList);
}
}
protected abstract void dataCalculations(Player player, float skillValue);
protected abstract void permissionsCheck(Player player);
//protected abstract List<String> effectsDisplay();
protected abstract List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky);
protected abstract List<TextComponent> getTextComponents(Player player);
/**
* Checks if a player can use a skill
*
* @param player target player
* @param subSkillType target subskill
* @return true if the player has permission and has the skill unlocked
*/
protected boolean canUseSubskill(Player player, SubSkillType subSkillType) {
return Permissions.isSubSkillEnabled(player, subSkillType) && RankUtils.hasUnlockedSubskill(player, subSkillType);
}
}

View File

@@ -1,27 +1,24 @@
package com.gmail.nossr50.commands.skills;
import java.util.ArrayList;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.util.StringUtils;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import com.gmail.nossr50.datatypes.skills.SkillType;
import com.gmail.nossr50.locale.LocaleLoader;
import com.gmail.nossr50.util.StringUtils;
import com.gmail.nossr50.util.skills.SkillUtils;
import java.util.ArrayList;
import java.util.Arrays;
public class SkillGuideCommand implements CommandExecutor {
private String header;
private String[] guide;
private ArrayList<String> guide;
private String invalidPage;
private String invalidPage = LocaleLoader.getString("Guides.Page.Invalid");
public SkillGuideCommand(SkillType skillType) {
header = LocaleLoader.getString("Guides.Header", SkillUtils.getSkillName(skillType));
guide = LocaleLoader.getString("Guides." + StringUtils.getCapitalized(skillType.toString())).split("\n");
invalidPage = LocaleLoader.getString("Guides.Page.Invalid");
public SkillGuideCommand(PrimarySkillType skill) {
header = LocaleLoader.getString("Guides.Header", skill.getName());
guide = getGuide(skill);
}
@Override
@@ -59,7 +56,7 @@ public class SkillGuideCommand implements CommandExecutor {
}
private int getTotalPageNumber() {
return (int) Math.ceil(guide.length / 8.0);
return (int) Math.ceil(guide.size() / 8.0);
}
private void sendGuide(CommandSender sender, int pageNumber) {
@@ -68,23 +65,45 @@ public class SkillGuideCommand implements CommandExecutor {
}
}
private ArrayList<String> grabPageContents(int pagenum) {
int pageIndexStart = 8 * (pagenum - 1); // Determine what string to start at
private ArrayList<String> grabPageContents(int page) {
int pageIndexStart = 8 * (page - 1); // Determine what string to start at
ArrayList<String> allStrings = new ArrayList<String>();
allStrings.add(header);
// Add targeted strings
while (allStrings.size() < 9) {
if (pageIndexStart + allStrings.size() > guide.length) {
if (pageIndexStart + allStrings.size() > guide.size()) {
allStrings.add("");
}
else {
allStrings.add(guide[pageIndexStart + (allStrings.size() - 1)]);
} else {
allStrings.add(guide.get(pageIndexStart + (allStrings.size() - 1)));
}
}
allStrings.add("Page " + pagenum + " of " + getTotalPageNumber());
allStrings.add("Page " + page + " of " + getTotalPageNumber());
return allStrings;
}
private ArrayList<String> getGuide(PrimarySkillType skill) {
ArrayList<String> guide = new ArrayList<String>();
for (int i = 0; i < 10; i++) {
String[] section = LocaleLoader.getString("Guides." + StringUtils.getCapitalized(skill.toString()) + ".Section." + i).split("\n");
if (section[0].startsWith("!")) {
break;
}
guide.addAll(Arrays.asList(section));
if (section.length < 8) {
for (int blankLine = 8 - section.length; blankLine > 0; blankLine--) {
guide.add("");
}
}
}
return guide;
}
}

View File

@@ -0,0 +1,99 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.child.smelting.Smelting;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class SmeltingCommand extends SkillCommand {
private String burnTimeModifier;
private String str_secondSmeltChance;
private String str_secondSmeltChanceLucky;
private String str_fluxMiningChance;
private String str_fluxMiningChanceLucky;
private boolean canFuelEfficiency;
private boolean canSecondSmelt;
private boolean canFluxMine;
private boolean canUnderstandTheArt;
public SmeltingCommand() {
super(PrimarySkillType.SMELTING);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// FUEL EFFICIENCY
if (canFuelEfficiency) {
burnTimeModifier = decimal.format(1 + ((skillValue / Smelting.burnModifierMaxLevel) * Smelting.burnTimeMultiplier));
}
// FLUX MINING
/*if (canFluxMine) {
String[] fluxMiningStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.SMELTING_FLUX_MINING);
str_fluxMiningChance = fluxMiningStrings[0];
str_fluxMiningChanceLucky = fluxMiningStrings[1];
}*/
// SECOND SMELT
if (canSecondSmelt) {
String[] secondSmeltStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.SMELTING_SECOND_SMELT);
str_secondSmeltChance = secondSmeltStrings[0];
str_secondSmeltChanceLucky = secondSmeltStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
canFuelEfficiency = canUseSubskill(player, SubSkillType.SMELTING_FUEL_EFFICIENCY);
canSecondSmelt = canUseSubskill(player, SubSkillType.SMELTING_SECOND_SMELT);
canFluxMine = canUseSubskill(player, SubSkillType.SMELTING_FLUX_MINING);
canUnderstandTheArt = Permissions.vanillaXpBoost(player, skill) && RankUtils.hasUnlockedSubskill(player, SubSkillType.SMELTING_UNDERSTANDING_THE_ART);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
/*if (canFluxMine) {
messages.add(getStatMessage(SubSkillType.SMELTING_FLUX_MINING, str_fluxMiningChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", str_fluxMiningChanceLucky) : ""));
//messages.add(LocaleLoader.getString("Smelting.Ability.FluxMining", str_fluxMiningChance) + (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", str_fluxMiningChanceLucky) : ""));
}*/
if (canFuelEfficiency) {
messages.add(getStatMessage(false, true, SubSkillType.SMELTING_FUEL_EFFICIENCY, burnTimeModifier));
}
if (canSecondSmelt) {
messages.add(getStatMessage(SubSkillType.SMELTING_SECOND_SMELT, str_secondSmeltChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", str_secondSmeltChanceLucky) : ""));
}
if (canUnderstandTheArt) {
messages.add(getStatMessage(false, true, SubSkillType.SMELTING_UNDERSTANDING_THE_ART,
String.valueOf(UserManager.getPlayer(player).getSmeltingManager().getVanillaXpMultiplier())));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.SMELTING);
return textComponents;
}
}

View File

@@ -0,0 +1,108 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.config.AdvancedConfig;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class SwordsCommand extends SkillCommand {
private String counterChance;
private String counterChanceLucky;
private int bleedLength;
private String bleedChance;
private String bleedChanceLucky;
private String serratedStrikesLength;
private String serratedStrikesLengthEndurance;
private boolean canCounter;
private boolean canSerratedStrike;
private boolean canBleed;
public SwordsCommand() {
super(PrimarySkillType.SWORDS);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// SWORDS_COUNTER_ATTACK
if (canCounter) {
String[] counterStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.SWORDS_COUNTER_ATTACK);
counterChance = counterStrings[0];
counterChanceLucky = counterStrings[1];
}
// SWORDS_RUPTURE
if (canBleed) {
bleedLength = UserManager.getPlayer(player).getSwordsManager().getRuptureBleedTicks();
String[] bleedStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.SWORDS_RUPTURE);
bleedChance = bleedStrings[0];
bleedChanceLucky = bleedStrings[1];
}
// SERRATED STRIKES
if (canSerratedStrike) {
String[] serratedStrikesStrings = calculateLengthDisplayValues(player, skillValue);
serratedStrikesLength = serratedStrikesStrings[0];
serratedStrikesLengthEndurance = serratedStrikesStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
canBleed = canUseSubskill(player, SubSkillType.SWORDS_RUPTURE);
canCounter = canUseSubskill(player, SubSkillType.SWORDS_COUNTER_ATTACK);
canSerratedStrike = RankUtils.hasUnlockedSubskill(player, SubSkillType.SWORDS_SERRATED_STRIKES) && Permissions.serratedStrikes(player);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
int ruptureTicks = UserManager.getPlayer(player).getSwordsManager().getRuptureBleedTicks();
double ruptureDamagePlayers = RankUtils.getRank(player, SubSkillType.SWORDS_RUPTURE) >= 3 ? AdvancedConfig.getInstance().getRuptureDamagePlayer() * 1.5D : AdvancedConfig.getInstance().getRuptureDamagePlayer();
double ruptureDamageMobs = RankUtils.getRank(player, SubSkillType.SWORDS_RUPTURE) >= 3 ? AdvancedConfig.getInstance().getRuptureDamageMobs() * 1.5D : AdvancedConfig.getInstance().getRuptureDamageMobs();
if (canCounter) {
messages.add(getStatMessage(SubSkillType.SWORDS_COUNTER_ATTACK, counterChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", counterChanceLucky) : ""));
}
if (canBleed) {
messages.add(getStatMessage(SubSkillType.SWORDS_RUPTURE, bleedChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", bleedChanceLucky) : ""));
messages.add(getStatMessage(true, true, SubSkillType.SWORDS_RUPTURE,
String.valueOf(ruptureTicks),
String.valueOf(ruptureDamagePlayers),
String.valueOf(ruptureDamageMobs)));
messages.add(LocaleLoader.getString("Swords.Combat.Rupture.Note"));
}
if (canSerratedStrike) {
messages.add(getStatMessage(SubSkillType.SWORDS_SERRATED_STRIKES, serratedStrikesLength)
+ (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", serratedStrikesLengthEndurance) : ""));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.SWORDS);
return textComponents;
}
}

View File

@@ -0,0 +1,102 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.primary.taming.Taming;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.EntityType;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class TamingCommand extends SkillCommand {
private String goreChance;
private String goreChanceLucky;
private boolean canBeastLore;
private boolean canGore;
private boolean canSharpenedClaws;
private boolean canEnvironmentallyAware;
private boolean canThickFur;
private boolean canShockProof;
private boolean canCallWild;
private boolean canFastFood;
private boolean canHolyHound;
public TamingCommand() {
super(PrimarySkillType.TAMING);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
if (canGore) {
String[] goreStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.TAMING_GORE);
goreChance = goreStrings[0];
goreChanceLucky = goreStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
canBeastLore = canUseSubskill(player, SubSkillType.TAMING_BEAST_LORE);
canCallWild = Permissions.callOfTheWild(player, EntityType.HORSE) || Permissions.callOfTheWild(player, EntityType.WOLF) || Permissions.callOfTheWild(player, EntityType.OCELOT);
canEnvironmentallyAware = canUseSubskill(player, SubSkillType.TAMING_ENVIRONMENTALLY_AWARE);
canFastFood = canUseSubskill(player, SubSkillType.TAMING_FAST_FOOD_SERVICE);
canGore = canUseSubskill(player, SubSkillType.TAMING_GORE);
canSharpenedClaws = canUseSubskill(player, SubSkillType.TAMING_SHARPENED_CLAWS);
canShockProof = canUseSubskill(player, SubSkillType.TAMING_SHOCK_PROOF);
canThickFur = canUseSubskill(player, SubSkillType.TAMING_THICK_FUR);
canHolyHound = canUseSubskill(player, SubSkillType.TAMING_HOLY_HOUND);
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canEnvironmentallyAware) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Taming.Ability.Bonus.0"), LocaleLoader.getString("Taming.Ability.Bonus.1")));
}
if (canFastFood) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Taming.Ability.Bonus.8"), LocaleLoader.getString("Taming.Ability.Bonus.9", percent.format(Taming.fastFoodServiceActivationChance / 100D))));
}
if (canGore) {
messages.add(LocaleLoader.getString("Ability.Generic.Template",
LocaleLoader.getString("Taming.Combat.Chance.Gore"),
goreChance) + (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", goreChanceLucky) : ""));
}
if (canHolyHound) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Taming.Ability.Bonus.10"), LocaleLoader.getString("Taming.Ability.Bonus.11")));
}
if (canSharpenedClaws) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Taming.Ability.Bonus.6"), LocaleLoader.getString("Taming.Ability.Bonus.7", Taming.sharpenedClawsBonusDamage)));
}
if (canShockProof) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Taming.Ability.Bonus.4"), LocaleLoader.getString("Taming.Ability.Bonus.5", Taming.shockProofModifier)));
}
if (canThickFur) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Taming.Ability.Bonus.2"), LocaleLoader.getString("Taming.Ability.Bonus.3", Taming.thickFurModifier)));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, this.skill);
return textComponents;
}
}

View File

@@ -0,0 +1,129 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class UnarmedCommand extends SkillCommand {
private String berserkLength;
private String berserkLengthEndurance;
private String deflectChance;
private String deflectChanceLucky;
private String disarmChance;
private String disarmChanceLucky;
private String ironGripChance;
private String ironGripChanceLucky;
private double ironArmBonus;
private boolean canBerserk;
private boolean canDisarm;
private boolean canIronArm;
private boolean canDeflect;
private boolean canIronGrip;
public UnarmedCommand() {
super(PrimarySkillType.UNARMED);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// UNARMED_ARROW_DEFLECT
if (canDeflect) {
String[] deflectStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.UNARMED_ARROW_DEFLECT);
;
deflectChance = deflectStrings[0];
deflectChanceLucky = deflectStrings[1];
}
// BERSERK
if (canBerserk) {
String[] berserkStrings = calculateLengthDisplayValues(player, skillValue);
berserkLength = berserkStrings[0];
berserkLengthEndurance = berserkStrings[1];
}
// UNARMED_DISARM
if (canDisarm) {
String[] disarmStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.UNARMED_DISARM);
;
disarmChance = disarmStrings[0];
disarmChanceLucky = disarmStrings[1];
}
// IRON ARM
if (canIronArm) {
ironArmBonus = UserManager.getPlayer(player).getUnarmedManager().getIronArmDamage();
}
// IRON GRIP
if (canIronGrip) {
String[] ironGripStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.UNARMED_IRON_GRIP);
ironGripChance = ironGripStrings[0];
ironGripChanceLucky = ironGripStrings[1];
}
}
@Override
protected void permissionsCheck(Player player) {
canBerserk = RankUtils.hasUnlockedSubskill(player, SubSkillType.UNARMED_BERSERK) && Permissions.berserk(player);
canIronArm = canUseSubskill(player, SubSkillType.UNARMED_IRON_ARM_STYLE);
canDeflect = canUseSubskill(player, SubSkillType.UNARMED_ARROW_DEFLECT);
canDisarm = canUseSubskill(player, SubSkillType.UNARMED_DISARM);
canIronGrip = canUseSubskill(player, SubSkillType.UNARMED_IRON_GRIP);
// TODO: Apparently we forgot about block cracker?
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canDeflect) {
messages.add(getStatMessage(SubSkillType.UNARMED_ARROW_DEFLECT, deflectChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", deflectChanceLucky) : ""));
//messages.add(LocaleLoader.getString("Unarmed.Ability.Chance.ArrowDeflect", deflectChance) + (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", deflectChanceLucky) : ""));
}
if (canBerserk) {
messages.add(getStatMessage(SubSkillType.UNARMED_BERSERK, berserkLength)
+ (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", berserkLengthEndurance) : ""));
//messages.add(LocaleLoader.getString("Unarmed.Ability.Berserk.Length", berserkLength) + (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", berserkLengthEndurance) : ""));
}
if (canDisarm) {
messages.add(getStatMessage(SubSkillType.UNARMED_DISARM, disarmChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", disarmChanceLucky) : ""));
//messages.add(LocaleLoader.getString("Unarmed.Ability.Chance.Disarm", disarmChance) + (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", disarmChanceLucky) : ""));
}
if (canIronArm) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Unarmed.Ability.Bonus.0"), LocaleLoader.getString("Unarmed.Ability.Bonus.1", ironArmBonus)));
}
if (canIronGrip) {
messages.add(getStatMessage(SubSkillType.UNARMED_IRON_GRIP, ironGripChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", ironGripChanceLucky) : ""));
//messages.add(LocaleLoader.getString("Unarmed.Ability.Chance.IronGrip", ironGripChance) + (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", ironGripChanceLucky) : ""));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.UNARMED);
return textComponents;
}
}

View File

@@ -0,0 +1,96 @@
package com.gmail.nossr50.commands.skills;
import com.gmail.nossr50.core.locale.LocaleLoader;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.TextComponentFactory;
import com.gmail.nossr50.core.util.skills.RankUtils;
import com.gmail.nossr50.core.util.skills.SkillActivationType;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public class WoodcuttingCommand extends SkillCommand {
private String treeFellerLength;
private String treeFellerLengthEndurance;
private String doubleDropChance;
private String doubleDropChanceLucky;
private boolean canTreeFell;
private boolean canLeafBlow;
private boolean canDoubleDrop;
private boolean canSplinter;
private boolean canBarkSurgeon;
private boolean canNaturesBounty;
public WoodcuttingCommand() {
super(PrimarySkillType.WOODCUTTING);
}
@Override
protected void dataCalculations(Player player, float skillValue) {
// DOUBLE DROPS
if (canDoubleDrop) {
setDoubleDropClassicChanceStrings(player);
}
// TREE FELLER
if (canTreeFell) {
String[] treeFellerStrings = calculateLengthDisplayValues(player, skillValue);
treeFellerLength = treeFellerStrings[0];
treeFellerLengthEndurance = treeFellerStrings[1];
}
}
private void setDoubleDropClassicChanceStrings(Player player) {
String[] doubleDropStrings = getAbilityDisplayValues(SkillActivationType.RANDOM_LINEAR_100_SCALE_WITH_CAP, player, SubSkillType.WOODCUTTING_HARVEST_LUMBER);
;
doubleDropChance = doubleDropStrings[0];
doubleDropChanceLucky = doubleDropStrings[1];
}
@Override
protected void permissionsCheck(Player player) {
canTreeFell = RankUtils.hasUnlockedSubskill(player, SubSkillType.WOODCUTTING_TREE_FELLER) && Permissions.treeFeller(player);
canDoubleDrop = canUseSubskill(player, SubSkillType.WOODCUTTING_HARVEST_LUMBER) && !skill.getDoubleDropsDisabled() && RankUtils.getRank(player, SubSkillType.WOODCUTTING_HARVEST_LUMBER) >= 1;
canLeafBlow = canUseSubskill(player, SubSkillType.WOODCUTTING_LEAF_BLOWER);
/*canSplinter = canUseSubskill(player, SubSkillType.WOODCUTTING_SPLINTER);
canBarkSurgeon = canUseSubskill(player, SubSkillType.WOODCUTTING_BARK_SURGEON);
canNaturesBounty = canUseSubskill(player, SubSkillType.WOODCUTTING_NATURES_BOUNTY);*/
}
@Override
protected List<String> statsDisplay(Player player, float skillValue, boolean hasEndurance, boolean isLucky) {
List<String> messages = new ArrayList<String>();
if (canDoubleDrop) {
messages.add(getStatMessage(SubSkillType.WOODCUTTING_HARVEST_LUMBER, doubleDropChance)
+ (isLucky ? LocaleLoader.getString("Perks.Lucky.Bonus", doubleDropChanceLucky) : ""));
}
if (canLeafBlow) {
messages.add(LocaleLoader.getString("Ability.Generic.Template", LocaleLoader.getString("Woodcutting.Ability.0"), LocaleLoader.getString("Woodcutting.Ability.1")));
}
if (canTreeFell) {
messages.add(getStatMessage(SubSkillType.WOODCUTTING_TREE_FELLER, treeFellerLength)
+ (hasEndurance ? LocaleLoader.getString("Perks.ActivationTime.Bonus", treeFellerLengthEndurance) : ""));
}
return messages;
}
@Override
protected List<TextComponent> getTextComponents(Player player) {
List<TextComponent> textComponents = new ArrayList<>();
TextComponentFactory.getSubSkillTextComponents(player, textComponents, PrimarySkillType.WOODCUTTING);
return textComponents;
}
}

View File

@@ -0,0 +1,566 @@
package com.gmail.nossr50.listeners;
import com.gmail.nossr50.config.experience.ExperienceConfig;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.config.ChunkConversionOptions;
import com.gmail.nossr50.core.config.WorldBlacklist;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SuperAbilityType;
import com.gmail.nossr50.core.skills.ToolType;
import com.gmail.nossr50.core.skills.child.salvage.Salvage;
import com.gmail.nossr50.core.skills.primary.alchemy.Alchemy;
import com.gmail.nossr50.core.skills.primary.excavation.ExcavationManager;
import com.gmail.nossr50.core.skills.primary.herbalism.Herbalism;
import com.gmail.nossr50.core.skills.primary.herbalism.HerbalismManager;
import com.gmail.nossr50.core.skills.primary.mining.MiningManager;
import com.gmail.nossr50.core.skills.primary.repair.Repair;
import com.gmail.nossr50.core.skills.primary.woodcutting.WoodcuttingManager;
import com.gmail.nossr50.core.util.BlockUtils;
import com.gmail.nossr50.core.util.EventUtils;
import com.gmail.nossr50.core.util.ItemUtils;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.skills.SkillUtils;
import com.gmail.nossr50.core.util.sounds.SoundManager;
import com.gmail.nossr50.core.util.sounds.SoundType;
import com.gmail.nossr50.core.worldguard.WorldGuardManager;
import com.gmail.nossr50.core.worldguard.WorldGuardUtils;
import com.gmail.nossr50.core.events.fake.FakeBlockBreakEvent;
import com.gmail.nossr50.core.events.fake.FakeBlockDamageEvent;
import com.gmail.nossr50.mcMMO;
import org.bukkit.GameMode;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.Tag;
import org.bukkit.block.*;
import org.bukkit.entity.EntityType;
import org.bukkit.entity.Player;
import org.bukkit.event.EventHandler;
import org.bukkit.event.EventPriority;
import org.bukkit.event.Listener;
import org.bukkit.event.block.*;
import org.bukkit.event.entity.EntityChangeBlockEvent;
import org.bukkit.inventory.ItemStack;
import org.bukkit.metadata.FixedMetadataValue;
import org.bukkit.metadata.MetadataValue;
import java.util.List;
public class BlockListener implements Listener {
private final mcMMO plugin;
public BlockListener(final mcMMO plugin) {
this.plugin = plugin;
}
/**
* Monitor BlockPistonExtend events.
*
* @param event The event to monitor
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onBlockPistonExtend(BlockPistonExtendEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
BlockFace direction = event.getDirection();
Block movedBlock = event.getBlock();
movedBlock = movedBlock.getRelative(direction, 2);
for (Block b : event.getBlocks()) {
if (BlockUtils.shouldBeWatched(b.getState()) && mcMMO.getPlaceStore().isTrue(b)) {
movedBlock = b.getRelative(direction);
mcMMO.getPlaceStore().setTrue(movedBlock);
}
}
}
/**
* Monitor BlockPistonRetract events.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onBlockPistonRetract(BlockPistonRetractEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
// Get opposite direction so we get correct block
BlockFace direction = event.getDirection();
Block movedBlock = event.getBlock().getRelative(direction);
mcMMO.getPlaceStore().setTrue(movedBlock);
for (Block block : event.getBlocks()) {
movedBlock = block.getRelative(direction);
mcMMO.getPlaceStore().setTrue(movedBlock);
}
}
/**
* Monitor blocks formed by entities (snowmen)
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onEntityBlockFormEvent(EntityBlockFormEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
if (BlockUtils.shouldBeWatched(event.getBlock().getState())) {
mcMMO.getPlaceStore().setTrue(event.getBlock());
}
}
/**
* Monitor falling blocks.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onFallingBlock(EntityChangeBlockEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
if (BlockUtils.shouldBeWatched(event.getBlock().getState()) && event.getEntityType().equals(EntityType.FALLING_BLOCK)) {
if (event.getTo().equals(Material.AIR) && mcMMO.getPlaceStore().isTrue(event.getBlock())) {
event.getEntity().setMetadata("mcMMOBlockFall", new FixedMetadataValue(plugin, event.getBlock().getLocation()));
} else {
List<MetadataValue> values = event.getEntity().getMetadata("mcMMOBlockFall");
if (!values.isEmpty()) {
if (values.get(0).value() == null) return;
Block spawn = ((org.bukkit.Location) values.get(0).value()).getBlock();
mcMMO.getPlaceStore().setTrue(event.getBlock());
mcMMO.getPlaceStore().setFalse(spawn);
}
}
}
}
/**
* Monitor BlockPlace events.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR)
public void onBlockPlace(BlockPlaceEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
Player player = event.getPlayer();
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
BlockState blockState = event.getBlock().getState();
/* Check if the blocks placed should be monitored so they do not give out XP in the future */
if (BlockUtils.shouldBeWatched(blockState)) {
// Don't count de-barking wood
if (!Tag.LOGS.isTagged(event.getBlockReplacedState().getType()) || !Tag.LOGS.isTagged(event.getBlockPlaced().getType()))
mcMMO.getPlaceStore().setTrue(blockState);
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
if (blockState.getType() == Repair.anvilMaterial && PrimarySkillType.REPAIR.getPermissions(player)) {
mcMMOPlayer.getRepairManager().placedAnvilCheck();
} else if (blockState.getType() == Salvage.anvilMaterial && PrimarySkillType.SALVAGE.getPermissions(player)) {
mcMMOPlayer.getSalvageManager().placedAnvilCheck();
}
}
/**
* Monitor BlockMultiPlace events.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onBlockMultiPlace(BlockMultiPlaceEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
Player player = event.getPlayer();
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
for (BlockState replacedBlockState : event.getReplacedBlockStates()) {
BlockState blockState = replacedBlockState.getBlock().getState();
/* Check if the blocks placed should be monitored so they do not give out XP in the future */
if (BlockUtils.shouldBeWatched(blockState)) {
mcMMO.getPlaceStore().setTrue(blockState);
}
}
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onBlockGrow(BlockGrowEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
BlockState blockState = event.getBlock().getState();
if (!BlockUtils.shouldBeWatched(blockState)) {
return;
}
mcMMO.getPlaceStore().setFalse(blockState);
}
/**
* Monitor BlockBreak events.
*
* @param event The event to monitor
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onBlockBreak(BlockBreakEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(event.getPlayer()))
return;
}
if (event instanceof FakeBlockBreakEvent) {
return;
}
BlockState blockState = event.getBlock().getState();
Location location = blockState.getLocation();
if (!BlockUtils.shouldBeWatched(blockState)) {
return;
}
/* ALCHEMY - Cancel any brew in progress for that BrewingStand */
if (blockState instanceof BrewingStand && Alchemy.brewingStandMap.containsKey(location)) {
Alchemy.brewingStandMap.get(location).cancelBrew();
}
Player player = event.getPlayer();
if (!UserManager.hasPlayerDataKey(player) || player.getGameMode() == GameMode.CREATIVE) {
return;
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
ItemStack heldItem = player.getInventory().getItemInMainHand();
/* HERBALISM */
if (BlockUtils.affectedByGreenTerra(blockState)) {
HerbalismManager herbalismManager = mcMMOPlayer.getHerbalismManager();
/* Green Terra */
if (herbalismManager.canActivateAbility()) {
mcMMOPlayer.checkAbilityActivation(PrimarySkillType.HERBALISM);
}
/*
* We don't check the block store here because herbalism has too many unusual edge cases.
* Instead, we check it inside the drops handler.
*/
if (PrimarySkillType.HERBALISM.getPermissions(player)) {
herbalismManager.herbalismBlockCheck(blockState);
}
}
/* MINING */
else if (BlockUtils.affectedBySuperBreaker(blockState) && ItemUtils.isPickaxe(heldItem) && PrimarySkillType.MINING.getPermissions(player) && !mcMMO.getPlaceStore().isTrue(blockState)) {
MiningManager miningManager = mcMMOPlayer.getMiningManager();
miningManager.miningBlockCheck(blockState);
}
/* WOOD CUTTING */
else if (BlockUtils.isLog(blockState) && ItemUtils.isAxe(heldItem) && PrimarySkillType.WOODCUTTING.getPermissions(player) && !mcMMO.getPlaceStore().isTrue(blockState)) {
WoodcuttingManager woodcuttingManager = mcMMOPlayer.getWoodcuttingManager();
if (woodcuttingManager.canUseTreeFeller(heldItem)) {
woodcuttingManager.processTreeFeller(blockState);
} else {
woodcuttingManager.woodcuttingBlockCheck(blockState);
}
}
/* EXCAVATION */
else if (BlockUtils.affectedByGigaDrillBreaker(blockState) && ItemUtils.isShovel(heldItem) && PrimarySkillType.EXCAVATION.getPermissions(player) && !mcMMO.getPlaceStore().isTrue(blockState)) {
ExcavationManager excavationManager = mcMMOPlayer.getExcavationManager();
excavationManager.excavationBlockCheck(blockState);
if (mcMMOPlayer.getAbilityMode(SuperAbilityType.GIGA_DRILL_BREAKER)) {
excavationManager.gigaDrillBreaker(blockState);
}
}
/* Remove metadata from placed watched blocks */
mcMMO.getPlaceStore().setFalse(blockState);
}
/**
* Handle BlockBreak events where the event is modified.
*
* @param event The event to modify
*/
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onBlockBreakHigher(BlockBreakEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(event.getPlayer()))
return;
}
if (event instanceof FakeBlockBreakEvent) {
return;
}
Player player = event.getPlayer();
if (!UserManager.hasPlayerDataKey(player) || player.getGameMode() == GameMode.CREATIVE) {
return;
}
BlockState blockState = event.getBlock().getState();
ItemStack heldItem = player.getInventory().getItemInMainHand();
if (Herbalism.isRecentlyRegrown(blockState)) {
event.setCancelled(true);
return;
}
if (ItemUtils.isSword(heldItem)) {
HerbalismManager herbalismManager = UserManager.getPlayer(player).getHerbalismManager();
if (herbalismManager.canUseHylianLuck()) {
if (herbalismManager.processHylianLuck(blockState)) {
blockState.update(true);
event.setCancelled(true);
} else if (blockState.getType() == Material.FLOWER_POT) {
blockState.setType(Material.AIR);
blockState.update(true);
event.setCancelled(true);
}
}
}
/*else if (!heldItem.containsEnchantment(Enchantment.SILK_TOUCH)) {
SmeltingManager smeltingManager = UserManager.getPlayer(player).getSmeltingManager();
if (smeltingManager.canUseFluxMining(blockState)) {
if (smeltingManager.processFluxMining(blockState)) {
blockState.update(true);
event.setCancelled(true);
}
}
}*/
}
/**
* Monitor BlockDamage events.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onBlockDamage(BlockDamageEvent event) {
Player player = event.getPlayer();
BlockState blockState = event.getBlock().getState();
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(event.getPlayer()))
return;
}
if (event instanceof FakeBlockDamageEvent) {
return;
}
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
/*
* ABILITY PREPARATION CHECKS
*
* We check permissions here before processing activation.
*/
if (BlockUtils.canActivateAbilities(blockState)) {
ItemStack heldItem = player.getInventory().getItemInMainHand();
if (mcMMOPlayer.getToolPreparationMode(ToolType.HOE) && ItemUtils.isHoe(heldItem) && (BlockUtils.affectedByGreenTerra(blockState) || BlockUtils.canMakeMossy(blockState)) && Permissions.greenTerra(player)) {
mcMMOPlayer.checkAbilityActivation(PrimarySkillType.HERBALISM);
} else if (mcMMOPlayer.getToolPreparationMode(ToolType.AXE) && ItemUtils.isAxe(heldItem) && BlockUtils.isLog(blockState) && Permissions.treeFeller(player)) {
mcMMOPlayer.checkAbilityActivation(PrimarySkillType.WOODCUTTING);
} else if (mcMMOPlayer.getToolPreparationMode(ToolType.PICKAXE) && ItemUtils.isPickaxe(heldItem) && BlockUtils.affectedBySuperBreaker(blockState) && Permissions.superBreaker(player)) {
mcMMOPlayer.checkAbilityActivation(PrimarySkillType.MINING);
} else if (mcMMOPlayer.getToolPreparationMode(ToolType.SHOVEL) && ItemUtils.isShovel(heldItem) && BlockUtils.affectedByGigaDrillBreaker(blockState) && Permissions.gigaDrillBreaker(player)) {
mcMMOPlayer.checkAbilityActivation(PrimarySkillType.EXCAVATION);
} else if (mcMMOPlayer.getToolPreparationMode(ToolType.FISTS) && heldItem.getType() == Material.AIR && (BlockUtils.affectedByGigaDrillBreaker(blockState) || blockState.getType() == Material.SNOW || BlockUtils.affectedByBlockCracker(blockState) && Permissions.berserk(player))) {
mcMMOPlayer.checkAbilityActivation(PrimarySkillType.UNARMED);
}
}
/*
* TREE FELLER SOUNDS
*
* We don't need to check permissions here because they've already been checked for the ability to even activate.
*/
if (mcMMOPlayer.getAbilityMode(SuperAbilityType.TREE_FELLER) && BlockUtils.isLog(blockState) && MainConfig.getInstance().getTreeFellerSoundsEnabled()) {
SoundManager.sendSound(player, blockState.getLocation(), SoundType.FIZZ);
}
}
private Player getPlayerFromFurnace(Block furnaceBlock) {
List<MetadataValue> metadata = furnaceBlock.getMetadata(mcMMO.furnaceMetadataKey);
if (metadata.isEmpty()) {
return null;
}
return plugin.getServer().getPlayerExact(metadata.get(0).asString());
}
/**
* Handle BlockDamage events where the event is modified.
*
* @param event The event to modify
*/
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onBlockDamageHigher(BlockDamageEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(event.getPlayer()))
return;
}
if (event instanceof FakeBlockDamageEvent) {
return;
}
Player player = event.getPlayer();
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
ItemStack heldItem = player.getInventory().getItemInMainHand();
Block block = event.getBlock();
BlockState blockState = block.getState();
/*
* ABILITY TRIGGER CHECKS
*
* We don't need to check permissions here because they've already been checked for the ability to even activate.
*/
if (mcMMOPlayer.getAbilityMode(SuperAbilityType.GREEN_TERRA) && BlockUtils.canMakeMossy(blockState)) {
if (mcMMOPlayer.getHerbalismManager().processGreenTerra(blockState)) {
blockState.update(true);
}
} else if (mcMMOPlayer.getAbilityMode(SuperAbilityType.BERSERK) && heldItem.getType() == Material.AIR) {
if (SuperAbilityType.BERSERK.blockCheck(block.getState()) && EventUtils.simulateBlockBreak(block, player, true)) {
event.setInstaBreak(true);
SoundManager.sendSound(player, block.getLocation(), SoundType.POP);
} else if (mcMMOPlayer.getUnarmedManager().canUseBlockCracker() && BlockUtils.affectedByBlockCracker(blockState) && EventUtils.simulateBlockBreak(block, player, true)) {
if (mcMMOPlayer.getUnarmedManager().blockCrackerCheck(blockState)) {
blockState.update();
}
}
} else if (mcMMOPlayer.getWoodcuttingManager().canUseLeafBlower(heldItem) && BlockUtils.isLeaves(blockState) && EventUtils.simulateBlockBreak(block, player, true)) {
event.setInstaBreak(true);
SoundManager.sendSound(player, block.getLocation(), SoundType.POP);
}
}
@EventHandler(priority = EventPriority.MONITOR)
public void onBlockDamageCleanup(BlockDamageEvent event) {
Player player = event.getPlayer();
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
BlockState blockState = event.getBlock().getState();
ItemStack heldItem = player.getInventory().getItemInMainHand();
cleanupAbilityTools(player, mcMMOPlayer, blockState, heldItem);
debugStickDump(player, blockState);
}
public void debugStickDump(Player player, BlockState blockState) {
if (player.getInventory().getItemInMainHand().getType() == Material.DEBUG_STICK) {
if (mcMMO.getPlaceStore().isTrue(blockState))
player.sendMessage("[mcMMO DEBUG] This block is not natural and does not reward treasures/XP");
else {
player.sendMessage("[mcMMO DEBUG] This block is considered natural by mcMMO");
UserManager.getPlayer(player).getExcavationManager().printExcavationDebug(player, blockState);
}
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (WorldGuardManager.getInstance().hasMainFlag(player))
player.sendMessage("[mcMMO DEBUG] World Guard main flag is permitted for this player in this region");
else
player.sendMessage("[mcMMO DEBUG] World Guard main flag is DENIED for this player in this region");
if (WorldGuardManager.getInstance().hasXPFlag(player))
player.sendMessage("[mcMMO DEBUG] World Guard xp flag is permitted for this player in this region");
else
player.sendMessage("[mcMMO DEBUG] World Guard xp flag is not permitted for this player in this region");
}
if (blockState instanceof Furnace) {
Furnace furnace = (Furnace) blockState;
if (furnace.hasMetadata(mcMMO.furnaceMetadataKey)) {
player.sendMessage("[mcMMO DEBUG] This furnace has a registered owner");
Player furnacePlayer = getPlayerFromFurnace(furnace.getBlock());
if (furnacePlayer != null) {
player.sendMessage("[mcMMO DEBUG] This furnace is owned by player " + furnacePlayer.getName());
}
} else
player.sendMessage("[mcMMO DEBUG] This furnace does not have a registered owner");
}
if (ExperienceConfig.getInstance().isExperienceBarsEnabled())
player.sendMessage("[mcMMO DEBUG] XP bars are enabled, however you should check per-skill settings to make sure those are enabled.");
}
}
public void cleanupAbilityTools(Player player, McMMOPlayer mcMMOPlayer, BlockState blockState, ItemStack heldItem) {
if (ChunkConversionOptions.getInstance().useEnchantmentBuffs()) {
if ((ItemUtils.isPickaxe(heldItem) && !mcMMOPlayer.getAbilityMode(SuperAbilityType.SUPER_BREAKER)) || (ItemUtils.isShovel(heldItem) && !mcMMOPlayer.getAbilityMode(SuperAbilityType.GIGA_DRILL_BREAKER))) {
SkillUtils.removeAbilityBuff(heldItem);
}
} else {
if ((mcMMOPlayer.getAbilityMode(SuperAbilityType.SUPER_BREAKER) && !BlockUtils.affectedBySuperBreaker(blockState)) || (mcMMOPlayer.getAbilityMode(SuperAbilityType.GIGA_DRILL_BREAKER) && !BlockUtils.affectedByGigaDrillBreaker(blockState))) {
SkillUtils.handleAbilitySpeedDecrease(player);
}
}
}
}

View File

@@ -0,0 +1,860 @@
package com.gmail.nossr50.listeners;
import com.gmail.nossr50.core.config.experience.ExperienceConfig;
import com.gmail.nossr50.core.config.AdvancedConfig;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.config.WorldBlacklist;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.datatypes.meta.OldName;
import com.gmail.nossr50.core.datatypes.player.McMMOPlayer;
import com.gmail.nossr50.core.party.PartyManager;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.primary.archery.Archery;
import com.gmail.nossr50.core.skills.primary.fishing.Fishing;
import com.gmail.nossr50.core.skills.primary.mining.BlastMining;
import com.gmail.nossr50.core.skills.primary.mining.MiningManager;
import com.gmail.nossr50.core.skills.primary.taming.Taming;
import com.gmail.nossr50.core.skills.primary.taming.TamingManager;
import com.gmail.nossr50.core.skills.subskills.interfaces.InteractType;
import com.gmail.nossr50.core.util.BlockUtils;
import com.gmail.nossr50.core.util.Misc;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.skills.CombatUtils;
import com.gmail.nossr50.core.worldguard.WorldGuardManager;
import com.gmail.nossr50.core.worldguard.WorldGuardUtils;
import com.gmail.nossr50.core.events.fake.FakeEntityDamageByEntityEvent;
import com.gmail.nossr50.core.events.fake.FakeEntityDamageEvent;
import com.gmail.nossr50.core.events.fake.FakeEntityTameEvent;
import com.gmail.nossr50.mcMMO;
import org.bukkit.Material;
import org.bukkit.OfflinePlayer;
import org.bukkit.block.Block;
import org.bukkit.enchantments.Enchantment;
import org.bukkit.entity.*;
import org.bukkit.event.EventHandler;
import org.bukkit.event.EventPriority;
import org.bukkit.event.Listener;
import org.bukkit.event.entity.*;
import org.bukkit.event.entity.EntityDamageEvent.DamageCause;
import org.bukkit.event.entity.EntityDamageEvent.DamageModifier;
import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.PotionMeta;
import org.bukkit.metadata.FixedMetadataValue;
import org.bukkit.metadata.MetadataValue;
import org.bukkit.potion.PotionEffect;
import org.bukkit.potion.PotionEffectType;
import org.bukkit.projectiles.ProjectileSource;
import java.util.List;
public class EntityListener implements Listener {
private final mcMMO plugin;
public EntityListener(final mcMMO plugin) {
this.plugin = plugin;
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onEntityTargetEntity(EntityTargetLivingEntityEvent event) {
if (!ExperienceConfig.getInstance().isEndermanEndermiteFarmingPrevented())
return;
//Prevent entities from giving XP if they target endermite
if (event.getTarget() instanceof Endermite) {
if (event.getEntity().getMetadata(mcMMO.entityMetadataKey) == null || event.getEntity().getMetadata(mcMMO.entityMetadataKey).size() <= 0)
event.getEntity().setMetadata(mcMMO.entityMetadataKey, mcMMO.metadataValue);
}
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onEntityShootBow(EntityShootBowEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
if (event.getEntity() instanceof Player) {
Player player = (Player) event.getEntity();
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
}
Entity projectile = event.getProjectile();
if (!(projectile instanceof Arrow)) {
return;
}
ItemStack bow = event.getBow();
if (bow != null && bow.containsEnchantment(Enchantment.ARROW_INFINITE)) {
projectile.setMetadata(mcMMO.infiniteArrowKey, mcMMO.metadataValue);
}
projectile.setMetadata(mcMMO.bowForceKey, new FixedMetadataValue(plugin, Math.min(event.getForce() * AdvancedConfig.getInstance().getForceMultiplier(), 1.0)));
projectile.setMetadata(mcMMO.arrowDistanceKey, new FixedMetadataValue(plugin, projectile.getLocation()));
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onProjectileLaunch(ProjectileLaunchEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
if (event.getEntity() instanceof Player) {
Player player = (Player) event.getEntity();
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
}
Projectile projectile = event.getEntity();
if (!(projectile instanceof Arrow) || projectile.hasMetadata(mcMMO.bowForceKey)) {
return;
}
projectile.setMetadata(mcMMO.bowForceKey, new FixedMetadataValue(plugin, 1.0));
projectile.setMetadata(mcMMO.arrowDistanceKey, new FixedMetadataValue(plugin, projectile.getLocation()));
}
/**
* Monitor EntityChangeBlock events.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onEntityChangeBlock(EntityChangeBlockEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
Block block = event.getBlock();
// When the event is fired for the falling block that changes back to a
// normal block
// event.getBlock().getType() returns AIR
if (!BlockUtils.shouldBeWatched(block.getState()) && block.getType() != Material.AIR) {
return;
}
Entity entity = event.getEntity();
if (entity instanceof FallingBlock || entity instanceof Enderman) {
boolean isTracked = entity.hasMetadata(mcMMO.entityMetadataKey);
if (mcMMO.getPlaceStore().isTrue(block) && !isTracked) {
mcMMO.getPlaceStore().setFalse(block);
entity.setMetadata(mcMMO.entityMetadataKey, mcMMO.metadataValue);
} else if (isTracked) {
mcMMO.getPlaceStore().setTrue(block);
}
} else if ((block.getType() == Material.REDSTONE_ORE)) {
return;
} else {
if (mcMMO.getPlaceStore().isTrue(block)) {
mcMMO.getPlaceStore().setFalse(block);
}
}
}
/**
* Handle EntityDamageByEntity events that involve modifying the event.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onEntityDamageByEntity(EntityDamageByEntityEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
if (event instanceof FakeEntityDamageByEntityEvent) {
return;
}
if (event.getEntity() instanceof ArmorStand) {
return;
}
if (event.getDamager().hasMetadata(mcMMO.funfettiMetadataKey)) {
event.setCancelled(true);
return;
}
double damage = event.getFinalDamage();
Entity defender = event.getEntity();
Entity attacker = event.getDamager();
if (attacker instanceof Player) {
Player player = (Player) attacker;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
}
if (damage <= 0) {
if (defender instanceof Player && attacker instanceof Player) {
Player defendingPlayer = (Player) defender;
Player attackingPlayer = (Player) attacker;
if (event.getDamage(DamageModifier.ABSORPTION) > 0) {
//If friendly fire is off don't allow players to hurt one another
if (!MainConfig.getInstance().getPartyFriendlyFire())
if ((PartyManager.inSameParty(defendingPlayer, attackingPlayer) || PartyManager.areAllies(defendingPlayer, attackingPlayer)) && !(Permissions.friendlyFire(attackingPlayer) && Permissions.friendlyFire(defendingPlayer))) {
event.setCancelled(true);
return;
}
}
}
return;
}
/*
As far as I can tell at one point we registered meta-data about custom damage and we no longer do that.
if (defender.hasMetadata(mcMMO.customDamageKey)) {
defender.removeMetadata(mcMMO.customDamageKey, plugin);
return;
}
*/
if (Misc.isNPCEntity(defender) || !defender.isValid() || !(defender instanceof LivingEntity)) {
return;
}
LivingEntity target = (LivingEntity) defender;
if (CombatUtils.isInvincible(target, damage)) {
return;
}
if (Misc.isNPCEntity(attacker)) {
return;
}
if (attacker instanceof Projectile) {
ProjectileSource projectileSource = ((Projectile) attacker).getShooter();
if (projectileSource instanceof LivingEntity) {
attacker = (LivingEntity) projectileSource;
}
} else if (attacker instanceof Tameable) {
AnimalTamer animalTamer = ((Tameable) attacker).getOwner();
if (animalTamer != null && ((OfflinePlayer) animalTamer).isOnline()) {
attacker = (Entity) animalTamer;
}
} else if (attacker instanceof TNTPrimed && defender instanceof Player) {
if (BlastMining.processBlastMiningExplosion(event, (TNTPrimed) attacker, (Player) defender)) {
return;
}
}
if (defender instanceof Player && attacker instanceof Player) {
Player defendingPlayer = (Player) defender;
Player attackingPlayer = (Player) attacker;
if (!UserManager.hasPlayerDataKey(defendingPlayer) || !UserManager.hasPlayerDataKey(attackingPlayer)) {
return;
}
// We want to make sure we're not gaining XP or applying abilities
// when we hit ourselves
if (defendingPlayer.equals(attackingPlayer)) {
return;
}
//Party Friendly Fire
if (!MainConfig.getInstance().getPartyFriendlyFire())
if ((PartyManager.inSameParty(defendingPlayer, attackingPlayer) || PartyManager.areAllies(defendingPlayer, attackingPlayer)) && !(Permissions.friendlyFire(attackingPlayer) && Permissions.friendlyFire(defendingPlayer))) {
event.setCancelled(true);
return;
}
}
CombatUtils.processCombatAttack(event, attacker, target);
CombatUtils.handleHealthbars(attacker, target, event.getFinalDamage(), plugin);
/**
* This sets entity names back to whatever they are supposed to be
*/
if (!(attacker instanceof Player) && defender instanceof Player) {
if (event.getFinalDamage() >= ((LivingEntity) defender).getHealth()) {
List<MetadataValue> metadataValue = attacker.getMetadata("mcMMO_oldName");
if (metadataValue.size() <= 0)
return;
if (metadataValue != null) {
OldName oldName = (OldName) metadataValue.get(0);
attacker.setCustomName(oldName.asString());
attacker.setCustomNameVisible(false);
}
}
}
}
/**
* Handle EntityDamage events that involve modifying the event.
*
* @param event The event to modify
*/
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onEntityDamage(EntityDamageEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
if (event.getEntity() instanceof Player) {
Player player = (Player) event.getEntity();
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
}
/*
* Process Registered Interactions
*/
InteractionManager.processEvent(event, plugin, InteractType.ON_ENTITY_DAMAGE);
/*
* Old code
*/
if (event instanceof FakeEntityDamageEvent) {
return;
}
double damage = event.getFinalDamage();
if (damage <= 0) {
return;
}
Entity entity = event.getEntity();
/*
As far as I can tell at one point we registered meta-data about custom damage and we no longer do that.
if (entity.hasMetadata(mcMMO.customDamageKey)) {
entity.removeMetadata(mcMMO.customDamageKey, plugin);
return;
}
*/
if (Misc.isNPCEntity(entity) || !entity.isValid() || !(entity instanceof LivingEntity)) {
return;
}
LivingEntity livingEntity = (LivingEntity) entity;
if (CombatUtils.isInvincible(livingEntity, damage)) {
return;
}
DamageCause cause = event.getCause();
if (livingEntity instanceof Player) {
Player player = (Player) entity;
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
McMMOPlayer mcMMOPlayer = UserManager.getPlayer(player);
/* Check for invincibility */
if (mcMMOPlayer.getGodMode()) {
event.setCancelled(true);
return;
}
if (event.getFinalDamage() >= 1) {
mcMMOPlayer.actualizeRecentlyHurt();
}
} else if (livingEntity instanceof Tameable) {
Tameable pet = (Tameable) livingEntity;
AnimalTamer owner = pet.getOwner();
if (owner instanceof Player) {
Player player = (Player) owner;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
}
if (Taming.canPreventDamage(pet, owner)) {
Player player = (Player) owner;
Wolf wolf = (Wolf) pet;
TamingManager tamingManager = UserManager.getPlayer(player).getTamingManager();
switch (cause) {
case CONTACT:
case FIRE:
case LAVA:
if (tamingManager.canUseEnvironmentallyAware()) {
tamingManager.processEnvironmentallyAware(wolf, event.getDamage());
}
return;
case FALL:
if (tamingManager.canUseEnvironmentallyAware()) {
event.setCancelled(true);
}
return;
case ENTITY_ATTACK:
case PROJECTILE:
if (tamingManager.canUseThickFur()) {
event.setDamage(Taming.processThickFur(wolf, event.getDamage()));
if (event.getFinalDamage() == 0) {
event.setCancelled(true);
}
}
return;
case FIRE_TICK:
if (tamingManager.canUseThickFur()) {
Taming.processThickFurFire(wolf);
}
return;
case MAGIC:
case POISON:
case WITHER:
if (tamingManager.canUseHolyHound()) {
Taming.processHolyHound(wolf, event.getDamage());
}
return;
case BLOCK_EXPLOSION:
case ENTITY_EXPLOSION:
case LIGHTNING:
if (tamingManager.canUseShockProof()) {
event.setDamage(Taming.processShockProof(wolf, event.getDamage()));
if (event.getFinalDamage() == 0) {
event.setCancelled(true);
}
}
return;
default:
return;
}
}
}
}
/**
* Monitor EntityDeath events.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.LOWEST)
public void onEntityDeathLowest(EntityDeathEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
LivingEntity entity = event.getEntity();
if (Misc.isNPCEntity(entity)) {
return;
}
if (entity.hasMetadata(mcMMO.customNameKey)) {
entity.setCustomName(entity.getMetadata(mcMMO.customNameKey).get(0).asString());
entity.removeMetadata(mcMMO.customNameKey, plugin);
}
if (entity.hasMetadata(mcMMO.customVisibleKey)) {
entity.setCustomNameVisible(entity.getMetadata(mcMMO.customVisibleKey).get(0).asBoolean());
entity.removeMetadata(mcMMO.customVisibleKey, plugin);
}
if (entity.hasMetadata(mcMMO.entityMetadataKey)) {
entity.removeMetadata(mcMMO.entityMetadataKey, plugin);
}
}
/**
* Monitor EntityDeath events.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR)
public void onEntityDeath(EntityDeathEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
LivingEntity entity = event.getEntity();
if (Misc.isNPCEntity(entity)) {
return;
}
Archery.arrowRetrievalCheck(entity);
}
/**
* Monitor CreatureSpawn events.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onCreatureSpawn(CreatureSpawnEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
LivingEntity entity = event.getEntity();
switch (event.getSpawnReason()) {
case NETHER_PORTAL:
case SPAWNER:
case SPAWNER_EGG:
entity.setMetadata(mcMMO.entityMetadataKey, mcMMO.metadataValue);
Entity passenger = entity.getPassenger();
if (passenger != null) {
passenger.setMetadata(mcMMO.entityMetadataKey, mcMMO.metadataValue);
}
return;
case BREEDING:
entity.setMetadata(mcMMO.bredMetadataKey, mcMMO.metadataValue);
return;
default:
return;
}
}
/**
* Handle ExplosionPrime events that involve modifying the event.
*
* @param event The event to modify
*/
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onExplosionPrime(ExplosionPrimeEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
Entity entity = event.getEntity();
if (!(entity instanceof TNTPrimed) || !entity.hasMetadata(mcMMO.tntMetadataKey)) {
return;
}
// We can make this assumption because we (should) be the only ones
// using this exact metadata
Player player = plugin.getServer().getPlayerExact(entity.getMetadata(mcMMO.tntMetadataKey).get(0).asString());
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
MiningManager miningManager = UserManager.getPlayer(player).getMiningManager();
if (miningManager.canUseBiggerBombs()) {
event.setRadius(miningManager.biggerBombs(event.getRadius()));
}
}
/**
* Handle EntityExplode events that involve modifying the event.
*
* @param event The event to modify
*/
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onEnitityExplode(EntityExplodeEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
Entity entity = event.getEntity();
if (!(entity instanceof TNTPrimed) || !entity.hasMetadata(mcMMO.tntMetadataKey)) {
return;
}
// We can make this assumption because we (should) be the only ones
// using this exact metadata
Player player = plugin.getServer().getPlayerExact(entity.getMetadata(mcMMO.tntMetadataKey).get(0).asString());
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
MiningManager miningManager = UserManager.getPlayer(player).getMiningManager();
if (miningManager.canUseBlastMining()) {
miningManager.blastMiningDropProcessing(event.getYield(), event.blockList());
event.setYield(0);
}
}
/**
* Handle EntityExplode events that involve modifying the event.
*
* @param event The event to modify
*/
@EventHandler(priority = EventPriority.LOWEST, ignoreCancelled = true)
public void onEntityExplodeMonitor(EntityExplodeEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
Entity entity = event.getEntity();
if (!(entity instanceof TNTPrimed) || !entity.hasMetadata(mcMMO.tntsafeMetadataKey)) {
return;
}
event.blockList().clear();
}
/**
* Handle FoodLevelChange events that involve modifying the event.
*
* @param event The event to modify
*/
@EventHandler(priority = EventPriority.LOW, ignoreCancelled = true)
public void onFoodLevelChange(FoodLevelChangeEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
Entity entity = event.getEntity();
if (!(entity instanceof Player)) {
return;
}
Player player = (Player) entity;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
int currentFoodLevel = player.getFoodLevel();
int newFoodLevel = event.getFoodLevel();
int foodChange = newFoodLevel - currentFoodLevel;
if (foodChange <= 0) {
return;
}
/*
* Some foods have 3 ranks Some foods have 5 ranks The number of ranks
* is based on how 'common' the item is We can adjust this quite easily
* if we find something is giving too much of a bonus
*/
switch (player.getInventory().getItemInMainHand().getType()) {
case BAKED_POTATO: /*
* RESTORES 3 HUNGER - RESTORES 5 1/2 HUNGER @
* 1000
*/
case BEETROOT:
case BREAD: /* RESTORES 2 1/2 HUNGER - RESTORES 5 HUNGER @ 1000 */
case CARROT: /*
* RESTORES 2 HUNGER - RESTORES 4 1/2 HUNGER @
* 1000
*/
case GOLDEN_CARROT: /*
* RESTORES 3 HUNGER - RESTORES 5 1/2 HUNGER @
* 1000
*/
case MUSHROOM_STEW: /*
* RESTORES 4 HUNGER - RESTORES 6 1/2 HUNGER @
* 1000
*/
case PUMPKIN_PIE: /*
* RESTORES 4 HUNGER - RESTORES 6 1/2 HUNGER @
* 1000
*/
if (Permissions.isSubSkillEnabled(player, SubSkillType.HERBALISM_FARMERS_DIET)) {
event.setFoodLevel(UserManager.getPlayer(player).getHerbalismManager().farmersDiet(newFoodLevel));
}
return;
case COOKIE: /* RESTORES 1/2 HUNGER - RESTORES 2 HUNGER @ 1000 */
case MELON_SLICE: /* RESTORES 1 HUNGER - RESTORES 2 1/2 HUNGER @ 1000 */
case POISONOUS_POTATO: /*
* RESTORES 1 HUNGER - RESTORES 2 1/2 HUNGER
* @ 1000
*/
case POTATO: /* RESTORES 1/2 HUNGER - RESTORES 2 HUNGER @ 1000 */
if (Permissions.isSubSkillEnabled(player, SubSkillType.HERBALISM_FARMERS_DIET)) {
event.setFoodLevel(UserManager.getPlayer(player).getHerbalismManager().farmersDiet(newFoodLevel));
}
return;
case COOKED_SALMON: /*
* RESTORES 2 1/2 HUNGER - RESTORES 5 HUNGER @
* 1000
*/
if (Permissions.isSubSkillEnabled(player, SubSkillType.FISHING_FISHERMANS_DIET)) {
event.setFoodLevel(UserManager.getPlayer(player).getFishingManager().handleFishermanDiet(Fishing.fishermansDietRankLevel1, newFoodLevel));
}
return;
case SALMON: /* RESTORES 1 HUNGER - RESTORES 2 1/2 HUNGER @ 1000 */
if (Permissions.isSubSkillEnabled(player, SubSkillType.FISHING_FISHERMANS_DIET)) {
event.setFoodLevel(UserManager.getPlayer(player).getFishingManager().handleFishermanDiet(Fishing.fishermansDietRankLevel2, newFoodLevel));
}
return;
default:
return;
}
}
/**
* Monitor EntityTame events.
*
* @param event The event to watch
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onEntityTame(EntityTameEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
if (event instanceof FakeEntityTameEvent) {
return;
}
Player player = (Player) event.getOwner();
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
LivingEntity entity = event.getEntity();
if (!UserManager.hasPlayerDataKey(player) || Misc.isNPCEntity(entity) || entity.hasMetadata(mcMMO.entityMetadataKey)) {
return;
}
entity.setMetadata(mcMMO.entityMetadataKey, mcMMO.metadataValue);
UserManager.getPlayer(player).getTamingManager().awardTamingXP(entity);
}
/**
* Handle EntityTarget events.
*
* @param event The event to process
*/
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onEntityTarget(EntityTargetEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
Entity entity = event.getEntity();
Entity target = event.getTarget();
if (!(entity instanceof Tameable) || !(target instanceof Player)) {
return;
}
Player player = (Player) target;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
Tameable tameable = (Tameable) entity;
if (!UserManager.hasPlayerDataKey(player) || !CombatUtils.isFriendlyPet(player, tameable)) {
return;
}
// isFriendlyPet ensures that the Tameable is: Tamed, owned by a player,
// and the owner is in the same party
// So we can make some assumptions here, about our casting and our check
if (!(Permissions.friendlyFire(player) && Permissions.friendlyFire((Player) tameable.getOwner()))) {
event.setCancelled(true);
}
}
/**
* Handle PotionSplash events in order to fix broken Splash Potion of
* Saturation.
*
* @param event The event to process
*/
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onPotionSplash(PotionSplashEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
for (PotionEffect effect : ((PotionMeta) event.getPotion().getItem().getItemMeta()).getCustomEffects()) {
if (!effect.getType().equals(PotionEffectType.SATURATION)) {
return;
}
for (LivingEntity entity : event.getAffectedEntities()) {
int duration = (int) (effect.getDuration() * event.getIntensity(entity));
entity.addPotionEffect(new PotionEffect(effect.getType(), duration, effect.getAmplifier(), effect.isAmbient()));
}
}
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onPigZapEvent(PigZapEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
return;
if (event.getEntity().hasMetadata(mcMMO.entityMetadataKey)) {
event.getPigZombie().setMetadata(mcMMO.entityMetadataKey, mcMMO.metadataValue);
}
}
}

View File

@@ -0,0 +1,107 @@
package com.gmail.nossr50.listeners;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.subskills.AbstractSubSkill;
import com.gmail.nossr50.core.skills.subskills.interfaces.InteractType;
import com.gmail.nossr50.core.skills.subskills.interfaces.Interaction;
import com.gmail.nossr50.mcMMO;
import org.bukkit.event.Event;
import java.util.ArrayList;
import java.util.HashMap;
public class InteractionManager {
private static HashMap<InteractType, ArrayList<Interaction>> interactRegister;
private static HashMap<String, AbstractSubSkill> subSkillNameMap; //Used for mmoinfo optimization
private static ArrayList<AbstractSubSkill> subSkillList;
/**
* Registers subskills with the Interaction registration
*
* @param abstractSubSkill the target subskill to register
*/
public static void registerSubSkill(AbstractSubSkill abstractSubSkill) {
/* INIT MAPS */
if (interactRegister == null)
interactRegister = new HashMap<>();
if (subSkillList == null)
subSkillList = new ArrayList<>();
if (subSkillNameMap == null)
subSkillNameMap = new HashMap<>();
//Store a unique copy of each subskill
if (!subSkillList.contains(abstractSubSkill))
subSkillList.add(abstractSubSkill);
//Init ArrayList
if (interactRegister.get(abstractSubSkill.getInteractType()) == null)
interactRegister.put(abstractSubSkill.getInteractType(), new ArrayList<>());
//Registration array reference
ArrayList<Interaction> arrayRef = interactRegister.get(abstractSubSkill.getInteractType());
//Register skill
arrayRef.add(abstractSubSkill);
String lowerCaseName = abstractSubSkill.getConfigKeyName().toLowerCase();
//Register in name map
if (subSkillNameMap.get(lowerCaseName) == null)
subSkillNameMap.put(lowerCaseName, abstractSubSkill);
System.out.println("[mcMMO] registered subskill: " + abstractSubSkill.getConfigKeyName());
}
/**
* Grabs the registered abstract skill by its name
* Is not case sensitive
*
* @param name name of subskill, not case sensitive
* @return null if the subskill is not registered
*/
public static AbstractSubSkill getAbstractByName(String name) {
return subSkillNameMap.get(name.toLowerCase());
}
/**
* Processes the associated Interactions for this event
*
* @param event target event
* @param plugin instance of mcMMO plugin
* @param curInteractType the associated interaction type
*/
public static void processEvent(Event event, mcMMO plugin, InteractType curInteractType) {
for (Interaction interaction : interactRegister.get(curInteractType)) {
interaction.doInteraction(event, plugin);
}
}
/**
* Returns the list that contains all unique instances of registered Interaction classes
* Interactions are extensions of abstract classes that represent modifying behaviours in Minecraft through events
*
* @return the unique collection of all registered Interaction classes
*/
public static ArrayList<AbstractSubSkill> getSubSkillList() {
return subSkillList;
}
public static boolean hasSubSkill(String name) {
return getAbstractByName(name) != null;
}
public static boolean hasSubSkill(SubSkillType subSkillType) {
return hasSubSkill(subSkillType.getNiceNameNoSpaces(subSkillType));
}
/**
* Returns the associative map which contains all registered interactions
*
* @return the interact register
*/
public static HashMap<InteractType, ArrayList<Interaction>> getInteractRegister() {
return interactRegister;
}
}

View File

@@ -0,0 +1,456 @@
package com.gmail.nossr50.listeners;
import com.gmail.nossr50.core.config.MainConfig;
import com.gmail.nossr50.core.config.WorldBlacklist;
import com.gmail.nossr50.core.data.UserManager;
import com.gmail.nossr50.core.runnables.player.PlayerUpdateInventoryTask;
import com.gmail.nossr50.core.skills.PrimarySkillType;
import com.gmail.nossr50.core.skills.SubSkillType;
import com.gmail.nossr50.core.skills.primary.alchemy.Alchemy;
import com.gmail.nossr50.core.skills.primary.alchemy.AlchemyPotionBrewer;
import com.gmail.nossr50.core.util.ItemUtils;
import com.gmail.nossr50.core.util.Permissions;
import com.gmail.nossr50.core.util.skills.SkillUtils;
import com.gmail.nossr50.core.worldguard.WorldGuardManager;
import com.gmail.nossr50.core.worldguard.WorldGuardUtils;
import com.gmail.nossr50.core.events.fake.FakeBrewEvent;
import com.gmail.nossr50.mcMMO;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.block.Block;
import org.bukkit.block.BlockState;
import org.bukkit.block.BrewingStand;
import org.bukkit.block.Furnace;
import org.bukkit.entity.HumanEntity;
import org.bukkit.entity.Player;
import org.bukkit.event.EventHandler;
import org.bukkit.event.EventPriority;
import org.bukkit.event.Listener;
import org.bukkit.event.inventory.*;
import org.bukkit.inventory.*;
import org.bukkit.metadata.MetadataValue;
import java.util.List;
public class InventoryListener implements Listener {
private final mcMMO plugin;
public InventoryListener(final mcMMO plugin) {
this.plugin = plugin;
}
@EventHandler(priority = EventPriority.LOW, ignoreCancelled = true)
public void onInventoryOpen(InventoryOpenEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getPlayer().getWorld()))
return;
Block furnaceBlock = processInventoryOpenOrCloseEvent(event.getInventory());
if (furnaceBlock == null) {
return;
}
HumanEntity player = event.getPlayer();
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
if (!furnaceBlock.hasMetadata(mcMMO.furnaceMetadataKey) && furnaceBlock.getMetadata(mcMMO.furnaceMetadataKey).size() == 0)
furnaceBlock.setMetadata(mcMMO.furnaceMetadataKey, UserManager.getPlayer((Player) player).getPlayerMetadata());
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onInventoryClose(InventoryCloseEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getPlayer().getWorld()))
return;
Block furnaceBlock = processInventoryOpenOrCloseEvent(event.getInventory());
if (furnaceBlock == null || furnaceBlock.hasMetadata(mcMMO.furnaceMetadataKey)) {
return;
}
HumanEntity player = event.getPlayer();
if (!UserManager.hasPlayerDataKey(player)) {
return;
}
furnaceBlock.removeMetadata(mcMMO.furnaceMetadataKey, plugin);
}
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onFurnaceBurnEvent(FurnaceBurnEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
Block furnaceBlock = event.getBlock();
BlockState furnaceState = furnaceBlock.getState();
ItemStack smelting = furnaceState instanceof Furnace ? ((Furnace) furnaceState).getInventory().getSmelting() : null;
if (!ItemUtils.isSmeltable(smelting)) {
return;
}
Player player = getPlayerFromFurnace(furnaceBlock);
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
if (!UserManager.hasPlayerDataKey(player) || !Permissions.isSubSkillEnabled(player, SubSkillType.SMELTING_FUEL_EFFICIENCY)) {
return;
}
event.setBurnTime(UserManager.getPlayer(player).getSmeltingManager().fuelEfficiency(event.getBurnTime()));
}
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onFurnaceSmeltEvent(FurnaceSmeltEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
Block furnaceBlock = event.getBlock();
ItemStack smelting = event.getSource();
if (!ItemUtils.isSmeltable(smelting)) {
return;
}
Player player = getPlayerFromFurnace(furnaceBlock);
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
if (!UserManager.hasPlayerDataKey(player) || !PrimarySkillType.SMELTING.getPermissions(player)) {
return;
}
event.setResult(UserManager.getPlayer(player).getSmeltingManager().smeltProcessing(smelting, event.getResult()));
}
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
public void onFurnaceExtractEvent(FurnaceExtractEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getPlayer().getWorld()))
return;
Block furnaceBlock = event.getBlock();
if (!ItemUtils.isSmelted(new ItemStack(event.getItemType(), event.getItemAmount()))) {
return;
}
Player player = getPlayerFromFurnace(furnaceBlock);
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
if (!UserManager.hasPlayerDataKey(player) || !Permissions.vanillaXpBoost(player, PrimarySkillType.SMELTING)) {
return;
}
int exp = UserManager.getPlayer(player).getSmeltingManager().vanillaXPBoost(event.getExpToDrop());
event.setExpToDrop(exp);
}
@EventHandler(priority = EventPriority.NORMAL, ignoreCancelled = true)
public void onInventoryClickEventNormal(InventoryClickEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getWhoClicked().getWorld()))
return;
Inventory inventory = event.getInventory();
if (event.getWhoClicked() instanceof Player) {
Player player = ((Player) event.getWhoClicked()).getPlayer();
Block furnaceBlock = processInventoryOpenOrCloseEvent(event.getInventory());
if (furnaceBlock != null) {
if (furnaceBlock.getMetadata(mcMMO.furnaceMetadataKey).size() > 0)
furnaceBlock.removeMetadata(mcMMO.furnaceMetadataKey, mcMMO.p);
furnaceBlock.setMetadata(mcMMO.furnaceMetadataKey, UserManager.getPlayer(player).getPlayerMetadata());
}
}
if (!(inventory instanceof BrewerInventory)) {
return;
}
InventoryHolder holder = inventory.getHolder();
if (!(holder instanceof BrewingStand)) {
return;
}
HumanEntity whoClicked = event.getWhoClicked();
if (!UserManager.hasPlayerDataKey(event.getWhoClicked()) || !Permissions.isSubSkillEnabled(whoClicked, SubSkillType.ALCHEMY_CONCOCTIONS)) {
return;
}
Player player = (Player) whoClicked;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
BrewingStand stand = (BrewingStand) holder;
ItemStack clicked = event.getCurrentItem();
ItemStack cursor = event.getCursor();
if ((clicked != null && (clicked.getType() == Material.POTION || clicked.getType() == Material.SPLASH_POTION || clicked.getType() == Material.LINGERING_POTION)) || (cursor != null && (cursor.getType() == Material.POTION || cursor.getType() == Material.SPLASH_POTION || cursor.getType() == Material.LINGERING_POTION))) {
AlchemyPotionBrewer.scheduleCheck(player, stand);
return;
}
ClickType click = event.getClick();
InventoryType.SlotType slot = event.getSlotType();
if (click.isShiftClick()) {
switch (slot) {
case FUEL:
AlchemyPotionBrewer.scheduleCheck(player, stand);
return;
case CONTAINER:
case QUICKBAR:
if (!AlchemyPotionBrewer.isValidIngredient(player, clicked)) {
return;
}
if (!AlchemyPotionBrewer.transferItems(event.getView(), event.getRawSlot(), click)) {
return;
}
event.setCancelled(true);
AlchemyPotionBrewer.scheduleUpdate(inventory);
AlchemyPotionBrewer.scheduleCheck(player, stand);
return;
default:
return;
}
} else if (slot == InventoryType.SlotType.FUEL) {
boolean emptyClicked = AlchemyPotionBrewer.isEmpty(clicked);
if (AlchemyPotionBrewer.isEmpty(cursor)) {
if (emptyClicked && click == ClickType.NUMBER_KEY) {
AlchemyPotionBrewer.scheduleCheck(player, stand);
return;
}
AlchemyPotionBrewer.scheduleCheck(player, stand);
} else if (emptyClicked) {
if (AlchemyPotionBrewer.isValidIngredient(player, cursor)) {
int amount = cursor.getAmount();
if (click == ClickType.LEFT || (click == ClickType.RIGHT && amount == 1)) {
event.setCancelled(true);
event.setCurrentItem(cursor.clone());
event.setCursor(null);
AlchemyPotionBrewer.scheduleUpdate(inventory);
AlchemyPotionBrewer.scheduleCheck(player, stand);
} else if (click == ClickType.RIGHT) {
event.setCancelled(true);
ItemStack one = cursor.clone();
one.setAmount(1);
ItemStack rest = cursor.clone();
rest.setAmount(amount - 1);
event.setCurrentItem(one);
event.setCursor(rest);
AlchemyPotionBrewer.scheduleUpdate(inventory);
AlchemyPotionBrewer.scheduleCheck(player, stand);
}
}
}
}
}
@EventHandler(priority = EventPriority.NORMAL, ignoreCancelled = true)
public void onInventoryDragEvent(InventoryDragEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getWhoClicked().getWorld()))
return;
Inventory inventory = event.getInventory();
if (!(inventory instanceof BrewerInventory)) {
return;
}
InventoryHolder holder = inventory.getHolder();
if (!(holder instanceof BrewingStand)) {
return;
}
HumanEntity whoClicked = event.getWhoClicked();
if (!UserManager.hasPlayerDataKey(event.getWhoClicked()) || !Permissions.isSubSkillEnabled(whoClicked, SubSkillType.ALCHEMY_CONCOCTIONS)) {
return;
}
if (!event.getInventorySlots().contains(Alchemy.INGREDIENT_SLOT)) {
return;
}
ItemStack cursor = event.getCursor();
ItemStack ingredient = ((BrewerInventory) inventory).getIngredient();
if (AlchemyPotionBrewer.isEmpty(ingredient) || ingredient.isSimilar(cursor)) {
Player player = (Player) whoClicked;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
if (AlchemyPotionBrewer.isValidIngredient(player, cursor)) {
// Not handled: dragging custom ingredients over ingredient slot (does not trigger any event)
AlchemyPotionBrewer.scheduleCheck(player, (BrewingStand) holder);
return;
}
event.setCancelled(true);
AlchemyPotionBrewer.scheduleUpdate(inventory);
}
}
// Apparently sometimes vanilla brewing beats our task listener to the actual brew. We handle this by cancelling the vanilla event and finishing our brew ourselves.
@EventHandler(priority = EventPriority.LOWEST, ignoreCancelled = true)
public void onBrew(BrewEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getBlock().getWorld()))
return;
if (event instanceof FakeBrewEvent)
return;
Location location = event.getBlock().getLocation();
if (Alchemy.brewingStandMap.containsKey(location)) {
Alchemy.brewingStandMap.get(location).finishImmediately();
event.setCancelled(true);
}
}
@EventHandler(priority = EventPriority.NORMAL, ignoreCancelled = true)
public void onInventoryMoveItemEvent(InventoryMoveItemEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getSource().getLocation().getWorld()))
return;
Inventory inventory = event.getDestination();
if (!(inventory instanceof BrewerInventory)) {
return;
}
InventoryHolder holder = inventory.getHolder();
if (!(holder instanceof BrewingStand)) {
return;
}
ItemStack item = event.getItem();
if (MainConfig.getInstance().getPreventHopperTransferIngredients() && item.getType() != Material.POTION && item.getType() != Material.SPLASH_POTION && item.getType() != Material.LINGERING_POTION) {
event.setCancelled(true);
return;
}
if (MainConfig.getInstance().getPreventHopperTransferBottles() && (item.getType() == Material.POTION || item.getType() == Material.SPLASH_POTION || item.getType() == Material.LINGERING_POTION)) {
event.setCancelled(true);
return;
}
if (MainConfig.getInstance().getEnabledForHoppers() && AlchemyPotionBrewer.isValidIngredient(null, item)) {
AlchemyPotionBrewer.scheduleCheck(null, (BrewingStand) holder);
}
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onInventoryClickEvent(InventoryClickEvent event) {
SkillUtils.removeAbilityBuff(event.getCurrentItem());
if (event.getAction() == InventoryAction.HOTBAR_SWAP) {
SkillUtils.removeAbilityBuff(event.getWhoClicked().getInventory().getItem(event.getHotbarButton()));
}
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onInventoryOpenEvent(InventoryOpenEvent event) {
SkillUtils.removeAbilityBuff(event.getPlayer().getInventory().getItemInMainHand());
}
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onCraftItem(CraftItemEvent event) {
/* WORLD BLACKLIST CHECK */
if (WorldBlacklist.isWorldBlacklisted(event.getWhoClicked().getWorld()))
return;
final HumanEntity whoClicked = event.getWhoClicked();
if (!whoClicked.hasMetadata(mcMMO.playerDataKey)) {
return;
}
ItemStack result = event.getRecipe().getResult();
if (!ItemUtils.isMcMMOItem(result)) {
return;
}
Player player = (Player) whoClicked;
/* WORLD GUARD MAIN FLAG CHECK */
if (WorldGuardUtils.isWorldGuardLoaded()) {
if (!WorldGuardManager.getInstance().hasMainFlag(player))
return;
}
new PlayerUpdateInventoryTask((Player) whoClicked).runTaskLater(plugin, 0);
}
private Block processInventoryOpenOrCloseEvent(Inventory inventory) {
if (!(inventory instanceof FurnaceInventory)) {
return null;
}
Furnace furnace = (Furnace) inventory.getHolder();
if (furnace == null) {
return null;
}
return furnace.getBlock();
}
private Player getPlayerFromFurnace(Block furnaceBlock) {
List<MetadataValue> metadata = furnaceBlock.getMetadata(mcMMO.furnaceMetadataKey);
if (metadata.isEmpty()) {
return null;
}
return plugin.getServer().getPlayerExact(metadata.get(0).asString());
}
}

Some files were not shown because too many files have changed in this diff Show More