[Delphi] Inhoud plaatje uit ander plaatje kopiëren

Pagina: 1
Acties:

  • Spinal
  • Registratie: Februari 2001
  • Laatst online: 13-08 11:55
Ik heb twee plaatjes, een van 640x400 en een van 128x128.
Het 128x128 plaatje bestaat uit 16x16 onderdelen. Het is voor een spel.
van 0,0 tot 15,15 bevat bijvoorbeeld een muur, van 16,0 tot 31,15 uit water enz.
Het plaatje van 640x400 is het level.
Nu wil ik dus het level opbouwen uit de onderdelen van het andere plaatje. Op dit moment doe ik dat zo:
code:
1
2
3
for y:=0 to 15 do
 for x:=0 to 15 do
  image1.canvas.pixels[doely+y,doelx+x]:=image2.canvas.pixels[brony+y,bronx+x];

Bijvoorbeeld de muur, die wil ik op positie 31,31 hebben, dan roep ik deze procedure aan met doely=31, doelx=31, brony=0, bronx=0

Dit werkt, maar is heel erg langzaam. Is er een snellere manier om dit te doen? Ik kom er echt niet uit...

Full-stack webdeveloper in Groningen


  • Hu9o
  • Registratie: Mei 2001
  • Laatst online: 18:19

Hu9o

Schokkend

Maak allemaal aparte Timage velden aan, en plaats die in een vierkant van 16x16.

Als een veld 5 "muur" moet worden doe dan zoiets als:
Delphi:
1
2
3
4
5
6
var
Jp  :   TJPEGImage;
begin
    Jp := TJPEGImage.create;
    Jp.LoadFromFile("muur.jpg");
    Image5.Picture.Assign(jp);


De methode die jij gebruikt, pixel voor pixel gaat idd heel erg langzaam voor grote groepen pixels. er is een snelere manier voor, maar dan krijg je alles 1 kleur (weet niet meer hoe die heet iets als drawbox oid). Dacht niet dat je daar een plaatje mee kan invullen.

Hopeljk heb je hier iets aan.

p.s. Is de methode die jij gebruikt wel "window"-vast?? Want ik geloof dat je de tekening weg kan poetsen als je met een ander scherm erover gaat.

[ Voor 5% gewijzigd door Hu9o op 15-06-2003 19:38 ]

>>>>>>>>>>>>>>>>>>>>>>>>>Vertel Microsoft over dit probleem <<<<<<<<<<<<<<<<<<<<<<<<<


  • Spinal
  • Registratie: Februari 2001
  • Laatst online: 13-08 11:55
Heb ik wel over gedacht, maar een 600x400 plaatje verdelen in 16x16 plaatjes betekend dat je uitkomt op 1000 aparte plaatjes :D
Daar had ik niet zo'n zin in...
De methode die ik gebruik is wel 'window-vast' zoals jij het noemt. Als ik er met een ander scherm over heen ga blijft het plaatje gewoon bestaan.

Full-stack webdeveloper in Groningen


  • Hu9o
  • Registratie: Mei 2001
  • Laatst online: 18:19

Hu9o

Schokkend

Kan je de plaatjes dan niet dynamisch laten genereren en als een plaatje al bestaat dan niet een nieuwe gebruiken natuurlijk?? Maar dit zal wel veel geheugen kosten ben ik bang.

Ik zou anders ook geen methode weten waarmee je een plaatje op een bepaalde positie op een canvas kan tekenen, zonder pixel voor pixel het plaatje over te nemen.

>>>>>>>>>>>>>>>>>>>>>>>>>Vertel Microsoft over dit probleem <<<<<<<<<<<<<<<<<<<<<<<<<


  • Spinal
  • Registratie: Februari 2001
  • Laatst online: 13-08 11:55
Dynamisch genereren is misschien een mogelijkheid, ik zal er eens naar kijken

Toch jammer. Ik dacht dat er misschien wel een of ander kopiëer functie bestond, waarmee je delen van plaatjes naar andere plaatjes kon kopiëren.
Blijkbaar niet dus.
Misschien moet ik toch maar een DirectX of OpenGL voor Delphi gaan leren, waarschijnlijk gaat het daarmee sneller

Full-stack webdeveloper in Groningen


  • Brothar
  • Registratie: Oktober 2000
  • Laatst online: 04-02 09:14

Brothar

meester

