Cleanup: use r_* prefix for return args
[blender.git] / source / blender / editors / screen / glutil.c
index 57d97178be5f35524293c0187be29b4cc2c09455..fd65d81baadcadb331ecbe803355f25dbdaf6dfa 100644 (file)
 #include "BLI_rect.h"
 #include "BLI_utildefines.h"
 #include "BLI_math.h"
-#include "BLI_threads.h"
 
-#include "BKE_blender.h"
-#include "BKE_global.h"
-#include "BKE_colortools.h"
 #include "BKE_context.h"
 
 #include "BIF_gl.h"
 #include "BIF_glutil.h"
 
-#include "GPU_extensions.h"
 
 #include "IMB_colormanagement.h"
 #include "IMB_imbuf_types.h"
 
+#include "UI_interface.h"
+
 #ifndef GL_CLAMP_TO_EDGE
 #define GL_CLAMP_TO_EDGE                        0x812F
 #endif
@@ -137,7 +134,18 @@ const GLubyte stipple_diag_stripes_neg[128] = {
        0x0f, 0xf0, 0x0f, 0xf0, 0x1f, 0xe0, 0x1f, 0xe0,
        0x3f, 0xc0, 0x3f, 0xc0, 0x7f, 0x80, 0x7f, 0x80};
 
-
+const GLubyte stipple_checker_8px[128] = {
+       255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0,
+       255,  0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0,
+       0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255,
+       0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255,
+       255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0,
+       255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0,
+       0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255,
+       0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255};
+
+/* UNUSED */
+#if 0
 void fdrawbezier(float vec[4][3])
 {
        float dist;
@@ -167,6 +175,7 @@ void fdrawbezier(float vec[4][3])
        }
        glEnd();
 }
+#endif
 
 void fdrawline(float x1, float y1, float x2, float y2)
 {
@@ -204,38 +213,30 @@ void fdrawcheckerboard(float x1, float y1, float x2, float y2)
 {
        unsigned char col1[4] = {40, 40, 40}, col2[4] = {50, 50, 50};
 
-       GLubyte checker_stipple[32 * 32 / 8] = {
-               255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0,
-               255,  0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0,
-               0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255,
-               0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255,
-               255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0,
-               255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0,
-               0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255,
-               0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255, 0, 255};
-       
        glColor3ubv(col1);
        glRectf(x1, y1, x2, y2);
        glColor3ubv(col2);
 
        glEnable(GL_POLYGON_STIPPLE);
-       glPolygonStipple(checker_stipple);
+       glPolygonStipple(stipple_checker_8px);
        glRectf(x1, y1, x2, y2);
        glDisable(GL_POLYGON_STIPPLE);
 }
 
-void sdrawline(short x1, short y1, short x2, short y2)
+void sdrawline(int x1, int y1, int x2, int y2)
 {
-       short v[2];
+       int v[2];
        
        glBegin(GL_LINE_STRIP);
        v[0] = x1; v[1] = y1;
-       glVertex2sv(v);
+       glVertex2iv(v);
        v[0] = x2; v[1] = y2;
-       glVertex2sv(v);
+       glVertex2iv(v);
        glEnd();
 }
 
+/* UNUSED */
+#if 0
 /*
  *     x1,y2
  *     |  \
@@ -244,47 +245,48 @@ void sdrawline(short x1, short y1, short x2, short y2)
  *     x1,y1-- x2,y1
  */
 
-static void sdrawtripoints(short x1, short y1, short x2, short y2)
+static void sdrawtripoints(int x1, int y1, int x2, int y2)
 {
-       short v[2];
+       int v[2];
        v[0] = x1; v[1] = y1;
-       glVertex2sv(v);
+       glVertex2iv(v);
        v[0] = x1; v[1] = y2;
-       glVertex2sv(v);
+       glVertex2iv(v);
        v[0] = x2; v[1] = y1;
-       glVertex2sv(v);
+       glVertex2iv(v);
 }
 
-void sdrawtri(short x1, short y1, short x2, short y2)
+void sdrawtri(int x1, int y1, int x2, int y2)
 {
        glBegin(GL_LINE_STRIP);
        sdrawtripoints(x1, y1, x2, y2);
        glEnd();
 }
 
-void sdrawtrifill(short x1, short y1, short x2, short y2)
+void sdrawtrifill(int x1, int y1, int x2, int y2)
 {
        glBegin(GL_TRIANGLES);
        sdrawtripoints(x1, y1, x2, y2);
        glEnd();
 }
+#endif
 
-void sdrawbox(short x1, short y1, short x2, short y2)
+void sdrawbox(int x1, int y1, int x2, int y2)
 {
-       short v[2];
+       int v[2];
        
        glBegin(GL_LINE_STRIP);
        
        v[0] = x1; v[1] = y1;
-       glVertex2sv(v);
+       glVertex2iv(v);
        v[0] = x1; v[1] = y2;
-       glVertex2sv(v);
+       glVertex2iv(v);
        v[0] = x2; v[1] = y2;
-       glVertex2sv(v);
+       glVertex2iv(v);
        v[0] = x2; v[1] = y1;
-       glVertex2sv(v);
+       glVertex2iv(v);
        v[0] = x1; v[1] = y1;
-       glVertex2sv(v);
+       glVertex2iv(v);
        
        glEnd();
 }
@@ -318,6 +320,8 @@ void set_inverted_drawing(int enable)
        GL_TOGGLE(GL_DITHER, !enable);
 }
 
