[cairo] PATCH cairo-www: Simpler explanation for how to get sharp, single-pixel-wide lines

Olaf Schmidt ng at vbRichClient.com
Wed May 17 19:28:22 UTC 2017

Am 17.05.2017 um 13:27 schrieb Guillermo Rodriguez:

>>> It occurs because integer coordinates map to points half way
>>> between sample point locations ...
>> That’s a common misconception.
> It's taken straight from the current Cairo FAQ.
> Again: A common use case is that you want to have antialiasing in
> general BUT at the same time be able to draw 1 pixel wide vertical or
> horizontal lines that don't look "blurry". The current text describes
> an approach which achieves exactly that by adjusting endpoints of
> horizontal / vertical lines by 0.5 in the appropriate direction. That
> gets you perfect sharp, single-pixel-wide vertical and horizontal
> lines without the need to turn off antialiasing. Your "simpler
> explanation" proposal misses that completely.

To "underline" the above (which is the suggestion I've followed in
a WidgetEngine) - here's a ScreenShot which shows both cases:


- btnHello1 following the more "general purpose" suggestion above

- btnHello2 following the suggestion of Lawrence (which has its
   place, but I'd think it should only be mentioned "in addition":
  (in case one wants to render straight horizontal or vertical lines only)

For those who want to run the little Mini-App which produced the
ScreenShot, below is the *.vbs-Code (sorry for the "Win-only" example).

The AntiAliasing-switchery is done in the Paint-Event of the little
cwSimpleButton-Class at the bottom...

Set New_c = CreateObject("vbRichClient5.cConstructor") 'Main-Constructor

Set Cairo = New_c.Cairo 'ensure the global Cairo-Namespace-Entrypoint
	Set Form=Cairo.WidgetForms.Create(2, "Widget-Renderquality", , 320, 240)

	WScript.ConnectObject Form, "Form_" '<- EventSink-Prefix and -Binding 
the VBScript-way
Cairo.WidgetForms.EnterMessageLoop 'here we enter the message-pump of 
our little Application

Sub Form_Load()
     Form.Widgets.Add New cwSimpleButton,"btnHello1", 10, 10, 100, 25 
'normal AntiAliasing
     Form.Widgets.Add(New cwSimpleButton,"btnHello2", 10, 40, 100, 
End Sub

'this Event travels through all the Parent-Widgets of a nested 
Widget-Hierarchy up to the Form
Sub Form_BubblingEvent(Sender, EventName, P1, P2, P3, P4, P5, P6, P7)
   Select Case EventName
     Case "W_Paint": Sender.Paint P1, P4, P5 're-route to the Class
     Case "W_Click": If TypeName(Sender) = "cwSimpleButton" Then MsgBox 
     Case "W_MouseEnter", "W_MouseLeave", "W_MouseDown", "W_MouseUp": 
   End Select
End Sub

'just to ensure the missing IIf()-Function in the VBScript-Context
Function IIf(Cond, ResultIfTrue, ResultIfFalse)
	If Cond Then IIf = ResultIfTrue Else IIf = ResultIfFalse
End Function

'a cairo-Widget-Class (for a simple ownerdrawn Command-Button)
Class cwSimpleButton
     Private W  'define and instantiate the internal W-WidgetBase
     Private Sub Class_Initialize(): Set W = Cairo.WidgetBase: End Sub

     'below the two Properties, any cwClass needs to implement
     Property Get Widget():  Set Widget  = W:         End Property
     Property Get Widgets(): Set Widgets = W.Widgets: End Property

     Public AntiAliasOff  'define a Property to allow DrawMode-switching 
from outside

     Sub Paint(ByVal CC, ByVal dx, ByVal dy)
        Dim State
            State = IIf(W.Root.MouseKeyDown And W.MouseOver, 1, 0) Or 
IIf(W.MouseOver, 2, 0)

        If AntiAliasOff Then CC.AntiAlias = 1 'CAIRO_ANTIALIAS_NONE

        Cairo.Theme.DrawTo (CC), (W), 0, State, 0, 0, dx, dy, 2 'draw a 
themed Button-Face first

        CC.SetSourceColor W.BorderColor 'and now the surrounding Border
           CC.SetLineWidth 2
           CC.RoundedRect 0, 0, dx, dy, 4, True '<- True to take care of 
"sharp coord-placement"

        W.SelectFontSettingsInto (CC) 'select all current 
W.Font*-Properties into the CairoContext
        CC.DrawText 1, 1, dx, dy, W.Key, , 2, 2, 1 'a Caption (using the 
W.Key to simplify things)
     End Sub
End Class



More information about the cairo mailing list