Of doe beiden ?
Op je CD staat de achtergrond zowel als 640 * 400,als als een opgedeeld 1000 vierkantjes.
Bij het ingaan van het level laad je het 640*400
Tijdens het spelen wordt elk vierkantje op je beeldscherm bepaald door de aktie op/in dat vierkantje.
Blijft het overanderd, dan hoef je het niet opnieuw te laten tekenen. Loopt er een bijv. poppetje overheen, dan hoef je dat vierkantje alleen opnieuw met de achtergrond te tekenen als het poppetje dat vierkantje verlaat.
Afhankelijk van de positie op het scherm van dat poppetje weet je welke van de duizend vierkantjes het is.
De duizend bmp-tjes laat je (per level) door een generator aanmaken vanuit het 640*400 plaatje.
Voor 1 poppetje hoef je dan steeds alleen maar 1/duizendste van je beeldscherm opnieuw te laten tekenen.

[ Voor 8% gewijzigd door Brothar op 15-06-2003 20:02 ]

eagle


  • Spinal
  • Registratie: Februari 2001
  • Laatst online: 13-08 11:55
Dat zou kunnen, maar het level is geen achtergrond. Het is een tekstbestand (wordt in een later stadium gecodeerd, maar voorlopig niet) van 25x40 tekens.
Dat bestand wordt ingeladen. Leest het programma bijvoorbeeld het teken '-' dan wordt op die positie in het level een horizontale muur getekend.
Ik probeer nog wel wat, iig bedankt voor jullie hulp

Full-stack webdeveloper in Groningen


  • curry684
  • Registratie: Juni 2000
  • Laatst online: 13-08 16:46

curry684

left part of the evil twins

Lol pixelen om te tekenen, dat schiet niet op nee. :)

De Win32 API heeft hier native functies voor die op low-level CPU- en driverniveau het zware werk doen. Zoek eens op MSDN Library Online (gooi 'm in je Favorites!!!) naar de functies BitBlt en StretchBlt. Zal een factor 100-500 sneller zijn :D

Professionele website nodig?


  • Reptile209
  • Registratie: Juni 2001
  • Laatst online: 02:19

Reptile209

- gers -

Kan je het niet in een imagelist laden (als ze allemaal bijv. 16x16 zijn) en daarmee je canvas vullen? Dat scheelt iig het werk om zelf de images te splitsen, en misschien tekent het ook nog sneller.

Zo scherp als een voetbal!


  • curry684
  • Registratie: Juni 2000
  • Laatst online: 13-08 16:46

curry684

left part of the evil twins

Hu9o schreef op 15 juni 2003 @ 19:36:
p.s. Is de methode die jij gebruikt wel "window"-vast?? Want ik geloof dat je de tekening weg kan poetsen als je met een ander scherm erover gaat.
Zolang je (in)direct tekent in een Paint-event zal alles gerepaint worden.

Professionele website nodig?


  • Spinal
  • Registratie: Februari 2001
  • Laatst online: 13-08 11:55
curry684: Bedankt! Ik zal er eens naar kijken, factor 100-500 is snel genoeg :)
Reptile209: Ja, dat zou kunnen. Mocht ik niet uit die API functies komen dan kan ik dat nog proberen natuurlijk...

Full-stack webdeveloper in Groningen


  • Knutselsmurf
  • Registratie: December 2000
  • Laatst online: 17:59

Knutselsmurf

LED's make things better

Eventueel kun je ook nog naar de scanlines-property van een TImage kijken. Dat is een pointer rechtstreeks naar de plaatjes-data. En hiermee kun je dus ook vrij snel data manipuleren en kopieren.

- This line is intentionally left blank -


  • NaliXL
  • Registratie: Maart 2002
  • Laatst online: 30-07 19:19
En als je de snelheid van de Windows API wilt combineren met het gemak van een TBitmap, dan doe je het met een Canvas.Draw operatie.

Dus bijvoorbeeld :
Delphi:
1
2
3
4
5
6
var Plaatje1, Plaatje2 : TBitmap; //  Declareer ff wat plaatjes...

Plaatje1 := TBitmap.Create;   // Creer de instanties
Plaatje2 := TBitmap.Create;
Plaatje1.LoadFromFile('bitmap.bmp'); // Geef ff wat inhoud aan het leven van Plaatje1 ;)
Plaatje2.Canvas.Draw(0, 0, Plaatje1); // Kopieer de inhoud van plaatje1 naar plaatje2, op coordinaten (Top/left) 0,0...

Genoeg is meer dan veel, en tart den overvloed


  • Brothar
  • Registratie: Oktober 2000
  • Laatst online: 04-02 09:14

Brothar

meester

Ik heb ooit 's een Acorn Electron gebruikt.
In het hobbyblad Electron User stond een 'handleiding' voor het schrijven van spelletjes.
O.a. de truc die jij toepast voor het coderen van een achtergrond.

