[RIOS ERROR] Delphi programozás - LOGOUT.hu Hozzászólások [RIOS ERROR]

Delphi programozás - Szoftverfejlesztés fórum

üzenetek

[RIOS ERROR] [RIOS ERROR]

hozzászólások

[RIOS ERROR]

Tomi_78
(tag)
[RIOS ERROR]

Ja, értem már (legalábbis remélem): tehát a MainMenu az azt a menüt jelenti, amely egy alkalmazás ablakának tetején van, míg a PopupMenu a felbukkanó menüt, ami egérkattintásra előjön(?).


vz12
(tag)
[RIOS ERROR]

Igen.
Pontosan olyan igényt fogalmaztál meg, amire pontosan a TPopupMenu a megoldás.


Tomi_78
(tag)
[RIOS ERROR]

Igaz, s most már értem is. Át is írtam a TMainMenu-t TPopupMenu-re és most már működik!
Köszönöm ismét a segítségeteket! :C


vz12
(tag)
[RIOS ERROR]

Rendben, örülök. :)


Fire/SOUL/CD
(félisten)
Blog
[RIOS ERROR]

Hákúúúnámátátáá, milyen gyönyörű szó... :DDD


Tomi_78
(tag)
[RIOS ERROR]

Az! :))
De még lenne egy apró kérdésem: az OnClick eseménnyel hívott függvény paraméterezhető vajon?
Mert valahogy így próbálkoztam, de nem tetszett a Lazarus-nak:
procedure epitvagyvesz(Sender: TObject; mit: string);
(...)
menupont.OnClick:=@epitvagyvesz('valami');
(...)
procedure TForm1.epitvagyvesz(Sender: TObject; mit: string);
begin
case mit of ...

Tehát azt szeretném elérni, hogy a különböző menüpontok más paraméterrel hívják ugyanazt a függvényt az OnClick eseményükben. És most ezt egyéb lehetőség híján a Caption-jük segítségével oldom meg, mert az különböző:
case TMenuItem(Sender).Caption of
(...)
De nagyban megkönnyítené a helyzetemet a függvényparaméterezés lehetősége - ha ez lehetséges.


vz12
(tag)
[RIOS ERROR]

Szerintem az OnClick-nek csak "Sender" paramétere van, és nem lehet második paramétert használni. Az alul lévő megoldás egyébként megfelelő, de egy kicsit azért lehet javítani rajta.
Hasonló, de talán egy kicsit szebb a Sender.tag használata, amit a property beállításoknál akár tervezési időben is meg lehet adni, de dinamikusan, kódból is. A "tag" viszont egész szám típusú (talán Longint), amit én 1,2,3, stb-re állítanék be (indulhat 0-tól is, de tudni kell, hogy alaphelyzetben minden objektumnál tag=0), amit úgy lehet a leghatékonyabban string típussá alakítani, ha definiálsz egy string típusú elemekből álló TÖMBÖT a programban 1,2,3, stb. tömbindexekkel. Az OnClick-ben pedig már csak használni kell a Tomb[Sender.tag] string értéket. :)
Persze némi validáció (intervallumba tartozás vizsgálat) a tömbindexre (Sender.tag) nem árthat.

Ja, természetesen a különböző elemek OnClickjébe ugyanazt a függvényt kell beállítani, a hívó objektum "tag" beállítása legyen csak különböző.

[ Szerkesztve ]


Tomi_78
(tag)
[RIOS ERROR]

Rendben, köszönöm ezt a választ is.
Egyébként nem muszáj nekem, hogy string típusú legyen a függvényparaméter, csak valami módot keresek arra, hogy ne kelljen minden menüponthoz külön függvényt írni.
Ez a tag segítségével történő megoldás talán jó lesz számomra.


Fire/SOUL/CD
(félisten)
Blog
[RIOS ERROR]

"Tehát azt szeretném elérni, hogy a különböző menüpontok más paraméterrel hívják ugyanazt a függvényt az OnClick eseményükben."
Ebben az esetben nem látom értelmét Caption avagy Tag alapján megkülönböztetni, hogy melyik menüelem volt a küldő, hisz mindegyik menüelem saját onclick eseményét hívod meg, az meg egyértelműen azonosítja a küldőt...
Ez esetben ennyi az egész.

procedure WriteStrToForm1Caption (MyCaption:String);
begin
Form1.Caption:=MyCaption;
end;

procedure TForm1.M11Click(Sender: TObject);
begin
WriteStrToForm1Caption('Első menüelem');
end;

procedure TForm1.M12Click(Sender: TObject);
begin
WriteStrToForm1Caption('Második menüelem');
end;

procedure TForm1.M1S11Click(Sender: TObject);
begin
WriteStrToForm1Caption('Első menüelem első almenüelem');
end;

A TAG-es megoldás jobb, mint a Caption-ös, de abba is bele lehet keveredni, hisz egy popupmenu a kód fejlesztése során módosulhat(hozzáadsz/törölsz menüelemeket) és ilyenkor aztán lehet végignézni az összes menüelemet, hogy akkor most mi is legyen a TAG új értéke (ami nincs még/már), hisz nem lehet 2 vagy több egyforma, arról meg már nem is beszélve, ha submenu-t is használsz majd a későbbiekben...
A submenu elemeinél is ott figyel a TAG tulajdonság, szóval onnantól már submenü TAG-jeit is figyelni kellene(a főmenüvel együtt), hogy ne legyen 2 vagy több egyforma... :DDD

Aztán egy olyan hiba, amit sokan elkövetnek: Amennyiben van submenu (linkelt submenu-s képen az M1 menü ilyen), akkor az M1 onclick eseményét nem programozzuk fel, ugyanis ilyen esetben elég az egérkurzort az M1 menü fölé vinni és egyből, kattintás nélkül lefut az M1 onclick eseménye... (ez a hibás helyzet van a linkelt képen)

[ Szerkesztve ]


vz12
(tag)
[RIOS ERROR]

> valami módot keresek arra, hogy ne kelljen minden menüponthoz külön függvényt írni

Pontosan olyan megoldást javasoltál, amit el szeretett volna kerülni ...
Ha sok menüpontnál hasonló vagy gyakorlatilag ugyanaz a kód kell, akkor nagyon is célszerű ezt összevonni, a kódismétlést ott kell kerülni, ahol csak lehet.
Ha eltérőek a menüpontok kódjai (VAGY várható, hogy a jövőben el fognak térni ...), akkor persze érdemes külön-külön függvényeket/kódokat írni, ilyenkor a "tag"-ra nincs szükség.
A "tag"-nak egyébként nem kötelező egyesével növekedni, a Longint miatt megoldható "beszédes" érték is, pl. a 324 lehet a 3. menüpont 2. almenüjének a 4. al-almenü végpontja, feltételezve, hogy egy szinten nincs 9 menüpontnál több.
Ha több elem van 9-nél, akkor lehet 2 jegyből álló blokkokat is csinálni, pl. 1205 a 12. menüpont 5. almenüpontja, de a legfelső szinten a vezető nulla sajnos nem működik, ott lehet 3 jegyű blokk. pl. 90203 a 2. menüpont 3. almenüje (a kezdő 9-es figyelmen kívül hagyandó). Így 99 menüpont lehet szintenként, ami már elég kell, hogy legyen, legtöbbször a 9 is elegendő.
Az ilyen "tagolt taggal" jobban átlátható a rendszer, persze egy nagyobb menü átalakítás után rendet kell csinálni a kódban, de bővítésre meglehetősen rugalmas ez a megoldás.

És igen, a menürendszernek csak a "végpontjait" kell OnClick-elni (a menüfa LEVELEIT). :K

[ Szerkesztve ]


Fire/SOUL/CD
(félisten)
Blog
[RIOS ERROR]

"Pontosan olyan megoldást javasoltál, amit el szeretett volna kerülni ..."
Amelyik hsz-re Én válaszoltam (amiből idéztem is), abban meg pont az ellenkezője van...
(másikat meg nem olvastam figyelmesen...) :B


Tomi_78
(tag)
[RIOS ERROR]

Egy gyors kérdés: Lazarus-ban van valami mód képcsíkból a képek kinyerésére?
Tehát van egy .BMP strip (esetleg .GIF, ha ez a formátum is használható), és abból valamilyen függvénnyel kiemelni az alképeket? Mert tudtommal Delphi-ben van olyan függvény erre, hogy CopyRect(), de Lazarus-ban ezt nem találom. Mi a használatának a módja? Vagy marad az a fáradtságos megoldás, hogy a képcsíkból egy képszerkesztővel egyesével külön alképeket veszek ki és azokat töltöm be a LoadFromFile-lal?


vz12
(tag)
[RIOS ERROR]

Én úgy látom, hogy Lazarusban is úgy működik a CopyRect(), mint a Delphiben.
Feltettem egy Lazarust, és kipróbáltam. :)
Egy üres formra rátettem egy "TImage" elemet, és gyorsan írtam egy példakódot. Rajzoltam egy kört, és "CopyRect"-tel klónoztam:

