質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.49%
Pygame

Pygameは、ビデオゲームの製作用に設計されたクロスプラットフォームのPythonモジュールセットです。Pythonでコンピューターグラフィックスと音声を扱うためのライブラリが含まれています。

Python 3.x

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

Q&A

解決済

1回答

1715閲覧

pygame ものが衝突したときの判定の書き方が分かりません。

mask1122

総合スコア1

Pygame

Pygameは、ビデオゲームの製作用に設計されたクロスプラットフォームのPythonモジュールセットです。Pythonでコンピューターグラフィックスと音声を扱うためのライブラリが含まれています。

Python 3.x

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

0グッド

0クリップ

投稿2022/07/20 08:46

前提

ここに質問の内容を詳しく書いてください。
(例)
pygame使って、ボールを的に当てるゲームを作っています
的とボールが当たった時に、反射するコードを書きたいのですが、書き方がよく分かりません。

実現したいこと

ここに実現したいことを箇条書きで書いてください。

  • ボールと的が当たった時に反射するコードを書きたい
  • なるべくクラスの中で書きたいが、どこでも大丈夫なので、とにかく判定さえできればうれしいです

発生している問題・エラーメッセージ

エラーメッセージ ```pygame 2.1.2 (SDL 2.0.18, Python 3.7.3) Hello from the pygame community. https://www.pygame.org/contribute.html Traceback (most recent call last): File "c:\Users\admin\Desktop\ProjExD2022\ex06\ryoga.py", line 155, in <module> main() File "c:\Users\admin\Desktop\ProjExD2022\ex06\ryoga.py", line 139, in main ball.ball_move(scr) File "c:\Users\admin\Desktop\ProjExD2022\ex06\ryoga.py", line 97, in ball_move if self.rct.collidedict(self.mato.rct): TypeError: first argument must be a dict ### 該当のソースコード ```ここに言語名を入力 ソースコード import random import sys import pygame as pg class Screen: def __init__(self, title, wh, image): #初期メソッド pg.display.set_caption(title) self.sfc = pg.display.set_mode(wh) # Surface self.rct = self.sfc.get_rect() # Rect self.bgi_sfc = pg.image.load(image) # Surface self.bgi_rct = self.bgi_sfc.get_rect() # Rect def blit(self): self.sfc.blit(self.bgi_sfc, self.bgi_rct) def text_blit(self,text,t_x,t_y): self.sfc.blit(text,[t_x,t_y]) class Mato: def __init__(self,image,size,xy): self.sfc = pg.image.load(image) # Surface self.sfc = pg.transform.rotozoom(self.sfc, 0, size) # Surface self.rct = self.sfc.get_rect() # Rect self.rct.center = xy def blit(self, scr: Screen): scr.sfc.blit(self.sfc, self.rct) def update(self,scr:Screen): #更新 scr.sfc.blit(self.image,self.rct) class Racket: def __init__(self, image: str, size: float, xy): self.sfc = pg.image.load(image) # Surface self.sfc = pg.transform.rotozoom(self.sfc, 0, size) # Surface self.rct = self.sfc.get_rect() # Rect self.rct.center = xy def blit(self, scr: Screen): scr.sfc.blit(self.sfc, self.rct) def update(self, scr: Screen): key_states = pg.key.get_pressed() if key_states[pg.K_LEFT]: self.rct.centerx -= 1 if key_states[pg.K_RIGHT]: self.rct.centerx += 1 if check_bound(self.rct, scr.rct) != (1, 1): # 領域外だったら if key_states[pg.K_LEFT]: self.rct.centerx += 1 if key_states[pg.K_RIGHT]: self.rct.centerx -= 1 self.blit(scr) class Ball: #ボール生成 def __init__(self, fname, rack, mato): self.image = pg.image.load(fname).convert_alpha() self.image = pg.transform.scale(self.image,(50,50)) self.rct = self.image.get_rect() self.v_x = 1 self.v_y = 1 self.racket = rack self.mato = mato def ball_move(self, scr: Screen): #ボールの挙動 self.rct.centerx += int(self.v_x) self.rct.centery += int(self.v_y) if self.rct.left < scr.rct.left: #左側のボール判定 self.rct.left = scr.rct.left self.v_x = -self.v_x if self.rct.right > scr.rct.right:#右側のボール判定 self.rct.right = scr.rct.right self.v_x = -self.v_x if self.rct.top < scr.rct.top:#上側のボール判定 self.rct.top = scr.rct.top self.v_y = -self.v_y if self.rct.colliderect(self.racket.rct): #ボールとバーの衝突 dist = self.rct.centerx - self.racket.rct.centerx if dist < 0: self.v_x = -1 elif dist > 0: self.v_x = 1 else: self.v_x = random.randint(-1,1) self.v_y = -1 if self.rct.collidedict(self.mato.rct): dist = self.rct.centerx - self.racket.rct.centerx if dist < 0: self.v_x = -1 elif dist > 0: self.v_x = 1 else: self.v_x = random.randint(-1,1) self.v_y = -1 if self.rct.bottom > scr.rct.bottom: #ボールが画面の下に行った場合 font = pg.font.Font(None, 100) text = font.render("GAME OVER", True,(255,0,0)) scr.text_blit(text, 400,200) def draw(self, sfc): #ボールの描画 sfc.blit(self.image, self.rct) def update(self,scr:Screen): #更新 scr.sfc.blit(self.image,self.rct) def main(): #メイン関数 clock = pg.time.Clock() scr = Screen("squash", (1200, 600), "fig/haikei.png") #スクリーン設定 rack = Racket("fig/beam.png",0.08,(550,550)) #バーの設定 mato = Mato("fig/mato1.png",0.5,(100,50)) ball = Ball("fig/0.png", rack,mato) #ボールの設定 while True: scr.blit() mato.blit(scr) font = pg.font.SysFont(None,60) message = font.render("score",False,(255,255,0)) scr.text_blit(message, 400,200) for event in pg.event.get(): #×ボタンで終了 if event.type == pg.QUIT: return ball.ball_move(scr) rack.update(scr) mato.update(scr) ball.update(scr) pg.display.update() clock.tick(1000) def check_bound(rct, scr_rct): #バーと壁の判定 yoko, tate = +1, +1 # 領域内 if rct.left < scr_rct.left or scr_rct.right < rct.right : yoko = -1 # 領域外 if rct.top < scr_rct.top or scr_rct.bottom < rct.bottom: tate = -1 # 領域外 return yoko, tate if __name__ == "__main__": #関数の呼び出し pg.init() main() pg.quit() sys.exit() ### 試したこと ここに問題に対して試したことを記載してください。 ### 補足情報(FW/ツールのバージョンなど) ここにより詳細な情報を記載してください。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

