Tôi cần gỡ lỗi chương trình GLSL nhưng tôi không biết cách xuất kết quả trung gian. Có thể thực hiện một số dấu vết gỡ rối (như với printf) bằng GLSL không?Làm cách nào để gỡ lỗi trình đổ bóng GLSL?
Trả lời
Bạn không thể dễ dàng liên lạc lại với CPU từ bên trong GLSL. Sử dụng glslDevil hoặc các công cụ khác là đặt cược tốt nhất của bạn.
Printf sẽ yêu cầu cố gắng lấy lại CPU từ GPU chạy mã GLSL. Thay vào đó, bạn có thể thử đẩy trước màn hình. Thay vì cố gắng xuất văn bản, xuất ra một cái gì đó trực quan khác biệt với màn hình. Ví dụ: bạn có thể tô màu cho một thứ cụ thể chỉ khi bạn đạt đến điểm mã của mình nơi bạn muốn thêm printf. Nếu bạn cần printf một giá trị, bạn có thể đặt màu theo giá trị đó.
Điều gì xảy ra nếu lý do chính xác bạn muốn gỡ lỗi trình đổ bóng của bạn là vì không có gì xuất hiện trên màn hình? –
Tại sao bạn muốn gỡ lỗi mọi thứ? Bởi vì mã của nó và anh ta muốn kiểm tra giá trị thời gian chạy tôi sẽ gây nguy hiểm .... – RichieHH
[GLSL-Debugger] (http://glsl-debugger.github.io/) là một nhánh nguồn mở của glslDevil. – Magnus
Hiển thị kết xuất ngoại tuyến thành kết cấu và đánh giá dữ liệu của kết cấu. Bạn có thể tìm mã liên quan bằng cách googling cho "render to texture" opengl Sau đó sử dụng glReadPixels để đọc đầu ra vào một mảng và thực hiện các xác nhận trên nó (vì nhìn qua một mảng khổng lồ trong trình gỡ rối thường không thực sự hữu ích).
Ngoài ra, bạn có thể muốn tắt tính năng kẹp thành giá trị đầu ra không nằm trong khoảng từ 0 đến 1, chỉ được hỗ trợ cho floating point textures.
Cá nhân tôi đã bị làm phiền bởi sự cố gỡ lỗi đúng cách trong một thời gian. Có vẻ như không phải là một cách hay - Nếu có ai tìm thấy trình gỡ rối tốt (và không lỗi thời/không dùng nữa), hãy cho tôi biết.
Bất kỳ câu trả lời hoặc nhận xét nào cho biết "google xyz" đều bị cấm hoặc bị bỏ phiếu từ Stackoverflow. – gregoiregentil
void main(){
float bug=0.0;
vec3 tile=texture2D(colMap, coords.st).xyz;
vec4 col=vec4(tile, 1.0);
if(something) bug=1.0;
col.x+=bug;
gl_FragColor=col;
}
Tôi đã tìm thấy Transform Feedback là công cụ hữu ích để gỡ lỗi trình tạo bóng đỉnh. Bạn có thể sử dụng điều này để nắm bắt các giá trị của các đầu ra VS, và đọc chúng trở lại ở phía CPU, mà không cần phải đi qua rasterizer.
Here là một liên kết khác đến hướng dẫn về Chuyển đổi phản hồi.
Tôi đang chia sẻ một ví dụ về trình đổ bóng phân đoạn, cách tôi thực sự gỡ lỗi.
#version 410 core
uniform sampler2D samp;
in VS_OUT
{
vec4 color;
vec2 texcoord;
} fs_in;
out vec4 color;
void main(void)
{
vec4 sampColor;
if(texture2D(samp, fs_in.texcoord).x > 0.8f) //Check if Color contains red
sampColor = vec4(1.0f, 1.0f, 1.0f, 1.0f); //If yes, set it to white
else
sampColor = texture2D(samp, fs_in.texcoord); //else sample from original
color = sampColor;
}
Nếu bạn muốn hình dung các biến thể của một giá trị trên màn hình, bạn có thể sử dụng một hàm Heatmap tương tự như sau (tôi đã viết nó trong HLSL, nhưng nó rất dễ dàng để thích ứng với GLSL):
float4 HeatMapColor(float value, float minValue, float maxValue)
{
#define HEATMAP_COLORS_COUNT 6
float4 colors[HEATMAP_COLORS_COUNT] =
{
float4(0.32, 0.00, 0.32, 1.00),
float4(0.00, 0.00, 1.00, 1.00),
float4(0.00, 1.00, 0.00, 1.00),
float4(1.00, 1.00, 0.00, 1.00),
float4(1.00, 0.60, 0.00, 1.00),
float4(1.00, 0.00, 0.00, 1.00),
};
float ratio=(HEATMAP_COLORS_COUNT-1.0)*saturate((value-minValue)/(maxValue-minValue));
float indexMin=floor(ratio);
float indexMax=min(indexMin+1,HEATMAP_COLORS_COUNT-1);
return lerp(colors[indexMin], colors[indexMax], ratio-indexMin);
}
Sau đó, trong pixel shader của bạn, bạn chỉ ra một cái gì đó như:
return HeatMapColor(myValue, 0.00, 50.00);
Và có thể có được một ý tưởng về cách nó thay đổi trên pixel của bạn:
Tất nhiên bạn có thể sử dụng bất kỳ tập hợp các màu sắc mà bạn thích.
GLSL Sandbox khá tiện dụng đối với tôi đối với trình đổ bóng.
Không gỡ lỗi mỗi lần (đã được trả lời là không có khả năng) nhưng tiện dụng để xem các thay đổi về đầu ra nhanh chóng.
Câu trả lời hiện có là tất cả các công cụ tốt, nhưng tôi muốn chia sẻ thêm một ít đá quý có giá trị trong việc gỡ lỗi các vấn đề chính xác phức tạp trong trình đổ bóng GLSL. Với các số int rất lớn được biểu diễn như một điểm nổi, người ta cần phải cẩn thận để sử dụng sàn (n) và sàn (n + 0.5) đúng để thực hiện vòng() đến một int chính xác. Sau đó, có thể hiển thị một giá trị float là một int chính xác theo logic sau để đóng gói các thành phần byte vào các giá trị đầu ra R, G và B.
// Break components out of 24 bit float with rounded int value
// scaledWOB = (offset >> 8) & 0xFFFF
float scaledWOB = floor(offset/256.0);
// c2 = (scaledWOB >> 8) & 0xFF
float c2 = floor(scaledWOB/256.0);
// c0 = offset - (scaledWOB << 8)
float c0 = offset - floor(scaledWOB * 256.0);
// c1 = scaledWOB - (c2 << 8)
float c1 = scaledWOB - floor(c2 * 256.0);
// Normalize to byte range
vec4 pix;
pix.r = c0/255.0;
pix.g = c1/255.0;
pix.b = c2/255.0;
pix.a = 1.0;
gl_FragColor = pix;
Ở dưới cùng của câu trả lời này là một ví dụ về mã GLSL cho phép để sản xuất các giá trị đầy đủ float
như màu sắc, mã hóa IEEE 754 binary32
. Tôi sử dụng nó như sau (đoạn này đưa ra yy
thành phần của ma trận modelview):
Sau khi bạn có được điều này trên màn hình, bạn chỉ có thể lấy bất kỳ chọn màu, định dạng màu dưới dạng HTML (phụ 00
đến rgb
giá trị nếu bạn không cần độ chính xác cao hơn và thực hiện lần thứ hai để nhận byte thấp hơn nếu bạn thực hiện) và bạn nhận được biểu diễn thập lục phân của float
là IEEE 754 binary32
.
Đây là việc thực hiện thực tế của toColor()
:
#version 120
const int emax=127;
// Input: x>=0
// Output: base 2 exponent of x if (x!=0 && !isnan(x) && !isinf(x))
// -emax if x==0
// emax+1 otherwise
int floorLog2(float x)
{
if(x==0) return -emax;
// NOTE: there exist values of x, for which floor(log2(x)) will give wrong
// (off by one) result as compared to the one calculated with infinite precision.
// Thus we do it in a brute-force way.
for(int e=emax;e>=1-emax;--e)
if(x>=exp2(float(e))) return e;
// If we are here, x must be infinity or NaN
return emax+1;
}
// Input: any x
// Output: IEEE 754 biased exponent with bias=emax
int biasedExp(float x) { return emax+floorLog2(abs(x)); }
// Input: any x such that (!isnan(x) && !isinf(x))
// Output: significand AKA mantissa of x if !isnan(x) && !isinf(x)
// undefined otherwise
float significand(float x)
{
// converting int to float so that exp2(genType) gets correctly-typed value
float expo=floorLog2(abs(x));
return abs(x)/exp2(expo);
}
// Input: x\in[0,1)
// N>=0
// Output: Nth byte as counted from the highest byte in the fraction
int part(float x,int N)
{
// All comments about exactness here assume that underflow and overflow don't occur
const int byteShift=256;
// Multiplication is exact since it's just an increase of exponent by 8
for(int n=0;n<N;++n)
x*=byteShift;
// Cut higher bits away.
// $q \in [0,1) \cap \mathbb Q'.$
float q=fract(x);
// Shift and cut lower bits away. Cutting lower bits prevents potentially unexpected
// results of rounding by the GPU later in the pipeline when transforming to TrueColor
// the resulting subpixel value.
// $c \in [0,255] \cap \mathbb Z.$
// Multiplication is exact since it's just and increase of exponent by 8
float c=floor(byteShift*q);
return int(c);
}
// Input: any x acceptable to significand()
// Output: significand of x split to (8,8,8)-bit data vector
ivec3 significandAsIVec3(float x)
{
ivec3 result;
float sig=significand(x)/2; // shift all bits to fractional part
result.x=part(sig,0);
result.y=part(sig,1);
result.z=part(sig,2);
return result;
}
// Input: any x such that !isnan(x)
// Output: IEEE 754 defined binary32 number, packed as ivec4(byte3,byte2,byte1,byte0)
ivec4 packIEEE754binary32(float x)
{
int e = biasedExp(x);
// sign to bit 7
int s = x<0 ? 128 : 0;
ivec4 binary32;
binary32.yzw=significandAsIVec3(x);
// clear the implicit integer bit of significand
if(binary32.y>=128) binary32.y-=128;
// put lowest bit of exponent into its position, replacing just cleared integer bit
binary32.y+=128*int(mod(e,2));
// prepare high bits of exponent for fitting into their positions
e/=2;
// pack highest byte
binary32.x=e+s;
return binary32;
}
vec4 toColor(float x)
{
ivec4 binary32=packIEEE754binary32(x);
// Transform color components to [0,1] range.
// Division is inexact, but works reliably for all integers from 0 to 255 if
// the transformation to TrueColor by GPU uses rounding to nearest or upwards.
// The result will be multiplied by 255 back when transformed
// to TrueColor subpixel value by OpenGL.
return binary32/255.;
}
- 1. Cách gỡ lỗi trình đổ bóng trên Android
- 2. Trình đổ bóng GLSL để cuộn kết cấu
- 3. Tôi làm cách nào để cải thiện trình đổ bóng ảnh xuống WebGL/GLSL này
- 4. Làm cách nào để trình đổ bóng vertex chuyển thông tin màu vào trình đổ bóng phân đoạn?
- 5. Bạn có thể chuyển ma trận bằng cách tham chiếu trong trình đổ bóng GLSL không?
- 6. GLSL với trình đổ bóng phân đoạn chỉ hiển thị màu đen GL_POINTS
- 7. Làm cách nào để thêm bóng đổ vào UIButton?
- 8. Giá trị float không đổi trong trình đổ bóng GLSL - bất kỳ lý do nào để sử dụng đồng phục?
- 9. Làm thế nào để tạo ra nhiều đổ bóng đổ gradient?
- 10. Có cách nào để đổ một luồng từ trình gỡ lỗi trong VS
- 11. Tôi làm cách nào để sử dụng trình đổ bóng GLSL để áp dụng hiệu ứng nhòe hình tròn cho toàn cảnh?
- 12. Bất cứ ai có thể giải thích trình đổ bóng đoạn GLSL này đang làm gì không?
- 13. Gỡ lỗi mã GLSL trong webgl
- 14. Làm thế nào để console.log trong trình che bóng webgl?
- 15. Tạo bộ lọc mờ với trình đổ bóng - truy cập các pixel liền kề từ trình đổ bóng phân đoạn?
- 16. Làm cách nào để bạn kiểm tra trình kiểm tra OpenGL được viết bằng GLSL?
- 17. Trình tạo bóng GLSL mặc định trông như thế nào? cho phiên bản 330
- 18. iOS: Cách thêm bóng đổ và bóng đổ nét trên UIView?
- 19. Làm cách nào để gỡ lỗi trình tải khởi động?
- 20. Chuyển màu thông qua trình đổ bóng pixel trong HLSL
- 21. Biên dịch bóng đổ trong PyQt
- 22. Làm cách nào để gỡ lỗi NSManagedObjects trong trình gỡ lỗi XCode?
- 23. Làm cách nào để viết mã glsl có thể tái sử dụng?
- 24. Thêm bóng đổ vào UITableView
- 25. Cách tốt nhất để phát hiện NaN trong bóng đổ OpenGL
- 26. Thêm bóng đổ để trượt điều hướng
- 27. Bật tiện ích mở rộng trên trình đổ bóng Three.js
- 28. Làm cách nào để sử dụng trình gỡ lỗi gdb MinGW để gỡ lỗi chương trình C++ trong Windows?
- 29. Cách tốt nhất để thực hiện loại đổ bóng này?
- 30. Làm cách nào để có hiệu ứng đổ bóng "Glow" trong OpenGL ES 2.0?
... mà không cần sử dụng phần mềm bên ngoài như glslDevil. –
hãy xem [sửa lỗi in biến nổi và văn bản từ trình đổ vỡ đoạn GLSL] (https://stackoverflow.com/a/44797902/2521214) bạn chỉ cần đơn vị kết cấu dự phòng đơn cho phông chữ và trạng thái không đổi của giá trị được xuất trong khu vực in – Spektre