// Path: src/main/java/info/deskchan/core/ResponseListener.java
// public interface ResponseListener {
// 	
// 	void handle(String sender, Object data);
// 	
// }


import groovy.lang.Closure;
import groovy.lang.Script;
import info.deskchan.core.Path;
import info.deskchan.core.PluginProperties;
import info.deskchan.core.PluginProxyInterface;
import info.deskchan.core.ResponseListener;
import java.util.*;
import java.util.concurrent.atomic.AtomicReference;
import java.util.function.Function;
package info.deskchan.groovy_support;



public abstract class Scenario extends Script{

    /** Object containing last user input.
     *  It has complex map structure, so we store it here instead of giving it right to user. */
    private Answer answer;

    /** Default help message in answer dialog. */
    private static final String DEFAULT_HELP = ScenarioPlugin.pluginProxy.getString("write-anything");

    /** Variable containing is current thread was interrupted. **/
    private volatile boolean interrupted = false;

    /** Thread locking object. **/
    private final Locker lock = new Locker();
    
    private PluginProxyInterface pluginProxy = null;
    private Object data = null;

    /** Get data passed by owner of plugin. **/
    public Object getPassedData(){ return data; }

    /** Sets Plugin Proxy for this scenario. Should be called only from scenario initializer. **/
    protected void initialize(PluginProxyInterface proxy, Object data){
        if (pluginProxy != null)
            throw new RuntimeException("This method should be called only once and from scenario initializer, it's not accessable anymore.");
        this.pluginProxy = proxy;
        this.data = data;
    }


    // Standard plugin API

    protected void sendMessage(String tag) {
        pluginProxy.sendMessage(tag, null);
    }

    protected void sendMessage(String tag, Object data) {
        pluginProxy.sendMessage(tag, data);
    }

    protected String getString(String key){
        return pluginProxy.getString(key);
    }

    protected Path getDataDirPath() {
        return pluginProxy.getDataDirPath();
    }

    protected Path getPluginDirPath() {
        return pluginProxy.getPluginDirPath();
    }

    protected Path getRootDirPath() {
        return pluginProxy.getRootDirPath();
    }

    protected Path getAssetsDirPath() {
        return pluginProxy.getAssetsDirPath();
    }

    protected void log(Object text) {
        pluginProxy.log(text.toString());
    }

    protected void log(Throwable e) {
        pluginProxy.log(e);
    }

    protected PluginProperties getProperties() { return pluginProxy.getProperties(); }



    protected void alert(String text) {
        pluginProxy.sendMessage("DeskChan:show-technical", new HashMap(){{
            put("text", text);
        }});
    }
    protected void alert(String name, String text) {
        pluginProxy.sendMessage("DeskChan:show-technical", new HashMap(){{
            put("name", name);
            put("text", text);
            put("priority", messagePriority);
        }});
    }

    protected void say(String text){
        pluginProxy.sendMessage("DeskChan:request-say", new HashMap(){{
            put("text", text);
            put("characterImage", currentSprite);
            put("priority", messagePriority);
            put("skippable", false);
        }}, (sender, data) -> {
            pluginProxy.sendMessage("DeskChan:say", data, (sender1, data1) -> {
                lock.unlock();
            });
        });
        lock.lock();
    }

    protected void requestPhrase(String intent){
        pluginProxy.sendMessage("DeskChan:request-say", new HashMap(){{
            put("intent", intent);
            put("priority", messagePriority);
            put("skippable", false);
        }});
    }

    /** Current sprite forced by this scenario. **/
    private String currentSprite = "normal";
    protected void sprite(String text){
        currentSprite = text;
        pluginProxy.sendMessage("gui:set-image", text);
    }

