Wykrywanie strzału w gre (Snajper)?

0

Czy jest jakiś sposób na wykrycie strzału w grze? chodzi mi o to, żeby wraz ze strzałem zapalać stroba. Klawisz odpada, bo gdy nie ma naboi to strob i tak się zapali. Analiza dźwięku? jak? Może gra wysyła jakieś komendy, które można przechwycić, porównać i włączyć pin na porcie lpt.

0

hmm.. ciezka sprawa...
ja bym to robil droga prob i bledow...
nie wiem jak jest z zrzutami ekranu w Twojej grze, czy da sie zrobic taki zrzut uzywajac delphi...
wtedy mogl bys sie pokusic o:
badanie malego fragmentu ekranu i sprawdzanie czy sa naboje. jesli sa to czeka na nacisniecie klawisza odpowiedzialnego za strzal (wtedy blysk). jesli magazynek jest pusty to nie pilnuj klawisza.

rozwiazenie drugie (bardziej sprzetowe):
jesli to mozliwe przerabiasz lekko dzwiek w grze (dzwiek strzalu). tak zeby np na lewym kanale wystapil bardzo krotki ale silny impuls. moglo by sie okazac ze wcale nie przeszkadza to w graniu a wystarczyl by maly uklad podpiety pod wyjscie liniowe, ktory wyzwoli blysk po przekroczeniu jakiejs wartosci.

coz.. moze sie uda;]
powodzenia (pomysl sie podoba wiec trzymam kciuki ;] )

0

Pomysł z badaniem fragmentu strony nie jest głupi, a jak zrobić, coś jakiego?

Ma początek dajmy,ze w prawym dolnym rogu, jest czerwony kwadrat 10px X 10px. Może pobierać wartości poszczególnych pixeli?

0
siekierzyński napisał(a)

Pomysł z badaniem fragmentu strony nie jest głupi, a jak zrobić, coś jakiego?

Ma początek dajmy,ze w prawym dolnym rogu, jest czerwony kwadrat 10px X 10px. Może pobierać wartości poszczególnych pixeli?

jak zrobic cos takiego to odsylam do google.
inna sprawa ze moze sie to okazac ciezkie do zrobienia jesli gra korzysta z directX czy tam jakiegos opengl.. proboj.

0

jak by co to jest ta gra:

http://www.gry-online.pl/S016.asp?ID=1444

0

Na forum jest napisane jak zrobić zrzut ekranu w Delphi. Nie dla wszystkich gier to działa. Np. w grze Hitman Blood Money - kod podany na forum robił mi piękne zrzuty ekranu z gry. Generalnie - jeśli możesz w grze zrobić czytelny zrzut ekranu kopiując obraz do schowka (klawisz Print Screen) i wklejając do Paint-a, to możesz w taki sam sposób pobrać obraz za pomocą kodu z forum.

//----------------------------------------------------------------------------------------------------------------
Dobra, nie mogę spać. Napiszę to mniej - więcej. Nie mam Delphi chwilowo w lapci, więc nie wiem czy to sie skompiluje. Piszę z głowy - prosto na stronce - bo nie mam Delphi chwilowo. Mogą być błędy składni i w ogóle błędy straszliwe [wstyd]

(Ja mam lapcie, Ty masz stroba)
Ogólny schemat jest taki:

type
  TPictureAnalyzer = class (TObject)
  //nie będzie property bo nie chce mi się pisać getterów i setterów, ale logika każe ich użyć!
  private
    BulletBitmap : TBitmap;
    ScreenBitmap : TBitmap;
    BulletBitmapPosition : TPoint;
  public
    constructor Create(iBulletBitmap : TBitmap; iBulletBitmapPosition : TPoint);
    destructor Destroy();    
    function IsBullet() : Boolean;
  private   
    function CreatePrintScreen() : TBitmap;
    function AreAllPixelsTheSame() : Boolean;
    function TheSamePixel(const iPixelX : Integer; const iPixelY : Integer) : Boolean;
  end;

