1 /**
2     Console
3 
4     Copyright: (c) Enalye 2017
5     License: Zlib
6     Authors: Enalye
7 */
8 
9 module atelier.ui.console.console;
10 
11 import atelier.common, atelier.core, atelier.render;
12 import atelier.ui.list, atelier.ui.gui_element, atelier.ui.layout, atelier.ui.inputfield;
13 import atelier.ui.gui_overlay, atelier.ui.text, atelier.ui.gui_manager;
14 /*
15 private {
16 	Console _console;
17 	ConsoleHandler _consoleHandler;
18 
19 	alias FunctionCallback = void function(string[]);
20 }
21 
22 void setupConsole(string invokeKey) {
23 	_consoleHandler = new ConsoleHandler(invokeKey);
24 	_console = new Console;
25 	addRootGui(_consoleHandler);
26 }
27 
28 void addConsoleCmd(string cmd, GuiElementCallback callback) {
29 	if(!_console)
30 		return;
31 	_console.addCmd(cmd, callback);
32 }
33 
34 void addConsoleCmd(string cmd, FunctionCallback callback) {
35 	if(!_console)
36 		return;
37 	_console.addCmd(cmd, callback);
38 }
39 
40 void removeConsoleCmd(string cmd) {
41 	if(!_console)
42 		return;
43 	_console.removeCmd(cmd);
44 }
45 
46 void logConsole(string log) {
47 	if(!_console)
48 		return;
49 	_console.addMessage(log);
50 }
51 
52 private class ConsoleHandler: GuiElement {
53 	private {
54 		bool _isToggled = false;
55 		string _invokeKey;
56 		Timer _timer;
57 	}
58 
59 	this(string invokeKey) {
60 		_invokeKey = invokeKey;
61 	}
62 
63 	override void onEvent(Event event) {}
64 
65 	override void update(float deltaTime) {
66 		if(_invokeKey.length && getKeyDown(_invokeKey))
67 			toggleConsole();
68 
69 		if(_timer.isRunning) {
70 			_timer.update(deltaTime);
71 			_console.position = lerp(
72 				Vec2f(_console.size.x /2f, -_console.size.y / 2f),
73 				_console.size / 2f,
74 				easeInOutSine(_timer.value01));
75 
76 			if(!_timer.isRunning && !_isToggled)
77 				stopOverlay();
78 		}
79 	}
80 
81 	override void draw() {}
82 
83 	void toggleConsole() {
84 		_isToggled = !_isToggled;
85 		if(_isToggled) {
86 			_console.setup();
87 			if(!_timer.isRunning) {
88 				setOverlay(_console);
89 				_timer.start(.25f);
90 			}
91 			else
92 				_timer.isReversed = false;
93 		}
94 		else {
95 			if(!_timer.isRunning)
96 				_timer.startReverse(.25f);
97 			else
98 				_timer.isReversed = true;
99 		}
100 	}
101 }
102 
103 private class Console: AnchoredLayout {
104 	private {
105 		LogList _log;
106 		InputField _inputField;
107 		GuiElementCallback[string] _widgetCallbacks;
108 		FunctionCallback[string] _functionCallbacks;
109 		Sprite _background;
110 	}
111 
112 	this() {
113 		size = Vec2f(screenWidth, screenHeight / 2f);
114 
115 		float inputFieldRatio = 25f / size.y;
116 		float inputFieldHeight = size.y * inputFieldRatio;
117 
118 		_inputField = new InputField(Vec2f(size.x, inputFieldHeight));
119 		_log = new LogList(size - Vec2f(0f, inputFieldHeight));
120 		
121 		_background = fetch!Sprite("gui_texel");
122 		_background.size = size;
123 
124 		addChildGui(_log, Vec2f(.5f, .5f - inputFieldRatio / 2f), Vec2f(1f, 1f - inputFieldRatio));
125 		addChildGui(_inputField, Vec2f(.5f, 1f - inputFieldRatio / 2f), Vec2f(1f, inputFieldRatio));
126 	}
127 
128 	override void onEvent(Event event) {
129 		super.onEvent(event);
130 
131 		switch(event.type) with(EventType) {
132 		case keyEnter:
133 			if(_inputField.hasFocus) {
134 				string text = _inputField.text;
135 				if(text.length) {
136 					parse(text);
137 					_inputField.clear();
138 				}
139 			}
140 			break;
141 		default:
142 			break;
143 		}
144 	}
145 
146 	override void draw() {
147 		_background.texture.setColorMod(Color.black * .25f);
148 		_background.draw(center);
149 		super.draw();
150 	}
151 
152 	void setup() {
153 		_inputField.hasFocus = true;
154 	}
155 
156 	void addCmd(string cmd, GuiElementCallback callback) {
157 		_widgetCallbacks[cmd] = callback;
158 	}
159 
160 	void addCmd(string cmd, FunctionCallback callback) {
161 		_functionCallbacks[cmd] = callback;
162 	}
163 
164 	void removeCmd(string cmd) {
165 		_widgetCallbacks.remove(cmd);
166 		_functionCallbacks.remove(cmd);
167 	}
168 
169 	void addMessage(string message) {
170 		//The bold tag is temporary since the font in LogList is not properly rendered.
171 		_log.addChildGui(new Text("{b}" ~ message));
172 	}
173 
174 	protected void parse(string text) {
175 		import std.array: split;
176 		auto parameters = text.split;
177 		if(!parameters.length)
178 			return;
179 		auto widgetCallback = parameters[0] in _widgetCallbacks;
180 		if(widgetCallback) {
181 			Event event;
182 			event.type = EventType.callback;
183 			event.id = (*widgetCallback).id;
184 			event.sarray = parameters[1..$];
185 			(*widgetCallback).widget.onEvent(event);
186 			return;
187 		}
188 		auto functionCallback = parameters[0] in _functionCallbacks;
189 		if(functionCallback) {
190 			(*functionCallback)(parameters[1..$]);
191 			return;
192 		}		
193 		addMessage("Invalid command \'" ~ parameters[0] ~ "\'.");
194 	}
195 }*/