+/* UNUSED */
+#if 0
 void sdrawXORline(int x0, int y0, int x1, int y1)
 {
        if (x0 == x1 && y0 == y1) return;
@@ -334,7 +338,7 @@ void sdrawXORline(int x0, int y0, int x1, int y1)
 
 void sdrawXORline4(int nr, int x0, int y0, int x1, int y1)
 {
-       static short old[4][2][2];
+       static int old[4][2][2];
        static char flags[4] = {0, 0, 0, 0};
        
        /* with builtin memory, max 4 lines */
@@ -345,8 +349,8 @@ void sdrawXORline4(int nr, int x0, int y0, int x1, int y1)
        if (nr == -1) { /* flush */
                for (nr = 0; nr < 4; nr++) {
                        if (flags[nr]) {
-                               glVertex2sv(old[nr][0]);
-                               glVertex2sv(old[nr][1]);
+                               glVertex2iv(old[nr][0]);
+                               glVertex2iv(old[nr][1]);
                                flags[nr] = 0;
                        }
                }
@@ -354,8 +358,8 @@ void sdrawXORline4(int nr, int x0, int y0, int x1, int y1)
        else {
                if (nr >= 0 && nr < 4) {
                        if (flags[nr]) {
-                               glVertex2sv(old[nr][0]);
-                               glVertex2sv(old[nr][1]);
+                               glVertex2iv(old[nr][0]);
+                               glVertex2iv(old[nr][1]);
                        }
 
                        old[nr][0][0] = x0;
@@ -388,6 +392,9 @@ void fdrawXORellipse(float xofs, float yofs, float hw, float hh)
 
        set_inverted_drawing(0);
 }
+
+#endif
+
 void fdrawXORcirc(float xofs, float yofs, float rad)
 {
        set_inverted_drawing(1);
@@ -460,7 +467,7 @@ void glaRasterPosSafe2f(float x, float y, float known_good_x, float known_good_y
        glBitmap(0, 0, 0, 0, x - known_good_x, y - known_good_y, &dummy);
 }
 
-static int get_cached_work_texture(int *w_r, int *h_r)
+static int get_cached_work_texture(int *r_w, int *r_h)
 {
        static GLint texid = -1;
        static int tex_w = 256;
@@ -484,15 +491,15 @@ static int get_cached_work_texture(int *w_r, int *h_r)
                glBindTexture(GL_TEXTURE_2D, ltexid);
        }
 
-       *w_r = tex_w;
-       *h_r = tex_h;
+       *r_w = tex_w;
+       *r_h = tex_h;
        return texid;
 }
 
 void glaDrawPixelsTexScaled(float x, float y, int img_w, int img_h, int format, int type, int zoomfilter, void *rect, float scaleX, float scaleY)
 {
        unsigned char *uc_rect = (unsigned char *) rect;
-       float *f_rect = (float *)rect;
+       const float *f_rect = (float *)rect;
        float xzoom = glaGetOneFloat(GL_ZOOM_X), yzoom = glaGetOneFloat(GL_ZOOM_Y);
        int ltexid = glaGetOneInteger(GL_TEXTURE_2D);
        int lrowlength = glaGetOneInteger(GL_UNPACK_ROW_LENGTH);
@@ -572,25 +579,25 @@ void glaDrawPixelsTexScaled(float x, float y, int img_w, int img_h, int format,
                                continue;
                        
                        if (type == GL_FLOAT) {
-                               glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, subpart_w, subpart_h, format, GL_FLOAT, &f_rect[subpart_y * offset_y * img_w * components + subpart_x * offset_x * components]);
+                               glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, subpart_w, subpart_h, format, GL_FLOAT, &f_rect[((size_t)subpart_y) * offset_y * img_w * components + subpart_x * offset_x * components]);
                                
                                /* add an extra border of pixels so linear looks ok at edges of full image. */
                                if (subpart_w < tex_w)
-                                       glTexSubImage2D(GL_TEXTURE_2D, 0, subpart_w, 0, 1, subpart_h, format, GL_FLOAT, &f_rect[subpart_y * offset_y * img_w * components + (subpart_x * offset_x + subpart_w - 1) * components]);
+                                       glTexSubImage2D(GL_TEXTURE_2D, 0, subpart_w, 0, 1, subpart_h, format, GL_FLOAT, &f_rect[((size_t)subpart_y) * offset_y * img_w * components + (subpart_x * offset_x + subpart_w - 1) * components]);
                                if (subpart_h < tex_h)
-                                       glTexSubImage2D(GL_TEXTURE_2D, 0, 0, subpart_h, subpart_w, 1, format, GL_FLOAT, &f_rect[(subpart_y * offset_y + subpart_h - 1) * img_w * components + subpart_x * offset_x * components]);
+                                       glTexSubImage2D(GL_TEXTURE_2D, 0, 0, subpart_h, subpart_w, 1, format, GL_FLOAT, &f_rect[(((size_t)subpart_y) * offset_y + subpart_h - 1) * img_w * components + subpart_x * offset_x * components]);
                                if (subpart_w < tex_w && subpart_h < tex_h)
-                                       glTexSubImage2D(GL_TEXTURE_2D, 0, subpart_w, subpart_h, 1, 1, format, GL_FLOAT, &f_rect[(subpart_y * offset_y + subpart_h - 1) * img_w * components + (subpart_x * offset_x + subpart_w - 1) * components]);
+                                       glTexSubImage2D(GL_TEXTURE_2D, 0, subpart_w, subpart_h, 1, 1, format, GL_FLOAT, &f_rect[(((size_t)subpart_y) * offset_y + subpart_h - 1) * img_w * components + (subpart_x * offset_x + subpart_w - 1) * components]);
                        }
                        else {
-                               glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, subpart_w, subpart_h, format, GL_UNSIGNED_BYTE, &uc_rect[subpart_y * offset_y * img_w * components + subpart_x * offset_x * components]);
+                               glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, subpart_w, subpart_h, format, GL_UNSIGNED_BYTE, &uc_rect[((size_t)subpart_y) * offset_y * img_w * components + subpart_x * offset_x * components]);
                                
                                if (subpart_w < tex_w)
-                                       glTexSubImage2D(GL_TEXTURE_2D, 0, subpart_w, 0, 1, subpart_h, format, GL_UNSIGNED_BYTE, &uc_rect[subpart_y * offset_y * img_w * components + (subpart_x * offset_x + subpart_w - 1) * components]);
+                                       glTexSubImage2D(GL_TEXTURE_2D, 0, subpart_w, 0, 1, subpart_h, format, GL_UNSIGNED_BYTE, &uc_rect[((size_t)subpart_y) * offset_y * img_w * components + (subpart_x * offset_x + subpart_w - 1) * components]);
                                if (subpart_h < tex_h)
-                                       glTexSubImage2D(GL_TEXTURE_2D, 0, 0, subpart_h, subpart_w, 1, format, GL_UNSIGNED_BYTE, &uc_rect[(subpart_y * offset_y + subpart_h - 1) * img_w * components + subpart_x * offset_x * components]);
+                                       glTexSubImage2D(GL_TEXTURE_2D, 0, 0, subpart_h, subpart_w, 1, format, GL_UNSIGNED_BYTE, &uc_rect[(((size_t)subpart_y) * offset_y + subpart_h - 1) * img_w * components + subpart_x * offset_x * components]);
                                if (subpart_w < tex_w && subpart_h < tex_h)
-                                       glTexSubImage2D(GL_TEXTURE_2D, 0, subpart_w, subpart_h, 1, 1, format, GL_UNSIGNED_BYTE, &uc_rect[(subpart_y * offset_y + subpart_h - 1) * img_w * components + (subpart_x * offset_x + subpart_w - 1) * components]);
+                                       glTexSubImage2D(GL_TEXTURE_2D, 0, subpart_w, subpart_h, 1, 1, format, GL_UNSIGNED_BYTE, &uc_rect[(((size_t)subpart_y) * offset_y + subpart_h - 1) * img_w * components + (subpart_x * offset_x + subpart_w - 1) * components]);
                        }
 
                        glEnable(GL_TEXTURE_2D);
@@ -682,17 +689,17 @@ void glaDrawPixelsSafe(float x, float y, int img_w, int img_h, int row_w, int fo
                glPixelStorei(GL_UNPACK_ROW_LENGTH, row_w);
                if (format == GL_LUMINANCE || format == GL_RED) {
                        if (type == GL_FLOAT) {
-                               float *f_rect = (float *)rect;
+                               const float *f_rect = (float *)rect;
                                glDrawPixels(draw_w, draw_h, format, type, f_rect + (off_y * row_w + off_x));
                        }
                        else if (type == GL_INT || type == GL_UNSIGNED_INT) {
-                               int *i_rect = (int *)rect;
+                               const int *i_rect = (int *)rect;
                                glDrawPixels(draw_w, draw_h, format, type, i_rect + (off_y * row_w + off_x));
                        }
                }
                else { /* RGBA */
                        if (type == GL_FLOAT) {
-                               float *f_rect = (float *)rect;
+                               const float *f_rect = (float *)rect;
                                glDrawPixels(draw_w, draw_h, format, type, f_rect + (off_y * row_w + off_x) * 4);
                        }
                        else if (type == GL_UNSIGNED_BYTE) {
@@ -825,23 +832,23 @@ gla2DDrawInfo *glaBegin2DDraw(rcti *screen_rect, rctf *world_rect)
 /**
  * Translate the (\a wo_x, \a wo_y) point from world coordinates into screen space.
  */
-void gla2DDrawTranslatePt(gla2DDrawInfo *di, float wo_x, float wo_y, int *sc_x_r, int *sc_y_r)
+void gla2DDrawTranslatePt(gla2DDrawInfo *di, float wo_x, float wo_y, int *r_sc_x, int *r_sc_y)
 {
-       *sc_x_r = (wo_x - di->world_rect.xmin) * di->wo_to_sc[0];
-       *sc_y_r = (wo_y - di->world_rect.ymin) * di->wo_to_sc[1];
+       *r_sc_x = (wo_x - di->world_rect.xmin) * di->wo_to_sc[0];
+       *r_sc_y = (wo_y - di->world_rect.ymin) * di->wo_to_sc[1];
 }
 
 /**
- * Translate the \a world point from world coordiantes into screen space.
+ * Translate the \a world point from world coordinates into screen space.
  */
-void gla2DDrawTranslatePtv(gla2DDrawInfo *di, float world[2], int screen_r[2])
+void gla2DDrawTranslatePtv(gla2DDrawInfo *di, float world[2], int r_screen[2])
 {
        screen_r[0] = (world[0] - di->world_rect.xmin) * di->wo_to_sc[0];
        screen_r[1] = (world[1] - di->world_rect.ymin) * di->wo_to_sc[1];
 }
 
 /**
- * Restores the previous OpenGL state and free's the auxilary gla data.
+ * Restores the previous OpenGL state and frees the auxiliary gla data.
  */
 void glaEnd2DDraw(gla2DDrawInfo *di)
 {
@@ -874,7 +881,7 @@ void bglBegin(int mode)
                glGetFloatv(GL_POINT_SIZE_RANGE, value);
                if (value[1] < 2.0f) {
                        glGetFloatv(GL_POINT_SIZE, value);
-                       pointhack = floor(value[0] + 0.5f);
+                       pointhack = iroundf(value[0]);
                        if (pointhack > 4) pointhack = 4;
                }
                else {
@@ -984,7 +991,7 @@ void bgl_get_mats(bglMats *mats)
 /**
  * \note \a viewdist is only for ortho at the moment.
  */
-void bglPolygonOffset(float viewdist, float dist) 
+void bglPolygonOffset(float viewdist, float dist)
 {
        static float winmat[16], offset = 0.0;
        
@@ -1000,8 +1007,25 @@ void bglPolygonOffset(float viewdist, float dist)
                
                /* dist is from camera to center point */
                
-               if (winmat[15] > 0.5f) offs = 0.00001f * dist * viewdist;  // ortho tweaking
-               else offs = 0.0005f * dist;  // should be clipping value or so...
+               if (winmat[15] > 0.5f) {
+#if 1
+                       offs = 0.00001f * dist * viewdist;  // ortho tweaking
+#else
+                       static float depth_fac = 0.0f;
+                       if (depth_fac == 0.0f) {
+                               int depthbits;
+                               glGetIntegerv(GL_DEPTH_BITS, &depthbits);
+                               depth_fac = 1.0f / (float)((1 << depthbits) - 1);
+                       }
+                       offs = (-1.0 / winmat[10]) * dist * depth_fac;
+
+                       UNUSED_VARS(viewdist);
+#endif
+               }
+               else {
+                       /* should be clipping value or so... */
+                       offs = 0.0005f * dist;
+               }
                
                winmat[14] -= offs;
                offset += offs;
@@ -1044,48 +1068,12 @@ void glaDrawImBuf_glsl(ImBuf *ibuf, float x, float y, int zoomfilter,
        if (ibuf->rect == NULL && ibuf->rect_float == NULL)
                return;
 
-       /* Dithering is not supported on GLSL yet */
-       force_fallback |= ibuf->dither != 0.0f;
-
        /* Single channel images could not be transformed using GLSL yet */
        force_fallback |= ibuf->channels == 1;
 
        /* If user decided not to use GLSL, fallback to glaDrawPixelsAuto */
        force_fallback |= (U.image_draw_method != IMAGE_DRAW_METHOD_GLSL);
 
-       /* This is actually lots of crap, but currently not sure about
-        * more clear way to bypass partial buffer update crappyness
-        * while rendering.
-        *
-        * The thing is -- render engines are only updating byte and
-        * display buffers for active render result opened in image
-        * editor. This works fine to show render progress without
-        * switching render layers in image editor user, but this is
-        * completely useless for GLSL display, where we need to have
-        * original buffer which we could color manage.
-        *
-        * For the time of rendering, we'll stick back to slower CPU
-        * display buffer update. GLSL could be used as soon as some
-        * fixes (?) are done in render itself, so we'll always have
-        * image buffer with relevant float buffer opened while
-        * rendering.
-        *
-        * On the other hand, when using Cycles, stressing GPU with
-        * GLSL could backfire on a performance.
-        *                                         - sergey -
-        */
-       if (G.is_rendering) {
-               /* Try to detect whether we're drawing render result,
-                * other images could have both rect and rect_float
-                * but they'll be synchronized
-                */
-               if (ibuf->rect_float && ibuf->rect &&
-                   ((ibuf->mall & IB_rectfloat) == 0))
-               {
-                       force_fallback = true;
-               }
-       }
-
        /* Try to draw buffer using GLSL display transform */
        if (force_fallback == false) {
                int ok;
@@ -1093,15 +1081,18 @@ void glaDrawImBuf_glsl(ImBuf *ibuf, float x, float y, int zoomfilter,
                if (ibuf->rect_float) {
                        if (ibuf->float_colorspace) {
                                ok = IMB_colormanagement_setup_glsl_draw_from_space(view_settings, display_settings,
-                                                                                   ibuf->float_colorspace, true);
+                                                                                   ibuf->float_colorspace,
+                                                                                   ibuf->dither, true);
                        }
                        else {
-                               ok = IMB_colormanagement_setup_glsl_draw(view_settings, display_settings, true);
+                               ok = IMB_colormanagement_setup_glsl_draw(view_settings, display_settings,
+                                                                        ibuf->dither, true);
                        }
                }
                else {
                        ok = IMB_colormanagement_setup_glsl_draw_from_space(view_settings, display_settings,
-                                                                           ibuf->rect_colorspace, false);
+                                                                           ibuf->rect_colorspace,
+                                                                           ibuf->dither, false);
                }
 
                if (ok) {
@@ -1162,7 +1153,44 @@ void glaDrawImBuf_glsl_ctx(const bContext *C, ImBuf *ibuf, float x, float y, int
 
 void cpack(unsigned int x)
 {
-       glColor3ub( ( (x)        & 0xFF),
-                   (((x) >>  8) & 0xFF),
-                   (((x) >> 16) & 0xFF) );
+       glColor3ub(( (x)        & 0xFF),
+                  (((x) >>  8) & 0xFF),
+                  (((x) >> 16) & 0xFF));
+}
+
+void glaDrawBorderCorners(const rcti *border, float zoomx, float zoomy)
+{
+       float delta_x = 4.0f * UI_DPI_FAC / zoomx;
+       float delta_y = 4.0f * UI_DPI_FAC / zoomy;
+
+       delta_x = min_ff(delta_x, border->xmax - border->xmin);
+       delta_y = min_ff(delta_y, border->ymax - border->ymin);
+
+       /* left bottom corner */
+       glBegin(GL_LINE_STRIP);
+       glVertex2f(border->xmin, border->ymin + delta_y);
+       glVertex2f(border->xmin, border->ymin);
+       glVertex2f(border->xmin + delta_x, border->ymin);
+       glEnd();
+
+       /* left top corner */
+       glBegin(GL_LINE_STRIP);
+       glVertex2f(border->xmin, border->ymax - delta_y);
+       glVertex2f(border->xmin, border->ymax);
+       glVertex2f(border->xmin + delta_x, border->ymax);
+       glEnd();
+
+       /* right bottom corner */
+       glBegin(GL_LINE_STRIP);
+       glVertex2f(border->xmax - delta_x, border->ymin);
+       glVertex2f(border->xmax, border->ymin);
+       glVertex2f(border->xmax, border->ymin + delta_y);
+       glEnd();
+
+       /* right top corner */
+       glBegin(GL_LINE_STRIP);
+       glVertex2f(border->xmax - delta_x, border->ymax);
+       glVertex2f(border->xmax, border->ymax);
+       glVertex2f(border->xmax, border->ymax - delta_y);
+       glEnd();
 }