@@ -63,6 +63,25 @@ class CliMenu
6363 */
6464 protected $ parent ;
6565
66+ /**
67+ * @var array
68+ */
69+ protected $ defaultControlMappings = [
70+ '^P ' => InputCharacter::UP ,
71+ 'k ' => InputCharacter::UP ,
72+ '^K ' => InputCharacter::DOWN ,
73+ 'j ' => InputCharacter::DOWN ,
74+ "\r" => InputCharacter::ENTER ,
75+ ' ' => InputCharacter::ENTER ,
76+ 'l ' => InputCharacter::LEFT ,
77+ 'm ' => InputCharacter::RIGHT ,
78+ ];
79+
80+ /**
81+ * @var array
82+ */
83+ protected $ customControlMappings = [];
84+
6685 /**
6786 * @var Frame
6887 */
@@ -180,6 +199,30 @@ private function selectFirstItem() : void
180199 }
181200 }
182201
202+ /**
203+ * Adds a custom control mapping
204+ */
205+ public function addCustomControlMapping (string $ input , callable $ callable ) : void
206+ {
207+ if (isset ($ this ->defaultControlMappings [$ input ]) || isset ($ this ->customControlMappings [$ input ])) {
208+ throw new \InvalidArgumentException ('Cannot rebind this input. ' );
209+ }
210+
211+ $ this ->customControlMappings [$ input ] = $ callable ;
212+ }
213+
214+ /**
215+ * Removes a custom control mapping
216+ */
217+ public function removeCustomControlMapping (string $ input ) : void
218+ {
219+ if (!isset ($ this ->customControlMappings [$ input ])) {
220+ throw new \InvalidArgumentException ('This input is not registered. ' );
221+ }
222+
223+ unset($ this ->customControlMappings [$ input ]);
224+ }
225+
183226 /**
184227 * Display menu and capture input
185228 */
@@ -188,17 +231,14 @@ private function display() : void
188231 $ this ->draw ();
189232
190233 $ reader = new NonCanonicalReader ($ this ->terminal );
191- $ reader ->addControlMappings ([
192- '^P ' => InputCharacter::UP ,
193- 'k ' => InputCharacter::UP ,
194- '^K ' => InputCharacter::DOWN ,
195- 'j ' => InputCharacter::DOWN ,
196- "\r" => InputCharacter::ENTER ,
197- ' ' => InputCharacter::ENTER ,
198- ]);
234+ $ reader ->addControlMappings ($ this ->defaultControlMappings );
199235
200236 while ($ this ->isOpen () && $ char = $ reader ->readCharacter ()) {
201237 if (!$ char ->isHandledControl ()) {
238+ $ rawChar = $ char ->get ();
239+ if (isset ($ this ->customControlMappings [$ rawChar ])) {
240+ $ this ->customControlMappings [$ rawChar ]($ this );
241+ }
202242 continue ;
203243 }
204244
0 commit comments