    /** Priority of all messages sent by this scenario. All messages with lower priority will be skipped. **/
    private int messagePriority = 2500;
    protected int setMessagePriority(int val){
        return (messagePriority = val);
    }
    public int getMessagePriority(){ return messagePriority; }

// Path: src/main/java/info/deskchan/core/ResponseListener.java
// public interface ResponseListener {
// 	
// 	void handle(String sender, Object data);
// 	
// }


// Path: src/main/java/info/deskchan/groovy_support/Scenario.java
import groovy.lang.Closure;
import groovy.lang.Script;
import info.deskchan.core.Path;
import info.deskchan.core.PluginProperties;
import info.deskchan.core.PluginProxyInterface;
import info.deskchan.core.ResponseListener;
import java.util.*;
import java.util.concurrent.atomic.AtomicReference;
import java.util.function.Function;

package info.deskchan.groovy_support;



public abstract class Scenario extends Script{

    /** Object containing last user input.
     *  It has complex map structure, so we store it here instead of giving it right to user. */
    private Answer answer;

    /** Default help message in answer dialog. */
    private static final String DEFAULT_HELP = ScenarioPlugin.pluginProxy.getString("write-anything");

    /** Variable containing is current thread was interrupted. **/
    private volatile boolean interrupted = false;

    /** Thread locking object. **/
    private final Locker lock = new Locker();
    
    private PluginProxyInterface pluginProxy = null;
    private Object data = null;

    /** Get data passed by owner of plugin. **/
    public Object getPassedData(){ return data; }

    /** Sets Plugin Proxy for this scenario. Should be called only from scenario initializer. **/
    protected void initialize(PluginProxyInterface proxy, Object data){
        if (pluginProxy != null)
            throw new RuntimeException("This method should be called only once and from scenario initializer, it's not accessable anymore.");
        this.pluginProxy = proxy;
        this.data = data;
    }


    // Standard plugin API

    protected void sendMessage(String tag) {
        pluginProxy.sendMessage(tag, null);
    }

    protected void sendMessage(String tag, Object data) {
        pluginProxy.sendMessage(tag, data);
    }

    protected String getString(String key){
        return pluginProxy.getString(key);
    }

    protected Path getDataDirPath() {
        return pluginProxy.getDataDirPath();
    }

    protected Path getPluginDirPath() {
        return pluginProxy.getPluginDirPath();
    }

    protected Path getRootDirPath() {
        return pluginProxy.getRootDirPath();
    }

    protected Path getAssetsDirPath() {
        return pluginProxy.getAssetsDirPath();
    }

    protected void log(Object text) {
        pluginProxy.log(text.toString());
    }

    protected void log(Throwable e) {
        pluginProxy.log(e);
    }

    protected PluginProperties getProperties() { return pluginProxy.getProperties(); }



    protected void alert(String text) {
        pluginProxy.sendMessage("DeskChan:show-technical", new HashMap(){{
            put("text", text);
        }});
    }
    protected void alert(String name, String text) {
        pluginProxy.sendMessage("DeskChan:show-technical", new HashMap(){{
            put("name", name);
            put("text", text);
            put("priority", messagePriority);
        }});
    }

    protected void say(String text){
        pluginProxy.sendMessage("DeskChan:request-say", new HashMap(){{
            put("text", text);
            put("characterImage", currentSprite);
            put("priority", messagePriority);
            put("skippable", false);
        }}, (sender, data) -> {
            pluginProxy.sendMessage("DeskChan:say", data, (sender1, data1) -> {
                lock.unlock();
            });
        });
        lock.lock();
    }

    protected void requestPhrase(String intent){
        pluginProxy.sendMessage("DeskChan:request-say", new HashMap(){{
            put("intent", intent);
            put("priority", messagePriority);
            put("skippable", false);
        }});
    }

    /** Current sprite forced by this scenario. **/
    private String currentSprite = "normal";
    protected void sprite(String text){
        currentSprite = text;
        pluginProxy.sendMessage("gui:set-image", text);
    }

    /** Priority of all messages sent by this scenario. All messages with lower priority will be skipped. **/
    private int messagePriority = 2500;
    protected int setMessagePriority(int val){
        return (messagePriority = val);
    }
    public int getMessagePriority(){ return messagePriority; }

    public ResponseListener interruptListener = new ResponseListener() {