implementation

  constructor TPictureAnalyzer.Create(iBulletBitmap : TBitmap; iBulletBitmapPosition : TPoint);
  begin
    BulletBitmap := iBulletBimap;
    BulletBitmapPosition := iBulletBitmapPosition;
  end;

  destructor TPictureAnalyzer.Destroy();
  begin
    if Assigned(BulletBitmap)
      FreeAndNil(BulletBitmap);
    if Assigned(ScreenBitmap)
      FreeAndNil(ScreenBitmap);
  end;

  function TPictureAnalyzer.IsBullet() : Boolean;
  begin
    Result := AreAllPixelsTheSame(); 
  end;
  
  function TPictureAnalyzer.AreAllPixelsTheSame() : Boolean;
  var
    vPixelX : Integer;
    vPixelY : Integer;
  begin
    Result := False; 
    if Assigned(ScreenBitmap) then
      FreeAndNil(ScreenBitmap);
    ScreenBitmap := CreatePrintScreen();

    for vPixelX := 0 to BulletBitmap.Width do
      for vPixelY := 0 to BulletBitmap.Height do
      begin
        if not TheSamePixel(vPixelX, vPixelY) then
           exit();
      end;
    Result := True;
  end;

  function TPictureAnalyzer.TheSamePixel(const iPixelX : Integer; const iPixelY : Integer) : Boolean;
  begin
    Result := False; 
    if (ScreenBitmap.Pixels[BulletBitmapPosition.X + iPixelX, BulletBitmapPosition.Y + iPixelY] = BulletBitmap.Pixels[iPixelX, iPixelY] ) then
      Result := True;  
  end;

  function TPictureAnalyzer.CreatePrintScreen() : TBitmap;
  var
    vCan: TCanvas;
    vBitmap: TBitmap;
  begin
    try
      vCan:= TCanvas.Create;
      vCan.Handle := GetWindowDC(GetDesktopWindow);
      vBitmap := TBitmap.Create();
      vBitmap.Width := Screen.Width;
      vBitmap.Height := Screen.Height;
      vBitmap.Canvas.CopyRect(Rect(0, 0, Screen.Width, Screen.Height), vCan, Rect(0, 0, Screen.Width, Screen.Height));
    finally 
      vCan.Free;
    end;
      Result := vBitmap;
  end;

//(...)
  

[soczek] enjoy
Myślę, że jak poprawisz literówki i różne proste błędy w kodzie (sorry - nie mam Delphi chwilowo, nie mam jak skompilować), to będziesz mógł sobie badać w każdej grze wszystko co zechcesz.

Posłuchaj, sprawa wygląda tak:

//w deklaracjach klasy formularza
private
  PositionOfBulletPictureOnScreen : TPoint;
  BulletPicture : TBitmap;
  BulletAnalyzer : TPictureAnalyzer;
  IsBullet : Boolean;
(...)

//po załadowaniu formularza do pamięci
//tworzysz obiekt klasy TPictureAnalyzer
procedure TForm1.FormCreate(Sender : TObject);
begin
  PositionOfBulletPictureOnScreen.X := 546;
  PositionOfBulletPictureOnScreen.Y := 356;
  BulletPicture := TBitmap.Create();
  BulletPicture.LoadFromFile('BulletPicture.bmp');
  IsBullet := False;
  BulletAnalyzer := TPictureAnalyzer.Create(BulletPicture, PositionOfBulletPictureOnScreen);
(...)

//komponent TTimer z Interval ustawionym np. na 100 milisekund
procedure TForm1.OnTimer(Sender : TObject; (...))
begin
  IsBullet := BulletAnalyzer.IsBullet();
  if IsBullet then
    CallStrob();
end;

//Sprzątamy po sobie
procedure TForm1.FormDestroy(Sender : TObject);
begin
  if Assigned(BulletPicture) then
    FreeAndNil(BulletPicture);
end;


W konstruktorze podajesz mu mały kwadracik, który jest fragmentem obrazu pocisku - tego rysowanego na ekranie i podajesz mu dokładne miejsce w pikselach, skąd wyciąłeś ten obrazek. Dla różnych rozdzielczości - miejsce wycięcia jak i sam fragment pocisku - naturalnie będą różne.
Sprawdzanie może być wołane np. co 100 milisekund. Core 2 Duo nawet się przy tym nie zająknie.

Daj znać jak zadziała - tzn. BulletAnalyzer.IsBullet() wykryje Ci pocisk. No trochę się będziesz z tym musiał pomęczyć, ale nie za dużo zresztą. O stroba mnie nie pytaj. Nawet nie wiem co to jest :P

//Delphi rulez
//Delphi - szybkość + niesamowita przejrzystość = bezpieczeństwo + prostota + możliwości + wygoda + Win32 + .NET + pierwszy język na świecie gdzie w standardzie tegoż języka były kontrolki wizualne 
0

Dzięki w wolnej chwili usiądę i dojadę co i jak, choć nie ukrywam, ze będę się o coś pytał. Ale pmysł z porównywaniem pocisku z obrazka jest zabójczy. Można było by połączyć to też z efektem dźwięku. Ten nagły impuls. A ze strobem se poradzę ;)

0

Poprawiłem. Chyba czytelniej się tego nie da już napisać [diabel]
Po prostu powklejaj ten kod do swojego programu i popraw literówki.

1 użytkowników online, w tym zalogowanych: 0, gości: 1