/*
 * This file is part of CraftoPlugin, licensed under the MIT License (MIT).
 *
 * Copyright (c) 2019 CraftolutionDE <https://craftolution.de>
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in all
 * copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 * SOFTWARE.
 *
 * Website: https://craftolution.de/
 * Contact: support@craftolution.de
 */
package de.craftolution.craftoplugin.module.chat;

import de.craftolution.craftoplugin.core.annotations.Dependencies;
import de.craftolution.craftoplugin.core.element.Provider;
import de.craftolution.craftoplugin.module.chat.block.BlockManager;
import de.craftolution.craftoplugin.module.chat.formatter.ChatFormatter;
import de.craftolution.craftoplugin.module.chat.formatter.ChatMessageFormatter;
import de.craftolution.craftoplugin.module.chat.formatter.PrefixUtils;
import de.craftolution.craftoplugin.module.chat.last.LastManager;
import de.craftolution.craftoplugin.module.chat.mute.MuteManager;
import de.craftolution.craftoplugin.module.chat.staffchat.StaffChatComponent;
import de.craftolution.craftoplugin.module.chat.storage.ChatStorage;
import de.craftolution.craftoplugin.module.chat.whisper.WhisperManager;
import de.craftolution.craftoplugin.service.database.DatabaseService;
import de.craftolution.craftoplugin.service.log.LogService;
import de.craftolution.craftoplugin.service.messenger.Messenger;
import de.craftolution.craftoplugin.service.messenger.text.Text;
import de.craftolution.craftoplugin.service.module.Module;
import de.craftolution.craftoplugin.service.module.ModuleService;
import de.craftolution.craftoplugin.service.module.annotation.Register;
import de.craftolution.craftoplugin.service.playerstorage.PlayerStorageService;
import de.craftolution.craftoplugin.service.playerstorage.StoredPlayer;
import org.bukkit.Bukkit;
import org.bukkit.entity.Player;

import java.util.UUID;

@Dependencies({LogService.class, DatabaseService.class, PlayerStorageService.class})
public class ChatModule extends Module {

	@Register ChatStorage storage;
	@Register ChatLogger logger;
	@Register BlockManager blockManager;
	@Register MuteManager muteManager;
	@Register LastManager lastManager;
	@Register WhisperManager whisperManager;
	@Register ChatFormatter formatter;
	@Register StaffChatComponent staffChatComponent;

	// --- SAY --------------------------------------------------------------------------------------------------------

	public void say(Player player, String chatMessage) {
		say(PrefixUtils.findPrefix(player), StoredPlayer.get(player), chatMessage);
	}

	public void say(Text prefix, StoredPlayer sender, String chatMessage) {
		Text text = ChatMessageFormatter.createText(sender.getName(), prefix, chatMessage);

		// Send to players individually
		for (final Player recipient : Bukkit.getOnlinePlayers()) {
			if (hasBlocked(StoredPlayer.get(recipient), sender)) { continue; } // Skip if recipient blocked sender

			Messenger.send(recipient, text);
		}
	}

	public void say(Text prefix, String senderName, String chatMessage) {
		Text text = ChatMessageFormatter.createText(senderName, prefix, chatMessage);

		// Send to players individually
		for (final Player recipient : Bukkit.getOnlinePlayers()) {
			Messenger.send(recipient, text);
		}
	}

	// --- MISC -------------------------------------------------------------------------------------------------------

	public boolean isMuted(UUID playerId) {
		return this.muteManager.isMuted(StoredPlayer.getOrThrow(playerId));
	}

	public boolean hasBlocked(StoredPlayer blocker, StoredPlayer blocked) {
		return this.blockManager.hasBlocked(blocker, blocked);
	}

	public boolean hasBlocked(Player recipient, Player sender) {
		return this.hasBlocked(StoredPlayer.get(recipient), StoredPlayer.get(sender));
	}

	public void whisper(StoredPlayer sender, StoredPlayer recipient, String msg) {
		this.whisperManager.sendWhisper(sender, recipient, msg);
	}

	// --- ACCESSOR ---------------------------------------------------------------------------------------------------

	public static Provider<ChatModule> instance() {
		return ModuleService.instance().get().getModule(ChatModule.class);
	}

}

