[Formel] Etwas fürs Auge

  • Aloha Community,

    durch den Thread Kleinster HD-Kurzfilm ausgehend hab ich mir mal Andys Grundlage geschnappt und die Formel etwas geändert :D
    Dass ist dabei rausgekommen:

    Code
    [autoit]


    $hUser32Dll = DllOpen("user32.dll")
    $hGdi32Dll = DllOpen("gdi32.dll")
    $iWidth = 400
    $iHeight = 400

    [/autoit] [autoit][/autoit] [autoit]

    Global $iPi = 4 * ATan(1)

    [/autoit] [autoit][/autoit] [autoit]

    $hWnd = GUICreate("FormelDummy", $iWidth, $iHeight)
    $hDCGui = GetDC($hWnd)
    GUISetState()

    [/autoit] [autoit][/autoit] [autoit]

    For $iX = 0 To $iWidth
    For $iY = 0 To $iHeight
    $iFormel = $iX * $iY * 11510 / 5 + $iPi ^ $iPi
    Pix($hDCGui, $iX, $iY, $iFormel)
    Next
    Next

    [/autoit] [autoit][/autoit] [autoit]

    While GUIGetMsg() <> -3
    WEnd

    [/autoit] [autoit][/autoit] [autoit]

    Func Pix($hDC, $iX, $iY, $iColor)
    DllCall($hGdi32Dll, "long", "SetPixel", "long", $hDC, "long", $iX, "long", $iY, "long", $iColor)
    EndFunc ;==>pix

    [/autoit] [autoit][/autoit] [autoit]

    Func GetDC($hHandle)
    $hDC = DllCall($hUser32Dll, "int", "GetDC", "hwnd", $hHandle)
    Return $hDC[0]
    EndFunc ;==>GetDC

    [/autoit]

    Hoffe es gefällt euch :P
    lg, die Blume

  • Hallo Blume,
    für so wenig Zeilen Code ist das Resultat überweltigend.
    Wäre cool wenn man daraus eine Animation machen könnte, aber die Berechnung für ein Bild dauert 10 Sekunden.
    Also gute Arbeit bei der änderung der Formel ;)
    MfG. PrideRage

    Meine Projekte:
    ClipBoard Manager (beendet)
    Gutes ClipBoard Verwaltungs Programm mit nützlichen Funktionen.

    HTML Creator (beendet)
    Nützliches Tool um schnell ein eigenes HTML Dokument zu erstellen.

  • Zitat

    Ich bin am überlegen ob ich die Berechnungen, etc in Assembler bringen soll aber wenn Andy oder Sprenger den Code sehen krieg ich eins aufs Dach

    Wer sagt das?
    Wir profitieren alle voneinander! Jeder kann vom anderen etwas lernen!
    Aber unter uns, je mehr Leute hier mit Assembler arbeiten, desto mehr Spass macht es!
    Und mit den wirklich einfachen Grafik-Bearbeitungen fällt der Einstieg nicht schwer :thumbup:

  • Den Fehler kenne ich, das musste ich bei meiern Formel auch beachten, du musst als erstes Blau an Position Rot schreiben, dann Grün zu Grün und dann Rot zu Position Blau, auch die Reihenfolge beachten. Wenn die Drehung dir etwas ausmacht, dann zähle die Positionen runter, also den Bildpointer an das Ende und dann runterzählen, dann sollte es genauso wie oben sein.
    Und die Autoit Form ist so sicherlich noch ein wenig schneller: (nur die Werte die bleiben nicht immer wieder berechnet)

    Spoiler anzeigen
    [autoit]


    $hUser32Dll = DllOpen("user32.dll")
    $hGdi32Dll = DllOpen("gdi32.dll")
    $iWidth = 400
    $iHeight = 400

    [/autoit] [autoit][/autoit] [autoit]

    Global $iPi = 4 * ATan(1)

    [/autoit] [autoit][/autoit] [autoit]

    $hWnd = GUICreate("FormelDummy", $iWidth, $iHeight)
    $hDCGui = GetDC($hWnd)
    GUISetState()

    [/autoit] [autoit][/autoit] [autoit]

    $iPiP=$iPi ^ $iPi
    $ldf=11510 / 5

    [/autoit] [autoit][/autoit] [autoit]

    For $iX = 0 To $iWidth
    For $iY = 0 To $iHeight
    $iFormel = $iX * $iY * $ldf + $iPiP
    Pix($hDCGui, $iX, $iY, $iFormel)
    Next
    Next

    [/autoit] [autoit][/autoit] [autoit]

    While GUIGetMsg() <> -3
    WEnd

    [/autoit] [autoit][/autoit] [autoit]

    Func Pix($hDC, $iX, $iY, $iColor)
    DllCall($hGdi32Dll, "long", "SetPixel", "long", $hDC, "long", $iX, "long", $iY, "long", $iColor)
    EndFunc ;==>pix

    [/autoit] [autoit][/autoit] [autoit]

    Func GetDC($hHandle)
    $hDC = DllCall($hUser32Dll, "int", "GetDC", "hwnd", $hHandle)
    Return $hDC[0]
    EndFunc ;==>GetDC

    [/autoit]
  • Hab in asm mal ein Grundgerüst gebastelt, in dem man die "Formel" nur noch Eintragen braucht.
    Das sollte man auch nur mit Grundkenntnissen hinbekommen (oder fragen wie es geht, wenn man eine Idee hat^^)

    Weil es sonst so langweilig wäre, habe ich mal einen "Zoom" eingebaut, per Pfeiltasten hoch/runter.
    Wer die Äuglein aufmacht, sieht im Consolefenster wie sich während des "zoomens" die Variable im Bytecode ändert.

    Dank AssembleIt kann man die AutoIt-Variablen natürlich auch im asm-code verwenden.
    In diesem Fall sollte man, wenn man auf Assembleit verzichten und den CallWindowProc() verwenden möchte, vor dem Call die Variablen direkt in den Bytecode schreiben, Little Endian nicht vergessen :D

    Spoiler anzeigen
    [autoit]

    #include <WinAPI.au3>
    #include <WindowsConstants.au3>
    #include <StructureConstants.au3>
    #include <GDIConstants.au3>
    #include <Misc.au3>

    [/autoit] [autoit][/autoit] [autoit]

    #include <assembleit.au3>

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    $hUser32Dll = DllOpen("user32.dll")
    $hGdi32Dll = DllOpen("gdi32.dll")
    $iWidth = 400
    $iHeight = 400

    [/autoit] [autoit][/autoit] [autoit]

    $hWnd = GUICreate("FormelDummy", $iWidth, $iHeight)
    GUISetState()

    [/autoit] [autoit][/autoit] [autoit]

    $hDC_Gui = _WinAPI_GetDC($hWnd)

    [/autoit] [autoit][/autoit] [autoit]

    Global $ptr_bmp, $hbmp_bmp
    $hDC_bmp = _CreateNewBmp32($iWidth, $iHeight, $ptr_bmp, $hbmp_bmp) ;bitmap erstellen, auf der "gemalt" wird

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    $var = 1111 ;irgendeine startzahl zw. 1 und 1e8
    ;$var=30854447 ;testen

    [/autoit] [autoit][/autoit] [autoit]

    While GUIGetMsg() <> -3
    If _IsPressed("26", $hUser32Dll) Then ;pfeiltaste oben
    $var *= 0.99 ;nur sehr grob
    If $var < 1 Then $var = 1
    ElseIf _IsPressed("28", $hUser32Dll) Then ;pfeiltaste unten
    $var *= 1.33 ;nur sehr grob
    If $var > 1e8 Then $var = 1e8
    EndIf
    Sleep(50) ;ist sonst viel zu schnell
    _assembleit("ptr", "_muster") ;bild berechnen
    _WinAPI_BitBlt($hDC_Gui, 0, 0, $iWidth, $iHeight, $hDC_bmp, 0, 0, $srccopy)
    WinSetTitle($hWnd, "", "variable = " & $var)
    WEnd

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    Func _muster()
    _("use32")
    _("mov edi," & $ptr_bmp) ;pointer bitmap
    _("mov esi," & $iWidth) ;fensterbreite (esi verwendet, weil edx beim mul zerstört würde)
    _("mov ecx," & $iHeight) ;fensterhöhe
    _("@@:") ;ein pixel weiter, bzw eine pixelzeile weiter
    ;**************** Formel hier...****************
    _("mov eax,esi") ;spalte
    _("mul ecx") ;spalte*zeile
    _("mov ebx," & Int($var)) ;variable
    _("mul ebx") ;eax=spalte*zeile*variable=farbe ARGB
    ;**************** ....bis hier ****************
    _("stosd") ;mov [edi],eax : add edi,4 ; pixel in bitmap schreiben
    _("mov edx," & $iWidth) ;fensterbreite
    _("sub esi,1") ;innerhalb der zeile eins weniger
    _("cmovz esi,edx") ;if (esi=)zero then esi=fensterbreite , achtung, befehl erst ab P6 verfügbar!
    _("jnz @b") ;if not zero then jump _hoehe;fensterbreite ist noch nicht erreicht
    _("loop @b") ;ecx=ecx-1 : jmp hoehe
    _("ret")
    EndFunc ;==>_muster

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    Func _CreateNewBmp32($iWidth, $iHeight, ByRef $ptr, ByRef $hbmp) ;erstellt leere 32-bit-Bitmap; Rückgabe DC und ptr und handle auf die Bitmapdaten
    ;by Andy
    Local $hcdc = _WinAPI_CreateCompatibleDC(0) ;Desktop-Kompatiblen DeviceContext erstellen lassen
    Local $tBMI = DllStructCreate($tagBITMAPINFO) ;Struktur der Bitmapinfo erstellen und Daten eintragen
    DllStructSetData($tBMI, "Size", DllStructGetSize($tBMI) - 4);Structgröße abzüglich der Daten für die Palette
    DllStructSetData($tBMI, "Width", $iWidth)
    DllStructSetData($tBMI, "Height", -$iHeight) ;minus =standard = bottomup
    DllStructSetData($tBMI, "Planes", 1)
    DllStructSetData($tBMI, "BitCount", 32) ;32 Bit = 4 Bytes => AABBGGRR
    Local $adib = DllCall($hGdi32Dll, 'ptr', 'CreateDIBSection', 'hwnd', 0, 'ptr', DllStructGetPtr($tBMI), 'uint', $DIB_RGB_COLORS, 'ptr*', 0, 'ptr', 0, 'uint', 0)
    $hbmp = $adib[0] ;hbitmap handle auf die Bitmap, auch per GDI+ zu verwenden
    $ptr = $adib[4] ;pointer auf den Anfang der Bitmapdaten, vom Assembler verwendet
    _WinAPI_SelectObject($hcdc, $hbmp) ;objekt hbitmap in DC
    Return $hcdc ;DC der Bitmap zurückgeben
    EndFunc ;==>_CreateNewBmp32

    [/autoit]

    ciao
    Andy


    "Schlechtes Benehmen halten die Leute doch nur deswegen für eine Art Vorrecht, weil keiner ihnen aufs Maul haut." Klaus Kinski
    "Hint: Write comments after each line. So you can (better) see what your program does and what it not does. And we can see what you're thinking what your program does and we can point to the missunderstandings." A-Jay

    Wie man Fragen richtig stellt... Tutorial: Wie man Script-Fehler findet und beseitigt...X-Y-Problem

    Einmal editiert, zuletzt von Andy (9. März 2011 um 00:19)

  • Hi Leuz,
    so ich habe erste Fortschritte gemacht :D. Ich hab jetzt die schwarzen Streifen auf meinem Bild. Musste aber um 500 Ecken denken weil SetPixel ein sehr ungewöhnliches Verhalten an den Tag legt.
    Erstmal arbeitet es nicht mit RBG sondern mit GBR und es unterstützt kein Alpha. Wenn aber doch ein Alpha Wert gegeben ist verhält sich SetPixel so:

    • wenn der Alpha Wert ungerade ist dann macht es den Pixel schwarz (Fehler)
    • wenn der Alpha Wert gerade ist interressiert das SetPixel gar nicht und macht weiter


    und bis ich das rausgefunden hab hats schon ne kleine Ewigkeit gedauert :rolleyes: :D.
    Bis auf das das Bild verkehrtherrum, die falschen Farben hat und die Streifen nicht gleichmäßig kleiner Werden hab ichs hinbekommen :P

    Hier mein Code

    Spoiler anzeigen
    [autoit]

    #AutoIt3Wrapper_UseX64=n
    #include "include/AssembleIt.au3"
    #include <ScreenCapture.au3>

    [/autoit] [autoit][/autoit] [autoit]

    $iWidth = 400
    $iHeight = 400

    [/autoit] [autoit][/autoit] [autoit]

    Global $pBitmap, $hBitmap
    _CreateNewBmp32($iWidth, $iHeight, $pBitmap, $hBitmap)

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    Func Test()
    _("use32")
    _("org " & Fasmgetbaseptr($FASM))
    _("mov edi,dword[esp+4]")
    _("mov ebx,dword[esp+8]") ;Breite
    _("mov edx,dword[esp+12]") ;Höhe

    [/autoit] [autoit][/autoit] [autoit]

    _("mov ecx,ebx")
    _("imul ecx,edx")

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _("_mainLoop:")

    [/autoit] [autoit][/autoit] [autoit]

    _("mov eax,ecx")
    _("xor edx,edx")
    _("div ebx")

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    ;EDX = Mod(ecx,Breite)
    ;EAX = ecx / Breite

    [/autoit] [autoit][/autoit] [autoit]

    _("imul eax,edx") ; Int($ix / $iWidth) * Mod($ix, $iWidth)
    _("imul eax,2302") ; * 11510 / 5

    [/autoit] [autoit][/autoit] [autoit]

    _("add eax,36") ; (36 = Pi²)

    [/autoit] [autoit][/autoit] [autoit]

    _("mov edx,eax")
    _("shr edx,16")
    _("cmp dh,1")
    _("jpo schwarz")

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    ;RRGGBB -> BBGGRR

    [/autoit] [autoit][/autoit] [autoit]

    _("mov dl,al"); Blau in das low von EDX
    _("mov dh,0xFF");Alpha 0 setzen
    _("shr edx,16");16 bit nach links schieben 000000BB -> 00BB0000

    [/autoit] [autoit][/autoit] [autoit]

    _("mov dh,ah") ;Grün
    _("ror eax,8")
    _("mov dl,ah");Rot

    [/autoit] [autoit][/autoit] [autoit]

    _("_schreibe:")

    [/autoit] [autoit][/autoit] [autoit]

    _("mov dword[edi],edx")
    _("add edi,4")

    [/autoit] [autoit][/autoit] [autoit]

    _("sub ecx,1")
    _("cmp ecx,0")
    _("jne _mainLoop")

    [/autoit] [autoit][/autoit] [autoit]

    _("ende:")
    _("ret")

    [/autoit] [autoit][/autoit] [autoit]

    _("schwarz:")
    _("mov edx,0xFF000000")
    _("jmp _schreibe")
    EndFunc ;==>Test

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _AssembleIt("int", "Test", "ptr", $pBitmap, "int", $iWidth, "int", $iHeight)
    _ScreenCapture_SaveImage(@ScriptDir & "\Hallo.jpg", $hBitmap)

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    Func _CreateNewBmp32($iWidth, $iHeight, ByRef $ptr, ByRef $hbmp) ;erstellt leere 32-bit-Bitmap; Rückgabe $HDC und $ptr und handle auf die Bitmapdaten
    $hcdc = _WinAPI_CreateCompatibleDC(0) ;Desktop-Kompatiblen DeviceContext erstellen lassen
    $tBMI = DllStructCreate($tagBITMAPINFO) ;Struktur der Bitmapinfo erstellen und Daten eintragen
    DllStructSetData($tBMI, "Size", DllStructGetSize($tBMI) - 4);Structgröße abzüglich der Daten für die Palette
    DllStructSetData($tBMI, "Width", $iWidth)
    DllStructSetData($tBMI, "Height", -$iHeight) ;minus =standard = bottomup
    DllStructSetData($tBMI, "Planes", 1)
    DllStructSetData($tBMI, "BitCount", 32) ;32 Bit = 4 Bytes => AABBGGRR
    $adib = DllCall('gdi32.dll', 'ptr', 'CreateDIBSection', 'hwnd', 0, 'ptr', DllStructGetPtr($tBMI), 'uint', 0, 'ptr*', 0, 'ptr', 0, 'uint', 0)
    $hbmp = $adib[0] ;hbitmap handle auf die Bitmap, auch per GDI+ zu verwenden
    $ptr = $adib[4] ;pointer auf den Anfang der Bitmapdaten, vom Assembler verwendet
    ;_arraydisplay($adib)
    _WinAPI_SelectObject($hcdc, $hbmp) ;objekt hbitmap in DC
    Return $hcdc ;DC der Bitmap zurückgeben
    EndFunc ;==>_CreateNewBmp32

    [/autoit]


    AssembleIt findet ihr hier Link


    //Edit:
    Ich hab mal noch eine kleine Spielerei gemacht

    Spoiler anzeigen
    [autoit]

    #include <GDIPlus.au3>
    Global $iWidth = 400
    Global $iHeight = 400

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_Startup()
    $hWnd = GUICreate("FormelDummy", $iWidth, $iHeight)
    GUISetState()

    [/autoit] [autoit][/autoit] [autoit]

    $hGraphics = _GDIPlus_GraphicsCreateFromHWND($hWnd)
    $hPen = _GDIPlus_PenCreate()
    $hPic = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\autoit.png")

    [/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_GraphicsDrawImageRect($hGraphics, $hPic, 0, 0, $iWidth, $iHeight)

    [/autoit] [autoit][/autoit] [autoit]

    For $x = 0 To $iWidth
    For $y = 0 To $iHeight
    $iFormel = $x * $y * 2302 + 36
    $sFormel = Hex($iFormel)

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    $Alpha = StringMid($sFormel, 1, 2)
    $iFormel = "0xFF" & StringMid($sFormel, 7, 2) & StringMid($sFormel, 5, 2) & StringMid($sFormel, 3, 2)

    [/autoit] [autoit][/autoit] [autoit]

    If Mod(Int("0x" & $Alpha), 2) Then $iFormel = BitAND(0x00FFFFFF, $iFormel)

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_PenSetColor($hPen, $iFormel)
    _GDIPlus_GraphicsDrawRect($hGraphics, $x, $y, 1, 1, $hPen)
    Next
    Next

    [/autoit] [autoit][/autoit] [autoit]

    While GUIGetMsg() <> -3
    WEnd

    [/autoit]
  • Hi,
    so erstmal sry für den Doppelpost :rolleyes:, aber ich habs endlich hinbekommen das das Bild so aussieht wie das aus dem Startpost.
    für 600x600 braucht mein Assembler Code, bei mir, rund 4ms.

    So ohne langes gerede. Hier ist der Code:

    Spoiler anzeigen
    [autoit]

    #AutoIt3Wrapper_UseX64=n
    ;~ #include "include/AssembleIt.au3"
    #include <WinAPI.au3>
    #include <WindowsConstants.au3>
    Global $pBitmap, $hBitmap
    Global $iWidth = 600
    Global $iHeight = 600

    [/autoit] [autoit][/autoit] [autoit]

    $hGUI = GUICreate("", $iWidth, $iHeight)
    $hDC_Bitmap = _CreateNewBmp32($iWidth, $iHeight, $pBitmap, $hBitmap)

    [/autoit] [autoit][/autoit] [autoit]

    $tCodeBuffer = DllStructCreate("byte[107]") ;reserve Memory for opcodes
    DllStructSetData($tCodeBuffer, 1, "0x8B7C24048B5C24088B54240C89D0F7E35053BB04000000F7E301C75B5989C831D2F7F35389D3F7E3BBFE080000F7E35B83C0245053C1E818BB02000000F7F383FA00751E5B5888C2B6FFC1E21088E6C1C80888E2891783EF0483E90183F90175BCC35B58BA000000FFEBE9") ;write opcodes into memory
    $Timer = TimerInit()
    $ret = DllCall("user32.dll", "int", "CallWindowProcW", "ptr", DllStructGetPtr($tCodeBuffer), "ptr", $pBitmap, "int", $iWidth, "int", $iHeight, "int", 0)
    $sTime = TimerDiff($Timer)
    $hDC_GUI = _WinAPI_GetDC($hGUI)
    WinSetTitle($hGUI, "", "Etwas fürs Auge | Benötigte Zeit: " & Round($sTime, 1) & "ms |by Blume (Assembler Tune by Sprenger120)")
    GUISetState(@SW_SHOW)

    [/autoit] [autoit][/autoit] [autoit]

    While GUIGetMsg() <> -3
    _WinAPI_BitBlt($hDC_GUI, 0, 0, $iWidth, $iHeight, $hDC_Bitmap, 0, 0, $SRCCOPY)
    WEnd

    [/autoit] [autoit][/autoit] [autoit]

    _WinAPI_ReleaseDC($hGUI, $hDC_GUI)
    _WinAPI_DeleteDC($hDC_Bitmap)
    _WinAPI_DeleteObject($hBitmap)
    $pBitmap = 0
    $tCodeBuffer = 0

    [/autoit] [autoit][/autoit] [autoit]

    Func _CreateNewBmp32($iWidth, $iHeight, ByRef $ptr, ByRef $hbmp) ;erstellt leere 32-bit-Bitmap; Rückgabe $HDC und $ptr und handle auf die Bitmapdaten
    $hcdc = _WinAPI_CreateCompatibleDC(0) ;Desktop-Kompatiblen DeviceContext erstellen lassen
    $tBMI = DllStructCreate($tagBITMAPINFO) ;Struktur der Bitmapinfo erstellen und Daten eintragen
    DllStructSetData($tBMI, "Size", DllStructGetSize($tBMI) - 4);Structgröße abzüglich der Daten für die Palette
    DllStructSetData($tBMI, "Width", $iWidth)
    DllStructSetData($tBMI, "Height", -$iHeight) ;minus =standard = bottomup
    DllStructSetData($tBMI, "Planes", 1)
    DllStructSetData($tBMI, "BitCount", 32) ;32 Bit = 4 Bytes => AABBGGRR
    $adib = DllCall('gdi32.dll', 'ptr', 'CreateDIBSection', 'hwnd', 0, 'ptr', DllStructGetPtr($tBMI), 'uint', 0, 'ptr*', 0, 'ptr', 0, 'uint', 0)
    $hbmp = $adib[0] ;hbitmap handle auf die Bitmap, auch per GDI+ zu verwenden
    $ptr = $adib[4] ;pointer auf den Anfang der Bitmapdaten, vom Assembler verwendet
    ;_arraydisplay($adib)
    _WinAPI_SelectObject($hcdc, $hbmp) ;objekt hbitmap in DC
    Return $hcdc ;DC der Bitmap zurückgeben
    EndFunc ;==>_CreateNewBmp32

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    #cs
    Func Etwas_Fuers_Auge()
    _("use32")
    ;~ _("org " & Fasmgetbaseptr($FASM))
    _("mov edi,dword[esp+4]")
    _("mov ebx,dword[esp+8]") ;Breite
    _("mov edx,dword[esp+12]") ;Höhe

    [/autoit] [autoit][/autoit] [autoit]

    _("mov eax,edx") ;Pixelanzahl berechnen
    _("mul ebx")

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _("push eax")
    _("push ebx")

    [/autoit] [autoit][/autoit] [autoit]

    _("mov ebx,4")
    _("mul ebx")
    _("add edi,eax")
    _("pop ebx")
    _("pop ecx")

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _("_mainLoop:")

    [/autoit] [autoit][/autoit] [autoit]

    _("mov eax,ecx")
    _("xor edx,edx")
    _("div ebx")

    [/autoit] [autoit][/autoit] [autoit]

    ;EDX = Mod(ecx,Breite)
    ;EAX = ecx / Breite

    [/autoit] [autoit][/autoit] [autoit]

    _("push ebx");Breite sichern
    _("mov ebx,edx");Breite in ebx schreiben
    _("mul ebx") ; ecx/Breite * Mod (ecx,Breite)
    _("mov ebx,2302")
    _("mul ebx")
    _("pop ebx") ;ebx wiederherstellen

    [/autoit] [autoit][/autoit] [autoit]

    _("add eax,36") ; (36 = Pi²)

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _("push eax")
    _("push ebx")

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _("shr eax,24") ; 16 Bit nach links schieben | AARRBBGG -> 0000AARR
    _("mov ebx,2")
    _("div ebx")

    [/autoit] [autoit][/autoit] [autoit]

    _("cmp edx,0") ; Prüfen ob ungleich
    _("jne schwarz") ;wenn ja pixel schwärzen

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _("pop ebx")
    _("pop eax")

    [/autoit] [autoit][/autoit] [autoit]

    ;RGB zu BGR umrechnen
    _("mov dl,al"); Blau in das low von EDX
    _("mov dh,0xFF");Alpha FF setzen
    _("shl edx,16");16 bit nach links schieben 000000BB -> 00BB0000
    _("mov dh,ah") ;Grün
    _("ror eax,8")
    _("mov dl,ah");Rot

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    _("_schreibe:")

    [/autoit] [autoit][/autoit] [autoit]

    _("mov dword[edi],edx")
    _("sub edi,4")

    [/autoit] [autoit][/autoit] [autoit]

    _("sub ecx,1")
    _("cmp ecx,1")
    _("jne _mainLoop")

    [/autoit] [autoit][/autoit] [autoit]

    _("ret")

    [/autoit] [autoit][/autoit] [autoit]

    _("schwarz:")
    _("pop ebx")
    _("pop eax")
    _("mov edx,0xFF000000")
    _("jmp _schreibe")
    EndFunc ;==>Etwas_Fuers_Auge

    [/autoit] [autoit][/autoit] [autoit]

    $_ASSEMBLEIT_FLAG = 0
    _AssembleIt("int", "Etwas_Fuers_Auge", "ptr", $pBitmap, "int", $iWidth, "int", $iHeight)
    #ce

    [/autoit]
    • Offizieller Beitrag

    Läuft bei mir auch bei 1700 x 1700 Auflösung. 8o

  • Ich weiss nicht, wieso ihr Beschränkungen bzgl. der Grösse habt....
    10000x10000 Pixel sind problemlos machbar

    Spoiler anzeigen
    [autoit]

    ;32-Bit only
    ;by Andy

    [/autoit] [autoit][/autoit] [autoit]

    #include <WinAPI.au3>
    #include <WindowsConstants.au3>
    #include <StructureConstants.au3>
    #include <GDIConstants.au3>
    #include <Misc.au3>

    [/autoit] [autoit][/autoit] [autoit]

    #include <assembleit.au3>

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    $hUser32Dll = DllOpen("user32.dll")
    $hGdi32Dll = DllOpen("gdi32.dll")
    $iWidth = 10000
    $iHeight = 10000

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    $hWnd = GUICreate("FormelDummy", $iWidth, $iHeight)
    GUISetState()

    [/autoit] [autoit][/autoit] [autoit]

    $hDC_Gui = _WinAPI_GetDC($hWnd)

    [/autoit] [autoit][/autoit] [autoit]

    Global $ptr_bmp, $hbmp_bmp
    $hDC_bmp = _CreateNewBmp32($iWidth, $iHeight, $ptr_bmp, $hbmp_bmp) ;bitmap erstellen, auf der "gemalt" wird

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    $var = 1111 ;irgendeine startzahl zw. 1 und 1e8
    ;$var=30854447 ;testen

    [/autoit] [autoit][/autoit] [autoit]

    While GUIGetMsg() <> -3
    If _IsPressed("26", $hUser32Dll) Then ;pfeiltaste oben
    $var *= 0.99 ;nur sehr grob
    If $var < 1 Then $var = 1
    ElseIf _IsPressed("28", $hUser32Dll) Then ;pfeiltaste unten
    $var *= 1.33 ;nur sehr grob
    If $var > 1e8 Then $var = 1e8
    EndIf
    ;Sleep(50) ;ist sonst viel zu schnell
    ;$_assembleit_flag=0
    ;$ret=DllCall("user32.dll", "ptr", "CallWindowProcW", "ptr", DllStructGetPtr($tCodeBuffer),"int",0,"int",0,"int",0,"int",0)
    $t=timerinit()
    _assembleit("ptr", "_muster") ;bild berechnen
    $m=timerdiff($t)
    _WinAPI_BitBlt($hDC_Gui, 0, 0, $iWidth, $iHeight, $hDC_bmp, 0, 0, $srccopy)
    WinSetTitle($hWnd, "", "variable = " & $var)
    MsgBox(0,"Grafikdemo","Auflösung: "&$iwidth&" x "&$iHeight&" Pixel"&@crlf&stringformat("in %.2f Millisekunden",$m))

    [/autoit] [autoit][/autoit] [autoit]

    WEnd

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    Func _muster()
    _("use32")
    _("mov edi," & $ptr_bmp) ;pointer bitmap
    _("mov esi," & $iWidth) ;fensterbreite (esi verwendet, weil edx beim mul zerstört würde)
    _("mov ecx," & $iHeight) ;fensterhöhe
    _("@@:") ;ein pixel weiter, bzw eine pixelzeile weiter
    ;**************** Formel hier...****************
    _("mov eax,esi") ;spalte
    _("mul ecx") ;spalte*zeile
    _("mov ebx," & Int($var)) ;variable
    _("mul ebx") ;eax=spalte*zeile*variable=farbe ARGB
    ;**************** ....bis hier ****************
    _("stosd") ;mov [edi],eax : add edi,4 ; pixel in bitmap schreiben
    _("mov edx," & $iWidth) ;fensterbreite
    _("sub esi,1") ;innerhalb der zeile eins weniger
    _("cmovz esi,edx") ;if (esi=)zero then esi=fensterbreite , achtung, befehl erst ab P6 verfügbar!
    _("jnz @b") ;if not zero then jump _hoehe;fensterbreite ist noch nicht erreicht
    _("loop @b") ;ecx=ecx-1 : jmp hoehe
    _("ret")
    EndFunc ;==>_muster

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    Func _CreateNewBmp32($iWidth, $iHeight, ByRef $ptr, ByRef $hbmp) ;erstellt leere 32-bit-Bitmap; Rückgabe DC und ptr und handle auf die Bitmapdaten
    ;by Andy
    Local $hcdc = _WinAPI_CreateCompatibleDC(0) ;Desktop-Kompatiblen DeviceContext erstellen lassen
    Local $tBMI = DllStructCreate($tagBITMAPINFO) ;Struktur der Bitmapinfo erstellen und Daten eintragen
    DllStructSetData($tBMI, "Size", DllStructGetSize($tBMI) - 4);Structgröße abzüglich der Daten für die Palette
    DllStructSetData($tBMI, "Width", $iWidth)
    DllStructSetData($tBMI, "Height", -$iHeight) ;minus =standard = bottomup
    DllStructSetData($tBMI, "Planes", 1)
    DllStructSetData($tBMI, "BitCount", 32) ;32 Bit = 4 Bytes => AABBGGRR
    Local $adib = DllCall($hGdi32Dll, 'ptr', 'CreateDIBSection', 'hwnd', 0, 'ptr', DllStructGetPtr($tBMI), 'uint', $DIB_RGB_COLORS, 'ptr*', 0, 'ptr', 0, 'uint', 0)
    $hbmp = $adib[0] ;hbitmap handle auf die Bitmap, auch per GDI+ zu verwenden
    $ptr = $adib[4] ;pointer auf den Anfang der Bitmapdaten, vom Assembler verwendet
    _WinAPI_SelectObject($hcdc, $hbmp) ;objekt hbitmap in DC
    Return $hcdc ;DC der Bitmap zurückgeben
    EndFunc ;==>_CreateNewBmp32

    [/autoit]


    die 400Mb-Grafik wird in einigen hundert millisekunden erstellt

  • Hi,
    meins würde auch in diesem schnellen Bereich liegen wenn ich nicht die 2 divisionen drinne hätte. Die fressen insgesamt 140 Takte und das ist zu viel !
    Ich könnte zwar den Code so weit umschreiben das er nur noch ein div bräuchte aber dazu hab ich keine lust ^^, und mal unter uns: wen interressierts ob das rendern nu 100ms oder 500 braucht. Schneller als AutoIt ist es allemal :thumbup: