Adding effects to 2D panels

Posted By: Evo

Adding effects to 2D panels - 04/20/20 14:32

I'm currently working on an (open-source) lightweight 2D game development library. Basically it's a lite-c plugin full of command methods that will have all the features needed to quickly and easily create 2D games. So far everything is going very well and it currently includes : Topdown Gameplay, Platformer Gameplay, New 2D collision system, 2D Simulated Camera System, Parallax background/Foreground system, and many other easy to use 2d features.

I'm now creating various other features and there are some things I would like to add but am unsure how to actually code.

I need to know if there's a way to add special effects to panel/bmaps.
* Is there a way to apply a shader to a pure 2d object. (Panels/Bmaps) (No 3D Level) (No 2D View Entities)
* If I wanted a panel to have a waving effect (Such as being underwater or other similar ideas), how would I code/apply those things to actually affect the panel/bmap?
* Does anyone have a working 2d shader or working code effect that alters/affects a 2d panel/bmap?

Posted By: 3run

Re: Adding effects to 2D panels - 04/20/20 14:47

Hey!

Long time ago, txesmi helped me out with adding postprocessing shader over panels, maybe it will be useful:
Postprocessing over panels

Best regards!
Posted By: Evo

Re: Adding effects to 2D panels - 04/20/20 15:32

Thanks, 3run.

It's good to know that there's a way to target panels with a material effect. I'm not very good with shader code, but this will give a great starting point for experimenting with some new ideas.
Posted By: Evo

Re: Adding effects to 2D panels - 04/21/20 14:15

I just can't seem to get that code to work the way I need it to. I think I need an actual 2d shader for testing it.

