[Tile Drawer] Palette brush now support right click to erase.

This commit is contained in:
Tanasart 2025-01-02 18:12:11 +07:00
parent fe28cc2fc1
commit bf5ce06a96
11 changed files with 213 additions and 69 deletions

View file

@ -1991,6 +1991,7 @@
{"name":"s_filter_type","order":62,"path":"sprites/s_filter_type/s_filter_type.yy",},
{"name":"s_filter","order":3,"path":"sprites/s_filter/s_filter.yy",},
{"name":"s_flare_type","order":1,"path":"sprites/s_flare_type/s_flare_type.yy",},
{"name":"s_flip_h_24","order":235,"path":"sprites/s_flip_h_24/s_flip_h_24.yy",},
{"name":"s_fluid_sim","order":63,"path":"sprites/s_fluid_sim/s_fluid_sim.yy",},
{"name":"s_folder_16","order":64,"path":"sprites/s_folder_16/s_folder_16.yy",},
{"name":"s_folder_24","order":65,"path":"sprites/s_folder_24/s_folder_24.yy",},

View file

@ -2642,6 +2642,7 @@
{"id":{"name":"s_filter_type","path":"sprites/s_filter_type/s_filter_type.yy",},},
{"id":{"name":"s_filter","path":"sprites/s_filter/s_filter.yy",},},
{"id":{"name":"s_flare_type","path":"sprites/s_flare_type/s_flare_type.yy",},},
{"id":{"name":"s_flip_h_24","path":"sprites/s_flip_h_24/s_flip_h_24.yy",},},
{"id":{"name":"s_fluid_sim","path":"sprites/s_fluid_sim/s_fluid_sim.yy",},},
{"id":{"name":"s_folder_16","path":"sprites/s_folder_16/s_folder_16.yy",},},
{"id":{"name":"s_folder_24","path":"sprites/s_folder_24/s_folder_24.yy",},},

View file

