【问题标题】:cairo : blurred shapes and text开罗:模糊的形状和文字
【发布时间】:2014-05-18 19:18:10
【问题描述】:

我在其图像表面通过cairo 绘制了一些随机矩形,缩放和平移它并使用

显示结果
unsigned char* data = cairo_image_surface_get_data(surface);

但矩形看起来很模糊: (我无法发布屏幕截图)

角(可能)未映射到整数坐标。包含data 的纹理与surface 的大小和格式相同,并且我已经使用了抗锯齿设置(文本显示更加模糊!!)。我应该怎么做才能将生成的形状映射到整数坐标并提高质量(不使用超级采样并且不放弃缩放转换)?

编辑:我使用了下面的代码(有和没有第三行),但它不起作用!:

cairo_save(cr);    
cairo_identity_matrix(cr);
cairo_translate(cr, 0.5, 0.5);
cairo_scale(cr, size.width, size.height);
cairo_set_antialias(cr, CAIRO_ANTIALIAS_GOOD);
(make the drawing!!)
cairo_restore(cr);

Edit2:我使用了捕捉乐趣。 (毕竟转换代码),但它也没有工作:

double szero1 = zero,szero2 = zero, sone1 = one, sone2 = one;
snapToPixel(cr, &szero1, &szero2);
snapToPixel(cr, &sone1, &sone2);
cairo_rectangle (cr, szero1, szero2, sone1, sone2);

【问题讨论】:

    标签: c++ performance graphics cairo blurry


    【解决方案1】:

    如果不预处理坐标,就无法强制 cairo 捕捉到最近的整数像素坐标。

    void snapToPixel(cairo_t *cr, float *x, float *y) {
         cairo_user_to_device (cr, x, y);
         *x = round(*x);
         *y = round(*y);
         cairo_device_to_user (cr, x, y);
    }
    

    笔画宽度也会有同样的问题(+如果width != heightx, y不同)。

    更多信息http://cairographics.org/FAQ/#sharp_lines

    【讨论】:

    • 不幸的是,它不起作用(@see 编辑);我在抽奖前进行缩放和平移...
    • @user3648895 根据你编辑,你的坐标(用于绘图)是从 0.0-1.0 ?
    • 是的,我在单位坐标中制作所有图纸,并在需要时进行比例平移;我希望 cairo 能够处理它,因为它是一个矢量库。顺便说一句,谢谢您的关注..
    【解决方案2】:

    我用的是整数,但还是很模糊

    func (me *canvas) DrawRectF(left, top, right, bottom float32, paint *Paint) {
        if right <= left || bottom <= top {
            return
        }
    
        C.cairo_set_antialias(me.ptr, C.CAIRO_ANTIALIAS_NONE)
    
        fix := paint.Style == STROKE && int32(paint.Width)%2 != 0
        fix = false
        if fix {
            me.Save()
            me.TranslateF(0.5, 0.5)
    
        }
        C.cairo_rectangle(me.ptr, 100, 100, 500, 500)
        C.cairo_rectangle(me.ptr, 110, 110, 510, 510)
        me.drawPaint(paint)
    
        if fix {
            me.Restore()
        }
    }
    

    这是开罗的一条线

    这是代码编辑器中的一行

    我应该怎么做才能像代码编辑器一样用单像素宽的线画一条锐利的线?

    【讨论】:

    • 不是cairo的问题,是SDL2的问题。当CreateWindow 可以时添加SDL_WINDOW_ALLOW_HIGHDPI
    【解决方案3】:

    我知道这不是cairo的问题而是SDL2,SDL2需要设置SDL_WINDOW_ALLOW_HIGHDPI才能显示单像素线,但是我发现anthor问题,这次我用cairo_surface_write_to_png没有SDL2,线条清晰明亮,但是文字模糊。吹出的图片是 cairo 和其他应用程序之间的文本比较。

    cairo_surface_t *surface;     
        cairo_t *cr;                  
        surface = cairo_image_surface_create (CAIRO_FORMAT_ARGB32, 100, 100);
        cr = cairo_create (surface);
    
        cairo_set_source_rgb (cr, 0.0, 0.0, 0.0);
        cairo_paint(cr);
    
    
        cairo_text_extents_t extents;
        const char *utf8 = "bulrry text";
        double x,y;
        printf("x = %f, y = %f ", x, y);
        snapToPixel(cr, &x, &y);
        printf("x = %f, y = %f ", x, y);
    
        // cairo_set_antialias(cr, CAIRO_ANTIALIAS_BEST);
        cairo_select_font_face (cr, "mono",
            CAIRO_FONT_SLANT_NORMAL,
            CAIRO_FONT_WEIGHT_NORMAL);
    
        cairo_set_font_size (cr, 14.0);
        cairo_text_extents (cr, utf8, &extents);
        x = 128.0-(extents.width/2 );
        y = 128.0-(extents.height/2 );
    
        cairo_move_to (cr, 0, 15);
        cairo_set_source_rgba (cr, 1, 1, 1, 1);
        cairo_show_text (cr, utf8);
    
        /* draw helping lines */
        cairo_set_source_rgb (cr, 1, 0, 0);
        cairo_set_line_width (cr, 1.0);
        cairo_rectangle(cr, 20.5, 20.5, 50, 50);
        cairo_stroke (cr);
        cairo_surface_write_to_png(surface , "./a.png");
    

    【讨论】:

    • 这可能是关于(底层)字体绘图库的问题,例如 freetype。高质量的字体/字形渲染需要抗锯齿、子像素渲染 (LCD) 等技术。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-12-24
    • 2022-11-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多