Changes on brushes memory management, in preparation for Issue 362
git-svn-id: svn://pulkomandy.tk/GrafX2/trunk@1699 416bcca6-2ee7-4201-b75f-2eb2f807beb1
This commit is contained in:
parent
4175226a4a
commit
40a7bcf40e
647
src/brush.c
647
src/brush.c
@ -482,66 +482,70 @@ void Display_paintbrush(short x,short y,byte color,byte is_preview)
|
||||
}
|
||||
}
|
||||
|
||||
///
|
||||
/// Changes the Brush size, discarding its previous content.
|
||||
/// @return 0 OK, 1 Failed
|
||||
byte Realloc_brush(word new_brush_width, word new_brush_height)
|
||||
/// @return 0 on success, non-zero on failure (memory?).
|
||||
/// @param new_brush: Optionally, you can provide an already allocated new
|
||||
/// brush - otherwise, this function performs the allocation.
|
||||
/// @param old_brush: If the caller passes NULL, this function will free the old
|
||||
/// pixel data. If the caller provides the address of a (free) byte
|
||||
/// pointer, the function will make it point to the original pixel data,
|
||||
/// in this case it will be the caller's responsibility to free() it
|
||||
/// (after transferring pixels to Brush, usually).
|
||||
byte Realloc_brush(word new_brush_width, word new_brush_height, byte *new_brush, byte **old_brush)
|
||||
{
|
||||
byte return_code=0;
|
||||
|
||||
byte *new_smear_brush;
|
||||
word new_smear_brush_width;
|
||||
word new_smear_brush_height;
|
||||
|
||||
if (new_brush==NULL)
|
||||
{
|
||||
new_brush=(byte *)malloc(((long)new_brush_height)*new_brush_width);
|
||||
if (new_brush == NULL)
|
||||
{
|
||||
Error(0);
|
||||
if (old_brush)
|
||||
*old_brush=NULL;
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
new_smear_brush_width=(new_brush_width>MAX_PAINTBRUSH_SIZE)?new_brush_width:MAX_PAINTBRUSH_SIZE;
|
||||
new_smear_brush_height=(new_brush_height>MAX_PAINTBRUSH_SIZE)?new_brush_height:MAX_PAINTBRUSH_SIZE;
|
||||
new_smear_brush=NULL;
|
||||
if ( (((long)Brush_height)*Brush_width) !=
|
||||
(((long)new_brush_height)*new_brush_width) )
|
||||
{
|
||||
free(Brush);
|
||||
Brush=(byte *)malloc(((long)new_brush_height)*new_brush_width);
|
||||
if (Brush == NULL)
|
||||
new_smear_brush=(byte *)malloc(((long)new_smear_brush_height)*new_smear_brush_width);
|
||||
if (new_smear_brush == NULL)
|
||||
{
|
||||
Error(0);
|
||||
return_code=1;
|
||||
|
||||
Brush=(byte *)malloc(1*1);
|
||||
if(Brush == NULL)
|
||||
{
|
||||
Error(ERROR_MEMORY);
|
||||
exit(ERROR_MEMORY);
|
||||
}
|
||||
new_brush_height=new_brush_width=1;
|
||||
*Brush=Fore_color;
|
||||
if (old_brush)
|
||||
*old_brush=NULL;
|
||||
return 2;
|
||||
}
|
||||
}
|
||||
|
||||
// All allocations successful: can replace globals
|
||||
Brush_width=new_brush_width;
|
||||
Brush_height=new_brush_height;
|
||||
|
||||
free(Smear_brush);
|
||||
Smear_brush_width=(Brush_width>MAX_PAINTBRUSH_SIZE)?Brush_width:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_height=(Brush_height>MAX_PAINTBRUSH_SIZE)?Brush_height:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush=(byte *)malloc(((long)Smear_brush_height)*Smear_brush_width);
|
||||
|
||||
if (Smear_brush == NULL) // Failed to allocate the smear brush
|
||||
if (new_smear_brush)
|
||||
{
|
||||
Error(0);
|
||||
return_code=1;
|
||||
|
||||
free(Brush);
|
||||
Brush=(byte *)malloc(1*1);
|
||||
if(Brush == NULL)
|
||||
{
|
||||
Error(ERROR_MEMORY);
|
||||
exit(ERROR_MEMORY);
|
||||
}
|
||||
Brush_height=1;
|
||||
Brush_width=1;
|
||||
|
||||
Smear_brush=(byte *)malloc(MAX_PAINTBRUSH_SIZE*MAX_PAINTBRUSH_SIZE);
|
||||
if(Smear_brush == NULL)
|
||||
{
|
||||
Error(ERROR_MEMORY);
|
||||
exit(ERROR_MEMORY);
|
||||
}
|
||||
Smear_brush_height=MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_width=MAX_PAINTBRUSH_SIZE;
|
||||
free(Smear_brush);
|
||||
Smear_brush=new_smear_brush;
|
||||
}
|
||||
return return_code;
|
||||
Smear_brush_width=new_smear_brush_width;
|
||||
Smear_brush_height=new_smear_brush_height;
|
||||
|
||||
// Save or free the old brush pixels
|
||||
if (old_brush)
|
||||
*old_brush=Brush;
|
||||
else
|
||||
free(old_brush);
|
||||
// Assign new brush
|
||||
Brush=new_brush;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@ -723,7 +727,7 @@ void Capture_brush(short start_x,short start_y,short end_x,short end_y,short cle
|
||||
if (start_y+new_brush_height>Main_image_height)
|
||||
new_brush_height=Main_image_height-start_y;
|
||||
|
||||
if (Realloc_brush(new_brush_width, new_brush_height) != 0)
|
||||
if (Realloc_brush(new_brush_width, new_brush_height, NULL, NULL))
|
||||
return; // Unable to allocate the new brush, keep the old one.
|
||||
|
||||
Copy_image_to_brush(start_x,start_y,Brush_width,Brush_height,Main_image_width);
|
||||
@ -746,32 +750,22 @@ void Capture_brush(short start_x,short start_y,short end_x,short end_y,short cle
|
||||
}
|
||||
|
||||
|
||||
void Rotate_90_deg()
|
||||
void Rotate_90_deg(void)
|
||||
{
|
||||
short temp;
|
||||
byte * new_brush;
|
||||
|
||||
new_brush=(byte *)malloc(((size_t)Brush_height)*Brush_width);
|
||||
if (new_brush)
|
||||
byte * old_brush;
|
||||
|
||||
if (Realloc_brush(Brush_height, Brush_width, NULL, &old_brush))
|
||||
{
|
||||
Rotate_90_deg_lowlevel(Brush,new_brush,Brush_width,Brush_height);
|
||||
free(Brush);
|
||||
Brush=new_brush;
|
||||
|
||||
temp=Brush_width;
|
||||
Brush_width=Brush_height;
|
||||
Brush_height=temp;
|
||||
|
||||
temp=Smear_brush_width;
|
||||
Smear_brush_width=Smear_brush_height;
|
||||
Smear_brush_height=temp;
|
||||
|
||||
// On centre la prise sur la brosse
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
}
|
||||
else
|
||||
Error(0);
|
||||
return;
|
||||
}
|
||||
Rotate_90_deg_lowlevel(old_brush,Brush,Brush_height,Brush_width);
|
||||
|
||||
free(old_brush);
|
||||
|
||||
// On centre la prise sur la brosse
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
}
|
||||
|
||||
|
||||
@ -829,104 +823,88 @@ void Outline_brush(void)
|
||||
{
|
||||
long /*Pos,*/x_pos,y_pos;
|
||||
byte state;
|
||||
byte * new_brush;
|
||||
byte * temp;
|
||||
word width;
|
||||
word height;
|
||||
byte * old_brush;
|
||||
word old_width;
|
||||
word old_height;
|
||||
|
||||
|
||||
width=Brush_width+2;
|
||||
height=Brush_height+2;
|
||||
new_brush=(byte *)malloc(((long)width)*height);
|
||||
|
||||
if (new_brush)
|
||||
old_width=Brush_width;
|
||||
old_height=Brush_height;
|
||||
|
||||
if(Realloc_brush(Brush_width+2, Brush_height+2, NULL, &old_brush))
|
||||
{
|
||||
// On remplit la bordure ajoutée par la Backcolor
|
||||
memset(new_brush,Back_color,((long)width)*height);
|
||||
Error(0);
|
||||
return;
|
||||
}
|
||||
|
||||
// On copie la brosse courante dans la nouvelle
|
||||
Copy_part_of_image_to_another(Brush, // source
|
||||
0, 0, Brush_width, Brush_height, Brush_width,
|
||||
new_brush, // Destination
|
||||
1, 1, width);
|
||||
// On remplit la bordure ajoutée par la Backcolor
|
||||
memset(Brush,Back_color,((long)Brush_width)*Brush_height);
|
||||
|
||||
// On intervertit la nouvelle et l'ancienne brosse:
|
||||
temp=Brush;
|
||||
Brush=new_brush;
|
||||
Brush_width+=2;
|
||||
Brush_height+=2;
|
||||
width-=2;
|
||||
height-=2;
|
||||
// On copie la brosse courante dans la nouvelle
|
||||
Copy_part_of_image_to_another(old_brush, // source
|
||||
0, 0, old_width, old_height, old_width,
|
||||
Brush, // Destination
|
||||
1, 1, Brush_width);
|
||||
|
||||
// Si on "outline" avec une couleur différente de la Back_color on y va!
|
||||
if (Fore_color!=Back_color)
|
||||
// Si on "outline" avec une couleur différente de la Back_color on y va!
|
||||
if (Fore_color!=Back_color)
|
||||
{
|
||||
// 1er balayage (horizontal)
|
||||
for (y_pos=1; y_pos<Brush_height-1; y_pos++)
|
||||
{
|
||||
// 1er balayage (horizontal)
|
||||
for (y_pos=1; y_pos<Brush_height-1; y_pos++)
|
||||
{
|
||||
state=0;
|
||||
for (x_pos=1; x_pos<Brush_width-1; x_pos++)
|
||||
{
|
||||
if (temp[((y_pos-1)*width)+x_pos-1]==Back_color)
|
||||
{
|
||||
if (state != 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos,y_pos,Fore_color);
|
||||
state=0;
|
||||
}
|
||||
}
|
||||
else if (state == 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos-1,y_pos,Fore_color);
|
||||
state=1;
|
||||
}
|
||||
}
|
||||
// Cas du dernier pixel à droite de la ligne
|
||||
if (state != 0)
|
||||
Pixel_in_brush(x_pos,y_pos,Fore_color);
|
||||
}
|
||||
|
||||
// 2ème balayage (vertical)
|
||||
state=0;
|
||||
for (x_pos=1; x_pos<Brush_width-1; x_pos++)
|
||||
{
|
||||
state=0;
|
||||
for (y_pos=1; y_pos<Brush_height-1; y_pos++)
|
||||
if (old_brush[((y_pos-1)*old_width)+x_pos-1]==Back_color)
|
||||
{
|
||||
if (temp[((y_pos-1)*width)+x_pos-1]==Back_color)
|
||||
if (state != 0)
|
||||
{
|
||||
if (state != 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos,y_pos,Fore_color);
|
||||
state=0;
|
||||
}
|
||||
}
|
||||
else if (state == 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos,y_pos-1,Fore_color);
|
||||
state=1;
|
||||
Pixel_in_brush(x_pos,y_pos,Fore_color);
|
||||
state=0;
|
||||
}
|
||||
}
|
||||
// Cas du dernier pixel en bas de la colonne
|
||||
if (state != 0)
|
||||
Pixel_in_brush(x_pos,y_pos,Fore_color);
|
||||
else if (state == 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos-1,y_pos,Fore_color);
|
||||
state=1;
|
||||
}
|
||||
}
|
||||
// Cas du dernier pixel à droite de la ligne
|
||||
if (state != 0)
|
||||
Pixel_in_brush(x_pos,y_pos,Fore_color);
|
||||
}
|
||||
|
||||
// On recentre la prise sur la brosse
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
|
||||
free(temp); // Libération de l'ancienne brosse
|
||||
temp = NULL;
|
||||
|
||||
// Réallocation d'un buffer de Smear
|
||||
free(Smear_brush);
|
||||
Smear_brush_width=(Brush_width>MAX_PAINTBRUSH_SIZE)?Brush_width:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_height=(Brush_height>MAX_PAINTBRUSH_SIZE)?Brush_height:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush=(byte *)malloc(((long)Smear_brush_width)*Smear_brush_height);
|
||||
// 2ème balayage (vertical)
|
||||
for (x_pos=1; x_pos<Brush_width-1; x_pos++)
|
||||
{
|
||||
state=0;
|
||||
for (y_pos=1; y_pos<Brush_height-1; y_pos++)
|
||||
{
|
||||
if (old_brush[((y_pos-1)*old_width)+x_pos-1]==Back_color)
|
||||
{
|
||||
if (state != 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos,y_pos,Fore_color);
|
||||
state=0;
|
||||
}
|
||||
}
|
||||
else if (state == 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos,y_pos-1,Fore_color);
|
||||
state=1;
|
||||
}
|
||||
}
|
||||
// Cas du dernier pixel en bas de la colonne
|
||||
if (state != 0)
|
||||
Pixel_in_brush(x_pos,y_pos,Fore_color);
|
||||
}
|
||||
}
|
||||
else
|
||||
Error(0); // Pas assez de mémoire!
|
||||
|
||||
// On recentre la prise sur la brosse
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
|
||||
free(old_brush); // Libération de l'ancienne brosse
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -934,112 +912,96 @@ void Nibble_brush(void)
|
||||
{
|
||||
long x_pos,y_pos;
|
||||
byte state;
|
||||
byte * new_brush;
|
||||
byte * temp;
|
||||
word width;
|
||||
word height;
|
||||
byte * old_brush;
|
||||
word old_width;
|
||||
word old_height;
|
||||
|
||||
if ( (Brush_width>2) && (Brush_height>2) )
|
||||
{
|
||||
width=Brush_width-2;
|
||||
height=Brush_height-2;
|
||||
new_brush=(byte *)malloc(((long)width)*height);
|
||||
|
||||
if (new_brush)
|
||||
old_width=Brush_width;
|
||||
old_height=Brush_height;
|
||||
|
||||
if (Realloc_brush(Brush_width-2, Brush_height-2, NULL, &old_brush))
|
||||
{
|
||||
// On copie la brosse courante dans la nouvelle
|
||||
Copy_part_of_image_to_another(Brush, // source
|
||||
1,
|
||||
1,
|
||||
width,
|
||||
height,
|
||||
Brush_width,
|
||||
new_brush, // Destination
|
||||
0,
|
||||
0,
|
||||
width);
|
||||
Error(0);
|
||||
return;
|
||||
}
|
||||
// On copie l'ancienne brosse dans la nouvelle
|
||||
Copy_part_of_image_to_another(old_brush, // source
|
||||
1,
|
||||
1,
|
||||
old_width-2,
|
||||
old_height-2,
|
||||
old_width,
|
||||
Brush, // Destination
|
||||
0,
|
||||
0,
|
||||
Brush_width);
|
||||
|
||||
// On intervertit la nouvelle et l'ancienne brosse:
|
||||
temp=Brush;
|
||||
Brush=new_brush;
|
||||
Brush_width-=2;
|
||||
Brush_height-=2;
|
||||
width+=2;
|
||||
height+=2;
|
||||
|
||||
// 1er balayage (horizontal)
|
||||
for (y_pos=0; y_pos<Brush_height; y_pos++)
|
||||
{
|
||||
state=(temp[(y_pos+1)*width]!=Back_color);
|
||||
for (x_pos=0; x_pos<Brush_width; x_pos++)
|
||||
{
|
||||
if (temp[((y_pos+1)*width)+x_pos+1]==Back_color)
|
||||
{
|
||||
if (state != 0)
|
||||
{
|
||||
if (x_pos>0)
|
||||
Pixel_in_brush(x_pos-1,y_pos,Back_color);
|
||||
state=0;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (state == 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos,y_pos,Back_color);
|
||||
state=1;
|
||||
}
|
||||
}
|
||||
}
|
||||
// Cas du dernier pixel à droite de la ligne
|
||||
if (temp[((y_pos+1)*width)+x_pos+1]==Back_color)
|
||||
Pixel_in_brush(x_pos-1,y_pos,Back_color);
|
||||
}
|
||||
|
||||
// 2ème balayage (vertical)
|
||||
// 1er balayage (horizontal)
|
||||
for (y_pos=0; y_pos<Brush_height; y_pos++)
|
||||
{
|
||||
state=(old_brush[(y_pos+1)*old_width]!=Back_color);
|
||||
for (x_pos=0; x_pos<Brush_width; x_pos++)
|
||||
{
|
||||
state=(temp[width+x_pos+1]!=Back_color);;
|
||||
for (y_pos=0; y_pos<Brush_height; y_pos++)
|
||||
if (old_brush[((y_pos+1)*old_width)+x_pos+1]==Back_color)
|
||||
{
|
||||
if (temp[((y_pos+1)*width)+x_pos+1]==Back_color)
|
||||
if (state != 0)
|
||||
{
|
||||
if (state)
|
||||
{
|
||||
if (y_pos>0)
|
||||
Pixel_in_brush(x_pos,y_pos-1,Back_color);
|
||||
state=0;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (state == 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos,y_pos,Back_color);
|
||||
state=1;
|
||||
}
|
||||
if (x_pos>0)
|
||||
Pixel_in_brush(x_pos-1,y_pos,Back_color);
|
||||
state=0;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (state == 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos,y_pos,Back_color);
|
||||
state=1;
|
||||
}
|
||||
}
|
||||
// Cas du dernier pixel en bas de la colonne
|
||||
if (temp[((y_pos+1)*width)+x_pos+1]==Back_color)
|
||||
Pixel_in_brush(x_pos,y_pos-1,Back_color);
|
||||
}
|
||||
|
||||
// On recentre la prise sur la brosse
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
|
||||
free(temp); // Libération de l'ancienne brosse
|
||||
temp = NULL;
|
||||
|
||||
// Réallocation d'un buffer de Smear
|
||||
free(Smear_brush);
|
||||
Smear_brush_width=(Brush_width>MAX_PAINTBRUSH_SIZE)?Brush_width:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_height=(Brush_height>MAX_PAINTBRUSH_SIZE)?Brush_height:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush=(byte *)malloc(((long)Smear_brush_width)*Smear_brush_height);
|
||||
// Cas du dernier pixel à droite de la ligne
|
||||
if (old_brush[((y_pos+1)*old_width)+x_pos+1]==Back_color)
|
||||
Pixel_in_brush(x_pos-1,y_pos,Back_color);
|
||||
}
|
||||
else
|
||||
Error(0); // Pas assez de mémoire!
|
||||
|
||||
// 2ème balayage (vertical)
|
||||
for (x_pos=0; x_pos<Brush_width; x_pos++)
|
||||
{
|
||||
state=(old_brush[old_width+x_pos+1]!=Back_color);;
|
||||
for (y_pos=0; y_pos<Brush_height; y_pos++)
|
||||
{
|
||||
if (old_brush[((y_pos+1)*old_width)+x_pos+1]==Back_color)
|
||||
{
|
||||
if (state)
|
||||
{
|
||||
if (y_pos>0)
|
||||
Pixel_in_brush(x_pos,y_pos-1,Back_color);
|
||||
state=0;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (state == 0)
|
||||
{
|
||||
Pixel_in_brush(x_pos,y_pos,Back_color);
|
||||
state=1;
|
||||
}
|
||||
}
|
||||
}
|
||||
// Cas du dernier pixel en bas de la colonne
|
||||
if (old_brush[((y_pos+1)*old_width)+x_pos+1]==Back_color)
|
||||
Pixel_in_brush(x_pos,y_pos-1,Back_color);
|
||||
}
|
||||
|
||||
free(old_brush);
|
||||
|
||||
// On recentre la prise sur la brosse
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@ -1057,7 +1019,6 @@ void Capture_brush_with_lasso(int vertices, short * points,short clear)
|
||||
word new_brush_width;
|
||||
word new_brush_height;
|
||||
|
||||
|
||||
// On recherche les bornes de la brosse:
|
||||
for (temp=0; temp<2*vertices; temp+=2)
|
||||
{
|
||||
@ -1099,46 +1060,15 @@ void Capture_brush_with_lasso(int vertices, short * points,short clear)
|
||||
new_brush_width=(end_x-start_x)+1;
|
||||
new_brush_height=(end_y-start_y)+1;
|
||||
|
||||
if ( (((long)Brush_height)*Brush_width) !=
|
||||
(((long)new_brush_height)*new_brush_width) )
|
||||
{
|
||||
free(Brush);
|
||||
Brush=(byte *)malloc(((long)new_brush_height)*new_brush_width);
|
||||
if (!Brush)
|
||||
{
|
||||
Error(0);
|
||||
|
||||
Brush=(byte *)malloc(1*1);
|
||||
if(Brush==NULL) Error(ERROR_MEMORY);
|
||||
new_brush_height=new_brush_width=1;
|
||||
*Brush=Fore_color;
|
||||
}
|
||||
}
|
||||
Brush_width=new_brush_width;
|
||||
Brush_height=new_brush_height;
|
||||
|
||||
free(Smear_brush);
|
||||
Smear_brush_width=(Brush_width>MAX_PAINTBRUSH_SIZE)?Brush_width:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_height=(Brush_height>MAX_PAINTBRUSH_SIZE)?Brush_height:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush=(byte *)malloc(((long)Smear_brush_height)*Smear_brush_width);
|
||||
|
||||
if (!Smear_brush) // On ne peut même pas allouer la brosse du smear!
|
||||
if (Realloc_brush(new_brush_width, new_brush_height, NULL, NULL))
|
||||
{
|
||||
Error(0);
|
||||
|
||||
free(Brush);
|
||||
Brush=(byte *)malloc(1*1);
|
||||
if(Brush==NULL) Error(ERROR_MEMORY);
|
||||
Brush_height=1;
|
||||
Brush_width=1;
|
||||
|
||||
Smear_brush=(byte *)malloc(MAX_PAINTBRUSH_SIZE*MAX_PAINTBRUSH_SIZE);
|
||||
Smear_brush_height=MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_width=MAX_PAINTBRUSH_SIZE;
|
||||
return;
|
||||
}
|
||||
|
||||
Brush_offset_X=start_x;
|
||||
Brush_offset_Y=start_y;
|
||||
|
||||
Pixel_figure=Pixel_figure_in_brush;
|
||||
|
||||
memset(Brush,Back_color,(long)Brush_width*Brush_height);
|
||||
@ -1199,50 +1129,25 @@ void Stretch_brush(short x1, short y1, short x2, short y2)
|
||||
}
|
||||
new_brush_height++;
|
||||
|
||||
// Free some memory
|
||||
free(Smear_brush);
|
||||
Smear_brush = NULL;
|
||||
|
||||
if ((new_brush=((byte *)malloc(new_brush_width*new_brush_height))))
|
||||
new_brush=((byte *)malloc(new_brush_width*new_brush_height));
|
||||
if (!new_brush)
|
||||
{
|
||||
Rescale(Brush, Brush_width, Brush_height, new_brush, new_brush_width, new_brush_height, x2<x1, y2<y1);
|
||||
|
||||
free(Brush);
|
||||
Brush=new_brush;
|
||||
|
||||
Brush_width=new_brush_width;
|
||||
Brush_height=new_brush_height;
|
||||
|
||||
Smear_brush_width=(Brush_width>MAX_PAINTBRUSH_SIZE)?Brush_width:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_height=(Brush_height>MAX_PAINTBRUSH_SIZE)?Brush_height:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush=(byte *)malloc(((long)Smear_brush_height)*Smear_brush_width);
|
||||
|
||||
if (!Smear_brush) // On ne peut même pas allouer la brosse du smear!
|
||||
{
|
||||
Error(0);
|
||||
|
||||
free(Brush);
|
||||
Brush=(byte *)malloc(1*1);
|
||||
Brush_height=1;
|
||||
Brush_width=1;
|
||||
|
||||
Smear_brush=(byte *)malloc(MAX_PAINTBRUSH_SIZE*MAX_PAINTBRUSH_SIZE);
|
||||
Smear_brush_height=MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_width=MAX_PAINTBRUSH_SIZE;
|
||||
}
|
||||
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Ici la libération de mémoire n'a pas suffi donc on remet dans l'état
|
||||
// où c'etait avant. On a juste à réallouer la Smear_brush car il y a
|
||||
// normalement la place pour elle puisque rien d'autre n'a pu être alloué
|
||||
// entre temps.
|
||||
Smear_brush=(byte *)malloc(((long)Smear_brush_height)*Smear_brush_width);
|
||||
Error(0);
|
||||
return;
|
||||
}
|
||||
|
||||
Rescale(Brush, Brush_width, Brush_height, new_brush, new_brush_width, new_brush_height, x2<x1, y2<y1);
|
||||
|
||||
if (Realloc_brush(new_brush_width, new_brush_height, new_brush, NULL))
|
||||
{
|
||||
free(new_brush);
|
||||
Error(0);
|
||||
return;
|
||||
}
|
||||
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -1473,9 +1378,6 @@ void Distort_brush(short x1, short y1, short x2, short y2, short x3, short y3, s
|
||||
short min_x, max_x, min_y, max_y;
|
||||
short width, height;
|
||||
byte * new_brush;
|
||||
byte * new_smear_brush;
|
||||
short new_smear_brush_width;
|
||||
short new_smear_brush_height;
|
||||
|
||||
// Move all coordinates to start on (0,0)
|
||||
min_x=Min4(x1,x2,x3,x4);
|
||||
@ -1496,24 +1398,11 @@ void Distort_brush(short x1, short y1, short x2, short y2, short x3, short y3, s
|
||||
width=Max(max_x-min_x, 1);
|
||||
height=Max(max_y-min_y, 1);
|
||||
|
||||
new_smear_brush_width=(width>MAX_PAINTBRUSH_SIZE)?width:MAX_PAINTBRUSH_SIZE;
|
||||
new_smear_brush_height=(height>MAX_PAINTBRUSH_SIZE)?height:MAX_PAINTBRUSH_SIZE;
|
||||
|
||||
new_smear_brush=(byte *)malloc(((long)new_smear_brush_height)*new_smear_brush_width);
|
||||
if (! new_smear_brush)
|
||||
{
|
||||
// Out of memory while allocating new smear brush
|
||||
Error(0);
|
||||
return;
|
||||
}
|
||||
|
||||
new_brush=((byte *)malloc((long)width*height));
|
||||
if (!new_brush)
|
||||
{
|
||||
// Out of memory while allocating new brush
|
||||
Error(0);
|
||||
free(new_smear_brush);
|
||||
new_smear_brush = NULL;
|
||||
return;
|
||||
}
|
||||
|
||||
@ -1526,18 +1415,12 @@ void Distort_brush(short x1, short y1, short x2, short y2, short x3, short y3, s
|
||||
Distort_buffer_width=width;
|
||||
Draw_brush_linear_distort(0, 0, (Brush_width<<16), (Brush_height<<16), (x1<<16), (y1<<16), (x2<<16), (y2<<16), (x3<<16), (y3<<16), (x4<<16), (y4<<16));
|
||||
|
||||
// Free old brushes
|
||||
free(Smear_brush);
|
||||
free(Brush);
|
||||
|
||||
// Point to the new ones
|
||||
Brush=new_brush;
|
||||
Brush_width=width;
|
||||
Brush_height=height;
|
||||
|
||||
Smear_brush=new_smear_brush;
|
||||
Smear_brush_width=new_smear_brush_width;
|
||||
Smear_brush_height=new_smear_brush_height;
|
||||
if (Realloc_brush(width, height, new_brush, NULL))
|
||||
{
|
||||
free(new_brush);
|
||||
Error(0);
|
||||
return;
|
||||
}
|
||||
|
||||
// Re-center brush handle
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
@ -1815,54 +1698,30 @@ void Rotate_brush(float angle)
|
||||
new_brush_width=x_max+1-x_min;
|
||||
new_brush_height=y_max+1-y_min;
|
||||
|
||||
free(Smear_brush); // On libère un peu de mémoire
|
||||
Smear_brush = NULL;
|
||||
|
||||
if ((new_brush=((byte *)malloc(new_brush_width*new_brush_height))))
|
||||
new_brush=(byte *)malloc(new_brush_width*new_brush_height);
|
||||
|
||||
if (!new_brush)
|
||||
{
|
||||
// Et maintenant on calcule la nouvelle brosse tournée.
|
||||
Compute_quad_texture(x1,y1, 0, 0,
|
||||
x2,y2,Brush_width-1, 0,
|
||||
x3,y3, 0,Brush_height-1,
|
||||
x4,y4,Brush_width-1,Brush_height-1,
|
||||
new_brush,new_brush_width,new_brush_height);
|
||||
|
||||
free(Brush);
|
||||
Brush=new_brush;
|
||||
|
||||
Brush_width=new_brush_width;
|
||||
Brush_height=new_brush_height;
|
||||
|
||||
Smear_brush_width=(Brush_width>MAX_PAINTBRUSH_SIZE)?Brush_width:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_height=(Brush_height>MAX_PAINTBRUSH_SIZE)?Brush_height:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush=(byte *)malloc(((long)Smear_brush_height)*Smear_brush_width);
|
||||
|
||||
if (!Smear_brush) // On ne peut même pas allouer la brosse du smear!
|
||||
{
|
||||
Error(0);
|
||||
|
||||
free(Brush);
|
||||
Brush=(byte *)malloc(1*1);
|
||||
Brush_height=1;
|
||||
Brush_width=1;
|
||||
|
||||
Smear_brush=(byte *)malloc(MAX_PAINTBRUSH_SIZE*MAX_PAINTBRUSH_SIZE);
|
||||
Smear_brush_height=MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_width=MAX_PAINTBRUSH_SIZE;
|
||||
}
|
||||
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Ici la libération de mémoire n'a pas suffit donc on remet dans l'état
|
||||
// où c'etait avant. On a juste à réallouer la Smear_brush car il y a
|
||||
// normalement la place pour elle puisque rien d'autre n'a pu être alloué
|
||||
// entre temps.
|
||||
Smear_brush=(byte *)malloc(((long)Smear_brush_height)*Smear_brush_width);
|
||||
Error(0);
|
||||
return;
|
||||
}
|
||||
// Et maintenant on calcule la nouvelle brosse tournée.
|
||||
Compute_quad_texture(x1,y1, 0, 0,
|
||||
x2,y2,Brush_width-1, 0,
|
||||
x3,y3, 0,Brush_height-1,
|
||||
x4,y4,Brush_width-1,Brush_height-1,
|
||||
new_brush,new_brush_width,new_brush_height);
|
||||
|
||||
if (Realloc_brush(new_brush_width, new_brush_height, new_brush, NULL))
|
||||
{
|
||||
free(new_brush);
|
||||
return;
|
||||
}
|
||||
|
||||
// Center offsets
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
13
src/brush.h
13
src/brush.h
@ -111,9 +111,16 @@ void Capture_brush_with_lasso(int vertices, short * points,short clear);
|
||||
|
||||
|
||||
///
|
||||
/// Changes the Brush size, discarding its previous content.
|
||||
/// @return 0 OK, 1 Failed
|
||||
byte Realloc_brush(word new_brush_width, word new_brush_height);
|
||||
/// Changes the Brush size.
|
||||
/// @return 0 on success, non-zero on failure (memory?).
|
||||
/// @param new_brush: Optionally, you can provide an already allocated new
|
||||
/// brush - otherwise, this function performs the allocation.
|
||||
/// @param old_brush: If the caller passes NULL, this function will free the old
|
||||
/// pixel data. If the caller provides the address of a (free) byte
|
||||
/// pointer, the function will make it point to the original pixel data,
|
||||
/// in this case it will be the caller's responsibility to free() it
|
||||
/// (after transferring pixels to Brush, usually).
|
||||
byte Realloc_brush(word new_brush_width, word new_brush_height, byte *new_brush, byte **old_brush);
|
||||
|
||||
|
||||
|
||||
|
||||
@ -3152,21 +3152,14 @@ void Load_picture(byte image)
|
||||
//if (!use_brush_palette)
|
||||
// memcpy(Main_palette,initial_palette,sizeof(T_Palette));
|
||||
|
||||
if (File_error==3) // On ne peut pas allouer la brosse
|
||||
if (File_error==3) // Memory allocation error when loading brush
|
||||
{
|
||||
free(Brush);
|
||||
Brush=(byte *)malloc(1*1);
|
||||
Brush_height=1;
|
||||
Brush_width=1;
|
||||
*Brush=Fore_color;
|
||||
|
||||
free(Smear_brush);
|
||||
Smear_brush=(byte *)malloc(MAX_PAINTBRUSH_SIZE*MAX_PAINTBRUSH_SIZE);
|
||||
Smear_brush_height=MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_width=MAX_PAINTBRUSH_SIZE;
|
||||
// Nothing to do here.
|
||||
// Previous versions of Grafx2 would have damaged the Brush,
|
||||
// and need reset it here, but now the loading is done in separate
|
||||
// memory buffers.
|
||||
}
|
||||
|
||||
|
||||
Tiling_offset_X=0;
|
||||
Tiling_offset_Y=0;
|
||||
|
||||
@ -4764,7 +4757,7 @@ void Draw_one_font_name(word x, word y, word index, byte highlighted)
|
||||
Print_in_window(x,y,Font_label(index), MC_Black, (highlighted)?MC_Dark:MC_Light);
|
||||
}
|
||||
|
||||
void Button_Text()
|
||||
void Button_Text(void)
|
||||
{
|
||||
static char str[256]="";
|
||||
static int font_size=32;
|
||||
@ -4987,11 +4980,15 @@ void Button_Text()
|
||||
Error(0);
|
||||
return;
|
||||
}
|
||||
free(Brush);
|
||||
if (Realloc_brush(new_width, new_height, new_brush, NULL))
|
||||
{
|
||||
free(new_brush);
|
||||
Close_window();
|
||||
Unselect_button(BUTTON_TEXT);
|
||||
Display_cursor();
|
||||
Error(0);
|
||||
}
|
||||
|
||||
Brush=new_brush;
|
||||
Brush_width=new_width;
|
||||
Brush_height=new_height;
|
||||
Brush_offset_X=Brush_width>>1;
|
||||
Brush_offset_Y=Brush_height>>1;
|
||||
|
||||
@ -5281,14 +5278,16 @@ byte Restore_brush(int index)
|
||||
// Color brushes
|
||||
if (shape == PAINTBRUSH_SHAPE_COLOR_BRUSH ||
|
||||
shape == PAINTBRUSH_SHAPE_MONO_BRUSH)
|
||||
{
|
||||
{
|
||||
Paintbrush_shape=shape;
|
||||
Realloc_brush(Brush_container[index].Width,Brush_container[index].Height);
|
||||
// Realloc sets Brush_width and Brush_height to new size.
|
||||
memcpy(Brush, Brush_container[index].Brush, Brush_height*Brush_width);
|
||||
|
||||
Brush_offset_X=Brush_width>>1;
|
||||
Brush_offset_Y=Brush_height>>1;
|
||||
if (!Realloc_brush(Brush_container[index].Width,Brush_container[index].Height,NULL,NULL))
|
||||
{
|
||||
// Realloc sets Brush_width and Brush_height to new size.
|
||||
memcpy(Brush, Brush_container[index].Brush, Brush_height*Brush_width);
|
||||
|
||||
Brush_offset_X=Brush_width>>1;
|
||||
Brush_offset_Y=Brush_height>>1;
|
||||
}
|
||||
|
||||
}
|
||||
Change_paintbrush_shape(shape);
|
||||
|
||||
@ -40,6 +40,7 @@
|
||||
#include "sdlscreen.h"
|
||||
#include "struct.h"
|
||||
#include "windows.h"
|
||||
#include "brush.h"
|
||||
|
||||
//---------- Menu dans lequel on tagge des couleurs (genre Stencil) ----------
|
||||
void Menu_tag_colors(char * window_title, byte * table, byte * mode, byte can_cancel, const char *help_section, word close_shortcut)
|
||||
@ -985,8 +986,8 @@ void Button_Sieve_menu(void)
|
||||
{
|
||||
clicked_button=Window_clicked_button();
|
||||
|
||||
origin_x=Window_pos_X+(Menu_factor_X*Window_special_button_list->Pos_X);
|
||||
origin_y=Window_pos_Y+(Menu_factor_Y*Window_special_button_list->Pos_Y);
|
||||
origin_x=Window_pos_X+(Menu_factor_X*Window_special_button_list->Pos_X);
|
||||
origin_y=Window_pos_Y+(Menu_factor_Y*Window_special_button_list->Pos_Y);
|
||||
|
||||
|
||||
switch (clicked_button)
|
||||
@ -1073,15 +1074,17 @@ void Button_Sieve_menu(void)
|
||||
break;
|
||||
|
||||
case 7 : // Transfer to brush
|
||||
Brush_width=Sieve_width;
|
||||
Brush_height=Sieve_height;
|
||||
free(Brush);
|
||||
Brush=(byte *)malloc(((long)Brush_height)*Brush_width);
|
||||
|
||||
if (Realloc_brush(Sieve_width, Sieve_height, NULL, NULL))
|
||||
break;
|
||||
|
||||
for (y_pos=0; y_pos<Sieve_height; y_pos++)
|
||||
for (x_pos=0; x_pos<Sieve_width; x_pos++)
|
||||
Pixel_in_brush(x_pos,y_pos,(Sieve[x_pos][y_pos])?Fore_color:Back_color);
|
||||
|
||||
Brush_offset_X=(Brush_width>>1);
|
||||
Brush_offset_Y=(Brush_height>>1);
|
||||
|
||||
Change_paintbrush_shape(PAINTBRUSH_SHAPE_COLOR_BRUSH);
|
||||
break;
|
||||
|
||||
|
||||
@ -161,10 +161,11 @@ int L_SetBrushSize(lua_State* L)
|
||||
LUA_ARG_NUMBER(1, "setbrushsize", w, 1, 10000);
|
||||
LUA_ARG_NUMBER(2, "setbrushsize", h, 1, 10000);
|
||||
|
||||
if (Realloc_brush(w, h))
|
||||
if (Realloc_brush(w, h, NULL, NULL))
|
||||
{
|
||||
return luaL_error(L, "setbrushsize: Resize failed");
|
||||
}
|
||||
|
||||
Brush_was_altered=1;
|
||||
// Fill with Back_color
|
||||
memset(Brush,Back_color,(long)Brush_width*Brush_height);
|
||||
|
||||
@ -48,6 +48,7 @@
|
||||
#include "struct.h"
|
||||
#include "windows.h"
|
||||
#include "engine.h"
|
||||
#include "brush.h"
|
||||
|
||||
// -- PKM -------------------------------------------------------------------
|
||||
void Test_PKM(T_IO_Context *);
|
||||
@ -773,19 +774,13 @@ void Load_image(T_IO_Context *context)
|
||||
}
|
||||
else if (context->Type == CONTEXT_BRUSH && File_error==0)
|
||||
{
|
||||
free(Brush);
|
||||
Brush=context->Buffer_image;
|
||||
context->Buffer_image = NULL;
|
||||
|
||||
Brush_width=context->Width;
|
||||
Brush_height=context->Height;
|
||||
|
||||
free(Smear_brush);
|
||||
Smear_brush_width=(Brush_width>MAX_PAINTBRUSH_SIZE)?Brush_width:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush_height=(Brush_height>MAX_PAINTBRUSH_SIZE)?Brush_height:MAX_PAINTBRUSH_SIZE;
|
||||
Smear_brush=(byte *)malloc(Smear_brush_width*Smear_brush_height);
|
||||
if (!Smear_brush)
|
||||
|
||||
if (Realloc_brush(context->Width, context->Height, context->Buffer_image, NULL))
|
||||
{
|
||||
File_error=3;
|
||||
free(context->Buffer_image);
|
||||
}
|
||||
context->Buffer_image = NULL;
|
||||
}
|
||||
else if (context->Type == CONTEXT_SURFACE)
|
||||
{
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user