Imports System.Collections.Generic
Imports System.Net
Imports System.Windows.Documents
Imports System.Windows.Controls
Imports System.Windows
Imports System.Windows.Markup

Public Class Project

    Private m_keywords As New List(Of Keyword)
    Private m_isDirty As Boolean = False
    Private m_currentFile As String
    Private WithEvents m_crawler As GoogleSearchResultCrawler

#Region "Event Handlers"

    Private Sub Project_Load(sender As Object, e As System.EventArgs) Handles Me.Load
        If (My.Application.CommandLineArgs.Count > 0 AndAlso Not String.IsNullOrEmpty(My.Application.CommandLineArgs(0))) Then
            OpenProject(My.Application.CommandLineArgs(0))
        End If

        AddHandler ResultView1.MadeDirty, AddressOf ResultView1_MadeDirty


        Dim menu As New Menu()
        Dim result = menu.ShowDialog()

        If result = Windows.Forms.DialogResult.Yes Then
            AddKeywords() ' New Project
        ElseIf result = Windows.Forms.DialogResult.No Then
            OpenProject() ' Open Project
            Exit Sub
        Else
            Me.Close()
            Exit Sub
        End If

    End Sub

    Private Sub crawler_StatusUpdate(sender As Object, e As CrawlerStatusEventArgs) Handles m_crawler.StatusUpdate
        Console.WriteLine(e.UrlsInspected)

        'FIXME: Not really sure why we need to Me.Invoke...
        Dim update = Sub()
                         Processing1.UrlsInspected = e.UrlsInspected
                         Processing1.KeywordsLeft = e.KeywordsLeft

                         If e.IsWaiting Then
                             Processing1.CurrentState = "Inspection In Progress... Waiting..."
                         Else
                             Processing1.CurrentState = "Inspection In Progress..."
                         End If
                     End Sub

        Me.Invoke(CType(update, [Delegate]))

    End Sub

    Private Sub crawler_Completed(sender As Object, e As CrawlerCompletedEventArgs) Handles m_crawler.Completed
        Console.WriteLine([Enum].GetName(GetType(CrawlerCompletedState), e.Status))

        'FIXME: Not really sure why we need to Me.Invoke...
        Dim update = Sub()
                         ResultView1.AddResults(m_crawler.Results)

                         If My.Settings.PREnabled Then
                             ResultView1.Sort("PR", System.ComponentModel.ListSortDirection.Descending)
                         Else
                             ResultView1.Sort("Notes", System.ComponentModel.ListSortDirection.Descending)
                         End If

                         Processing1.Visible = False
                         ElementHost1.Enabled = True
                         MenuStrip1.Enabled = True
                         Dim report As New Report()
                         report.ShowDialog()

                     End Sub

        Me.Invoke(CType(update, [Delegate]))

        m_crawler = Nothing
    End Sub

    Private Sub ResultView1_MadeDirty()
        m_isDirty = True
    End Sub


