2011-10-01 40 views
6

Tôi đang tạo một trình tạo hình đại diện trong đó các thành phần hình đại diện từ các tệp PNG có độ trong suốt. Các tệp là những thứ như body_1.png hoặc leg_5.png. Độ trong suốt xung quanh các phần nhưng không nằm trong chúng và các hình ảnh đều là màu xám. Các bộ phận được phân lớp tốt và tôi có thể có được một avatar màu xám.Cách thích hợp để tô màu hình ảnh thang độ xám với độ trong suốt trong Java là gì?

Tôi muốn có thể tô màu các phần này một cách linh hoạt, nhưng cho đến nay tôi không có may mắn. Tôi đã thử chuyển đổi dữ liệu pixel từ RGB thành HSL và sử dụng giá trị L của pixel ban đầu, trong khi cung cấp giá trị H màu mới, nhưng kết quả không lớn.

Tôi đã xem Colorize grayscale image nhưng tôi dường như không thể làm những gì anh ấy nói về công việc trong Java. Tôi kết thúc với một hình ảnh có màu sắc neon khá tươi sáng ở khắp mọi nơi.

Điều tôi muốn là duy trì độ trong suốt, đồng thời tô màu phần màu xám. Các đường viền màu đen vẫn phải là màu đen và các vùng đánh dấu màu trắng vẫn phải là màu trắng (tôi nghĩ).

Có ai có cách hay để thực hiện việc này không?

EDIT:

Dưới đây là một hình ảnh tôi có thể cố gắng để màu: Sample Body

lần nữa, tôi muốn duy trì mức độ sáng của hình ảnh màu xám (vì vậy cương ở lại tối, các gradient có thể nhìn thấy, và các mảng trắng có màu trắng).

Tôi đã có thể nhận được một LookupOp hoạt động phần nào dựa trên Colorizing images in Java nhưng màu sắc luôn luôn trông buồn tẻ và tối.

Dưới đây là một ví dụ về đầu ra của tôi: Sample Output

Màu rằng đã được sử dụng là một trong này (lưu ý sự khác biệt độ sáng): http://www.color-hex.com/color/b124e7

Đây là lookupOp tôi

protected LookupOp createColorizeOp(short R1, short G1, short B1) { 
    short[] alpha = new short[256]; 
short[] red = new short[256]; 
short[] green = new short[256]; 
short[] blue = new short[256]; 

//int Y = 0.3*R + 0.59*G + 0.11*B 

    for (short i = 0; i < 30; i++) { 
    alpha[i] = i; 
     red[i] = i; 
     green[i] = i; 
     blue[i] = i; 
} 

for (short i = 30; i < 256; i++) {  
    alpha[i] = i; 
    red[i] = (short)Math.round((R1 + i*.3)/2); 
     green[i] = (short)Math.round((G1 + i*.59)/2); 
     blue[i] = (short)Math.round((B1 + i*.11)/2); 

    } 


    short[][] data = new short[][] { 
      red, green, blue, alpha 
    }; 

    LookupTable lookupTable = new ShortLookupTable(0, data); 
    return new LookupOp(lookupTable, null); 
} 

EDIT 2 : Tôi đã thay đổi LookupOp của mình để sử dụng như sau và có nhiều màu sắc đẹp hơn:

red[i] = (short)((R1)*(float)i/255.0); 
green[i] = (short)((G1)*(float)i/255.0); 
blue[i] = (short)((B1)*(float)i/255.0); 
+0

Để được trợ giúp tốt hơn sớm hơn, hãy đăng [SSCCE] (http://pscode.org/sscce.html). Sử dụng hình ảnh trong một SSCCE là khó khăn. Bạn có thể liên kết nóng với hình ảnh trên internet hoặc tạo một hình ảnh trong mã. –

Trả lời

2

Có vẻ như những gì sẽ làm việc cho bạn là một cái gì đó như thế này:

for each pixel 
    if pixel is white, black or transparent then leave it alone 
    else 
     apply desired H and S and make grayscale value the L 
     convert new HSL back to RGB 

Sửa: sau khi nhìn thấy hình ảnh của bạn tôi có một vài ý kiến:

Có vẻ như bạn muốn điều trị đặc biệt tông màu tối , vì bạn không tô màu bất cứ thứ gì dưới 30. Theo cùng một logic, bạn cũng không được miễn colorizing các giá trị cao hơn? Điều đó sẽ ngăn chặn người da trắng và gần người da trắng khỏi bị nhuộm màu.

Bạn không nên đặt giá trị alpha cùng với RGB. Giá trị alpha từ hình ảnh gốc phải luôn được giữ nguyên. Thuật toán bảng tra cứu của bạn chỉ nên ảnh hưởng đến RGB.

Trong khi bạn nói rằng bạn đã thử HSL, đó không phải là mã mà bạn đã đăng. Bạn nên làm màu sắc của bạn trong HSL, sau đó chuyển đổi các màu sắc kết quả thành RGB cho bảng tra cứu của bạn vì nó sẽ giữ nguyên độ sáng ban đầu của thang độ xám.Tạo bảng tra cứu của bạn có thể giống như sau:

short H = ??; // your favorite hue 
short S = ??; // your favorite saturation 
for (short i = 0; i < 256; i++) { 
    if (i < 30 || i > 226) { 
     red[i] = green[i] = blue[i] = i; // don't do alpha here 
    } 
    else { 
     HSL_to_RGB(H, S, i, red[i], green[i], blue[i]) 
    } 
} 

Lưu ý: bạn phải cung cấp chức năng chuyển đổi HSL sang RGB. Xem câu trả lời của tôi trên Colorize grayscale image để biết các liên kết đến mã nguồn.

Các vấn đề liên quan