按文件名排序
# -*- coding:utf-8 -*-
import os
from pathlib import Path
import time
from threading import Thread, current_thread
from tkinter import Tk, StringVar, Frame, Label, LEFT, Entry, Button, mainloop
from PIL import Image
import click
from reportlab.pdfgen import canvas
SUCCESS_MESSAGE = '生成成功'
FILE_NOT_EXIST_MESSAGE = '文件地址不存在'
GENERATING_MESSAGE = '生成中...'
class ConvertJob(object):
def __init__(self, dir_path):
self.dir_path = dir_path
@property
def pdf_file(self):
return os.path.join(self.dir_path, f'{time.strftime("%Y-%m-%d", time.localtime())}.pdf')
def convert_pdf(self):
try:
self._convert_pdf()
except (FileExistsError, OSError, PermissionError):
return FILE_NOT_EXIST_MESSAGE
except Exception as e:
return e.args[0]
return SUCCESS_MESSAGE
def _convert_pdf(self):
cv = canvas.Canvas(self.pdf_file)
empty_flag = True
for file_path in self.get_list_images():
try:
im = Image.open(file_path)
except OSError:
continue
cv.setPageSize(im.size)
cv.drawImage(file_path, 0, 0, * im.size)
cv.showPage()
empty_flag = False
if not empty_flag:
cv.save()
else:
raise FileExistsError
def get_list_images(self):
file_list = []
if os.path.isdir(self.dir_path):
for image_name in os.listdir(self.dir_path):
abs_path = Path(os.path.join(self.dir_path, image_name))
file_list.append(abs_path)
file_list.sort(key=self.file_name_sort_key)
return file_list
@staticmethod
def file_name_sort_key(file_name):
base_file_name = file_name.name.split('.', 1)[0]
i = -1
for i, c in enumerate(base_file_name):
if '0' <= c <= '9':
continue
break
else:
i += 1
return int(base_file_name[:i]) if i else -1, base_file_name[i:]
class PdfTkinter(object):
"""
界面
"""
current_thread = None
def __init__(self):
top = Tk()
sw = top.winfo_screenwidth()
sh = top.winfo_screenheight()
top_width = 500
top_height = 200
top.title('图片转pdf生成器')
top.geometry(
f"{top_width}x{top_height}+{(sw - top_width) // 2}+{(sh - top_height) // 2}"
)
self._dir_path = StringVar(top)
Frame(top, height=50).pack()
dir_frame = Frame(top)
dir_label = Label(dir_frame, width=4, text='路径:')
dir_label.pack(side=LEFT)
dir_entry = Entry(dir_frame, width=50, textvariable=self._dir_path)
dir_entry.pack(side=LEFT, padx=5)
dir_frame.pack()
Frame(top, height=5).pack()
self.message_frame = Frame(top, height=30, width=50)
self.text_area = Label(self.message_frame, text='')
self.text_area.pack(side=LEFT, padx=60)
self.message_frame.pack()
Frame(top, height=5).pack()
button_frame = Frame(top)
convert_button = Button(
button_frame, width=10, text='生成PDF', command=self.convert,
activeforeground='white', activebackground='blue')
quit_button = Button(
button_frame, width=10, text='退出', command=top.quit, activeforeground='white',
activebackground='blue'
)
convert_button.pack(side=LEFT, padx=10)
quit_button.pack(side=LEFT, padx=10)
button_frame.pack()
def message(self, text, color='black'):
self.text_area.destroy()
self.text_area = Label(self.message_frame, text=text, fg=color)
self.text_area.pack(side=LEFT, padx=60)
def convert(self):
self.message(GENERATING_MESSAGE, 'red')
self.current_thread = Thread(target=self.convert_thread)
self.current_thread.start()
def convert_thread(self):
text = ConvertJob(self._dir_path.get()).convert_pdf()
if self.current_thread is current_thread():
self.message(text, 'red')
@click.command()
@click.option('-d', 'dir_path', default=None, help='image document path')
def run(dir_path):
if dir_path is None:
PdfTkinter()
mainloop()
else:
ConvertJob(dir_path).convert_pdf()
if __name__ == '__main__':
run()
网友评论