Witam, zaczynam się bawić Javą i chciałbym przekształcić kolory wczytanego obrazka z RGB na HSL. Niestety, nie za bardzo wiem, jak to zrobić - chodzi o poprawne odwołanie.
Mój poniższy kod robi jedną rzecz - wczytuje obrazek o podanej nazwie. Co dodać, jak się odwołać do obrazka, żeby zmienić kolory?
Proszę przy okazji o poprawki kodu - jak widzicie, że coś jest bzdurą, to napiszcie, żebym się później nie zaplątał w trakcie rozbudowywania programu. :>
import java.util.Scanner;
import javax.swing.*;
import java.awt.*;
import java.awt.geom.*;
import java.awt.Color;
import java.awt.BasicStroke;
import java.io.*;
import java.awt.image.*;
import javax.imageio.*;
public class Zadanie2a
{
static JFrame ramka;
private static Scanner in;
public static void main(String[] args)
{
in = new Scanner(System.in);
Zadanie2a zadanie = new Zadanie2a();
zadanie.GUI();
String image_name;
BufferedImage input_image;
int img_width, img_height;
input_image = null;
System.out.println( "Podaj nazwę pliku: " );
image_name = readStr();
try
{
input_image = ImageIO.read( new File( image_name ) );
}
catch (IOException e) {
System.out.println("Błąd odczytu obrazka.");
}
img_height = input_image.getHeight();
img_width = input_image.getWidth();
Graphics g = ramka.getGraphics();
Graphics2D g2d = (Graphics2D) g;
g2d.drawImage( input_image, 60, 60, null);
System.out.println( "Wciśnij jakiś klawisz, aby zakończyć. ");
readln();
System.exit(0);
}
public void GUI()
{
ramka = new JFrame();
ramka.setDefaultCloseOperation( JFrame.EXIT_ON_CLOSE );
ramka.getContentPane().add(new MojPanelRysunkowy());
ramka.setSize( 800, 700 );
ramka.setVisible(true);
}
class MojPanelRysunkowy extends JPanel
{
MojPanelRysunkowy()
{
super();
setBackground( new Color( 200, 200, 200) );
JButton button = new JButton();
button.setLocation( 100, 100 );
// add( button );
button.setVisible( true );
}
public void paintComponent( Graphics g)
{
super.paintComponent(g);
}
}
static void readln()
{
try
{
while( System.in.read() != '\n' );
}
catch( Throwable obj )
{
}
}
static String readStr() {
return in.next();
}
static int readInt()
{
return (in.nextInt());
}
}
Poniżej znajduje się kod (znaleziony w Internecie - nie wiem, czy dobry) zmieniający RGB do HSL:
private void rgb2hsl(int r, int g, int b, int hsl[]) {
float var_R = ( r / 255f );
float var_G = ( g / 255f );
float var_B = ( b / 255f );
float var_Min; //Min. value of RGB
float var_Max; //Max. value of RGB
float del_Max; //Delta RGB value
if (var_R > var_G)
{ var_Min = var_G; var_Max = var_R; }
else
{ var_Min = var_R; var_Max = var_G; }
if (var_B > var_Max) var_Max = var_B;
if (var_B < var_Min) var_Min = var_B;
del_Max = var_Max - var_Min;
float H = 0, S, L;
L = ( var_Max + var_Min ) / 2f;
if ( del_Max == 0 ) { H = 0; S = 0; } // gray
else { //Chroma
if ( L < 0.5 )
S = del_Max / ( var_Max + var_Min );
else
S = del_Max / ( 2 - var_Max - var_Min );
float del_R = ( ( ( var_Max - var_R ) / 6f ) + ( del_Max / 2f ) ) / del_Max;
float del_G = ( ( ( var_Max - var_G ) / 6f ) + ( del_Max / 2f ) ) / del_Max;
float del_B = ( ( ( var_Max - var_B ) / 6f ) + ( del_Max / 2f ) ) / del_Max;
if ( var_R == var_Max )
H = del_B - del_G;
else if ( var_G == var_Max )
H = ( 1 / 3f ) + del_R - del_B;
else if ( var_B == var_Max )
H = ( 2 / 3f ) + del_G - del_R;
if ( H < 0 ) H += 1;
if ( H > 1 ) H -= 1;
}
hsl[0] = (int)(360*H);
hsl[1] = (int)(S*100);
hsl[2] = (int)(L*100);
}
Jak to połączyć, żeby było dobrze? ;-)