Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/console/src/core/CommandExecutor.cc @ 1434

Last change on this file since 1434 was 1434, checked in by landauf, 16 years ago

autocompletion is almost done

File size: 32.0 KB
RevLine 
[947]1/*
2 *   ORXONOX - the hottest 3D action shooter ever to exist
[1056]3 *                    > www.orxonox.net <
[947]4 *
5 *
6 *   License notice:
7 *
8 *   This program is free software; you can redistribute it and/or
9 *   modify it under the terms of the GNU General Public License
10 *   as published by the Free Software Foundation; either version 2
11 *   of the License, or (at your option) any later version.
12 *
13 *   This program is distributed in the hope that it will be useful,
14 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
15 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 *   GNU General Public License for more details.
17 *
18 *   You should have received a copy of the GNU General Public License
19 *   along with this program; if not, write to the Free Software
20 *   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
21 *
22 *   Author:
23 *      Fabian 'x3n' Landau
24 *   Co-authors:
25 *      ...
26 *
27 */
28
29#include "CommandExecutor.h"
30#include "ConsoleCommand.h"
31#include "util/String.h"
[1030]32#include "util/Convert.h"
[947]33#include "Identifier.h"
34#include "Language.h"
35#include "Debug.h"
[1198]36#include "TclBind.h"
[947]37
38namespace orxonox
39{
[949]40    CommandExecutor& CommandExecutor::getInstance()
41    {
42        static CommandExecutor instance;
43        return instance;
44    }
[947]45
[952]46    CommandEvaluation& CommandExecutor::getEvaluation()
47    {
48        return CommandExecutor::getInstance().evaluation_;
49    }
50
[1194]51    const CommandEvaluation& CommandExecutor::getLastEvaluation()
52    {
53        return CommandExecutor::getInstance().evaluation_;
54    }
55
[1341]56    ConsoleCommand& CommandExecutor::addConsoleCommandShortcut(ConsoleCommand* command)
[947]57    {
[1390]58        std::map<std::string, ConsoleCommand*>::const_iterator it = CommandExecutor::getInstance().consoleCommandShortcuts_.find(command->getName());
59        if (it != CommandExecutor::getInstance().consoleCommandShortcuts_.end())
60        {
61            COUT(2) << "Warning: Overwriting console-command shortcut with name " << command->getName() << "." << std::endl;
62        }
63
64
[1341]65        CommandExecutor::getInstance().consoleCommandShortcuts_[command->getName()] = command;
66        CommandExecutor::getInstance().consoleCommandShortcuts_LC_[getLowercase(command->getName())] = command;
67        return (*command);
[947]68    }
69
70    /**
71        @brief Returns the executor of a console command shortcut with given name.
72        @brief name The name of the requested console command shortcut
73        @return The executor of the requested console command shortcut
74    */
[1341]75    ConsoleCommand* CommandExecutor::getConsoleCommandShortcut(const std::string& name)
[947]76    {
[1341]77        std::map<std::string, ConsoleCommand*>::const_iterator it = CommandExecutor::getInstance().consoleCommandShortcuts_.find(name);
[951]78        if (it != CommandExecutor::getInstance().consoleCommandShortcuts_.end())
[947]79            return (*it).second;
80        else
81            return 0;
82    }
83
84    /**
85        @brief Returns the executor of a console command shortcut with given name in lowercase.
86        @brief name The name of the requested console command shortcut in lowercase
87        @return The executor of the requested console command shortcut
88    */
[1341]89    ConsoleCommand* CommandExecutor::getLowercaseConsoleCommandShortcut(const std::string& name)
[947]90    {
[1341]91        std::map<std::string, ConsoleCommand*>::const_iterator it = CommandExecutor::getInstance().consoleCommandShortcuts_LC_.find(name);
[951]92        if (it != CommandExecutor::getInstance().consoleCommandShortcuts_LC_.end())
[947]93            return (*it).second;
94        else
95            return 0;
96    }
97
[1198]98    bool CommandExecutor::execute(const std::string& command, bool useTcl)
[947]99    {
[1198]100        if (useTcl)
[1351]101            return TclBind::eval(command);
[947]102
[1402]103        CommandExecutor::parseIfNeeded(command);
[1351]104        return CommandExecutor::getEvaluation().execute();
[952]105    }
[948]106
[947]107    std::string CommandExecutor::complete(const std::string& command)
108    {
[1402]109        CommandExecutor::parseIfNeeded(command);
[1351]110        return CommandExecutor::getEvaluation().complete();
[952]111    }
[948]112
[947]113    std::string CommandExecutor::hint(const std::string& command)
114    {
[1402]115        CommandExecutor::parseIfNeeded(command);
[1351]116        return CommandExecutor::getEvaluation().hint();
[952]117    }
[948]118
[953]119    CommandEvaluation CommandExecutor::evaluate(const std::string& command)
[952]120    {
[1416]121        CommandExecutor::parse(command);
[967]122        CommandExecutor::getEvaluation().evaluateParams();
[952]123        return CommandExecutor::getEvaluation();
124    }
125
[1402]126    void CommandExecutor::parseIfNeeded(const std::string& command)
127    {
[1434]128std::cout << "parse if needed: command:      >" << command << "<" << std::endl;
129std::cout << "                 old original: >" << CommandExecutor::getEvaluation().originalCommand_ << "<" << std::endl;
130std::cout << "                 old modified: >" << CommandExecutor::getEvaluation().command_ << "<" << std::endl;
[1424]131        if (CommandExecutor::getEvaluation().state_ == CS_Uninitialized)
132        {
[1434]133std::cout << "parse if needed: parse!" << std::endl;
[1402]134            CommandExecutor::parse(command);
[1424]135        }
[1434]136        else if (/*removeTrailingWhitespaces*/(CommandExecutor::getEvaluation().originalCommand_) != /*removeTrailingWhitespaces*/(command))
[1424]137        {
138            if (CommandExecutor::getEvaluation().command_ == command)
139            {
[1434]140std::cout << "parse if needed: parse and set bNewCommand_ to false" << std::endl;
[1424]141                CommandExecutor::parse(command);
142                CommandExecutor::getEvaluation().bNewCommand_ = false;
143            }
144            else
145            {
[1434]146std::cout << "parse if needed: parse!" << std::endl;
[1424]147                CommandExecutor::parse(command);
148            }
149        }
[1434]150std::cout << "parse if needed: don't parse" << std::endl;
[1402]151    }
152
[947]153    void CommandExecutor::parse(const std::string& command, bool bInitialize)
154    {
[1427]155std::cout << "parse (" << bInitialize << "): command: >" << command << "<" << std::endl;
[947]156        if (bInitialize)
[1351]157            CommandExecutor::getEvaluation().initialize(command);
[947]158
[1417]159        CommandExecutor::getEvaluation().commandTokens_.split(command, " ", SubString::WhiteSpaces, false, '\\', false, '"', false, '(', ')', false, '\0');
160        CommandExecutor::getEvaluation().command_ = command;
[1351]161
[1417]162        switch (CommandExecutor::getEvaluation().state_)
[947]163        {
[1390]164            case CS_Uninitialized:
[1434]165std::cout << "0: Uninitialized\n";
[1402]166            {
[1390]167                // Impossible
168                break;
[1402]169            }
[1390]170            case CS_Empty:
[1434]171std::cout << "0: Empty\n";
[1402]172            {
[1424]173                if (CommandExecutor::argumentsGiven() == 0)
[1390]174                {
[1424]175                    CommandExecutor::createListOfPossibleFunctions("");
176                    CommandExecutor::createListOfPossibleIdentifiers("");
177                    break;
178                }
179                else
180                {
[1417]181                    CommandExecutor::getEvaluation().state_ = CS_ShortcutOrIdentifier;
[1424]182                    // Move on to next case
[1390]183                }
[1402]184            }
[1390]185            case CS_ShortcutOrIdentifier:
[1434]186std::cout << "0: ShortcutOrIdentifier\n";
[1402]187            {
[1424]188                if (CommandExecutor::argumentsGiven() > 1)
[1390]189                {
[1424]190                    // There's a finished first argument - check if it's a shortcut or a classname
191                    CommandExecutor::getEvaluation().function_ = CommandExecutor::getPossibleCommand(CommandExecutor::getArgument(0));
[1417]192                    CommandExecutor::getEvaluation().functionclass_ = CommandExecutor::getPossibleIdentifier(CommandExecutor::getArgument(0));
[1390]193
[1417]194                    if (CommandExecutor::getEvaluation().function_)
[1390]195                    {
[1424]196                        // It's a shortcut
[1427]197                        CommandExecutor::getEvaluation().state_ = CS_ParamPreparation;
[1424]198                        CommandExecutor::getEvaluation().functionclass_ = 0;
199                        // Move on to next case
[1390]200                    }
[1417]201                    else if (CommandExecutor::getEvaluation().functionclass_)
[1390]202                    {
[1434]203std::cout << "MEP" << std::endl;
[1424]204                        // It's a functionname
[1417]205                        CommandExecutor::getEvaluation().state_ = CS_Function;
[1424]206                        CommandExecutor::getEvaluation().function_ = 0;
207                        // Move on to next case
208                    }
209                    else
210                    {
211                        // The first argument is bad
212                        CommandExecutor::getEvaluation().state_ = CS_Error;
213                        AddLanguageEntry("commandexecutorunknownfirstargument", "is not a shortcut nor a classname");
214                        CommandExecutor::getEvaluation().errorMessage_ = "Error: " + CommandExecutor::getArgument(0) + " " + GetLocalisation("commandexecutorunknownfirstargument") + ".";
[1390]215                        return;
216                    }
217                }
[1424]218                else
219                {
220                    // There's no finished first argument - search possible shortcuts or classnames
221                    CommandExecutor::createListOfPossibleFunctions(CommandExecutor::getArgument(0));
222                    CommandExecutor::createListOfPossibleIdentifiers(CommandExecutor::getArgument(0));
[1390]223
[1424]224                    unsigned int num_functions = CommandExecutor::getEvaluation().listOfPossibleFunctions_.size();
225                    unsigned int num_identifiers = CommandExecutor::getEvaluation().listOfPossibleIdentifiers_.size();
[1402]226
[1424]227                    if (num_functions == 1 && num_identifiers == 0)
[1390]228                    {
[1424]229                        // It's a shortcut
230                        std::string functionname = *(*CommandExecutor::getEvaluation().listOfPossibleFunctions_.begin()).first;
231                        CommandExecutor::getEvaluation().function_ = CommandExecutor::getPossibleCommand(functionname);
232                        if (getLowercase(functionname) != getLowercase(CommandExecutor::getArgument(0)))
233                        {
234                            // Unfinished shortcut
235                            CommandExecutor::getEvaluation().bCommandChanged_ = true;
236                        }
[1427]237                        CommandExecutor::getEvaluation().state_ = CS_ParamPreparation;
[1424]238                        CommandExecutor::getEvaluation().functionclass_ = 0;
239                        CommandExecutor::getEvaluation().command_ = CommandExecutor::getEvaluation().function_->getName();
240                        if (CommandExecutor::getEvaluation().function_->getParamCount() > 0)
[1427]241                        {
[1424]242                            CommandExecutor::getEvaluation().command_ += " ";
[1427]243                            CommandExecutor::getEvaluation().bCommandChanged_ = true;
244                        }
[1424]245                        // Move on to next case
[1390]246                    }
[1424]247                    else if (num_identifiers == 1 && num_functions == 0)
[1390]248                    {
[1424]249                        // It's a classname
250                        std::string classname = *(*CommandExecutor::getEvaluation().listOfPossibleIdentifiers_.begin()).first;
251                        CommandExecutor::getEvaluation().functionclass_ = CommandExecutor::getPossibleIdentifier(classname);
252                        if (getLowercase(classname) != getLowercase(CommandExecutor::getArgument(0)))
253                        {
254                            // Unfinished classname
255                            CommandExecutor::getEvaluation().bCommandChanged_ = true;
256                        }
[1417]257                        CommandExecutor::getEvaluation().state_ = CS_Function;
[1424]258                        CommandExecutor::getEvaluation().function_ = 0;
259                        CommandExecutor::getEvaluation().command_ = CommandExecutor::getEvaluation().functionclass_->getName() + " ";
260                        // Move on to next case
261                    }
262                    else if (num_identifiers == 0 && num_functions == 0)
263                    {
264                        // No possibilities
265                        CommandExecutor::getEvaluation().state_ = CS_Error;
266                        AddLanguageEntry("commandexecutorunknownfirstargumentstart", "There is no command or classname starting with");
267                        CommandExecutor::getEvaluation().errorMessage_ = "Error: " + GetLocalisation("commandexecutorunknownfirstargumentstart") + " " + CommandExecutor::getArgument(0) + ".";
[1390]268                        return;
269                    }
[1424]270                    else
271                    {
272                        // There are several possiblilities
273                        std::list<std::pair<const std::string*, const std::string*> > temp;
274                        temp.insert(temp.end(), CommandExecutor::getEvaluation().listOfPossibleFunctions_.begin(), CommandExecutor::getEvaluation().listOfPossibleFunctions_.end());
275                        temp.insert(temp.end(), CommandExecutor::getEvaluation().listOfPossibleIdentifiers_.begin(), CommandExecutor::getEvaluation().listOfPossibleIdentifiers_.end());
276                        CommandExecutor::getEvaluation().command_ = CommandExecutor::getCommonBegin(temp);
277                        CommandExecutor::getEvaluation().function_ = CommandExecutor::getPossibleCommand(CommandExecutor::getArgument(0));
278                        CommandExecutor::getEvaluation().functionclass_ = CommandExecutor::getPossibleIdentifier(CommandExecutor::getArgument(0));
[1427]279                        CommandExecutor::getEvaluation().bCommandChanged_ = true;
[1424]280                        return;
281                    }
[1390]282                }
[1402]283            }
[1390]284            case CS_Function:
[1434]285std::cout << "0: Function\n";
[1402]286            {
[1424]287                if (CommandExecutor::getEvaluation().functionclass_)
[1390]288                {
[1424]289                    // There is a classname - search for the commandname
290                    if (CommandExecutor::argumentsGiven() > 2)
[1390]291                    {
[1424]292                        // There is a finished second argument - check if it's a commandname
[1417]293                        CommandExecutor::getEvaluation().function_ = CommandExecutor::getPossibleCommand(CommandExecutor::getArgument(1), CommandExecutor::getEvaluation().functionclass_);
[1390]294
[1417]295                        if (CommandExecutor::getEvaluation().function_)
[1390]296                        {
[1434]297std::cout << "MEP2" << std::endl;
[1424]298                            // It's a function
[1427]299                            CommandExecutor::getEvaluation().state_ = CS_ParamPreparation;
[1424]300                            // Move on to next case
[1390]301                        }
[1424]302                        else
[1402]303                        {
[1424]304                            // The second argument is bad
[1417]305                            CommandExecutor::getEvaluation().state_ = CS_Error;
[1424]306                            AddLanguageEntry("commandexecutorunknownsecondargument", "is not a function of");
307                            CommandExecutor::getEvaluation().errorMessage_ = "Error: " + CommandExecutor::getArgument(1) + " " + GetLocalisation("commandexecutorunknownsecondargument") + " " + CommandExecutor::getEvaluation().functionclass_->getName() + ".";
308                            return;
[1402]309                        }
[1390]310                    }
[1424]311                    else
[1390]312                    {
[1424]313                        // There is no finished second argument - search for possibilities
314                        CommandExecutor::createListOfPossibleFunctions(CommandExecutor::getArgument(1), CommandExecutor::getEvaluation().functionclass_);
315                        unsigned int num_functions = CommandExecutor::getEvaluation().listOfPossibleFunctions_.size();
[1390]316
[1424]317                        if (num_functions == 1)
[1390]318                        {
[1424]319                            // It's a function
320                            std::string functionname = *(*CommandExecutor::getEvaluation().listOfPossibleFunctions_.begin()).first;
321                            CommandExecutor::getEvaluation().function_ = CommandExecutor::getPossibleCommand(functionname, CommandExecutor::getEvaluation().functionclass_);
322                            if (getLowercase(functionname) != getLowercase(CommandExecutor::getArgument(1)))
323                            {
324                                // Unfinished function
325                                CommandExecutor::getEvaluation().bCommandChanged_ = true;
326                            }
[1427]327                            CommandExecutor::getEvaluation().state_ = CS_ParamPreparation;
[1424]328                            CommandExecutor::getEvaluation().command_ = CommandExecutor::getEvaluation().functionclass_->getName() + " " + CommandExecutor::getEvaluation().function_->getName();
329                            if (CommandExecutor::getEvaluation().function_->getParamCount() > 0)
[1427]330                            {
[1424]331                                CommandExecutor::getEvaluation().command_ += " ";
[1427]332                                CommandExecutor::getEvaluation().bCommandChanged_ = true;
333                            }
[1424]334                            // Move on to next case
[1390]335                        }
[1424]336                        else if (num_functions == 0)
[1402]337                        {
[1424]338                            // No possibilities
[1417]339                            CommandExecutor::getEvaluation().state_ = CS_Error;
[1424]340                            AddLanguageEntry("commandexecutorunknownsecondargumentstart", "has no function starting with");
341                            CommandExecutor::getEvaluation().errorMessage_ = "Error: " + CommandExecutor::getEvaluation().functionclass_->getName() + " " + GetLocalisation("commandexecutorunknownsecondargumentstart") + " " + CommandExecutor::getArgument(1) + ".";
[1390]342                            return;
343                        }
344                        else
345                        {
[1424]346                            // There are several possibilities
347                            CommandExecutor::getEvaluation().command_ = CommandExecutor::getEvaluation().functionclass_->getName() + " " + CommandExecutor::getCommonBegin(CommandExecutor::getEvaluation().listOfPossibleFunctions_);
348                            CommandExecutor::getEvaluation().function_ = CommandExecutor::getPossibleCommand(CommandExecutor::getArgument(1), CommandExecutor::getEvaluation().functionclass_);
[1427]349                            CommandExecutor::getEvaluation().bCommandChanged_ = true;
[1424]350                            return;
[1390]351                        }
352                    }
353                }
[1424]354                else
355                {
[1427]356                    // There is no classname - move on to CS_ParamPreparation
[1424]357                }
358            }
[1427]359std::cout << "1\n";
360            case CS_ParamPreparation:
361std::cout << "2\n";
362            {
363                if (CommandExecutor::getEvaluation().function_->getParamCount() == 0 || CommandExecutor::enoughArgumentsGiven(CommandExecutor::getEvaluation().function_))
364                {
365                    CommandExecutor::getEvaluation().state_ = CS_Finished;
366                    return;
367                }
368                else
369                {
[1430]370                    unsigned int argumentNumber = CommandExecutor::argumentsGiven() - 2;
[1427]371                    if (CommandExecutor::getEvaluation().functionclass_)
372                        argumentNumber -= 1;
373
[1430]374std::cout << "arglist: " << CommandExecutor::getLastArgument() << ", " << CommandExecutor::getEvaluation().function_->getName() << ", " << argumentNumber << std::endl;
[1427]375                    CommandExecutor::createListOfPossibleArguments(CommandExecutor::getLastArgument(), CommandExecutor::getEvaluation().function_, argumentNumber);
376                    CommandExecutor::getEvaluation().state_ = CS_Params;
377
378                    if (CommandExecutor::getEvaluation().bCommandChanged_)
379                    {
380                        // Don't do more than one change
381                        return;
382                    }
383                }
384            }
[1424]385            case CS_Params:
[1427]386std::cout << "3\n";
[1424]387            {
[1427]388                if (CommandExecutor::getEvaluation().listOfPossibleArguments_.size() == 1)
389                {
390std::cout << "3_1\n";
391                    // There is exactly one possible argument
[1434]392                    CommandExecutor::getEvaluation().argument_ = (*CommandExecutor::getEvaluation().listOfPossibleArguments_.begin()).second;
393                    CommandExecutor::getEvaluation().possibleArgument_ = (*CommandExecutor::getEvaluation().listOfPossibleArguments_.begin()).second;
[1427]394                    CommandExecutor::getEvaluation().state_ = CS_ParamPreparation;
395                    return;
396                }
397                else if (CommandExecutor::getEvaluation().listOfPossibleArguments_.size() == 0)
398                {
399std::cout << "3_2\n";
400                    // The user tries something new - we let him do
401                    CommandExecutor::getEvaluation().state_ = CS_ParamPreparation;
402                    CommandExecutor::getEvaluation().argument_ = CommandExecutor::getLastArgument();
403                    return;
404                }
405                else
406                {
407std::cout << "3_3\n";
408                    // There are several possibilities
[1434]409                    unsigned int argumentNumber = CommandExecutor::argumentsGiven();
410                    if (argumentNumber > 0)
411                        --argumentNumber;
412std::cout << "3_3_1\n";
413                    if (CommandExecutor::getEvaluation().functionclass_ && argumentNumber > 0)
414                        --argumentNumber;
[1427]415
[1434]416std::cout << "3_3_2\n";
[1427]417                    CommandExecutor::getEvaluation().argument_ = CommandExecutor::getCommonBegin(CommandExecutor::getEvaluation().listOfPossibleArguments_);
[1434]418std::cout << "3_3_3\n";
[1427]419                    CommandExecutor::getEvaluation().possibleArgument_ = CommandExecutor::getPossibleArgument(CommandExecutor::getLastArgument(), CommandExecutor::getEvaluation().function_, argumentNumber);
[1434]420std::cout << "3_3_4\n";
[1427]421                    CommandExecutor::getEvaluation().state_ = CS_ParamPreparation;
[1434]422std::cout << "3_3_5\n";
[1427]423                    return;
424                }
[1424]425            }
426            case CS_Finished:
[1427]427std::cout << "4\n";
[1424]428            {
429                // Nothing more to do
[1390]430                break;
[1402]431            }
[1390]432            case CS_Error:
[1424]433            {
434                // Bad, very bad
[1390]435                break;
[1424]436            }
[947]437        }
438    }
439
[1351]440    unsigned int CommandExecutor::argumentsFinished()
[947]441    {
[1424]442        unsigned int argumentsGiven = CommandExecutor::argumentsGiven();
443        if (argumentsGiven > 0)
444            return argumentsGiven - 1;
445        else
446            return 0;
[947]447    }
448
[1390]449    unsigned int CommandExecutor::argumentsGiven()
[947]450    {
[1424]451        if (CommandExecutor::getEvaluation().command_.size() > 0 && CommandExecutor::getEvaluation().command_[CommandExecutor::getEvaluation().command_.size() - 1] == ' ')
452            return CommandExecutor::getEvaluation().commandTokens_.size() + 1;
453        else
454            return CommandExecutor::getEvaluation().commandTokens_.size();
[1390]455    }
456
457    bool CommandExecutor::enoughArgumentsGiven(ConsoleCommand* command)
458    {
[1417]459        if (CommandExecutor::getEvaluation().functionclass_)
[1427]460            return (CommandExecutor::argumentsGiven() > (2 + command->getParamCount()));
[1390]461        else
[1427]462            return (CommandExecutor::argumentsGiven() > (1 + command->getParamCount()));
[1390]463    }
464
465    std::string CommandExecutor::getArgument(unsigned int index)
466    {
[1424]467        if (index < (CommandExecutor::getEvaluation().commandTokens_.size()))
[1417]468            return CommandExecutor::getEvaluation().commandTokens_[index];
[947]469        else
470            return "";
471    }
472
[1390]473    std::string CommandExecutor::getLastArgument()
[947]474    {
[1427]475        return CommandExecutor::getArgument(CommandExecutor::argumentsGiven() - 1);
[947]476    }
477
[1390]478    void CommandExecutor::createListOfPossibleIdentifiers(const std::string& fragment)
[1351]479    {
[1417]480        CommandExecutor::getEvaluation().listOfPossibleIdentifiers_.clear();
[1402]481        std::string lowercase = getLowercase(fragment);
[947]482        for (std::map<std::string, Identifier*>::const_iterator it = Identifier::getLowercaseIdentifierMapBegin(); it != Identifier::getLowercaseIdentifierMapEnd(); ++it)
483            if ((*it).second->hasConsoleCommands())
[1402]484                if ((*it).first.find(lowercase) == 0 || fragment == "")
[1417]485                    CommandExecutor::getEvaluation().listOfPossibleIdentifiers_.push_back(std::pair<const std::string*, const std::string*>(&(*it).first, &(*it).second->getName()));
[947]486
[1417]487        CommandExecutor::getEvaluation().listOfPossibleIdentifiers_.sort(CommandExecutor::compareStringsInList);
[947]488    }
489
490    void CommandExecutor::createListOfPossibleFunctions(const std::string& fragment, Identifier* identifier)
491    {
[1417]492        CommandExecutor::getEvaluation().listOfPossibleFunctions_.clear();
[1402]493        std::string lowercase = getLowercase(fragment);
[1351]494        if (!identifier)
[947]495        {
[1351]496            for (std::map<std::string, ConsoleCommand*>::const_iterator it = CommandExecutor::getLowercaseConsoleCommandShortcutMapBegin(); it != CommandExecutor::getLowercaseConsoleCommandShortcutMapEnd(); ++it)
[1402]497                if ((*it).first.find(lowercase) == 0 || fragment == "")
[1417]498                    CommandExecutor::getEvaluation().listOfPossibleFunctions_.push_back(std::pair<const std::string*, const std::string*>(&(*it).first, &(*it).second->getName()));
[947]499        }
[1351]500        else
[947]501        {
[1351]502            for (std::map<std::string, ConsoleCommand*>::const_iterator it = identifier->getLowercaseConsoleCommandMapBegin(); it != identifier->getLowercaseConsoleCommandMapEnd(); ++it)
[1402]503                if ((*it).first.find(lowercase) == 0 || fragment == "")
[1417]504                    CommandExecutor::getEvaluation().listOfPossibleFunctions_.push_back(std::pair<const std::string*, const std::string*>(&(*it).first, &(*it).second->getName()));
[947]505        }
[1402]506
[1417]507        CommandExecutor::getEvaluation().listOfPossibleFunctions_.sort(CommandExecutor::compareStringsInList);
[947]508    }
509
[1390]510    void CommandExecutor::createListOfPossibleArguments(const std::string& fragment, ConsoleCommand* command, unsigned int param)
511    {
[1430]512        CommandExecutor::createArgumentCompletionList(command, param);
513
[1417]514        CommandExecutor::getEvaluation().listOfPossibleArguments_.clear();
[1402]515        std::string lowercase = getLowercase(fragment);
[1430]516        for (std::list<std::pair<std::string, std::string> >::const_iterator it = command->getArgumentCompletionListBegin(); it != command->getArgumentCompletionListEnd(); ++it)
[1402]517            if ((*it).first.find(lowercase) == 0 || fragment == "")
[1434]518                CommandExecutor::getEvaluation().listOfPossibleArguments_.push_back(std::pair<std::string, std::string>((*it).first, (*it).second));
[1390]519
[1434]520        CommandExecutor::getEvaluation().listOfPossibleArguments_.sort(CommandExecutor::compareStringsInList2);
[1390]521    }
522
[1351]523    Identifier* CommandExecutor::getPossibleIdentifier(const std::string& name)
[947]524    {
[1402]525        std::string lowercase = getLowercase(name);
526        std::map<std::string, Identifier*>::const_iterator it = Identifier::getLowercaseIdentifierMap().find(lowercase);
[947]527        if ((it != Identifier::getLowercaseIdentifierMapEnd()) && (*it).second->hasConsoleCommands())
528            return (*it).second;
529
530        return 0;
531    }
532
[1351]533    ConsoleCommand* CommandExecutor::getPossibleCommand(const std::string& name, Identifier* identifier)
[947]534    {
[1402]535        std::string lowercase = getLowercase(name);
[1351]536        if (!identifier)
[955]537        {
[1402]538            std::map<std::string, ConsoleCommand*>::const_iterator it = CommandExecutor::getLowercaseConsoleCommandShortcutMap().find(lowercase);
[1351]539            if (it != CommandExecutor::getLowercaseConsoleCommandShortcutMapEnd())
540                return (*it).second;
[955]541        }
[1351]542        else
[947]543        {
[1402]544            std::map<std::string, ConsoleCommand*>::const_iterator it = identifier->getLowercaseConsoleCommandMap().find(lowercase);
[1351]545            if (it != identifier->getLowercaseConsoleCommandMapEnd())
546                return (*it).second;
[947]547        }
[1351]548        return 0;
[947]549    }
550
[1427]551    std::string CommandExecutor::getPossibleArgument(const std::string& name, ConsoleCommand* command, unsigned int param)
[1390]552    {
[1434]553std::cout << "4_1\n";
[1430]554        CommandExecutor::createArgumentCompletionList(command, param);
555
[1434]556std::cout << "4_2\n";
[1402]557        std::string lowercase = getLowercase(name);
[1434]558std::cout << "4_3\n";
[1430]559        for (std::list<std::pair<std::string, std::string> >::const_iterator it = command->getArgumentCompletionListBegin(); it != command->getArgumentCompletionListEnd(); ++it)
[1434]560        {
561std::cout << "4_4\n";
[1402]562            if ((*it).first == lowercase)
[1427]563                return (*it).second;
[1434]564        }
[1390]565
[1434]566std::cout << "4_5\n";
567        return "";
[1390]568    }
569
[1430]570    void CommandExecutor::createArgumentCompletionList(ConsoleCommand* command, unsigned int param)
571    {
572        std::string params[5];
573
574        unsigned int index = 0;
575        unsigned int lowestIndex = 1 + (CommandExecutor::getEvaluation().functionclass_ != 0);
576
577        for (unsigned int i = CommandExecutor::argumentsGiven() - 2; i >= lowestIndex; --i)
578        {
579            params[index] = CommandExecutor::getArgument(i);
580            ++index;
581            if (index >= 5)
582                break;
583        }
584
585        command->createArgumentCompletionList(param, params[0], params[1], params[2], params[3], params[4]);
586    }
587
[1424]588    std::string CommandExecutor::getCommonBegin(const std::list<std::pair<const std::string*, const std::string*> >& list)
589    {
590        if (list.size() == 0)
591        {
592            return "";
593        }
594        else if (list.size() == 1)
595        {
596            return ((*(*list.begin()).first) + " ");
597        }
598        else
599        {
600            std::string output = "";
601            for (unsigned int i = 0; true; i++)
602            {
603                char temp = 0;
604                for (std::list<std::pair<const std::string*, const std::string*> >::const_iterator it = list.begin(); it != list.end(); ++it)
605                {
606                    if ((*(*it).first).size() > i)
607                    {
608                        if (it == list.begin())
609                        {
610                            temp = (*(*it).first)[i];
611                        }
612                        else
613                        {
614                            if (temp != (*(*it).first)[i])
615                                return output;
616                        }
617                    }
618                    else
619                    {
620                        return output;
621                    }
622                }
623                output += temp;
624            }
625            return output;
626        }
627    }
628
[1434]629    std::string CommandExecutor::getCommonBegin(const std::list<std::pair<std::string, std::string> >& list)
630    {
631        if (list.size() == 0)
632        {
633            return "";
634        }
635        else if (list.size() == 1)
636        {
637            return ((*list.begin()).first + " ");
638        }
639        else
640        {
641            std::string output = "";
642            for (unsigned int i = 0; true; i++)
643            {
644                char temp = 0;
645                for (std::list<std::pair<std::string, std::string> >::const_iterator it = list.begin(); it != list.end(); ++it)
646                {
647                    if ((*it).first.size() > i)
648                    {
649                        if (it == list.begin())
650                        {
651                            temp = (*it).first[i];
652                        }
653                        else
654                        {
655                            if (temp != (*it).first[i])
656                                return output;
657                        }
658                    }
659                    else
660                    {
661                        return output;
662                    }
663                }
664                output += temp;
665            }
666            return output;
667        }
668    }
669
[1351]670    bool CommandExecutor::compareStringsInList(const std::pair<const std::string*, const std::string*>& first, const std::pair<const std::string*, const std::string*>& second)
[947]671    {
[1351]672        return ((*first.first) < (*second.first));
[947]673    }
[1434]674
675    bool CommandExecutor::compareStringsInList2(const std::pair<std::string, std::string>& first, const std::pair<std::string, std::string>& second)
676    {
677        return (first.first < second.first);
678    }
[947]679}
Note: See TracBrowser for help on using the repository browser.