procedure TForm1.FormCreate(Sender: TObject);
var r1,r2:TRect;
begin
    Image1.left:=0;
    Image1.top:=0;
    Image1.width:=200;
    Image1.height:=100;;
    Image1.Canvas.pen.color:=clWhite;
    Image1.Canvas.brush.color:=clWhite;
    Image1.Canvas.Rectangle(0,0,200,100);
    Image1.Canvas.pen.color:=clRed;
    Image1.Canvas.brush.color:=clYellow;
    Image1.Canvas.Ellipse(0,0,100,100);
  r1.left:=0;   r1.top:=0; r1.right:=100; r1.bottom:=100;
    r2.left:=100; r2.top:=0; r2.right:=200; r2.bottom:=100;
    Image1.Canvas.CopyRect(r2,Image1.Canvas,r1);
end;            

Az eredmény 2 db kör egymás mellett, tehát működik. :)
A CopyRect() szintaktikája talán egy kicsit furcsa, de meg lehet szokni, és pontosan olyan, mint Delphi-ben, nem látok különbséget.


Tomi_78
(tag)
[RIOS ERROR]

Ez jó hír és köszönöm a fáradozásodat! :K
Tehát r1 téglalap tartalmát másoltad az r2-re vele, ha jól látom, és mindezt az Image1 vásznán keresztül.


vz12
(tag)
[RIOS ERROR]

Igen, a példában ugyanaz a "Canvas" volt a forrás és a cél is, de 2 db különböző "Canvas" között is működnie kell, amennyiben a méretük megfelelő.

> tudtommal Delphi-ben van olyan függvény erre, hogy CopyRect(), de Lazarus-ban ezt nem találom
> Mi a használatának a módja?

Én csak "megtaláltam" neked, amit egy példával illusztráltam. :)
Így talán hanyagolni lehet a "külső" képszerkesztőt. :K


Tomi_78
(tag)
[RIOS ERROR]

Külön köszönöm, hogy most megtanultam tőled, hogy a Rect téglalap a top, bottom, left és right értékei megadásával is definiálható.
Sőt, kipróbáltam és width-height-je is van. Így sokkal könnyebb létrehozni, mint a Rect() függvénnyel.
Nagyon szépen köszönöm a segítségedet! :C


Tomi_78
(tag)
[RIOS ERROR]

A fenébe is, valami nem jó, mert ezt a géppuskáskatona képet nem jeleníti meg, és nem értem, hogy miért? :F :W
Ez a kód:
gpkatallkcs:=TBitmap.Create;
  gpkatallkcs.LoadFromFile('kepei/egysegek/gpkat/gpkatall.bmp');
  kcsbal:=0;
  for i:=0 to 7 do
begin

gpkatallkep[i]:=TBitmap.Create;
    t1.left:=kcsbal; t1.top:=0; t1.right:=kcsbal+round(gpkatallkcs.width/8); t1.bottom:=gpkatallkcs.height;
    t2.width:=t1.width; t2.height:=t1.height;
    gpkatallkep[i].Canvas.CopyRect(t2,gpkatallkcs.Canvas,t1);
    gpkatallkep[i].transparent:=true;
    if i<7 then
       kcsbal:=kcsbal+round(gpkatallkcs.width/8)
    else
        kcsbal:=0;
  end;
  gpkatallkcs.Free;

[ Szerkesztve ]


Tomi_78
(tag)
[RIOS ERROR]

Megvan a megoldás! :DD
A gpkatallkep[i]:=TBitmap.Create; egy csupán 1x1 képpont méretű képet hoz létre, ezért ki kellett egészíteni ezzel a kóddarabbal:
gpkatallkep[i].width:=t2.width;
gpkatallkep[i].height:=t2.height;

De most meg valamiért az átlátszóság veszett el, mert a transparent hiába true, így is kirajzolja a háttérszínét... :F Valaki tudja, miért van ez és hogyan orvosolható?


vz12
(tag)
[RIOS ERROR]

Szerintem a BMP nem tud átlátszó lenni, vagy igen?
Halványan régről emlékszem olyanra, hogy ha a ".bmp" fájl mellett van egy ugyanolyan nevű ".msk" fájl IS (maszk fájl), akkor HA a szoftver fel van rá készítve, akkor az ".msk" fájl segítségével működhet az átlátszóság a BMP-nél is. Nem tudom, hogy a Delphi ismeri-e ezt a módszert, illetve van-e neked ".msk" fájlod.

Véleményem szerint a TImage jobb lenne neked, mint a TBitmap, mert annak a "Picture.LoadFromFile"-ja több formátumot is kezel, pl. a PNG-t, ami viszont alapból átlátszó. A "transparent" property-t persze biztos true-ra kell állítani ilyenkor is.
De ez csak egy ötlet volt.


Tomi_78
(tag)
[RIOS ERROR]

A többi képem is .BMP és azokat mind átlátszóvá tudtam tenni. Lehet, hogy a mostani esetben máshová kellene tennem a transparent beállítását? Majd még kísérletezem...

üzenetek

[RIOS ERROR] [RIOS ERROR] [RIOS ERROR] [RIOS ERROR] [RIOS ERROR]