2022년 임인년을 맞아 파워포인트로 윷놀이 게임을 만들어 보았습니다.
첫화면에서 6가지 스킨을 선택하면 윷놀이 게임을 시작합니다.
게임에 앞서 왼쪽 아래 Roulette Style에서 회전 룰렛의 스타일을 선택할 수 있습니다.
스킨들
실행 화면
왼쪽 윷을 클릭하면
룰렛 회전판이 뜨고 돌다가 자동으로 멈춥니다.
이 때 나온 윷모양을 확인하고 클릭해서 닫고
오른쪽 팀별 말을 하나 클릭해서 드래그해서 윷판의 위치에 말을 표시합니다.
말은 다시 클릭해서 옮길 수 있습니다.
윷놀이 규칙에 따라 말을 움직여서 먼저 들어온 팀이 이기게 됩니다.
다시 시작할 때는 Reset 을 누르면 됩니다.
말을 놓을 때 오른쪽 영역에 놓으면 자동으로 원위치로 돌아갑니다.
룰렛 회전 소스:
'by konahn(at)naver.com(http://konahn.tistory.com)
Option Explicit
#If VBA7 Then
Public Declare PtrSafe Function WaitMessage Lib "user32" () As Long
#Else
Public Declare Function WaitMessage Lib "user32" () As Long
#End If
Public ROption As Integer 'ROption 룰렛 회전판 옵션(default=0)
Function waitTimer(tick As Double)
Dim oldTimer As Double
oldTimer = Timer
Do While Timer <= oldTimer + tick
DoEvents
WaitMessage
Loop
End Function
Function PlayMedia(oSld As Slide, str As String)
Dim shp As Shape, oShp As Shape
Dim mPlayer As Player
Dim i As Integer
Set shp = oSld.Shapes(str)
'For Each oShp In oSld.Shapes
' If oShp.Type = msoMedia Then
' SlideShowWindows(1).View.Player(oShp.Id).Stop
' End If
'Next oShp
With SlideShowWindows(1).View.Player(shp.Id)
'If .State <> ppPlaying Then
'.Stop
.Play
End With
End Function
'Sub test()
' Dim shp As Shape
' Set shp = ActivePresentation.Slides(1).Shapes("Box_1_1")
' Call onClick(shp)
'End Sub
'Sub test2()
' Dim shp As Shape
' Set shp = ActivePresentation.Slides(1).Shapes("Dice")
' Call doRoulette(shp)
'End Sub
Sub doRoulette(shp As Shape)
Dim sld As Slide, oSld As Object
Dim oShp As Shape
Dim eft As Effect
Dim SW As Single, SH As Single
Call getROption
If ROption = 0 Then ROption = 4 'Default Custom Layout
Randomize
With ActivePresentation.PageSetup
SW = .SlideWidth: SH = .SlideHeight
End With
Set sld = shp.Parent
If shpExist(sld, "Triangle") Then sld.Shapes("Triangle").Delete
If shpExist(sld, "Roulette") Then sld.Shapes("Roulette").Delete
If shpExist(sld, "Rectangle") Then sld.Shapes("Rectangle").Delete
'배경 박스
Set oShp = sld.Parent.SlideMaster.CustomLayouts(ROption).Shapes("Rectangle")
oShp.Copy
With sld.Shapes.Paste(1)
.Left = 0: .Top = 0
End With
Set oShp = sld.Parent.SlideMaster.CustomLayouts(ROption).Shapes("Roulette")
Set oSld = oShp.Parent
'룰렛도형의 마지막 두번째 회전 효과 변경
Set eft = oSld.TimeLine.MainSequence.Item(oSld.TimeLine.MainSequence.Count - 1)
eft.Timing.Duration = 0.5 + 1 * Rnd '지속 시간
eft.EffectParameters.Amount = -1 * (30 + 360 * Rnd) '회전 각도
'룰렛도형의 마지막 회전 효과 변경
Set eft = oSld.TimeLine.MainSequence.Item(oSld.TimeLine.MainSequence.Count)
eft.Timing.Duration = 3 + 2 * Rnd '지속 시간
eft.EffectParameters.Amount = 720 + 720 * Rnd '회전 각도
oShp.Copy
sld.Shapes.Paste (1)
Set oShp = sld.Parent.SlideMaster.CustomLayouts(ROption).Shapes("Triangle")
oShp.Copy
sld.Shapes.Paste (1)
'Call PlayMedia(sld, "Spin")
End Sub
'Sub test3()
' Dim shp As Shape
' Set shp = ActivePresentation.Slides(1).Shapes("Load")
' Call loadBingo(shp)
'End Sub
Function shpExist(oSld As Slide, shpName As String) As Boolean
Dim shp As Shape
For Each shp In oSld.Shapes
If shp.Name = shpName Then shpExist = True: Exit Function
Next shp
shpExist = False
End Function
Sub removeRoulette(oShp As Shape)
If oShp.Name = "Triangle" Then
oShp.Parent.Shapes("Roulette").Delete
oShp.Parent.Shapes("Rectangle").Delete
oShp.Parent.Shapes("Triangle").Delete
ElseIf oShp.Name = "Rectangle" Then
oShp.Parent.Shapes("Triangle").Delete
oShp.Parent.Shapes("Roulette").Delete
oShp.Parent.Shapes("Rectangle").Delete
Else
oShp.Parent.Shapes("Triangle").Delete
oShp.Parent.Shapes("Rectangle").Delete
oShp.Parent.Shapes("Roulette").Delete
End If
End Sub
Sub Reset(rshp As Shape)
Dim shp As Shape, fu As Shape
Dim sld As Slide
Dim s As Long
'Set sld = ActivePresentation.Slides(1)
Set sld = rshp.Parent
Set fu = sld.Shapes("FFlag_Under")
For Each shp In sld.Shapes
If shp.Name Like "Flag*" Then
Call putFlag(shp, fu)
End If
Next shp
'Flag zOrder 정렬
Call ArrangeFlags(sld)
End Sub
Private Sub ResetTest()
ArrangeFlags ActiveWindow.View.Slide
End Sub
Function ArrangeFlags(oSld As Slide)
Dim arr() As String, tmp As String
Dim s As Long, t As Long
Dim shp As Shape
'collect Flag names
For Each shp In oSld.Shapes
If shp.Name Like "Flag*" Then
s = s + 1
ReDim Preserve arr(1 To s)
arr(s) = shp.Name
End If
Next shp
'sort Flag array
For s = 1 To UBound(arr) - 1
For t = s + 1 To UBound(arr)
If arr(s) > arr(t) Then
tmp = arr(s)
arr(s) = arr(t)
arr(t) = tmp
End If
Next t
Next s
'Flag zOrder 정렬
For s = 1 To UBound(arr)
'Debug.Print arr(s), oSld.Shapes(arr(s)).ZOrderPosition, oSld.Shapes.Count - s
While oSld.Shapes(arr(s)).ZOrderPosition < oSld.Shapes(oSld.Shapes.Count).ZOrderPosition - s
oSld.Shapes(arr(s)).ZOrder msoBringForward
Wend
Next s
End Function
Function putFlag(fShp As Shape, uShp As Shape)
Dim m As Single
m = 10 '좌우상하 여백
fShp.Left = uShp.Left + m + (Mid(fShp.Name, 6, 1) - 1) * (uShp.Width - 2 * m) / 2 + ((uShp.Width - 2 * m) / 2 - fShp.Width) / 2
fShp.Top = m + (uShp.Height - 2 * m) / 5 * (Asc(Mid(fShp.Name, 5, 1)) - Asc("A")) + ((uShp.Height - 2 * m) / 5 - fShp.Height) / 2
End Function
Sub ROptionClick(shp As Shape)
Dim sld As Slide
Dim oShp As Shape
Set sld = shp.Parent
shp.PictureFormat.ColorType = msoPictureAutomatic
For Each oShp In sld.Shapes
If oShp.Name Like "ROption#" Then
If Not oShp Is shp Then oShp.PictureFormat.ColorType = msoPictureGrayscale
End If
Next oShp
ROption = Int(Mid(shp.Name, 8)) 'SlideMaster Custom Layout Index
End Sub
Function getROption()
Dim sld As Slide
Dim oShp As Shape
Set sld = ActivePresentation.Slides(1)
For Each oShp In sld.Shapes
If oShp.Name Like "ROption#" Then
If oShp.PictureFormat.ColorType = msoPictureAutomatic Then
ROption = Int(Mid(oShp.Name, 8))
Exit For
End If
End If
Next oShp
End Function
'Sub addActionToButtons()
'
' Dim sld As Slide
' Dim shp As Shape
' Dim i As Integer
'
' Set sld = ActiveWindow.Selection.SlideRange(1)
'
' For Each shp In sld.Shapes
' If shp.Name Like "Box_*" Then
'
' With shp.ActionSettings(ppMouseClick)
' .Action = ppActionRunMacro
' .Run = "onClick"
' End With
' i = i + 1
' End If
' Next shp
'
' MsgBox i & " 개의 도형에 적용완료"
'End Sub
'Sub addActionToChildren()
'
' Dim sld As CustomLayout
' Dim shp As Shape
' Dim i As Integer
'
' 'Set sld = ActiveWindow.Selection.SlideRange(1)
' Set sld = ActivePresentation.SlideMaster.CustomLayouts(4)
'
'
' For Each shp In sld.Shapes("Roulette").GroupItems
' If shp.Name Like "Arc_*" Or shp.Name Like "TextBox_*" Then
' With shp.ActionSettings(ppMouseClick)
' .Action = ppActionRunMacro
' .Run = "removeRoulette"
' End With
' i = i + 1
' End If
' Next
'
' MsgBox i & " 개의 도형에 적용완료"
'End Sub
Function removeTrash(tSld As Slide)
If shpExist(tSld, "Triangle") Then tSld.Shapes("Triangle").Delete
If shpExist(tSld, "Roulette") Then tSld.Shapes("Roulette").Delete
If shpExist(tSld, "Rectangle") Then tSld.Shapes("Rectangle").Delete
End Function
'
'Sub OnSlideShowTerminate(SSW As SlideShowWindow)
' Dim sld As Slide
'
' For Each sld In ActivePresentation.Slides
' Call removeTrash(sld)
' Next sld
'
'End Sub
개체 드래그 소스:
#If VBA7 Then
Public Declare PtrSafe Function GetCursorPos Lib "user32" (lpPoint As PointAPI) As Long
Public Declare PtrSafe Function GetDC Lib "user32" (ByVal hWnd As Long) As Long
Public Declare PtrSafe Function ReleaseDC Lib "user32" (ByVal hWnd As Long, ByVal hDc As Long) As Long
Public Declare PtrSafe Function GetDeviceCaps Lib "gdi32" (ByVal hDc As Long, ByVal nIndex As Long) As Long
Public Declare PtrSafe Function GetSystemMetrics Lib "user32" (ByVal nIndex As Long) As Long
Public Declare PtrSafe Function SetTimer Lib "user32" (ByVal hWnd As LongPtr, ByVal nIDEvent As LongPtr, ByVal uElapse As Long, ByVal IpTimerFunc As LongPtr) As LongPtr
Public Declare PtrSafe Function KillTimer Lib "user32" (ByVal hWnd As LongPtr, ByVal nIDEvent As LongPtr) As LongPtr
Public TimerID As LongPtr
#Else
Public Declare Function GetCursorPos Lib "user32" (lpPoint As PointAPI) As Long
Public Declare Function GetDC Lib "user32" (ByVal hWnd As Long) As Long
Public Declare Function ReleaseDC Lib "user32" (ByVal hWnd As Long, ByVal hDc As Long) As Long
Public Declare Function GetDeviceCaps Lib "gdi32" (ByVal hDc As Long, ByVal nIndex As Long) As Long
Public Declare Function GetSystemMetrics Lib "user32" (ByVal nIndex As Long) As Long
Public Declare Function SetTimer Lib "user32" (ByVal hWnd As Long, ByVal nIDEvent As Long, ByVal uElapse As Long, ByVal IpTimerFunc As Long) As Long
Public Declare Function KillTimer Lib "user32" (ByVal hWnd As Long, ByVal nIDEvent As Long) As Long
Public TimerID As Long
#End If
Public Const LOGPIXELSX = 88
Public Const LOGPIXELSY = 90
Public Const SM_CXSCREEN = 0
Public Const SM_CYSCREEN = 1
Public Type PointAPI
x As Long
y As Long
End Type
Public Cur As PointAPI
Public Picked As Shape
Public Air As Boolean
Private Function Delta(lngVal As Long)
Dim hDc As Long, ppi As Long
hDc = GetDC(0)
ppi = GetDeviceCaps(hDc, LOGPIXELSX)
ReleaseDC 0, hDc
Delta = lngVal * 72 / ppi / (ActivePresentation.SlideShowWindow.View.Zoom / 100)
End Function
Sub Pick(shp As Shape)
Set Picked = shp
TimerON
shp.Parent.Shapes("Screen").Visible = True
'맨 위 Screen도형 다음으로
shp.ZOrder msoBringToFront
shp.ZOrder msoSendBackward
End Sub
Sub Drop(shp As Shape)
Dim fu As Shape
TimerOFF
Set fu = shp.Parent.Shapes("FFlag_Under")
'깃발 도형이면 원위치
If Picked.Name Like "Flag*" And Picked.Left >= fu.Left Then
Call putFlag(Picked, fu)
End If
Set Picked = Nothing
shp.Parent.Shapes("Screen").Visible = False
End Sub
Sub Proc()
On Error Resume Next
GetCursorPos Cur
Dim bX As Long, bY As Long
bX = (Delta(GetSystemMetrics(SM_CXSCREEN)) - ActivePresentation.PageSetup.SlideWidth) / 2
bY = (Delta(GetSystemMetrics(SM_CYSCREEN)) - ActivePresentation.PageSetup.SlideHeight) / 2
Picked.Left = Delta(Cur.x) - Picked.Width / 2 - bX
Picked.Top = Delta(Cur.y) - Picked.Height / 2 - bY
End Sub
Public Function TimerON()
If TimerID = 0 Then
TimerID = SetTimer(0&, 0&, 10&, AddressOf Proc)
End If
End Function
Public Function TimerOFF()
KillTimer 0&, TimerID
TimerID = 0
End Function
Sub OnSlideShowTerminate(SSW As SlideShowWindow)
Dim sld As Slide
Set sld = ActiveWindow.View.Slide
'Set sld = ActivePresentation.Slides(1)
KillTimer 0&, TimerID
TimerID = 0
Set Picked = Nothing
'룰렛도형 삭제
Call removeTrash(sld)
'깃발 원위치
Call Reset(sld.Shapes("Reset"))
End Sub
'깃발 도형을 추가한 경우 최초 1회 실행할 것!
Sub A_RunFirst()
Dim shp As Shape
Dim sld As Slide
On Error GoTo Oops
'//선택된 도형들에 'Pick' 매크로를 걸어줌
For Each shp In ActiveWindow.Selection.ShapeRange
With shp.ActionSettings(ppMouseClick)
.Action = ppActionRunMacro
.Run = "Pick"
End With
Next shp
Set sld = ActiveWindow.Selection.SlideRange(1)
'Screen 도형을 맨 앞으로보내고, 감추기, Drop 매크로 지정
With sld.Shapes("Screen")
.ActionSettings(ppMouseClick).Action = ppActionRunMacro
.ActionSettings(ppMouseClick).Run = "Drop"
.ZOrder msoBringToFront
.Visible = msoFalse
End With
Oops:
If Err Then MsgBox Err.Description
End Sub
'// not used
Sub B_RandomLocation()
Dim shp As Shape
Dim sld As Slide
Dim SW As Single, SH As Single
Const Margin As Single = 50
Randomize
With ActivePresentation.PageSetup
SW = .SlideWidth: SH = .SlideHeight
End With
Set sld = ActiveWindow.Selection.SlideRange(1)
'// 'Pick' 매크로가 걸린 도형의 위치를 섞어줌
For Each shp In sld.Shapes
If shp.ActionSettings(ppMouseClick).Run = "Pick" Then
shp.Left = Rnd * SW
If shp.Left < Margin Then shp.Left = Margin
If shp.Left + shp.Width > SW - Margin Then shp.Left = SW - Margin - shp.Width
shp.Top = Rnd * SH
If shp.Top < Margin Then shp.Top = Margin
If shp.Top + shp.Height > SH - Margin Then shp.Top = SH - Margin - shp.Height
End If
Next shp
End Sub
파일 첨부합니다.
(참고: 윷놀이 배경판과 말모양은 인터넷에서 받은 그림을 벡터로 Tracing한 것들이 포함되어 있습니다.)
※ 주의) '서울한강 장체 EB' 폰트가 없는 경우 아래 사이트에서 폰트를 설치하셔야 합니다.
https://www.seoul.go.kr/seoul/font.do
365와 2021에서 테스트하였습니다.
스킨 슬라이드 추가/수정 방법:
기존 스킨 슬라이드 복제 후 윷놀이 배경 그림만 교체하면 됩니다.
슬라이드를 추가한 경우 1슬라이드의 요약/확대를 변경해야 합니다.
(요약확대는 2019나 35구독버전에서만 지원)
말 도형/그림 변경 방법:
말 도형은 FlagA1, FlagB2, FlagF3 이런 형식이어야 합니다.
만들어진 말 도형은 선택하고 Alt-F8누르고 A_RunFirst 를 한번 실행해서 Pick 매크로를 지정해주세요.
(도형 클릭 드래그 소스는 파겜마의 ShortFox님의 코드를 참고했습니다.)
룰렛 회전판 변경 방법:
슬라이드마스터의 4번과 5번에 기존 룰렛이 있는데 참고하여
변경하되 룰렛 생성기를 이용하면 편함.
애니메이션도 기존 룰렛의 애니메이션복사해서 애니메이션 붙여넣기로 나타나기, 역회전, 회전 3가지 애니메이션이 들어 있어야 함. 회전 각도는 랜덤하게 변경됨.
1슬라이드 왼쪽 아래 Roulette Style에 룰렛 그림을 추가하고 도형이름은 ROption6 으로 변경(6은 슬라이드 마스터의 레이아웃 순서)
'PPT GAME' 카테고리의 다른 글
랜덤 주사위 + 누적 통계 차트 (1) | 2024.08.30 |
---|---|
[Bomb Game 템플릿] OX퀴즈 템플릿, 16칸짜리 (0) | 2024.06.04 |
[Bomb Game 템플릿] Book Game (2) | 2021.12.19 |
십자낱말퀴즈 생성 도우미 (5) | 2021.10.06 |
순간포착 게임 (8) | 2021.07.14 |
[Bomb Game] 학교소개 PPT퀴즈 게임 템플릿 (3) | 2021.05.15 |
Pick Me 선택 게임 (15) | 2020.05.26 |
고전게임 갤러그 유형 적탄 피하기 데모판 (0) | 2017.01.12 |
최근댓글