#Region "Menu Item Click Events"

    Private Sub OpenProjectToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles OpenProjectToolStripMenuItem.Click
        OpenProject()
    End Sub

    Private Sub NewProjectToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles NewProjectToolStripMenuItem.Click
        ResultView1.Results.Clear()

        m_keywords = New List(Of Keyword)
        m_isDirty = False
        m_currentFile = ""
        m_crawler = Nothing

        AddKeywords()
    End Sub

    Private Sub SaveProjectToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles SaveProjectToolStripMenuItem.Click
        SaveProject()
    End Sub

    Private Sub SaveProjectAsToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles SaveProjectAsToolStripMenuItem.Click
        SaveProject()
    End Sub

    Private Sub PrintToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles PrintToolStripMenuItem.Click
        Dim dlg As New Windows.Controls.PrintDialog()
        Const ItemsPerpage As Integer = 50

        If dlg.ShowDialog() = True Then
            Dim document = New FixedDocument()
            document.DocumentPaginator.PageSize = New Windows.Size(dlg.PrintableAreaWidth, dlg.PrintableAreaHeight)

            Dim lastSiteId As Integer = 0

            Do
                Dim page = New FixedPage()
                Dim list As New HeaderedItemsControl()
                Dim printDict As New ResourceDictionary()
                page.Children.Add(list)

                Dim content As New PageContent()
                CType(content, IAddChild).AddChild(page)
                document.Pages.Add(content)

                printDict.Source = New Uri("/Backlinks Warrior;component/PrintResourceDictionary.xaml", UriKind.RelativeOrAbsolute)
                list.Style = printDict("printedItems")
                list.ItemTemplate = printDict("keywordTemplate")
                list.Width = dlg.PrintableAreaWidth

                Dim pageEnd As Integer = ItemsPerpage
                If document.Pages.Count = CInt(ResultView1.Results.Count / ItemsPerpage) Then
                    pageEnd = ResultView1.Results.Count Mod ItemsPerpage
                End If

                For j As Integer = 0 To pageEnd - 1
                    If lastSiteId + j >= ResultView1.Results.Count Then Continue For
                    list.Items.Add(ResultView1.Results(lastSiteId + j))
                Next

                lastSiteId = lastSiteId + 50

            Loop While lastSiteId < ResultView1.Results.Count - 1

            dlg.PrintDocument(document.DocumentPaginator, Forms.Application.ProductName)
        End If
    End Sub

    Private Sub ExportListToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles ExportListToolStripMenuItem.Click
        Dim dlg As New SaveFileDialog()
        dlg.Filter = "CSV Files|*.csv|HTML Files|*.html"
        If dlg.ShowDialog() = Forms.DialogResult.OK Then
            Select Case IO.Path.GetExtension(dlg.FileName)
                Case ".html"
                    BLWFile.SaveHTML(dlg.FileName, ResultView1.Results)
                Case ".csv"
                    BLWFile.SaveCSV(dlg.FileName, ResultView1.Results)
            End Select
        End If
    End Sub

    Private Sub ExitToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles ExitToolStripMenuItem.Click
        Me.Close()
    End Sub

    Private Sub SelectAllToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles SelectAllToolStripMenuItem.Click
        ResultView1.SelectAll()
    End Sub

    Private Sub RemoveSelectedToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles RemoveSelectedToolStripMenuItem.Click
        ResultView1.RemoveSelected()
    End Sub

    Private Sub FindMoreSitesByKeywordToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles FindMoreSitesByKeywordToolStripMenuItem.Click
        AddKeywords()
    End Sub

    Private Sub NewToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles NewToolStripMenuItem.Click
        ResultView1.SetStatusNew()
    End Sub

    Private Sub LinkAddedToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles LinkAddedToolStripMenuItem.Click
        ResultView1.SetStatusAdded()
    End Sub

    Private Sub IgnoredToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles IgnoredToolStripMenuItem.Click
        ResultView1.SetStatusIgnored()
    End Sub

    Private Sub OpenUrlToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles OpenUrlToolStripMenuItem.Click
        ResultView1.OpenSelectedUrl()
    End Sub

    Private Sub CopyURLToClipboardToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles CopyURLToClipboardToolStripMenuItem.Click
        ResultView1.CopyToClipboard()
    End Sub

    Private Sub ViewEditUserNotesToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles ViewEditUserNotesToolStripMenuItem.Click
        ResultView1.VeiwEditNotes()
    End Sub

    Private Sub AboutBacklinksWarriorToolStripMenuItem_Click(sender As System.Object, e As System.EventArgs) Handles AboutBacklinksWarriorToolStripMenuItem.Click
        Dim a As New About()
        a.ShowDialog()
    End Sub

#End Region

#End Region

