
Imports System.IO

Public Class FrameType

  Dim oldnow As Integer
  Dim elapsedtime As Integer
  Dim phase As Integer = 0
  Dim showingmovie As Boolean

  Private z, z1, z2 As Double
  Private pixelheight, pixelwidth As Integer
  Private ox, oy, ox1, ox2, oy1, oy2 As Integer
  Private mousex, mousey As Integer
  Private DragInProgress As Boolean = False

  Public Event Finished()

  Private Sub FrameType_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
    Me.WindowState = FormWindowState.Maximized
  End Sub

  Public Sub Start(ByVal p)
    GetSlide()
    oldnow = My.Computer.Clock.TickCount
    elapsedtime = 0 : phase = p : PauseOnceFlag = True
    Timer1.Enabled = True ' start timer after slide has completed loading
  End Sub
  Public Sub Finish()
    Me.Opacity = 0
    PictureBox1.Image = Nothing
    Timer1.Enabled = False
  End Sub

  Private Sub FrameType_KeyDown(ByVal sender As Object, ByVal e As System.Windows.Forms.KeyEventArgs) Handles Me.KeyDown
    Select Case e.KeyCode
      Case 32
        If phase > 1 Then Paused = Not Paused
        If showingmovie Then
          If Paused Then mediaPause() Else mediaPlay()
        End If
      Case 39
        If showingmovie Then mediaClose()
        BackOneSlide = False
        Paused = False : PauseOnceFlag = False : elapsedtime = 0 : phase = 5
      Case 37
        If showingmovie Then mediaClose()
        BackOneSlide = True
        Paused = False : PauseOnceFlag = False : elapsedtime = 0 : phase = 5
      Case Else
        MainWindow.KeyPressed(e.KeyCode)
    End Select
  End Sub

  Private Sub PictureBox1_MouseClick1(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseClick, Me.MouseClick, Label1.MouseClick, Label2.MouseClick
    ' this is necessary to avoid going back one slide at the end of a drag
    If DragInProgress Then DragInProgress = False : Exit Sub
    If sender Is Me Then
      'must convert to picturebox coords
      mousex = e.X - ox : mousey = e.Y - oy
    Else
      mousex = e.X : mousey = e.Y
    End If
    If phase < 2 Or phase > 4 Then Exit Sub ' disable buttons if a change is in progress
    Select Case e.Button
      Case Windows.Forms.MouseButtons.Left
        BackOneSlide = True
        Paused = False : PauseOnceFlag = False : elapsedtime = 0 : phase = 5
      Case Windows.Forms.MouseButtons.Right
        BackOneSlide = False
        Paused = False : PauseOnceFlag = False : elapsedtime = 0 : phase = 5
      Case Windows.Forms.MouseButtons.Middle
        Paused = Not Paused
    End Select
  End Sub
  Private Sub PictureBox1_MouseWheel(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseWheel, Me.MouseWheel
    If Not Paused Then Exit Sub
    Dim r As Double
    If e.Delta > 0 Then r = 1.1 Else r = 1 / 1.1
    z = z * r
    ' (ox,oy) is the current origin of the picture
    ox = r * ox - ScreenSize.Width * (r - 1) / 2
    oy = r * oy - ScreenSize.Height * (r - 1) / 2
    PictureBox1.Height = CInt(pixelheight * z)
    PictureBox1.Width = CInt(pixelwidth * z)
    PictureBox1.Location = New Point(ox, oy)
    PictureBox1.Refresh()
  End Sub
  Private Sub Picturebox1_MouseMove(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseMove
    If Not Paused Then Exit Sub
    Select e.Button
      Case 0
        mousex = e.X : mousey = e.Y
      Case Windows.Forms.MouseButtons.Left
        ox += e.X - mousex : oy += e.Y - mousey
        PictureBox1.Location = New Point(ox, oy)
        PictureBox1.Refresh()
        DragInProgress = True
    End Select
  End Sub
  Public Sub GetSlide()
    mediaClose()
    With CurrentSlide
      Label1.Text = .Caption
      Label1.Font = New Font(CaptionFont, .PointSize, FontStyle.Italic)
      Dim x, y As Integer
      x = (ScreenSize.Width - Label1.Width) / 2
      y = ScreenSize.Height - Label1.Height - 50
      Label1.Location = New Point(x, y)
      showingmovie = False
      Select Case .Type
        Case "BLANK"
          PictureBox1.Hide()
          y = (ScreenSize.Height - Label1.Height) / 2
          Label1.Location = New Point(x, y)
          Label1.Show()
        Case "IMAGE"
          pixelwidth = .ImageWidth / WsFactor
          pixelheight = .ImageHeight
          ox1 = .OriginStart.X / WsFactor
          oy1 = .OriginStart.Y
          ox2 = .OriginFinish.X / WsFactor
          oy2 = .OriginFinish.Y
          z1 = .ZfactorStart
          z2 = .ZfactorFinish
          ox = ox1 : oy = oy1 : z = z1
          PictureBox1.Height = CInt(pixelheight * z1)
          PictureBox1.Width = CInt(pixelwidth * z1)
          PictureBox1.Location = New Point(ox1, oy1)
          Using TemporaryImage As New Bitmap(.Filename)
            PictureBox1.Image = New Bitmap(TemporaryImage)
          End Using
          y = ScreenSize.Height - Label1.Height - 50
          Label1.Location = New Point(x, y)
          If ShowCaption Then Label1.Show() Else Label1.Hide()
          PictureBox1.Refresh()
          PictureBox1.Show()
        Case "MOVIE"
          PictureBox1.Image = Nothing
          If ShowCaption Then Label1.Show() Else Label1.Hide()
          mediaOpen(.Filename, PictureBox1.Handle.ToString)
          CurrentSlide.Interval2 = mediaGetLength()
          Dim r As New Rectangle
          r = mediaGetDimentions()
          Dim f As Double = ScreenSize.Width / r.Width
          If f * r.Height > ScreenSize.Height Then f = ScreenSize.Height / r.Height
          If f > 1 Then f = 1
          PictureBox1.Size = New Size(f * r.Width, f * r.Height)
          x = (ScreenSize.Width - PictureBox1.Width) / 2
          y = (ScreenSize.Height - PictureBox1.Height) / 2
          PictureBox1.Location = New Point(x, y)
          mediaSetDimentions(0, 0, PictureBox1.Width, PictureBox1.Height)
          PictureBox1.Show()
          showingmovie = True
      End Select
    End With
    BackOneSlide = False
  End Sub
  Private Function Inter(ByVal a, ByVal b, ByVal f)
    Return a + f * (b - a)
  End Function
  Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
    Dim now As Integer = My.Computer.Clock.TickCount
    If Paused Then
      Me.Label2.Show()
    Else
      Me.Label2.Hide()
    End If
    Dim f As Double
    Dim fadetime As Integer = My.Settings.FadeTime * 1000
    Select Case phase
      Case 1 ' fade in
        elapsedtime += now - oldnow
        ' opacity must always be less than 1 else glitches occur on fading
        f = elapsedtime / fadetime
        If f >= 1 Then
          'Debug.Print("Finished phase 1 after" & Str(elapsedtime))
          f = 0.99 : elapsedtime = 0 : phase = 2
          If showingmovie Then mediaPlay() Else Me.Opacity = f
        Else
          If Not showingmovie Then Me.Opacity = f
        End If
      Case 2        ' pause do nothing
        If Not showingmovie Then Me.Opacity = 0.99
        elapsedtime += now - oldnow
        If elapsedtime > CurrentSlide.Interval1 Then
          'Debug.Print("Finished phase 2 after" & Str(elapsedtime))
          elapsedtime = 0 : phase = 3
        End If
      Case 3 'pan / zoom
        If Not Paused Then
          elapsedtime += now - oldnow
          If CurrentSlide.Interval2 = 0 Then f = 1 Else f = elapsedtime / CurrentSlide.Interval2
          If CurrentSlide.PanFlag Then
            z = Inter(z1, z2, f)
            PictureBox1.Height = CInt(pixelheight * z)
            PictureBox1.Width = CInt(pixelwidth * z)
            ox = CInt(Inter(ox1, ox2, f))
            oy = CInt(Inter(oy1, oy2, f))
            PictureBox1.Location = New Point(ox, oy)
            PictureBox1.Refresh()
          End If
          If f >= 1 Then
            'Debug.Print("Finished phase 3 after" & Str(elapsedtime))
            elapsedtime = 0 : phase = 4
          End If
        End If
      Case 4 ' pause
        If Not Paused Then
          elapsedtime += now - oldnow
          If elapsedtime > CurrentSlide.Interval3 Then
            'Debug.Print("Finished phase 4 after" & Str(elapsedtime))
            elapsedtime = 0 : phase = 5
          End If
        End If
      Case 5 ' start next slide
        If CurrentSlide.PauseFlag And PauseOnceFlag Then Paused = True : PauseOnceFlag = False
        If Not Paused Then
          If Not testing AndAlso MainWindow.FindNextSlide Then
            'start other frame going
            'Debug.Print("Starting next slide")
            RaiseEvent Finished()
          End If
          'now = My.Computer.Clock.TickCount
          'elapsedtime += now - oldnow
          'Debug.Print("Finished phase 5 after" & Str(elapsedtime))
          elapsedtime = 0 : phase = 6
        End If
      Case 6 ' fade out
        elapsedtime += now - oldnow
        f = (fadetime - elapsedtime) / fadetime
        ' opacity must always be less than 1 else glitches occur on fading
        If f >= 1 Then f = 0.99
        If f > 0 Then
          If Not showingmovie Then Me.Opacity = f
        Else
          Me.Opacity = 0
          PictureBox1.Image = Nothing
          If testing Then
            MainWindow.KeyPressed(27)
          Else
            Timer1.Enabled = False
            'Debug.Print("Finished phase 6 after" & Str(elapsedtime))
            elapsedtime = 0 : phase = 0
          End If
        End If
    End Select
    oldnow = now
  End Sub
  'Private Function FindNextSlide()
  '  Dim s, cs As SlideType
  '  cs = CurrentSlide
  '  Dim i As Integer = 9999999
  '  Dim j As Integer
  '  For Each c As Control In MainWindow.pnlSlides.Controls
  '    If c.GetType Is GetType(SlideType) Then
  '      s = c
  '      j = s.Index - CurrentSlide.Index
  '      If BackOneSlide Then j = -j
  '      If s.EnableFlag And j > 0 And j < i Then cs = s : i = j
  '    End If
  '  Next
  '  BackOneSlide = False
  '  If i < 9999999 Then CurrentSlide = cs : Return True
  '  Return False
  'End Function
End Class