Печать расписания в PDF - PullRequest
       15

Печать расписания в PDF

2 голосов
/ 11 июля 2020

Итак, моя жена ведет табели учета рабочего времени для своей компании-работодателя и должна распечатать табель рабочего времени в формате PDF для каждого сотрудника, который работал над проектом клиента A 1. Например:

Клиент A - Проект 1 - Сотрудник 1 - Время & Расходы Клиент A - Проект 1 - Сотрудник 2 - Время и расходы Клиент A - Проект 1 - Сотрудник 3 - Время и расходы Клиент A - Проект 2 - Сотрудник 2 - Время и расходы Клиент A - Проект 2 - Сотрудник 4 - Время и расходы Клиент A - Проект 3 - Сотрудник 3 - Время и расходы ... Клиент Б - Проект 1 - Сотрудник 1 - Время и расходы Клиент B - Проект 2 - Сотрудник 2 - Время и расходы Клиент Б - Проект 2 - Сотрудник 3 - Время и расходы Клиент B - Проект 3 - Сотрудник 1 - Время и расходы Клиент B - Проект 3 - Сотрудник 4 - Время и расходы ... et c.

У моей жены довольно обычный рабочий процесс, который, честно говоря, не требует больших ручных манипуляций, поэтому я пытался выяснить, как я могу автоматизировать / оптимизировать ее рабочий процесс, чтобы она могла проводить больше времени с нашим сыном.

У нее может быть до 10 клиентов, и у каждого клиента может быть до 20 активных проектов, и у нее может быть до 10 сотрудников на проект. Она должна делать это каждые 15 дней. Она компилирует все PDF-файлы в объединенный PDF-файл для проекта клиента, а затем вручную вводит информацию в Quickbooks для создания сводного счета-фактуры. Затем счет-фактура объединяется с отдельными табелями учета рабочего времени. Затем все счета рассылаются каждому клиенту. Процесс повторяется бесконечно.

Сейчас я ни в коем случае не разбираюсь в кодировании, но считаю, что знаю о нем больше, чем средний человек. Для меня это скорее хобби / занятие, которым я могу заниматься, когда на улице 110 градусов. То, что я сделал до сих пор, - это составление запроса powerquery, который загружает все расписания сотрудников, фильтрует и очищает информацию в одной таблице основных данных. Мой текущий код «работает», но занимает много времени и, вероятно, очень неэффективен. Краткое изложение моего процесса:

  1. Копировать столбец имени сотрудника
  2. Вставить имена сотрудников на отдельный рабочий лист (временный диапазон) A1
  3. Удалить дубликаты, чтобы у меня был столбец уникальных имен.
  4. Для каждого имени применить фильтр «Имя» к моей таблице основных данных.
    1. Копировать столбец клиента
    2. Вставить клиентов в временный диапазон B1
    3. Удалить дубликаты, чтобы у меня был столбец с уникальными клиентами, с которыми работал сотрудник.
    4. Для каждого клиента, с которым работал сотрудник, примените фильтр «Клиент» к моим основным данным таблица.
      1. Копировать столбец имени проекта
      2. Вставить имена проектов во временную папку C1
      3. Удалить дубликаты, чтобы у меня был столбец уникального проекта, над которым сотрудник работал для клиента .
      4. Для каждого проекта, над которым работал сотрудник, примените фильтр «Проект» к таблице основных данных.
        1. Скопируйте отфильтрованные данные (только видимые ячейки) из таблицы основных данных
        2. Вставить данные в предварительно отформатированный рабочий лист (табель) таблица.
        3. Применить фильтр, чтобы скрыть все пустые строки в таблице расписания.
        4. Распечатать табель учета рабочего времени в формате pdf в заранее определенном месте.
        5. Показать строки из таблиц табеля и очистите содержимое для следующего проекта.

Я ищу предложения, как улучшить мой процесс, чтобы сократить время , ошибки и общая структура. У меня пока нет обработки ошибок в коде. Предложения по этому поводу тоже были бы хороши, хотя в идеале у вас нет ошибок, верно;). Мой длинный и уродливый код вставлен ниже. Я пытаюсь использовать переменную, но по какой-то причине у меня возникают ошибки, поэтому я просто переписываю переменную, и она работает ....

Public Sub EAS_AutoTS()
Dim wb As Workbook: Set wb = ThisWorkbook
Dim wsTemp As Worksheet, po As Worksheet, que As Worksheet
Dim tempEmp As Range, tempClient As Range, tempProject As Range
Dim Emp As String, Client As String, Project As String
Dim PathName As String, SvAs As String
Dim e As Integer, c As Integer, p As Integer, ne As Integer, nc As Integer, np As Integer

Application.ScreenUpdating = False
PathName = ActiveWorkbook.Path

'Refresh Connection
wb.Connections("Query - Timesheets").Refresh
'Clear Filter on PrintOut Sheet
Set que = wb.Sheets("Data")
Set po = wb.Sheets("PrintOut")
'Create new sheet "Temp" and set Temp variable
'Sheets.Add After:=Data
'Sheets("Sheet1").Name = "Temp"
wb.Sheets("Temp").Visible = xlSheetVisible
Set wsTemp = wb.Sheets("Temp")
wsTemp.Cells.Clear
'Copy Name Column in query table to Temp Sheet A1
que.Range("A4").Select
que.AutoFilter.ShowAllData
que.Range("tblTS[Name]").Copy
wsTemp.Range("A1").PasteSpecial Paste:=xlPasteValues
'Remove Duplicates in the tempEmp Named Range to result in unique names only
wsTemp.Range("$A:$A").RemoveDuplicates Columns:=1, Header:=xlNo
'Create Dynamic Name Range for Employee Names
wb.Names.Add Name:="tempEmp", RefersTo:="=OFFSET(Temp!$A$1,0,0,COUNTA(Temp!$A:$A),1)"
'Set tempEmp = Range("tempEmp")
e = Range("tempEmp").Count