#Region "Private Helper Methods"
    Private Sub OpenProject()
        Dim dlg As New OpenFileDialog()
        dlg.Filter = "Backlinks Warrior Project Files|*.blw"

        If dlg.ShowDialog() = Windows.Forms.DialogResult.OK Then
            OpenProject(dlg.FileName)
        End If
    End Sub

    Private Sub OpenProject(fileName As String)
        Dim data = BLWFile.LoadXML(fileName)
        ResultView1.Results = data.Sites
        m_keywords = data.Keywords
        m_currentFile = fileName
    End Sub

    Private Sub SaveProject()
        If Not String.IsNullOrEmpty(m_currentFile) Then
            BLWFile.SaveXML(m_currentFile, ResultView1.Results, m_keywords)
            lblStatus.Text = String.Format("Project Last Save at: {0:MM/dd/yyyy h:mm:ss tt}", Date.Now)
            m_isDirty = False
            Exit Sub
        End If

        Dim dlg As New SaveFileDialog
        dlg.Filter = "Backlinks Warrior Project Files|*.blw"

        If dlg.ShowDialog() = Windows.Forms.DialogResult.OK AndAlso ResultView1.Results IsNot Nothing Then
            m_currentFile = dlg.FileName
            BLWFile.SaveXML(m_currentFile, ResultView1.Results, m_keywords)
            lblStatus.Text = String.Format("Project Last Save at: {0:MM/dd/yyyy h:mm:ss tt}", Date.Now)
            m_isDirty = False
        End If
    End Sub

    Private Sub AddKeywords()
        Dim findSite As New FindSites()

        If m_keywords IsNot Nothing Then
            findSite.SearchTerms = m_keywords
        End If

        If findSite.ShowDialog() <> Windows.Forms.DialogResult.OK Then
            Exit Sub
        End If

        m_keywords = findSite.SearchTerms
        BuildQueryList()
    End Sub

    Private Sub BuildQueryList()
        'Dim wc As New WebClient()
        'wc.DownloadStringAsync(New Uri("URLHERE"))
        'AddHandler wc.DownloadStringCompleted, Sub(s As Object, e As DownloadStringCompletedEventArgs)




        Dim queryTemplates = System.IO.File.ReadAllText(System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly.Location) & "\resources\queries.txt").Split(Environment.NewLine).Where(Function(val) Not String.IsNullOrWhiteSpace(val)).ToArray() ' Remove blank line at end... or any other blanks
        m_crawler = New GoogleSearchResultCrawler()
        Processing1.UrlsInspected = 0
        Processing1.KeywordsLeft = m_keywords.Count

        For Each keyword In m_keywords
            For Each template In queryTemplates

                Dim query As SearchQuery

                query = New SearchQuery(template, keyword)

                If query IsNot Nothing Then
                    m_crawler.Queries.Add(query)
                End If
            Next
        Next
        m_crawler.StartCrawl()


        MenuStrip1.Enabled = False
        ElementHost1.Enabled = False

        Processing1.Visible = True

        AddHandler Processing1.StopRequest, Sub(s, e)
                                                m_crawler.StopCrawl()
                                            End Sub
    End Sub

    ''' <summary>
    ''' Checks if the project is dirty. If it is the user is prompted to save.
    ''' </summary>
    ''' <returns>Returns true if the user confirms saving(yes)/not-saving(no), or if the project is not dirty. If the user cancles it return false.</returns>
    ''' <remarks></remarks>
    Private Function CheckDirtyAndSave() As Boolean
        If m_isDirty Then
            Dim result = Windows.MessageBox.Show("Do you want to save changes to your current project?", "Save Changes", Windows.MessageBoxButton.YesNoCancel, Windows.MessageBoxImage.Question)

            If result = Windows.MessageBoxResult.Yes Then
                SaveProject()
                Return True
            ElseIf result = Windows.MessageBoxResult.No Then
                Return True
            ElseIf result = Windows.MessageBoxResult.Cancel Then
                Return False
            End If
        End If

        Return True
    End Function
#End Region

    Private Sub CustomizeQueriesToolStripMenuItem_Click(sender As Object, e As EventArgs) Handles CustomizeQueriesToolStripMenuItem.Click

        Dim QD As New QueriesDialog()
        QD.ShowDialog()

    End Sub
End Class
