The MASM Forum

Projects => MasmBasic & the RichMasm IDE => Topic started by: jj2007 on November 18, 2018, 03:26:49 PM

Title: Cairo
Post by: jj2007 on November 18, 2018, 03:26:49 PM
This looks promising, I hope I'll find some time to explore Cairo:

include \masm32\MasmBasic\MasmBasic.inc         ; download (http://masm32.com/board/index.php?topic=94.0)
  Init
  Dll "\Masm32\Cairo\lib\x86\cairo.dll"
  Declare cairo_version
  Inkey Str$("This is Cairo version %i", cairo_version())
EndOfCode


This is Cairo version 11512
Title: Re: Cairo
Post by: Biterider on November 18, 2018, 06:49:20 PM
Hello
I saw the opportunity to add something to this project and translated the header files with h2incX.
Since it worked fine, I share the result with those who want to experiment with Cairo.

Biterider
Title: Re: Cairo
Post by: jj2007 on November 18, 2018, 07:24:54 PM
Very good idea, biterider :t

Does it run on your machine? I get some errors:
*** Assemble using \masm32\bin\UAsm64 /c /coff  tmp_file.asm ***
UASM v2.46, Dec  8 2017, Masm-compatible assembler.
Portions Copyright (c) 1992-2002 Sybase, Inc. All Rights Reserved.
Source code is available under the Sybase Open Watcom Public License.

Cairo.inc(18) : Error A2102: Symbol not defined : Defined
Cairo.inc(18): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(35) : Error A2210: Syntax error: @DefProto
Cairo.inc(35): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(36) : Error A2210: Syntax error: @DefProto
Cairo.inc(36): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(38) : Error A2102: Symbol not defined : _cairo
Cairo.inc(38): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(40) : Error A2102: Symbol not defined : _cairo_surface
Cairo.inc(40): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(42) : Error A2102: Symbol not defined : _cairo_device
Cairo.inc(42): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(54) : Error A2102: Symbol not defined : _cairo_pattern
Cairo.inc(54): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(136) : Error A2210: Syntax error: @DefProto
Cairo.inc(136): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(137) : Error A2210: Syntax error: @DefProto
Cairo.inc(137): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(138) : Error A2210: Syntax error: @DefProto
Cairo.inc(138): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(139) : Error A2210: Syntax error: @DefProto
Cairo.inc(139): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(140) : Error A2210: Syntax error: @DefProto
Cairo.inc(140): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(141) : Error A2210: Syntax error: @DefProto
Cairo.inc(141): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(142) : Error A2210: Syntax error: @DefProto
Cairo.inc(142): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(143) : Error A2210: Syntax error: @DefProto
Cairo.inc(143): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(144) : Error A2210: Syntax error: @DefProto
Cairo.inc(144): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(145) : Error A2210: Syntax error: @DefProto
Cairo.inc(145): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(146) : Error A2210: Syntax error: @DefProto
Cairo.inc(146): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(147) : Error A2210: Syntax error: @DefProto
Cairo.inc(147): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(180) : Error A2210: Syntax error: @DefProto
Cairo.inc(180): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(181) : Error A2210: Syntax error: @DefProto
Cairo.inc(181): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(182) : Error A2210: Syntax error: @DefProto
Cairo.inc(182): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(183) : Error A2210: Syntax error: @DefProto
Cairo.inc(183): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(184) : Error A2210: Syntax error: @DefProto
Cairo.inc(184): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(185) : Error A2210: Syntax error: @DefProto
Cairo.inc(185): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(196) : Error A2210: Syntax error: @DefProto
Cairo.inc(196): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(202) : Error A2210: Syntax error: @DefProto
Cairo.inc(202): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(203) : Error A2210: Syntax error: @DefProto
Cairo.inc(203): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(210) : Error A2210: Syntax error: @DefProto
Cairo.inc(210): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(217) : Error A2210: Syntax error: @DefProto
Cairo.inc(217): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(218) : Error A2210: Syntax error: @DefProto
Cairo.inc(218): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(219) : Error A2210: Syntax error: @DefProto
Cairo.inc(219): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(220) : Error A2210: Syntax error: @DefProto
Cairo.inc(220): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(221) : Error A2210: Syntax error: @DefProto
Cairo.inc(221): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(222) : Error A2210: Syntax error: @DefProto
Cairo.inc(222): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(223) : Error A2210: Syntax error: @DefProto
Cairo.inc(223): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(224) : Error A2210: Syntax error: @DefProto
Cairo.inc(224): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(225) : Error A2210: Syntax error: @DefProto
Cairo.inc(225): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(226) : Error A2210: Syntax error: @DefProto
Cairo.inc(226): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(227) : Error A2210: Syntax error: @DefProto
Cairo.inc(227): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(228) : Error A2210: Syntax error: @DefProto
Cairo.inc(228): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(229) : Error A2210: Syntax error: @DefProto
Cairo.inc(229): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(230) : Error A2210: Syntax error: @DefProto
Cairo.inc(230): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(231) : Error A2210: Syntax error: @DefProto
Cairo.inc(231): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(232) : Error A2210: Syntax error: @DefProto
Cairo.inc(232): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(233) : Error A2210: Syntax error: @DefProto
Cairo.inc(233): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(234) : Error A2210: Syntax error: @DefProto
Cairo.inc(234): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(235) : Error A2210: Syntax error: @DefProto
Cairo.inc(235): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(236) : Error A2210: Syntax error: @DefProto
Cairo.inc(236): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(237) : Error A2210: Syntax error: @DefProto
Cairo.inc(237): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(238) : Error A2210: Syntax error: @DefProto
Cairo.inc(238): Included by
  Tmp_File.asm(2): Main line code
Cairo.inc(238) : Fatal error A1113: Too many errors
*** Assembly Error ***
Title: Re: Cairo
Post by: TimoVJL on November 19, 2018, 12:09:35 AM
A link for Cairo (https://preshing.com/20170529/heres-a-standalone-cairo-dll-for-windows/)
EDIT: example compiled with PellesC 9
Title: Re: Cairo
Post by: Biterider on November 19, 2018, 12:20:45 AM
Hi JJ
I was able to compile a test application changing some of the symbols that point to nirvana. It seems to be a leftover from the windows translation.
I commented them out and I could compile.
Since I'm using a variation of the WinInc project with the most recent header files, I had no problems with the @DefProto macro. If you are using another source, like "MASM32 windows.inc", you have to define your own macro. Here the original:
  ifdef _WIN64
    WIN_STD_CALL_CONV equ <fastcall>
    @DefProto macro ApiQual, ProcName, CallConv, NameSuffix, Params, DecorSuffix
      ifdif <CallConv>, <vectorcall>
        ??CallConv equ <fastcall>
      else
        ??CallConv equ <&CallConv>
      endif

      ifidn <ApiQual>, <DllImport>                      ;;Call [IAT], a bit faster
        TYPE_&ProcName typedef proto ??CallConv Params
        externdef __imp_&ProcName: ptr TYPE_&ProcName
        ProcName&NameSuffix equ <__imp_&ProcName>
      else
        ProcName&NameSuffix proto ??CallConv Params     ;;Call thunk (jmp [IAT])
      endif
    endm
  else
    WIN_STD_CALL_CONV equ <stdcall>
    @DefProto macro ApiQual, ProcName, CallConv, NameSuffix, Params, DecorSuffix

      ifidn <ApiQual>, <DllImport>                      ;;Call [IAT], a bit faster
        TYPE_&ProcName typedef proto CallConv Params
        ifnb <DecorSuffix>
          externdef WIN_STD_CALL_CONV _imp__&ProcName&@&DecorSuffix: ptr TYPE_&ProcName
          ProcName&NameSuffix equ <_imp__&ProcName&@&DecorSuffix>
        else
          externdef c _imp__&ProcName: ptr TYPE_&ProcName
          ProcName&NameSuffix equ <_imp__&ProcName>
        endif
      else
        ProcName&NameSuffix proto CallConv Params       ;;Call thunk (jmp [IAT])
      endif
    endm
  endif


I noticed, that the symbol naming decoration of the import library is not the windows standard, so you have to change the macro to fit to cairo.lib.
I did it and found that the loader had some problems resolving some addresses.
I reuploaded the files to the previous post with the uncommented symbols.

Tomorrow I'll try to generate my own import lib with windows native tools. We will see...  :biggrin:

Biterider
Title: Re: Cairo
Post by: jj2007 on November 19, 2018, 05:37:24 AM
Quote from: Biterider on November 19, 2018, 12:20:45 AMTomorrow I'll try to generate my own import lib with windows native tools. We will see...  :biggrin:

Good luck :bgrin:

Quote from: TimoVJL on November 19, 2018, 12:09:35 AM
A link for Cairo (https://preshing.com/20170529/heres-a-standalone-cairo-dll-for-windows/)

Thanks, Timo - that was actually the binary I was already using, it pops up on top for googling cairo windows binaries. Here is my first successful attempt:

GuiParas equ "Cairo demo", x550, y20, w160, h180, cblack, b RgbCol(255, 255, 160)
include \masm32\MasmBasic\Res\MbGui.asm         ; part of MasmBasic (http://masm32.com/board/index.php?topic=94.0)
Dll "\Masm32\Cairo\lib\x86\cairo.dll"  ; suggested path to the Dll
Declare cairo_version
Declare cairo_win32_surface_create, C:1
Declare cairo_create, C:1
Declare void cairo_rectangle, C:5
Declare void cairo_set_source_rgba, C:5
Declare void cairo_set_fill_rule, C:2
Declare void cairo_fill, C:1
Declare void cairo_destroy, C:1
Declare void cairo_surface_write_to_png, C:2
Declare void cairo_surface_destroy, C:1
Declare void cairo_status, C:1
Declare void cairo_surface_status, C:1
Declare void cairo_status_to_string, C:1
Enum 0:CAIRO_FILL_RULE_WINDING, CAIRO_FILL_RULE_EVEN_ODD
SetGlobals surface, context, double red, green, blue

Event Paint
  invoke TextOut, PtDC, 9, 5, Str$("Cairo version %i\n", cairo_version()), s$Len
  mov surface, cairo_win32_surface_create(PtDC)
  mov context, cairo_create(surface)
  cairo_rectangle(context, FP8(20.0), FP8(30.0), FP8(100.0), FP8(100.0))
  Rand(0.0, 1.0, red)
  Rand(0.0, 1.0, green)         ; generate random colours
  Rand(0.0, 1.0, blue)
  cairo_set_source_rgba(context, red, green, blue, FP8(0.5))    ; last arg is transparency
  cairo_set_fill_rule(context, CAIRO_FILL_RULE_EVEN_ODD)
  cairo_fill(context)
  cairo_destroy(context);
  ; cairo_surface_write_to_png(surface, "test.png")    ; saves client area to disk
  cairo_surface_destroy(surface);
GuiEnd


When sizing, you can see the random colours generated. I ran it with a timer and MemState (http://www.webalice.it/jj2006/MasmBasicQuickReference.htm#Mb1380), no leaks detected.

Source & exe attached, including my Pelles C test case (which works only when in the same folder as the DLL... :()

The DLL is 2MB, too big to be posted here; but all you need is cairo.dll from the link you posted (download (https://preshing.com/20170529/heres-a-standalone-cairo-dll-for-windows/)), which I suggest to save to \Masm32\Cairo\lib\x86\cairo.dll for those who want to follow this thread.
Title: Re: Cairo
Post by: HSE on November 19, 2018, 09:07:49 AM
A problem with Declare:
N:\jj\varios>asmC cairo2.asm
Asmc Macro Assembler Version 2.28.05
Copyright (C) The Asmc Contributors. All Rights Reserved.

Assembling: cairo2.asm
*** MasmBasic version 25.12.2017 ***
** SetProcessUserModeExceptionPolicy
## MasmBasic GUI build ##
cairo2.asm(5) : error A2091: index value past end of string
Declare(50)[MasmBasic.inc]: Macro called from
  cairo2.asm(5): Main line code
cairo2.asm(5) : error A2006: undefined symbol : ??03BB
Declare(51)[MasmBasic.inc]: Macro called from
  cairo2.asm(5): Main line code
cairo2.asm(5) : error A2091: index value past end of string
Declare(73)[MasmBasic.inc]: Macro called from
  cairo2.asm(5): Main line code
cairo2.asm(22) : error A2091: index value past end of string
cairo_version(6)[cairo2.asm]: Macro called from
  cairo2.asm(22): Main line code
cairo2.asm(22) : error A2006: undefined symbol : ??04A0
cairo_version(7)[cairo2.asm]: Macro called from
  cairo2.asm(22): Main line code
cairo2.asm(22) : error A2006: undefined symbol : ??04A0
cairo_version(99)[cairo2.asm]: Macro called from
  cairo2.asm(22): Main line code
cairo2.asm(22) : error A2006: undefined symbol : ??04A0
cairo_version(140)[cairo2.asm]: Macro called from
  cairo2.asm(22): Main line code
Title: Re: Cairo
Post by: jj2007 on November 19, 2018, 10:11:43 AM
Quote from: HSE on November 19, 2018, 09:07:49 AM
A problem with Declare

Sorry, I haven't updated the package for a while. Attached the new Declare version, to be inserted after the Dll line.
Title: Re: Cairo
Post by: HSE on November 19, 2018, 10:21:35 AM
 :t Thanks.
Title: Re: Cairo
Post by: jj2007 on November 19, 2018, 10:25:11 AM
If you are successful in testing other Cairo functions, please post them. I am curious if this lib offers any advantage over plain Gdi or Gdi+.

Complete Cairo API (http://www.dynaset.org/dogusanh/download/luacairo.html#cairo_api)

P.S.: Try inserting a MakePath/GuiDraw (http://www.webalice.it/jj2006/MasmBasicQuickReference.htm#Mb1374) element (resizable!):

SetGlobals surface, context, double red, green, blue
MakePath 111, Bezier(150:0, 0:90, 0:120, 300:300)
MakePen hPenBez, RgbCol(200, 160, 160, 0), width 4, startarrow LineCapRoundAnchor, endarrow 12:9, inset 2
Event Paint
  invoke TextOut, PtDC, 9, 5, Str$("Cairo version %i\n", cairo_version()), s$Len
  GuiDraw 111, hPenBez, 45.0, 25.0
  mov surface, cairo_win32_surface_create(PtDC)
Title: Re: Cairo
Post by: Biterider on November 20, 2018, 06:45:59 AM
Hi
I got it working now after changing the calling convention!  ;)
I had to change the proto definition macro accordingly and all works fine now.

Attached is a demo that uses the code shown by JJ

Method CairoApp.OnPaint, uses esi, wParam:WPARAM, lParam:LPARAM
    local PS:PAINTSTRUCT, hDC:HDC, Rct:RECT
    local Surface:HANDLE, Context:HANDLE

    SetObject esi
    mov hDC, $invoke(BeginPaint, [esi].hWnd, addr PS)

    mov Surface, $invoke(cairo_win32_surface_create, hDC)
    mov Context, $invoke(cairo_create, Surface)
   
    invoke cairo_rectangle, Context, $CReal8(20.0), $CReal8(30.0), $CReal8(100.0), $CReal8(100.0)
    invoke cairo_set_source_rgba, Context, $CReal8(0.1), $CReal8(0.5), $CReal8(0.8), $CReal8(0.5)
    invoke cairo_set_fill_rule, Context, CAIRO_FILL_RULE_EVEN_ODD
    invoke cairo_fill, Context

    invoke cairo_rectangle, Context, $CReal8(50.0), $CReal8(60.0), $CReal8(100.0), $CReal8(100.0)
    invoke cairo_set_source_rgba, Context, $CReal8(0.3), $CReal8(0.7), $CReal8(0.8), $CReal8(0.5)
    invoke cairo_set_fill_rule, Context, CAIRO_FILL_RULE_EVEN_ODD
    invoke cairo_fill, Context

    invoke cairo_rectangle, Context, $CReal8(80.0), $CReal8(90.0), $CReal8(100.0), $CReal8(100.0)
    invoke cairo_set_source_rgba, Context, $CReal8(0.8), $CReal8(0.7), $CReal8(0.8), $CReal8(0.5)
    invoke cairo_set_fill_rule, Context, CAIRO_FILL_RULE_EVEN_ODD
    invoke cairo_fill, Context

    invoke cairo_destroy, Context
    invoke cairo_surface_destroy, Surface

    invoke GetClientRect, [esi].hWnd, addr Rct
    invoke DrawEdge, hDC, addr Rct, EDGE_SUNKEN, BF_RECT

    invoke EndPaint, [esi].hWnd, addr PS
    mov eax, TRUE
MethodEnd


To use the exe, put the cairo.dll in the same directory.

The rest is now experimenting with the API.

I reuploaded the modified include file set to the above post.

Biterider

Title: Re: Cairo
Post by: jj2007 on November 20, 2018, 08:11:48 AM
Quote from: Biterider on November 20, 2018, 06:45:59 AMI reuploaded the modified include file set to the above post.

Your exe works fine, but the includes still throw numerous errors despite using this macro as you suggested:
    WIN_STD_CALL_CONV equ <stdcall>
    @DefProto macro ApiQual, ProcName, CallConv, NameSuffix, Params, DecorSuffix

      ifidn <ApiQual>, <DllImport>                      ;;Call [IAT], a bit faster
        TYPE_&ProcName typedef proto CallConv Params
        ifnb <DecorSuffix>
          externdef WIN_STD_CALL_CONV _imp__&ProcName&@&DecorSuffix: ptr TYPE_&ProcName
          ProcName&NameSuffix equ <_imp__&ProcName&@&DecorSuffix>
        else
          externdef c _imp__&ProcName: ptr TYPE_&ProcName
          ProcName&NameSuffix equ <_imp__&ProcName>
        endif
      else
        ProcName&NameSuffix proto CallConv Params       ;;Call thunk (jmp [IAT])
      endif
    endm
include \Masm32\Cairo\cairo.inc

Title: Re: Cairo
Post by: Biterider on November 20, 2018, 06:10:47 PM
Hi JJ
Cairo.inc contains the macro used for prototyping (@DefCairoProto). The one I posted is the standard for Windows API, which does not apply here. Theoretically, you do not have to add anything special to the include files.

For the posted application I simply used:
include .\Inc\cairo-win32.inc


The .inc files include the required files. Some of them are part of the windows header files. This is the case for Cairo_ft.inc. Others include Windows.inc. I did not test it with the masm32 set of include files. Maybe there is an incompatibility.
I used UASM as an assembler.
I have not experimented with SVG or PDF backends yet. I hope I can spend some time this weekend to play with them.

You can PM me sending the errors you are seeing and the context of your application. 8)
If there is of any use, I cam post the sources of the demo application.

Regards, Biterider
Title: Re: Cairo
Post by: jj2007 on November 20, 2018, 07:01:13 PM
Quote from: Biterider on November 20, 2018, 06:10:47 PMYou can PM me sending the errors you are seeing and the context of your application. 8)
Done.

QuoteIf there is of any use, I cam post the sources of the demo application.
That would certainly be interesting, thanks :icon14:
Title: Re: Cairo
Post by: Biterider on November 21, 2018, 04:05:10 AM
Hi
Here are the sources of the demo application.
Biterider
Title: Re: Cairo
Post by: TimoVJL on November 21, 2018, 04:38:21 AM
cairo-windows-1.15.12 have lib files for it, so what was the problem with them?
calling convention is C __cdecl

CONS: PDF text don't work :(
EDIT:// https://cairographics.org/manual/cairo-text.html
// https://www.cairographics.org/tutorial/
#define WIN32_LEAN_AND_MEAN
#include <windows.h>

int printf(const char *, ...);
#pragma comment(lib, "msvcrt.lib")
#pragma comment(linker,"/subsystem:console,5.1")
void __cdecl mainCRTStartup(void)
{
int __cdecl main(void);
__declspec(dllimport) void __cdecl exit(int status);
exit(main());
}

typedef void * (__cdecl *CPROC)();

int __cdecl main(void)
{
HMODULE hDll = LoadLibrary("cairo.dll");
if (!hDll) hDll = LoadLibrary("libcairo-2.dll");
if (hDll) {
CPROC cairo_version_string = (CPROC)GetProcAddress(hDll, "cairo_version_string");
CPROC cairo_pdf_surface_create = (CPROC)GetProcAddress(hDll, "cairo_pdf_surface_create");
CPROC cairo_surface_destroy = (CPROC)GetProcAddress(hDll, "cairo_surface_destroy");
CPROC cairo_create = (CPROC)GetProcAddress(hDll, "cairo_create");
CPROC cairo_destroy = (CPROC)GetProcAddress(hDll, "cairo_destroy");
CPROC cairo_show_page = (CPROC)GetProcAddress(hDll, "cairo_show_page");
CPROC cairo_move_to = (CPROC)GetProcAddress(hDll, "cairo_move_to");
//CPROC cairo_line_to = (CPROC)GetProcAddress(hDll, "cairo_line_to");
//CPROC cairo_stroke = (CPROC)GetProcAddress(hDll, "cairo_stroke");
CPROC cairo_select_font_face = (CPROC)GetProcAddress(hDll, "cairo_select_font_face");
CPROC cairo_set_font_size = (CPROC)GetProcAddress(hDll, "cairo_set_font_size");
CPROC cairo_show_text = (CPROC)GetProcAddress(hDll, "cairo_show_text");
if (cairo_version_string && cairo_pdf_surface_create && cairo_create
&& cairo_surface_destroy && cairo_destroy && cairo_show_page
&& cairo_show_text)
{
printf("Version: %s\n", (char*)cairo_version_string());
void *surface = cairo_pdf_surface_create("test.pdf", 504.0, 648.0);
void *cr = cairo_create(surface);
cairo_move_to(cr, 10.0, 50.0);
//cairo_line_to(cr, 30, 25);
//cairo_stroke(cr);
cairo_select_font_face (cr, "Arial", 0, 0);
cairo_set_font_size (cr, 40.0);
cairo_show_text(cr, cairo_version_string());
cairo_show_page(cr);
cairo_destroy(cr);
cairo_surface_destroy(surface);
}
} else printf("error: missing libcairo-2.dll or cairo.dll\n");
return 0;
}

Title: Re: Cairo
Post by: jj2007 on November 21, 2018, 05:05:39 AM
And here is the full source of my version. The attachment contains also the adapted version that uses biterider's Cairo.inc, which I finally got working - thanks, biterider :icon14:

@Timo: No problem with lib, it works. Biterider's version needs the Cairo.lib, but my version below doesn't; both need Cairo.dll (which raises the question what the added value of a static lib is ... I see that relatively often in packages coming from the Linux world 8))

GuiParas equ "Cairo demo", x550, y20, w160, h180, cblack, b RgbCol(255, 255, 160)
include \masm32\MasmBasic\Res\MbGui.asm        ; pure MasmBasic (http://masm32.com/board/index.php?topic=94.0) :P
Dll "\Masm32\Cairo\lib\x86\cairo.dll"          ; suggested path to the Dll (Cairo.lib is not needed)
Declare cairo_version                          ; hit F6 to build; this version works from any folder
Declare cairo_win32_surface_create, C:1
Declare cairo_create, C:1
Declare void cairo_rectangle, C:5
Declare void cairo_set_source_rgba, C:5
Declare void cairo_set_fill_rule, C:2
Declare void cairo_fill, C:1
Declare void cairo_destroy, C:1
Declare void cairo_surface_write_to_png, C:2
Declare void cairo_surface_destroy, C:1
Declare void cairo_status, C:1                 ; for context errors
Declare void cairo_surface_status, C:1         ; for surface errors
Declare void cairo_status_to_string, C:1       ; for all errors
Enum 0:CAIRO_FILL_RULE_WINDING, CAIRO_FILL_RULE_EVEN_ODD       ; for usage, click here (http://www.webalice.it/jj2006/MasmBasicQuickReference.htm#Mb1016)
SetGlobals surface, context, ctGuiRefresh, double red, green, blue

Event Timer
  If_ ctGuiRefresh<100 Then mcs inc ctGuiRefresh : GuiRefresh   ; show random colours for a few seconds

Event Paint
  invoke TextOut, PtDC, 9, 5, Str$("Cairo version %i\n", cairo_version()), s$Len
  mov surface, cairo_win32_surface_create(PtDC)
  mov context, cairo_create(eax)
  cairo_rectangle(context, FP8(20.0), FP8(30.0), FP8(100.0), FP8(100.0))
  Rand(0.0, 1.0, red)
  Rand(0.0, 1.0, green)         ; generate random colours
  Rand(0.0, 1.0, blue)
  cairo_set_source_rgba(context, red, green, blue, FP8(0.7))    ; last arg: 0=fully transparent, 1.0=opaque
  cairo_set_fill_rule(context, CAIRO_FILL_RULE_EVEN_ODD)
  cairo_fill(context)
  cairo_destroy(context);
  ; cairo_surface_write_to_png(surface, "test.png")    ; optional: saves client area to disk
  cairo_surface_destroy(surface)
GuiEnd


P.S.: For the old MasmBasic package, the latest version of the Declare (http://www.webalice.it/jj2006/MasmBasicQuickReference.htm#Mb1018) macro posted here for HSE (http://masm32.com/board/index.php?topic=7534.msg82214#msg82214) is needed; insert an include before Dll...
Title: Re: Cairo
Post by: HSE on November 21, 2018, 05:39:37 AM
Quote from: Biterider on November 21, 2018, 04:05:10 AM
Here are the sources of the demo application.

I think the code is not ObjAsm32 compatible  :biggrin: :biggrin: :biggrin:

Something is silently not working with AsmC (perhaps is a diferent Defined ¿?).


Title: Re: Cairo
Post by: HSE on November 21, 2018, 05:44:31 AM
Quote from: jj2007 on November 21, 2018, 05:05:39 AM
P.S.: For the old MasmBasic package, the latest version of the Declare (http://www.webalice.it/jj2006/MasmBasicQuickReference.htm#Mb1018) macro posted here for HSE (http://masm32.com/board/index.php?topic=7534.msg82214#msg82214) is needed; insert an include before Dll...

And s$Len?  :biggrin:
Title: Re: Cairo
Post by: Vortex on November 21, 2018, 06:07:16 AM
It's easy to create the import library with Pelle's library manager Polib :

\PellesC\bin\polib.exe  /OUT:cairo.lib /MACHINE:x86 cairo.dll

Thanks Timo for your example. I tested the import library generated by Polib with your example project.

I assume that all the exported functions are following the C calling convention :

\PellesC\bin\podump.exe /EXPORTS cairo.dll > cairo_exports.txt

      1     0  1006F760  cairo_append_path
              2     1  1006F7D0  cairo_arc
              3     2  1006F890  cairo_arc_negative
              4     3  1006F950  cairo_clip
              5     4  1006F980  cairo_clip_extents
              6     5  1006F9F0  cairo_clip_preserve
              7     6  1006FA20  cairo_close_path
              8     7  1006FA50  cairo_copy_clip_rectangle_list
              9     8  1006FA80  cairo_copy_page
              A     9  1006FAB0  cairo_copy_path
              B     A  1006FAE0  cairo_copy_path_flat
              C     B  1006FB10  cairo_create
              D     C  1006FB80  cairo_curve_to
              E     D  10026660  cairo_debug_reset_static_data
              F     E  1006FC00  cairo_destroy
             10     F  100281B0  cairo_device_acquire
             11    10  10028210  cairo_device_destroy
             12    11  100282A0  cairo_device_finish
.
.
Title: Re: Cairo
Post by: Biterider on November 21, 2018, 07:56:06 AM
Hi
The .dll and .lib files work fine. No need to rebuild them, but if anyone wants to do it, I attach the .def file.  :idea:

@JJ: you are welcome.  :t

@HSE: it is OA32 but with some additional features I'm working on right now. To avoid naming conflicts, I've added namespaces for objects and interfaces.  In a few weeks, I'll bring the next version showing these improvements.  ;)

Biterider
Title: Re: Cairo
Post by: HSE on November 21, 2018, 08:55:59 AM
@Biterider:
   
    Perfect now  :t
   
    My mistake, naturally. I was forgotten that I commented background line. You are not using "IncludeAPIs Gdi32" now!
     
    Thanks.

Title: Gdi+
Post by: jj2007 on November 21, 2018, 11:31:19 AM
include \masm32\MasmBasic\Res\MbGui.asm

MakePen       hPenBez, RgbCol(255, 255, 0, 0), width 4
MakePath      123, Bezier(10:10, 80:40, 40:190, 190:50, 100:170, 180:170, 100:0)

Event Paint
  GuiDraw 123, hPenBez, 10.0, 10.0, 4000, 5000  ; x, y, scaleX, scaleY
GuiEnd


Source & exe attached
Title: Re: Cairo
Post by: TimoVJL on November 21, 2018, 09:40:00 PM
Quote from: jj2007 on November 21, 2018, 05:05:39 AM
@Timo: No problem with lib, it works. Biterider's version needs the Cairo.lib, but my version below doesn't;
With C, without lib:
http://masm32.com/board/index.php?topic=7534.msg82238#msg82238
Title: Re: Cairo
Post by: HSE on November 22, 2018, 11:13:09 AM
I think cairo have problems with text:  invoke cairo_select_font_face, Context, $OfsCStr("Times New Roman"), CAIRO_FONT_SLANT_OBLIQUE, CAIRO_FONT_WEIGHT_NORMAL
invoke cairo_set_font_size , Context, $CReal8(30)
invoke cairo_move_to , Context, $CReal8(30.0),$CReal8(84.0)
invoke cairo_text_path , Context, $OfsCStr("Que lo pario Mendieta...")
invoke cairo_set_source_rgb, Context, $CReal8(0.0),$CReal8(0.0),$CReal8(0.0)
invoke cairo_set_line_width, Context, $CReal8(10.0)
invoke cairo_stroke, Context

invoke cairo_set_font_size , Context,$CReal8(30)
invoke cairo_move_to , Context, $CReal8(30.0),$CReal8(84.0)
invoke cairo_text_path , Context, $OfsCStr("Que lo pario Mendieta...")
invoke cairo_set_source_rgb, Context, $CReal8(200.0),$CReal8(200.0),$CReal8(0.0)
invoke cairo_set_line_width, Context, $CReal8(3.0)
invoke cairo_stroke, Context
   
; Just a line
    invoke cairo_new_path, Context
    invoke cairo_move_to, Context, $CReal8(100.0), $CReal8(100.0)
invoke cairo_line_to, Context, $CReal8(200.0), $CReal8(200.0)
invoke cairo_set_source_rgba, Context, $CReal8(1.0), $CReal8(0.0), $CReal8(0.0), $CReal8(1.0)
    invoke cairo_set_line_width, Context, $CReal8(20.0)
    invoke cairo_stroke, Context
Title: Re: Cairo
Post by: TimoVJL on November 22, 2018, 05:20:26 PM
Version: 1.14.12 VbCairo (https://github.com/VBForumsCommunity/VbCairo/tree/master/bin/dll) stdcall version.
Title: Re: Cairo
Post by: Biterider on November 22, 2018, 05:55:42 PM
Hi
@HSE: cooolll  :P   :t


Biterider
Title: Re: Cairo
Post by: jj2007 on November 22, 2018, 07:04:12 PM
Quote from: TimoVJL on November 22, 2018, 05:20:26 PM
Version: 1.14.12 VbCairo (https://github.com/VBForumsCommunity/VbCairo/tree/master/bin/dll) stdcall version.

Works like a charm, just replace in my versions
Dll "\Masm32\Cairo\lib\x86\cairo.dll" ; suggested path to the Dll (Cairo.lib is not needed)
Declare cairo_version ; hit F6 to build; this version works from any folder
Declare cairo_win32_surface_create, C:1
Declare cairo_create, C:1
...

with
Dll "\Masm32\Cairo\lib\x86\vbcairo.dll" ; suggested path to the Dll (Cairo.lib is not needed)
Declare cairo_version ; hit F6 to build; this version works from any folder
Declare cairo_win32_surface_create, 1
Declare cairo_create, 1
...

... i.e. adapt to StdCall instead of C:

The bigger issue is discussed here: Is this worth the effort? (https://github.com/VBForumsCommunity/VbCairo/issues/4)
QuoteI have spent the past few months comprehensively perf-testing Cairo against GDI+. In nearly every area where the two libraries overlap (which is 90+% of features), GDI+ is preferable from a performance standpoint. This isn't surprising, given that Cairo's Windows backend largely wraps existing GDI functions ...

etc etc, a long post but worth reading. And it answers my previous question:
Quote from: jj2007 on November 19, 2018, 10:25:11 AMI am curious if this lib offers any advantage over plain Gdi or Gdi+

If Cairo offered a lot more than what is possible with Gdi+ (http://masm32.com/board/index.php?topic=6631.msg71135#msg71135), then I would pursue that road. But it seems just a wrapper for Gdi+, and a complicated one :(

For comparison:

A Gdi+ rectangle in MasmBasic:
  MakePath MyRect, Rect(96:250)                ; before the events
  MakeBrush brushes(0), RgbCol(200, 255, 0, 0)
...
  GuiFill MyRect, brushes(0), 100, 100 ; handle, brush, x, y   ; Event Paint


A Gdi+ rectangle in Cairo (WM_PAINT handler):
  mov surface, cairo_win32_surface_create(PtDC)
  mov context, cairo_create(eax)
  cairo_rectangle(context, FP8(20.0), FP8(30.0), FP8(100.0), FP8(100.0))
  cairo_set_source_rgba(context, red, green, blue, FP8(0.7))
  cairo_set_fill_rule(context, CAIRO_FILL_RULE_EVEN_ODD)
  cairo_fill(context)
  cairo_destroy(context);
  cairo_surface_destroy(surface)

Title: Re: Cairo
Post by: Biterider on November 22, 2018, 07:38:58 PM
Hi JJ
The biggest plus point I see is the platform portability. AFAIK GDI+ is Windows only.
I known, you need much more than cairo to shift to another OS...


My 2 cents.


Biterider
Title: Re: Cairo
Post by: jj2007 on November 22, 2018, 08:23:15 PM
I know, I know... but in my lifetime, I will stick to Windows. It's good that Linux exists, that creates a bit of competition, but honestly, there is not even one Linux; see DistroWatch (https://distrowatch.com/dwres.php?resource=popularity) for the top 300 "distros". Is there a Cairo.lib that works on all of them, as in the Windows world?

What I hate most about portability is that such packages often ship with the Linux equivalent of the whole Windows OS. Gigabytes of extra stuff, slow and bloated. What is the minimum size of a standalone QT executable? 8MB?
Title: Re: Cairo
Post by: TimoVJL on November 22, 2018, 08:51:05 PM
Usually linux is not so portable, almost every distro needs own packages.
So a bit easier for a programmer, not for a user.

If PDF don't work in cairo.dll, who use or need that in Windows? Python ?