2D MATERIAL EFFECT (Need a real 2d shader)
It needs to be applied and to add the material effect to the panels bmap/window of the panel that's targeted.
(Something that actually affects the panels image automatically once applied.

It would be greatly appreciated If anyone with knowledge of this can create a basic working example.

If I use :
bmap_process ( sprite_A, player_pan.target_map, mtlEffect );
How do I target a panels (bmap/window sprite) and apply the effect directly to the image?
How can I get the view materials to work with this method?
Posted By: Evo

Re: Adding effects to 2D panels - 04/21/20 19:16

I seem to have gotten it to work in a different way. Basically all I have to do to target a defined BMAP and apply a view shader is :

bmap_process ( sprite_A, sprite_A, mtl_emboss );

It applies the material effect to the BMAP. Changes apply to any panels using the BMAP.

Q. What material code do I use to make the sprites transparent?
When applied to a window sprite, it colors the transparent pixels.

(Note : Not all view material work since they don't seem to be set up for this purpose. Only certain materials like "Negative" seem to work, but transparency is not correct.)
Posted By: Ayumi

Re: Adding effects to 2D panels - 04/21/20 21:38

maybe you should write your own small Shader because of controlling.

Example: Set alpha to View-Bitmap (clear the bitmap)

Code

Texture TargetMap;

sampler2D SrcColor = sampler_state
{ 
	texture = <TargetMap>; 
	MinFilter = linear;
   MagFilter = linear;
   MipFilter = linear;
   AddressU = Clamp;
   AddressV = Clamp;	
};

float4 FillAlpha( float2 texCoord : TEXCOORD0 ) : COLOR0
{
	float4 color;

	color = tex2D(SrcColor, texCoord);
	color.a = 0;
	color.rgb = 1;
	return color;
}

technique PostProcess 
{
	pass p1 
	{
		AlphaBlendEnable = false;	
		VertexShader = null;
		PixelShader = compile ps_1_0 FillAlpha();
	}
}


MATERIAL* MatObjFillAlpha =
{	
	effect ="FillAlpha.fx";		
}



Code

View.bmap = bmap_for_entity(my, 1);
bmap_process (View.bmap, NULL, MatObjFillAlpha);




And your bmap_process is wrong, set NULL to Source.




If you want to set Alpha Channel to Emboss, set AlphablendEnable to true and set Color.a

Code
Texture TargetMap;
sampler2D g_samSrcColor = sampler_state { texture = <TargetMap>; MipFilter = Linear;	};

float4 vecViewPort;

float4 postprocessing_emboss( float2 Tex : TEXCOORD0 ) : COLOR0 
{
   float4 Color = float4(0.5,0.5,0.5,1.0);
	Color -= tex2D( g_samSrcColor, Tex.xy-vecViewPort.zw)*2.0f;
	Color += tex2D( g_samSrcColor, Tex.xy+vecViewPort.zw)*2.0f;	
	Color.rgb = (Color.r+Color.g+Color.b)/3.0f;
	Color.a = 0.2; 
	return Color;
}

technique PostProcess 
{
	pass p1 
	{
		AlphaBlendEnable = true;
		VertexShader = null;
		PixelShader = compile ps_2_0 postprocessing_emboss();
	}
}




Posted By: Evo

Re: Adding effects to 2D panels - 04/21/20 23:01

Hi, Ayumi. Thanks for your reply and your help.

My project doesn't use 3D levels, views, or entities. It's also not drawing into anything. It's pure 2D and it's just a lot of panels and bmaps.

Calling NULL in "bmap_process( sprite_A, NULL, mtl_emboss );" won't work. It has to be set to the same thing so that the effect applies to the same bmap that is being targeted.

bmap_process ( sprite_A, sprite_A, mtl_emboss ); This is all that's needed to apply a material to a defined bmap. My issue is that I know very little about coding shaders.
Posted By: Emre

Re: Adding effects to 2D panels - 04/22/20 10:43

Originally Posted by Evo
(Note : Not all view material work since they don't seem to be set up for this purpose. Only certain materials like "Negative" seem to work, but transparency is not correct.)


In that effect (Negative), transparency is indicated by number. That's the problem.

Code
float4 postprocessing_negative( float2 Tex : TEXCOORD0 ) : COLOR0 
{
   //you have the color of the texture but not the alpha!
   float3 Color = 1. - tex2D( g_samSrcColor, Tex.xy).xyz;
   
   //you set the alpha by number (1) that means your texture doesn't have transparent parts.
   return float4(Color,1.);
}



If you change it like this, the problem will disappear:

Code
float4 postprocessing_negative( float2 Tex : TEXCOORD0 ) : COLOR0 
{
	//you have the color and alpha of the texture.
	float4 Color = tex2D( g_samSrcColor, Tex.xy);
	
	//now you change colors, but not touch the alpha.
	Color.xyz=1. - tex2D( g_samSrcColor, Tex.xy).xyz;
	
	return Color;
}


Color.xyz means rgb and Color.a means alpha. So if you specify the alpha in numbers float4(Color.xyz,1), it won't affect texture. First, you should get rgb and alpha with float4. Then you can change it as you wish.

I would like to help more, but i'm not familiar of bmap_process.
Posted By: Evo

Re: Adding effects to 2D panels - 04/22/20 12:25

Thanks, Emre. That solution works well and the transparency on the negative material looks great now.

bmap_process applies the selected material to a defined bmap. Then bmap_purge can quickly remove the edited version from memory which will make the bmap return to its original state. Doing it this way to add effects to bmaps seems to work well. At the moment I've only tested material that effects color changes.

I'll keep digging into some shader code and try to figure some thing's out. Thanks again for your help.
Posted By: Evo

Re: Adding effects to 2D panels - 04/22/20 13:19

My evo2d method library will now have a custom 2D FX system for material effects.

So far it's only standard material effects that alter the color. But now I need a final test of a shader that alters shape or some other cool effect.

If anyone can create a basic effect to alter the shape (such as a wave effect that changes the bmap), that would verify if a real effect works or not. Sorry to ask for help in creating it, but I know little about shader code at this time.

Thanks for everyone's help so far. I appreciate your time and effort.
Posted By: Emre

Re: Adding effects to 2D panels - 04/22/20 17:36

As far as i understand, bmap_process does not add shaders to bmap, but render shader on it (target map). That means some shader effect will not work if you use panel.bmap for source and target at the same time. You can simply test it;

Code
///////////////////////////////
#include <acknex.h>
#include <default.c>
#define PRAGMA_PATH "%EXE_DIR%\templates\images";
#define PRAGMA_PATH "%EXE_DIR%\samples";

//bumpmap for wave
BMAP* bump_map="rock.tga";
MATERIAL* test_mat =
{
	skin1=bump_map;
	
	effect="
	texture TargetMap;
	texture mtlSkin1;
	sampler2D Map1 = sampler_state
	{
		Texture = <TargetMap>;
	};
	sampler2D BumpSampler = sampler_state
	{
		Texture = <mtlSkin1>;
	};
	float4 vecTime;
	float4 PIXEL_S(float2 Tex:TEXCOORD0 ):COLOR
	{
		float2 BumpText = tex2D(BumpSampler, float2(Tex.x,Tex.y-0.1*0.1*vecTime.w)).rg*2-1;
		Tex += BumpText*(0.01f);
		float4 color = tex2D(Map1,Tex);
		return color;
	}
	technique testtech
	{
		pass p1
		{
			PixelShader = compile ps_2_0 PIXEL_S();
		}
	}";
}


//sourcemap
BMAP* lite_c_logo="logo_800.jpg";

//panelmap (targetmap)
BMAP* panelmap="logo_800.jpg";
PANEL* testpan =
{
	bmap=panelmap;
	flags=SHOW;
}

function main()
{
	fps_max=75;
	video_mode=9;
	video_screen=2;
	video_set(800,600,32,2);
	wait(3);
	
	//Need this. Otherwise vecTime doesn't work.
	level_load("");
	
	//convert rock.tga to normalmap
	bmap_to_normals(bump_map,10);
	
	while(1)
	{
		//render lite-c logo on the panelmap with shader
		bmap_process(testpan.bmap,lite_c_logo,test_mat);
		
		//render panelmap on the panelmap? This will not work.
		//bmap_process(testpan.bmap,testpan.bmap,test_mat);
		
				
		//This will not work either.
		//bmap_process(testpan.bmap,NULL,test_mat);
		
		wait(1);
	}
}


Posted By: Evo

Re: Adding effects to 2D panels - 04/22/20 18:04

Thanks, Emre.
This clears up why certain issues were happening. This will greatly help with finishing the 2dfx methods. Thank you for your help and the example. Also thanks to everyone else for helping out.
Posted By: txesmi

Re: Adding effects to 2D panels - 04/23/20 16:58

Quote

//This will not work either.
//bmap_process(testpan.bmap,NULL,test_mat);


That sentence works. The only difference is that the TargetMap shader texture is empty. No more. You can paint bitmaps procedurally that way, or from other texture resources.

Alternatively, you can set a view with PROCESS_TARGET flag set instead of calling bmap_process inside a loop.

Code
///////////////////////////////
#include <acknex.h>
#include <default.c>
#define PRAGMA_PATH "%EXE_DIR%\templates\images";
#define PRAGMA_PATH "%EXE_DIR%\samples";

//sourcemap
BMAP* lite_c_logo="logo_800.jpg";

//bumpmap for wave
BMAP* bump_map="rock.tga";
MATERIAL* test_mat =
{
	skin1=bump_map;
	skin2=lite_c_logo;
	
	effect="
	float4 vecSkill1;
	
	texture mtlSkin1;
	sampler2D BumpSampler = sampler_state
	{
		Texture = <mtlSkin1>;
		AddressU = Wrap;
		AddressV = Wrap;
	};
	texture mtlSkin2;
	sampler2D SourceSampler = sampler_state
	{
		Texture = <mtlSkin2>;
		AddressU = Clamp;
		AddressV = Clamp;
	};
	float4 vecTime;
	float4 PIXEL_S(float2 pos:VPOS ):COLOR // VPOS gives the pixel coords instead of normalized ones
	{
		float2 Tex = (pos + 0.5f) / vecSkill1.xy;
		float2 BumpText = tex2D(BumpSampler, float2(Tex.x,Tex.y-0.1*0.1*vecTime.w)).rg*2-1;
		Tex += BumpText*(0.01f);
		float4 color = tex2D(SourceSampler,Tex);
		return color;
	}
	technique testtech
	{
		pass p1
		{
			PixelShader = compile ps_3_0 PIXEL_S();
		}
	}
	";
}


//panelmap (targetmap)
BMAP* panelmap="#800x600x24";
PANEL* testpan =
{
	bmap=panelmap;
	flags=SHOW;
}

VIEW *viewtest = {
	bmap = panelmap;
	size_x = 800;
	size_y = 600;
	material = test_mat;
	flags = PROCESS_TARGET | SHOW;
}

function main()
{
	fps_max=75;
	video_mode=9;
	video_screen=2;
	video_set(800,600,32,2);
	wait(3);
	
	//Need this. Otherwise vecTime doesn't work.
	level_load("");
	
	//convert rock.tga to normalmap
	bmap_to_normals(bump_map,10);
	
	// Need this to get the real size of the bitmap
	bmap_lock(lite_c_logo, 0);
	bmap_unlock(lite_c_logo);
	test_mat->skill1 = floatv(lite_c_logo.finalwidth);
	test_mat->skill2 = floatv(lite_c_logo.finalheight);
}

Posted By: Emre

Re: Adding effects to 2D panels - 04/24/20 11:52

Thanks for correcting me. smile
Posted By: Evo

Re: Adding effects to 2D panels - 04/25/20 04:36

Thanks, txesmi.
Thanks to everyone for your help and examples.

After testing each method of adding effects, directly targeting the BMAP as source or using VIEWs to render it into, didn't seem flexible enough for what I needed. Instead, I decided to go with the original panel-based approach using target_map and use strings to clone panel/elements into the fx panels that overlay the targeted panels. The fx panels are in sync with the targeted panel and they can be moved around and resized by changing the pos and size of the targeted panel. It seems to work well so far.

Code
///////////////////////////////
#include <acknex.h>
#include <default.c>
#include <mtlView.c>
#define PRAGMA_PATH "%EXE_DIR%\templates\images";
#define PRAGMA_PATH "%EXE_DIR%\samples";
FONT* testfont = font_create("Arial#40");

//material to clear the fx canvas
MATERIAL* MatObjFillAlpha =
{	
	effect="
	Texture TargetMap;

	sampler2D SrcColor = sampler_state
	{ 
		texture = <TargetMap>; 
		MinFilter = linear;
		MagFilter = linear;
		MipFilter = linear;
		AddressU = Clamp;
		AddressV = Clamp;	
	};

	float4 FillAlpha( float2 texCoord : TEXCOORD0 ) : COLOR0
	{
		float4 color;

		color = tex2D(SrcColor, texCoord);
		color.a = 0;
		color.rgb = 1;
		return color;
	}

	technique PostProcess 
	{
		pass p1 
		{
			AlphaBlendEnable = false;	
			VertexShader = null;
			PixelShader = compile ps_1_0 FillAlpha();
		}
	}
	";
}

//bumpmap for wave effect
BMAP* bump_map="rock.tga";

//material for wave effect
MATERIAL* test_mat =
{
	skin1=bump_map;
	
	effect="
	texture TargetMap;
	texture mtlSkin1;
	sampler2D Map1 = sampler_state
	{
		Texture = <TargetMap>;
	};
	sampler2D BumpSampler = sampler_state
	{
		Texture = <mtlSkin1>;
	};
	float4 vecTime;
	float4 PIXEL_S(float2 Tex:TEXCOORD0 ):COLOR
	{
		float2 BumpText = tex2D(BumpSampler, float2(Tex.x,Tex.y-0.1*0.1*vecTime.w)).rg*2-1;
		Tex += BumpText*(0.01f);
		float4 color = tex2D(Map1,Tex);
		return color;
	}
	technique testtech
	{
		pass p1
		{
			PixelShader = compile ps_2_0 PIXEL_S();
		}
	}";
}

//BMAPS
BMAP* lite_c_logo="logo_800.jpg";
BMAP* invent="invent.pcx";

//PRIMARY PANELS
PANEL* testpanA;
PANEL* testpanB;
PANEL* testpanC;

//PRIMARY PANEL BLUEPRINTS FOR PANEL CREATION
//ALSO USED FOR FX PANELS TO CLONE PANELS/ELEMENTS
STRING* testpanAstr = 
"
bmap=lite_c_logo;
digits(20,20,\"ID 1\",*,0,0);
button(40, 40, invent, invent, invent, NULL, NULL, NULL);
pos_x=0;
pos_y=0;
size_x=800;
size_y=600;
red=128;
green=128;
blue=128;
layer=0;
flags=LIGHT;
";

STRING* testpanBstr = 
"
bmap=lite_c_logo;
digits(20,20,\"ID 2\",*,0,0);
digits(20,40,\"ID 2\",*,0,0);
pos_x=100;
pos_y=100;
size_x=400;
size_y=200;
red=128;
green=128;
blue=128;
layer=1;
flags=LIGHT;
";

STRING* testpanCstr = 
"
bmap=lite_c_logo;
digits(20,20,\"ID 3\",*,0,0);
pos_x=350;
pos_y=150;
size_x=350;
size_y=250;
red=128;
green=128;
blue=128;
layer=2;
flags=LIGHT;
";

//EVO2D PANEL SHADER

//fx_ids
int fx_id[100];

//Remove any Fx from any panel that uses the fx_id
void remove_fx(int fx_ids)
{
	fx_id[fx_ids] = false;
}

//Apply Fx to a panel
void fx_shader(int fx_ids, PANEL* target_panel, STRING* clone_str, MATERIAL* add_mtl, int fx_transparency, int fx_layer)
{
	if(fx_ids<0){fx_ids=0;}
	if(fx_ids>99){fx_ids=99;}
	fx_id[fx_ids] = true;
	PANEL* targetpan = pan_create ( clone_str, fx_layer );
	PANEL* destpan = pan_create ( "", fx_layer );
	targetpan.alpha = fx_transparency;
	layer_sort(target_panel, fx_layer);
	layer_sort(targetpan, fx_layer);
	layer_sort(destpan, fx_layer);
	set(targetpan,SHOW | LIGHT);
	set(destpan, SHOW );
	targetpan.target_map = bmap_createblack ( screen_size.x, screen_size.y, 32 );
	destpan.bmap = bmap_createblack ( screen_size.x, screen_size.y, 32 );
	while ( fx_id[fx_ids] )
	{
		bmap_process ( destpan.bmap, targetpan.target_map, MatObjFillAlpha );
		bmap_process ( destpan.bmap, targetpan.target_map, add_mtl );
		vec_set(targetpan.blue, target_panel.blue);
		destpan.pos_x = target_panel.pos_x;
		destpan.pos_y = target_panel.pos_y;
		destpan.size_x = target_panel.size_x;
		destpan.size_y = target_panel.size_y;
		targetpan.pos_x=destpan.pos_x-target_panel.pos_x;
		targetpan.pos_y=destpan.pos_y-target_panel.pos_y;
		targetpan.size_x=target_panel.size_x;
		targetpan.size_y=target_panel.size_y;
		wait(1);
	}
	safe_remove(targetpan.target_map);
	safe_remove(destpan.bmap);
	safe_remove(targetpan);
	safe_remove(destpan);
}

//EVO2D FX Test
function main()
{
	fps_max=60;
	vec_set(screen_color,vector(1,1,1));
	vec_set(sky_color,vector(0,0,0));
	video_mode=9;
	video_screen=2;
	video_set(800,600,32,2);
	wait(3);
	
	//Create primary panels from string data
	testpanA = pan_create ( testpanAstr, 0 );
	testpanB = pan_create ( testpanBstr, 1 );
	testpanC = pan_create ( testpanCstr, 2 );
	wait(1);
	
	//Need this. Otherwise vecTime doesn't work.
	level_load("");
	
	//convert rock.tga to normalmap
	bmap_to_normals(bump_map,10);
	
	//Example
	//Plays through adding and removing material effect panels
	//If fx have the same ID, they will be removed at the same time when calling remove_fx(ID);
	//If fx have different IDs, only that fx ID will be removed when calling remove_fx(ID);
	wait(-2);
	fx_shader(0, testpanA, testpanAstr, test_mat, 100, 0);
	wait(-2); 
	fx_shader(0, testpanB, testpanBstr, mtl_erode, 100, 1);
	wait(-2);
	fx_shader(0, testpanC, testpanCstr, mtl_sharpen2, 100, 2);
	wait(-2);
	remove_fx(0);
	wait(-2);
	fx_shader(0, testpanA, testpanAstr, mtl_sepia, 100, 0);
	wait(-2); 
	fx_shader(0, testpanB, testpanBstr, mtl_monochrome, 100, 1);
	wait(-2);
	fx_shader(0, testpanC, testpanCstr, mtl_negative, 100, 2);
	wait(-2);
	remove_fx(0);
	wait(-2);
	fx_shader(0, testpanA, testpanAstr, mtl_emboss, 100, 0);
	wait(-2); 
	fx_shader(0, testpanB, testpanBstr, mtl_laplace, 100, 1);
	wait(-2);
	fx_shader(0, testpanC, testpanCstr, mtl_lens, 100, 2);
	wait(-2);
	remove_fx(0);
	wait(-2);
	
	fx_shader(0, testpanA, testpanAstr, test_mat, 100, 0);
	
	while(!key_esc){wait(1);}
	sys_exit("exit");
}

© 2024 lite-C Forums