@ -1,3 +1,10 @@
function array_create_2d(_x, _y, val = 0) {
var _arr = array_create(_x);
for( var i = 0; i < _x; i++ )
_arr[i] = array_create(_y, val);
return _arr;
}
function array_create_from_list(list) {
if(list == undefined) return [];
if(!ds_exists(list, ds_type_list)) return [];

View file

@ -5,8 +5,8 @@ function buttonGroup(_data, _onClick) : widget() constructor {
display_button = false;
buttonSpr = [ THEME.button_left, THEME.button_middle, THEME.button_right ];
sprBlend = c_white;
fColor = COLORS._main_text;
tooltips = [];
current_selecting = 0;
@ -21,6 +21,7 @@ function buttonGroup(_data, _onClick) : widget() constructor {
static setFont = function(ff, fc = fColor) { font = ff; fColor = fc; return self; }
static setTooltips = function(tt) { tooltips = tt; return self; }
static setCollape = function(cc) { collapsable = cc; return self; }
static setBlend = function(bb) { sprBlend = bb; return self; }
static trigger = function() {
if(current_selecting + 1 >= array_length(data))
@ -100,8 +101,7 @@ function buttonGroup(_data, _onClick) : widget() constructor {
buttons[i].setFocusHover(active, hover);
buttons[i].tooltip = array_safe_get(tooltips, i, "");
if(is(_d, scrollItem))
_d = _d.spr;
if(is(_d, scrollItem)) _d = _d.spr;
var bww = !is_string(_d) && sprite_exists(_d) && _mx? _sw : ww;
var spr = i == 0 ? buttonSpr[0] : (i == amo - 1? buttonSpr[2] : buttonSpr[1]);
@ -120,7 +120,7 @@ function buttonGroup(_data, _onClick) : widget() constructor {
draw_text_add(bx + bww / 2, _y + _h / 2, _d);
} else if(sprite_exists(_d))
draw_sprite_ui_uniform(_d, i, bx + bww / 2, _y + _h / 2, 1);
draw_sprite_ui_uniform(_d, i, bx + bww / 2, _y + _h / 2, 1, sprBlend);
bx += bww;
}

View file

@ -144,7 +144,7 @@ function addHotkey(_context, _name, _key, _mod, _action) {
}
function find_hotkey(_context, _name) {
if(!ds_map_exists(HOTKEYS, _context)) return noone;
if(!ds_map_exists(HOTKEYS, _context)) return getToolHotkey(_context, _name);
for(var j = 0; j < ds_list_size(HOTKEYS[? _context]); j++) {
if(HOTKEYS[? _context][| j].name == _name)

View file

@ -2,9 +2,6 @@ function Node_Tile_Drawer(_x, _y, _group = noone) : Node_Processor(_x, _y, _grou
name = "Tile Drawer";
bypass_grid = true;
tileset = noone;
gmTileLayer = noone;
newInput( 0, nodeValue_Tileset("Tileset", self, noone))
.setVisible(true, true);
@ -32,6 +29,9 @@ function Node_Tile_Drawer(_x, _y, _group = noone) : Node_Processor(_x, _y, _grou
output_display_list = [ 2, 1, 0, 3 ];
tileset = noone;
gmTileLayer = noone;
#region ++++ data ++++
canvas_surface = surface_create_empty(1, 1, surface_rgba16float);
canvas_buffer = buffer_create(1, buffer_grow, 1);
@ -81,11 +81,17 @@ function Node_Tile_Drawer(_x, _y, _group = noone) : Node_Processor(_x, _y, _grou
.setCollape(false);
tool_fil8 = [ "Fill", tool_fil8_edit, "fillType", tool_attribute ];
tool_varient_rotate = [ "", new buttonGroup( [ s_canvas_rotate, s_canvas_rotate ], function(v) /*=>*/ {return brush_action_rotate(v)} )
.setCollape(0).setTooltips([ "Rotate CW", "Rotate CCW" ]) ];
tool_varient_rotate = [ "", new buttonGroup( [ s_canvas_rotate, s_canvas_rotate ], function(v) /*=>*/ { if(tileset != noone) tileset.brush_action_rotate(v) } )
.setCollape(0)
.setBlend(COLORS._main_icon_light)
.setTooltips([ new tooltipHotkey("Rotate CW", "Node_Tile_Drawer", "Brush Rotate CW"),
new tooltipHotkey("Rotate CCW", "Node_Tile_Drawer", "Brush Rotate CCW")]) ];
tool_varient_flip = [ "", new buttonGroup( [ s_canvas_flip, s_canvas_flip ], function(v) /*=>*/ {return brush_action_flip(v)} )
.setCollape(0).setTooltips([ "Flip X", "Flip Y" ]) ];
tool_varient_flip = [ "", new buttonGroup( [ s_canvas_flip, s_canvas_flip ], function(v) /*=>*/ { if(tileset != noone) tileset.brush_action_flip(v) } )
.setCollape(0)
.setBlend(COLORS._main_icon_light)
.setTooltips([ new tooltipHotkey("Flip H", "Node_Tile_Drawer", "Brush Flip H"),
new tooltipHotkey("Flip V", "Node_Tile_Drawer", "Brush Flip V")]) ];
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
@ -115,41 +121,12 @@ function Node_Tile_Drawer(_x, _y, _group = noone) : Node_Processor(_x, _y, _grou
tool_tile_picker = false;
#endregion
#region ++++ tools actions ++++
function brush_action_rotate(ccw) {
if(tileset == noone) return;
var brush = tileset.brush;
var _rot = ccw? -1 : 1;
for( var i = 0, n = brush.brush_height; i < n; i++ )
for( var j = 0, m = brush.brush_width; j < m; j++ ) {
var _b = brush.brush_indices[i][j];
var _fl = floor(_b[1] / 4) * 4;
var _rt = _b[1] % 4;
_b[1] = _fl + (_rt + _rot + 4) % 4;
}
}
function brush_action_flip(axs) {
if(tileset == noone) return;
var brush = tileset.brush;
var flp = axs? 0b1000 : 0b0100;
for( var i = 0, n = brush.brush_height; i < n; i++ )
for( var j = 0, m = brush.brush_width; j < m; j++ ) {
var _b = brush.brush_indices[i][j];
_b[1] = _b[1] ^ flp;
}
}
#endregion
#region ++++ hotkeys ++++
hotkeys = [
["Brush Rotate CW", function() /*=>*/ { brush_action_rotate(0); }],
["Brush Rotate CCW", function() /*=>*/ { brush_action_rotate(1); }],
["Brush Flip H", function() /*=>*/ { brush_action_flip(0); }],
["Brush Flip V", function() /*=>*/ { brush_action_flip(1); }],
["Brush Rotate CW", function() /*=>*/ { if(tileset != noone) tileset.brush_action_rotate(0); }],
["Brush Rotate CCW", function() /*=>*/ { if(tileset != noone) tileset.brush_action_rotate(1); }],
["Brush Flip H", function() /*=>*/ { if(tileset != noone) tileset.brush_action_flip(0); }],
["Brush Flip V", function() /*=>*/ { if(tileset != noone) tileset.brush_action_flip(1); }],
];
#endregion

View file

@ -67,6 +67,8 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
tile_selector_s = 2;
tile_selector_s_to = 2;
tile_selector_vm = 0;
tile_dragging = false;
tile_drag_sx = 0;
tile_drag_sy = 0;
@ -464,23 +466,28 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
var _sw = _ss * _sel_sw;
var _sh = _ss * _sel_sh;
var _vv = [ 0, 0b0001, 0b0010, 0b0011, 0b0100, 0b0101, 0b0110, 0b0111 ];
var _vv = [ 0, 0b0001, 0b0010, 0b0011 ];
var p = array_length(_vv)
var _col = max(1, floor((_w - ui(8)) / (_sw + ui(8))));
var _row = brush.brush_width * brush.brush_height == 1? ceil((p + 1) / _col) : 1;
var _row = 1;
var _th = ui(8) + (_sh + ui(8)) * _row;
_h += ui(8) + _th;
draw_sprite_stretched_ext(THEME.ui_panel_bg, 1, _x, _ty, _w, _th, COLORS.node_composite_bg_blend, 1);
//////////////////
var _shov = _hover && point_in_rectangle(_m[0], _m[1], _sx, _sy, _sx + _sw, _sy + _sh);
var _aa = 0.5 + 0.5 * _shov;
var _aa = .75 + .25 * _shov;
draw_sprite_stretched_ext(THEME.ui_panel, 1, _sx, _sy, _sw, _sh, COLORS._main_icon, _aa);
draw_sprite_uniform(THEME.cross, 0, _sx + _sw / 2, _sy + _sh / 2, 1, COLORS._main_icon, _aa);
draw_sprite_uniform(THEME.cross, 0, _sx + _sw / 2, _sy + _sh / 2, 1, _shov? COLORS._main_value_negative : COLORS._main_icon, _aa);
_sx += _sw + ui(8);
if(_shov) {
if(object_selecting == noone) {
TOOLTIP = "Set empty";
if(mouse_press(mb_left, _focus)) {
brush.brush_indices = [[[ -1, 0 ]]];
brush.brush_width = 1;
@ -500,15 +507,33 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
}
}
//////////////////
var _fpx = bool(tile_selector_vm);
var _shov = _hover && point_in_rectangle(_m[0], _m[1], _sx, _sy, _sx + _sw, _sy + _sh);
var _aa = .75 + .25 * _shov;
draw_sprite_stretched_ext(THEME.ui_panel, 1, _sx, _sy, _sw, _sh, COLORS._main_icon, _aa);
draw_sprite_ext(s_flip_h_24, 0, _sx + _sw / 2, _sy + _sh / 2, _fpx? -1 : 1, 1, 0, _fpx? COLORS._main_accent : COLORS._main_icon, _aa);
_sx += _sw + ui(8);
if(_shov) {
TOOLTIP = "Flip X";
if(mouse_press(mb_left, _focus)) {
tile_selector_vm = _fpx? 0 : 0b0100;
brush_action_flip(0);
}
}
//////////////////
if(brush.brush_width * brush.brush_height != 1) return _h;
var _bb = brush.brush_indices[0][0];
var _vi = 1;
for( var v = 0; v < p; v++ ) {
var _var = _vv[v];
var _var = _vv[v] | tile_selector_vm;
surface_set_shader(selecting_surface, sh_draw_tile_brush, true, BLEND.over);
shader_set_f("index", _bb[0]);
@ -541,11 +566,11 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
_bb[1] = _var;
_sx += _sw + ui(8);
if(++_vi >= _col) {
_sx = _x + ui(8);
_sy += _sh + ui(8);
_vi = 0;
}
// if(++_vi >= _col) {
// _sx = _x + ui(8);
// _sy += _sh + ui(8);
// _vi = 0;
// }
}
#endregion
@ -1138,7 +1163,6 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
#endregion
if(palette_tool == 1) {
#region // pencil tool
surface_set_target(palette_selector_mask);
DRAW_CLEAR
draw_set_color(c_white);
@ -1170,7 +1194,10 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
shader_reset();
surface_reset_target();
if(mouse_click(mb_left, _hov && _focus)) {
var lc = mouse_click(mb_left);
var rc = mouse_click(mb_right);
if(_hov && _focus && (lc || rc)) {
palette_tool_using = true;
surface_set_target(brush_palette);
@ -1180,8 +1207,8 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
for( var i = 0, n = array_length(brush.brush_indices); i < n; i++ )
for( var j = 0, m = array_length(brush.brush_indices[i]); j < m; j++ ) {
var _b = brush.brush_indices[i][j];
shader_set_f("index", _b[0]);
shader_set_f("varient", _b[1]);
shader_set_f("index", lc? _b[0] : -1);
shader_set_f("varient", lc? _b[1] : 0);
draw_point(_mtx + j, _mty + i);
}
@ -1197,10 +1224,8 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
buffer_delete_safe(brush_palette_buffer);
brush_palette_buffer = buffer_from_surface(brush_palette);
}
#endregion
} else if(palette_tool == 2) {
#region eraser tool
surface_set_target(brush_palette_prev);
DRAW_CLEAR
@ -1224,7 +1249,7 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
shader_set(sh_draw_tile_brush);
BLEND_OVERRIDE
shader_set_f("index", 0);
shader_set_f("index", -1);
shader_set_f("varient", 0);
draw_point(_mtx, _mty);
@ -1240,7 +1265,6 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
buffer_delete_safe(brush_palette_buffer);
brush_palette_buffer = buffer_from_surface(brush_palette);
}
#endregion
} else if(palette_using) {
#region no tool
@ -1688,4 +1712,48 @@ function Node_Tile_Tileset(_x, _y, _group = noone) : Node(_x, _y, _group) constr
refreshAnimatedData();
}
////- Tools
#region ++++ tools actions ++++
function brush_action_rotate(ccw) {
var bid = array_create_2d(brush.brush_width, brush.brush_height);
var _rot = ccw? -1 : 1;
for( var i = 0, n = brush.brush_height; i < n; i++ )
for( var j = 0, m = brush.brush_width; j < m; j++ ) {
var _b = brush.brush_indices[i][j];
var _fl = floor(_b[1] / 4) * 4;
var _rt = _b[1] % 4;
var _i = !ccw? j : brush.brush_width - j - 1;
var _j = ccw? i : brush.brush_height - i - 1;
bid[_i][_j] = [ _b[0], _fl + (_rt + _rot + 4) % 4 ];
}
brush.brush_indices = bid;
var _t = brush.brush_width;
brush.brush_width = brush.brush_height;
brush.brush_height = _t;
}
function brush_action_flip(axs) {
var bid = array_create_2d(brush.brush_height, brush.brush_width);
var flp = axs? 0b1000 : 0b0100;
for( var i = 0, n = brush.brush_height; i < n; i++ )
for( var j = 0, m = brush.brush_width; j < m; j++ ) {
var _b = brush.brush_indices[i][j];
var _i = !axs? i : brush.brush_height - i - 1;
var _j = axs? j : brush.brush_width - j - 1;
bid[_i][_j] = [ _b[0], _b[1] ^ flp ];
}
brush.brush_indices = bid;
}
#endregion
}

View file

@ -2130,9 +2130,9 @@ function Panel_Preview() : PanelContent() constructor {
tool_x = lerp_float(tool_x, tool_x_to, 5);
var tolx = tool_x + ui(8);
var toly = ui(7);
var toly = ui(6);
var tolw = ui(48);
var tolh = toolbar_height - ui(20);
var tolh = toolbar_height - ui(18);
var tol_max_w = ui(16);
for( var i = 0, n = array_length(settings); i < n; i++ ) {

Binary file not shown.

After

Width:  |  Height:  |  Size: 583 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 583 B

View file

@ -0,0 +1,90 @@
{
"$GMSprite":"",
"%Name":"s_flip_h_24",
"bboxMode":0,
"bbox_bottom":22,
"bbox_left":1,
"bbox_right":22,
"bbox_top":1,
"collisionKind":1,
"collisionTolerance":0,
"DynamicTexturePage":false,
"edgeFiltering":false,
"For3D":false,
"frames":[
{"$GMSpriteFrame":"","%Name":"6a8adf87-5273-47ca-b497-d62cc57c9296","name":"6a8adf87-5273-47ca-b497-d62cc57c9296","resourceType":"GMSpriteFrame","resourceVersion":"2.0",},
],
"gridX":0,
"gridY":0,
"height":24,
"HTile":false,
"layers":[
{"$GMImageLayer":"","%Name":"1ec9d065-7785-4116-99be-2d6cc89b06b1","blendMode":0,"displayName":"default","isLocked":false,"name":"1ec9d065-7785-4116-99be-2d6cc89b06b1","opacity":100.0,"resourceType":"GMImageLayer","resourceVersion":"2.0","visible":true,},
],
"name":"s_flip_h_24",
"nineSlice":null,
"origin":4,
"parent":{
"name":"icon",
"path":"folders/sprites/theme/icon.yy",
},
"preMultiplyAlpha":false,
"resourceType":"GMSprite",
"resourceVersion":"2.0",
"sequence":{
"$GMSequence":"",
"%Name":"s_flip_h_24",
"autoRecord":true,
"backdropHeight":768,
"backdropImageOpacity":0.5,
"backdropImagePath":"",
"backdropWidth":1366,
"backdropXOffset":0.0,
"backdropYOffset":0.0,
"events":{
"$KeyframeStore<MessageEventKeyframe>":"",
"Keyframes":[],
"resourceType":"KeyframeStore<MessageEventKeyframe>",
"resourceVersion":"2.0",
},
"eventStubScript":null,
"eventToFunction":{},
"length":1.0,
"lockOrigin":false,
"moments":{
"$KeyframeStore<MomentsEventKeyframe>":"",
"Keyframes":[],
"resourceType":"KeyframeStore<MomentsEventKeyframe>",
"resourceVersion":"2.0",
},
"name":"s_flip_h_24",
"playback":1,
"playbackSpeed":30.0,
"playbackSpeedType":0,
"resourceType":"GMSequence",
"resourceVersion":"2.0",
"showBackdrop":true,
"showBackdropImage":false,
"timeUnits":1,
"tracks":[
{"$GMSpriteFramesTrack":"","builtinName":0,"events":[],"inheritsTrackColour":true,"interpolation":1,"isCreationTrack":false,"keyframes":{"$KeyframeStore<SpriteFrameKeyframe>":"","Keyframes":[
{"$Keyframe<SpriteFrameKeyframe>":"","Channels":{
"0":{"$SpriteFrameKeyframe":"","Id":{"name":"6a8adf87-5273-47ca-b497-d62cc57c9296","path":"sprites/s_flip_h_24/s_flip_h_24.yy",},"resourceType":"SpriteFrameKeyframe","resourceVersion":"2.0",},
},"Disabled":false,"id":"4ea91bf0-f370-4c17-b337-121d2329b851","IsCreationKey":false,"Key":0.0,"Length":1.0,"resourceType":"Keyframe<SpriteFrameKeyframe>","resourceVersion":"2.0","Stretch":false,},
],"resourceType":"KeyframeStore<SpriteFrameKeyframe>","resourceVersion":"2.0",},"modifiers":[],"name":"frames","resourceType":"GMSpriteFramesTrack","resourceVersion":"2.0","spriteId":null,"trackColour":0,"tracks":[],"traits":0,},
],
"visibleRange":null,
"volume":1.0,
"xorigin":12,
"yorigin":12,
},
"swatchColours":null,
"swfPrecision":0.5,
"textureGroupId":{
"name":"Default",
"path":"texturegroups/Default",
},
"type":0,
"VTile":false,
"width":24,
}