'Begin first for loop. First loop is for all employee names.
For ne = 1 To e
    'Clear all filters in query table
    que.Select
    que.AutoFilter.ShowAllData
    'Apply name to Printout sheet
    po.Range("E1") = wsTemp.Range("A" & ne).Value
    'Apply name filter to query table
    que.Range("tblTS").AutoFilter Field:=1, Criteria1:="=" & wsTemp.Range("A" & ne).Value, Operator:=xlFilterValues
    wsTemp.Range("$B:$C").ClearContents
    'Copy Client Column in query table to Temp Sheet B1
    que.Range("tblTS[Client]").SpecialCells(xlCellTypeVisible).Copy
    wsTemp.Range("B1").PasteSpecial Paste:=xlPasteValues
    'Remove Duplicate clients to result in unique clients only
    wsTemp.Range("$B:$B").RemoveDuplicates Columns:=1, Header:=xlNo
    'Create Dynamic Name Range for Client Names
    wb.Names.Add Name:="tempClient", RefersTo:="=OFFSET(Temp!$B$1,0,0,COUNTA(Temp!$B:$B),1)"
    'Set tempClient = Range("tempClient")
    'Determine number of Clients for the FOR loop.
    c = Range("tempClient").Count
    'Begin second for loop. Second loop is for all employee names.
    For nc = 1 To c
        'Apply client filter to query table
        que.Range("tblTS").AutoFilter Field:=6
        que.Range("tblTS").AutoFilter Field:=5, Criteria1:="=" & wsTemp.Range("B" & nc).Value, Operator:=xlFilterValues
        'Copy Project Column in query table to Temp Sheet C1
        wsTemp.Range("$C:$C").ClearContents
        que.Range("tblTS[Project Name]").SpecialCells(xlCellTypeVisible).Copy
        wsTemp.Range("C1").PasteSpecial Paste:=xlPasteValues
        'Remove Duplicates in the tempProject Named Range to result in unique projects only
        wsTemp.Range("$C:$C").RemoveDuplicates Columns:=1, Header:=xlNo
        'Create Dynamic Name Range for Project Names
        wb.Names.Add Name:="tempProject", RefersTo:="=OFFSET(Temp!$C$1,0,0,COUNTA(Temp!$C:$C),1)"
        'Set tempProject = Range("tempProject")
        'Determine number of Clients for the FOR loop.
        p = Range("tempProject").Count
        'Begin third (final) for loop: Third loop is for project filtering
        For np = 1 To p
            'Apply Project filter to query table
            If p <> 1 Then que.Range("tblTS").AutoFilter Field:=6, Criteria1:="=" & wsTemp.Range("C" & np).Value, Operator:=xlFilterValues
            'Copy query table to Printout sheet
            If po.Range("A3").Value <> "" Then po.AutoFilter.ShowAllData
            po.Range("tblPrint").ClearContents
            Range("tblTS[Date]:tblTS[Total Expenses]").SpecialCells(xlCellTypeVisible).Copy
            po.Select
            po.Range("A3").Select
            po.Range("A3").PasteSpecial Paste:=xlPasteValues
            'Filter (hide) blank cells.
            po.Range("tblPrint").AutoFilter Field:=1, Criteria1:="<>"
            'Print PDF to folder
            po.Range("W1").NumberFormat = "@"
            po.Range("W1").Value = Format(po.Range("W1").Value, "m-d-yy")
            SvAs = PathName & "\PDFs\" & po.Range("D3") & "_" & po.Range("E3") & "_" & po.Range("E1") & "_" & po.Range("W1") & ".pdf"
            po.ExportAsFixedFormat Type:=xlTypePDF, Filename:=SvAs, Quality:=xlQualityStandard, _
                IncludeDocProperties:=False, IgnorePrintAreas:=False, OpenAfterPublish:=False
        Next 'End of third for loop
    Next 'End of second for loop
Next 'End of first for loop
po.Range("A3").Select
po.AutoFilter.ShowAllData
po.Range("tblPrint").ClearContents
po.Range("E1").Value = ""
po.Range("W1").Value = ""
wsTemp.Range("$A:$C").ClearContents
wsTemp.Visible = xlSheetHidden
e = 0
c = 0
p = 0
ne = 0
nc = 0
np = 0
que.Select
que.AutoFilter.ShowAllData
Application.ScreenUpdating = True
MsgBox "Timesheets have been created at the following location:" & vbNewLine & PathName & "\PDFs", _
    vbOKOnly, "Finished!"
End Sub

1 Ответ

1 голос
/ 11 июля 2020

Эх, вы действительно выиграете здесь от PowerQuery.

Весь диапазон, выбор и очистка, я имею в виду, что вам нужно научиться фундаментально кодировать с переменными, чтобы улучшить это.

Но я бы сказал, что если вы берете таблицу и сортируете, у PQ есть потрясающий визуальный редактор и интерактивные шаги, которые может изучить любой, включая вашу жену.

Это скользкая дорожка для использования VBA с вашей второй половинкой в конце концов, ошибки и проблемы будут давить на отношения. PQ станет вашим доктором Филом здесь и заставит каждого жить своей лучшей жизнью самостоятельно.

См. Ответ Уилла Вуллимса о том, как это автоматизировать: здесь

...