При программировании на C / C ++ у меня иногда был словарь со ссылками на функции по указанным ключам. Однако я действительно не знаю, как сделать что-то подобное в C #, позволяющее использовать динамические ключи .

Я работаю над Unity, и я хотел бы, например, вызывать функцию, когда я нажимаю левую кнопку мыши на моем проекте Unity, возможно ли это?

Буду очень признателен за каждый комментарий по этому поводу.

2
Néo 7 Сен 2016 в 11:23

3 ответа

Лучший ответ

Для этого вы можете использовать подпись Dictionary<KeyCode, System.Action>. Получите все коды кода и сохраните их в массиве с помощью System.Enum.GetValues(typeof(KeyCode));. Затем вы можете связать свои клавиши со своими функциями с помощью keyCodeToFuncDic.Add(KeyCode.YourKeyCode, YourFunction);

В функции Update используйте цикл for, чтобы перебрать KeyCodes, сохраненный в начале. Проверьте, нажата ли какая-либо из этих клавиш. Если нажата, проверьте, находится ли он в Dictionary. Если эти KeyCode существуют в словаре, используйте нажатую клавишу для Invoke функции в значении Dictionary, которая в конечном итоге вызовет функцию, которая хранится в Dictionary .

Код:

Dictionary<KeyCode, System.Action> keyCodeToFuncDic = new Dictionary<KeyCode, System.Action>();
Array allKeyCodes;

void Start()
{
    //Get all codecodes
    allKeyCodes = System.Enum.GetValues(typeof(KeyCode));

    //Register Keycodes to functios
    keyCodeToFuncDic.Add(KeyCode.Mouse0, myFunction); //Left mouse
    keyCodeToFuncDic.Add(KeyCode.Mouse1, myFunction2); //Right mouse
}

void myFunction()
{
    Debug.Log("Left Mouse Clicked");
}

void myFunction2()
{
    Debug.Log("Right Mouse Clicked");
}

void Update()
{
    foreach (KeyCode tempKey in allKeyCodes)
    {
        //Check if any key is pressed
        if (Input.GetKeyDown(tempKey))
        {
            //Check if the key pressed exist in the dictionary key
            if (keyCodeToFuncDic.ContainsKey(tempKey))
            {
                //Debug.Log("Pressed" + tempKey);

                //Call the function stored in the Dictionary's value
                keyCodeToFuncDic[tempKey].Invoke();
            }
        }
    }
}
1
Programmer 7 Сен 2016 в 08:59

Я думаю, вы можете использовать это: сначала определите делегата для вашей задачи (задания, назначенные для нажатия клавиш в вашем примере):

public delegate void MyJob();

Затем определите свой словарь:

Dictionary<string, MyJob> myBinding = new Dictionary<string, MyJob>()
{
    { "left", delegate() { Console.WriteLine("Left Key pressed"); } },
    { "right", delegate() { Console.WriteLine("Right Key pressed"); } },
    { "up", delegate() { Console.WriteLine("Up Key pressed"); } },
    { "down", delegate() { Console.WriteLine("Down Key pressed"); } }
};

И напоследок воспользуйтесь:

public void Mapper(string pressedKey)
{
    myBinding[pressedKey]();
}

Надеюсь, это поможет вам решить вашу проблему. Если вам нужна более подробная информация, дайте мне знать.

4
Imran Shamszadeh 7 Сен 2016 в 08:34

Когда я вижу «динамические ключи», я думаю, что что-то еще, например, тип dynamic будет ключом для словаря. Однако то, что вам нужно, может быть легко достигнуто. В C # «указатели на функции» называются delegates (но намного лучше, чем указатели на функции в C), поэтому вам нужен словарь, который имеет тип char в качестве ключа и один из этих делегатов в качестве значения. В .NET framework 4.0 и выше есть предопределенные универсальные делегаты, называемые Func<T...> и Action<T...>. Обычно, если вы хотите, чтобы ваша функция возвращала значение, вы должны использовать Func, а Action будет использоваться вместо метода void.

У вас может получиться что-то вроде этого:

var keyMap = new Dictionary<char, Func<string, bool>>()
{
    {'w', MoveUp},
    {'s', MoveDown},
    {'a', s => true}, // using lambda expression
    {
        'd', delegate(string s)
        {
            if (string.IsNullOrWhiteSpace(s) == false)
            {
                //
            }
            return true;
        }
    } // using anonymous method
};

// then you can call those like this
var allow = keyMap['w']("some input");
if (allow)
{
    // .... 
}

public bool MoveUp(string input)
{
    return true;
}

public bool MoveDown(string input)
{
    return true;
}

Вот документы https://msdn.microsoft. ru / en-us / library / bb549151 (версия = 110) .aspx

1
Mihail Shishkov 7 Сен 2016 в 08:41