TakaiY

2022/07/20 10:39

> ボールと的が当たった時に反射するコードを書きたい とありますが、ball_move()メソッドの中の以下のところで判定と動作方向の変更をしているようです。 if self.rct.collidedict(self.mato.rct): これにどのような問題があるのでしょう。 具体的に教えてください。
mask1122

2022/07/20 10:57 編集

コメントありがとうございます。 if self.rct.collidedict(self.mato.rct): self.v_x = -1 self.v_y = -1 上のコードを書けば、ボールと的がぶつかった時に反転出来るのかなと思ったのですが、実行しても、動かないという感じです。どのように書き換えれば出来るのか知りたいです。
mask1122

2022/07/20 11:05

指摘されたコードをいじってを実行したら、出来るようになってました! コメントありがとうございました
guest

回答1

0

ベストアンサー

コメントで自己解決したようですが、いちおう。

python

1if self.rct.collidedict(self.mato.rct): 2 self.v_x = -1 3 self.v_y = -1

反射させたいのであれば、 このように固定の値を設定するのではなく、他のところにあるように符号の反転の操作をする必要があるんじゃないかと思います。

投稿2022/07/20 11:47

TakaiY

総合スコア12738

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

mask1122

2022/07/20 13:09

self.v_x *= -1  のような感じですかね? プログラミング初心者なので、試行錯誤して頑張ってみようと思います。親切に教えていただきありがとうございます。これからも機会がありましたら、よろしくお願いします!
TakaiY

2022/07/20 15:31

その方法でもOKですが、他のところでは以下のように書いてありますね。 self.v_x = -self.v_x こうすることで、符号が反転 = 逆向きに動くようになります。 的がどちらに向いているのか知らないので、xとしましたが、x,yどちらの測度成分を反転させるかは決めてみればいいでしょう。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.49%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問