eagle


  • curry684
  • Registratie: Juni 2000
  • Laatst online: 13-08 16:46

curry684

left part of the evil twins

NaliXL schreef op 15 June 2003 @ 23:27:
En als je de snelheid van de Windows API wilt combineren met het gemak van een TBitmap, dan doe je het met een Canvas.Draw operatie.
<...knip...>
En als jij even het topic had gelezen had je gezien dat het niet ging om een volledig plaatje blitten, maar om een stukje te kopieren, iets waarvan TCanvas::Draw niet in voorziet :)

Sowieso zie ik het probleem of de complexiteit niet met een statement als dit:
C++:
1
2
BitBlt(MyBitmap->Canvas->Handle, 10, 20, 30, 40, 
       MyScreen->Canvas->Handle, 50, 60, SRCCOPY);

(en ja dat is in Delphi vrijwel dezelfde regel ;) )

Professionele website nodig?


  • curry684
  • Registratie: Juni 2000
  • Laatst online: 13-08 16:46

curry684

left part of the evil twins

Brothar schreef op 15 June 2003 @ 23:32:
Ik heb ooit 's een Acorn Electron gebruikt.
In het hobbyblad Electron User stond een 'handleiding' voor het schrijven van spelletjes.
O.a. de truc die jij toepast voor het coderen van een achtergrond.
Uhm dank je voor deze donatie... en wat is nu de relevantie/nut van deze opmerking? :?

Professionele website nodig?


  • Brothar
  • Registratie: Oktober 2000
  • Laatst online: 04-02 09:14

Brothar

meester

Als je dus meer zoekt, zou je in de bibliotheek kunnen duiken, en hoef je niet opnieuw het wiel uit te vinden (tenzij je het uiteraard leuker vindt)

eagle


  • curry684
  • Registratie: Juni 2000
  • Laatst online: 13-08 16:46

curry684

left part of the evil twins

Brothar schreef op 15 juni 2003 @ 23:55:
Als je dus meer zoekt, zou je in de bibliotheek kunnen duiken, en hoef je niet opnieuw het wiel uit te vinden (tenzij je het uiteraard leuker vindt)
Het is de meest standaard manier om gamemaps te bouwen, en in use sinds de begindagen (toen nog met ASCII-karakters ipv grafische tiles). Ik programmeerde spellen ook zo op de C-64 en Amiga. Het probleem zit dan ook absoluut niet in de aanpak (tilebased maps is de nette naam overigens) maar op de manier waarop ie het in Delphi moet renderen. Vandaar mijn opmerking dat jou donatie nogal irrelevant was binnen het topic.

Verder weer ontopic dus aub. :)

Professionele website nodig?


  • jvdmeer
  • Registratie: April 2000
  • Laatst online: 00:17
Kijk eens naar TCanvas. Deze bevat CopyRect met een bron-TRect en een doel TRect. Zie de help:

Delphi:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
var
  Bitmap: TBitmap;
  MyRect, MyOther: TRect;
begin

  MyRect := Rect(10,10,100,100);

  MyOther := Rect(10,111,100, 201);
  Bitmap := TBitmap.Create;
  Bitmap.LoadFromFile('c:\windows\tartan.bmp');
  Form1.Canvas.BrushCopy(MyRect, Bitmap, MyRect, clBlack);
  Form1.Canvas.CopyRect(MyOther,Bitmap.Canvas,MyRect);
  Bitmap.Free;
end;

  • Spinal
  • Registratie: Februari 2001
  • Laatst online: 13-08 11:55
curry684 schreef op 15 juni 2003 @ 23:43:
[...]
Sowieso zie ik het probleem of de complexiteit niet met een statement als dit:
C++:
1
2
BitBlt(MyBitmap->Canvas->Handle, 10, 20, 30, 40, 
       MyScreen->Canvas->Handle, 50, 60, SRCCOPY);

(en ja dat is in Delphi vrijwel dezelfde regel ;) )
:| Wow... Dat is inderdaad wel erg simpel en vooral ook erg snel.
Heel erg bedankt hiervoor!
Jullie hebben allemaal een plaatsje verdiend in het helpbestand, en jij zeker ;)

Full-stack webdeveloper in Groningen


  • curry684
  • Registratie: Juni 2000
  • Laatst online: 13-08 16:46

curry684

left part of the evil twins

Daar hoor ik sowieso al te staan als mod, maar drm is een lamme tak :)

Professionele website nodig?

Pagina: 1