Add custom hotkeys to internal Unity Editor window

I’m using the Tile Palette and I find it so clunky. I want to add custom hotkeys to speed up my work flow, maybe change the tilemap I’m painting with ctrl+up/down- that kind of thing.
I started looking into Editor Scripting but it doesn’t seem like I’m actually able to do this. I just want to read/write values to/from existing editor windows.

Hey @Aniki219,

The UnityEditor.Tilemaps.GridPaintingState class has the following public properties you can use:

  • validTargets, which is all available tilemaps
  • scenePaintTarget, which is the current active tilemap

If the properties you wanted to change happened to be private instead of public, you could still use Reflection to set them. Here is an example of using the properties above to change the active tilemap, and Reflection to change the active palette.

Editor/TilemapHelper.cs

using System.Collections.Generic;
using UnityEngine;
using UnityEditor;
using System.Linq;
using UnityEditor.Tilemaps;

public class TilemapHelper
{
    [MenuItem("Custom Tools/Next Tilemap %&q")]
    static void SelectNextTilemap()
    {
        // Current/available tilemaps can be found in GridPaintingState
        var tilemaps = GridPaintingState.validTargets;
        var numTilemaps = tilemaps.Length;
        var currentTilemap = GridPaintingState.scenePaintTarget;
        // Handle trivial cases
        if (numTilemaps == 0) { return; }
        if (numTilemaps == 1) { GridPaintingState.scenePaintTarget = tilemaps[0]; return; }
        // Find current tilemap index
        var idx = 0;
        for (; idx < numTilemaps; idx++)
        {
            var tilemap = tilemaps[idx];
            if (tilemap == currentTilemap) { break; }
        }
        // Move to next tilemap, with wraparound
        idx = (idx + 1) % numTilemaps;
        // Set new tilemap
        GridPaintingState.scenePaintTarget = tilemaps[idx];
    }
    
    [MenuItem("Custom Tools/Next Palette %&e")]
    static void SelectNextPalette()
    {
        // Find current/all palettes using reflection
        var knownType = typeof(GridPaintingState);
        var assembly = knownType.Assembly;
        var assmeblyTypes = assembly.GetTypes();
        var wndType = assmeblyTypes.Single(x => x.Name == "GridPaintPaletteWindow");
        var wnd = EditorWindow.GetWindow(wndType);
        var currentPaletteProp = wndType.GetProperty("palette");
        var currentPalette = (GameObject)currentPaletteProp.GetValue(wnd);
        var gridPalettesType = assmeblyTypes.Single(x => x.Name == "GridPalettes");
        var palettesProp = gridPalettesType.GetProperty("palettes");
        var palettes = (List<GameObject>)palettesProp.GetValue(gridPalettesType);
        var numPalettes = palettes.Count;
        // Handle trivial cases
        if (numPalettes == 0) { return; }
        if (numPalettes == 1) { currentPaletteProp.SetValue(wnd, palettes[0]); return; }
        // Find current palette and choose next
        GameObject newPalette = null;
        for (var i = 0; i < numPalettes; i++) 
        {
            if (palettes *== currentPalette)* 

{
var nextIdx = (i + 1) % numPalettes;
newPalette = palettes[nextIdx];
break;
}
}
// Set palette using reflection
currentPaletteProp.SetValue(wnd, newPalette);
}
}
Hope this helps!