mirror of
https://github.com/koreader/koreader
synced 2024-11-10 01:10:34 +00:00
122 lines
3.4 KiB
Lua
122 lines
3.4 KiB
Lua
local lfs = require("libs/libkoreader-lfs")
|
|
local DataStorage = require("datastorage")
|
|
local DocSettings = require("docsettings")
|
|
local joinPath = require("ffi/util").joinPath
|
|
local dump = require("dump")
|
|
|
|
local history_file = joinPath(DataStorage:getDataDir(), "history.lua")
|
|
|
|
local ReadHistory = {
|
|
hist = {},
|
|
}
|
|
|
|
local function buildEntry(input_time, input_file)
|
|
return {
|
|
time = input_time,
|
|
text = input_file:gsub(".*/", ""),
|
|
file = input_file,
|
|
callback = function()
|
|
local ReaderUI = require("apps/reader/readerui")
|
|
ReaderUI:showReader(input_file)
|
|
end
|
|
}
|
|
end
|
|
|
|
function ReadHistory:_sort()
|
|
for i = #self.hist, 1, -1 do
|
|
if lfs.attributes(self.hist[i].file, "mode") ~= "file" then
|
|
table.remove(self.hist, i)
|
|
end
|
|
end
|
|
table.sort(self.hist, function(l, r) return l.file < r.file end)
|
|
-- TODO(zijiehe): Use binary insert instead of a loop to deduplicate.
|
|
for i = #self.hist, 2, -1 do
|
|
if self.hist[i].file == self.hist[i - 1].file then
|
|
if self.hist[i].time < self.hist[i - 1].time then
|
|
table.remove(self.hist, i)
|
|
else
|
|
table.remove(self.hist,i - 1)
|
|
end
|
|
end
|
|
end
|
|
table.sort(self.hist, function(v1, v2) return v1.time > v2.time end)
|
|
-- TODO(zijiehe): Use binary search to find an item when deleting it.
|
|
for i = 1, #self.hist, 1 do
|
|
self.hist[i].index = i
|
|
end
|
|
end
|
|
|
|
-- Reduces total count in hist list to a reasonable number by removing last
|
|
-- several items.
|
|
function ReadHistory:_reduce()
|
|
while #self.hist > 500 do
|
|
table.remove(self.hist, #self.hist)
|
|
end
|
|
end
|
|
|
|
-- Flushes current history table into file.
|
|
function ReadHistory:_flush()
|
|
local content = {}
|
|
for k, v in pairs(self.hist) do
|
|
content[k] = {
|
|
time = v.time,
|
|
file = v.file
|
|
}
|
|
end
|
|
local f = io.open(history_file, "w")
|
|
f:write("return " .. dump(content) .. "\n")
|
|
f:close()
|
|
end
|
|
|
|
-- Reads history table from file
|
|
function ReadHistory:_read()
|
|
local ok, data = pcall(dofile, history_file)
|
|
if ok then
|
|
for k, v in pairs(data) do
|
|
table.insert(self.hist, buildEntry(v.time, v.file))
|
|
end
|
|
end
|
|
end
|
|
|
|
-- Reads history from legacy history folder
|
|
function ReadHistory:_readLegacyHistory()
|
|
local history_dir = DataStorage:getHistoryDir()
|
|
for f in lfs.dir(history_dir) do
|
|
local path = joinPath(history_dir, f)
|
|
if lfs.attributes(path, "mode") == "file" then
|
|
local file = joinPath(DocSettings:getPathFromHistory(f),
|
|
DocSettings:getNameFromHistory(f))
|
|
table.insert(self.hist,
|
|
buildEntry(lfs.attributes(path, "modification"), file))
|
|
end
|
|
end
|
|
end
|
|
|
|
function ReadHistory:_init()
|
|
self:_read()
|
|
self:_readLegacyHistory()
|
|
self:_sort()
|
|
self:_reduce()
|
|
end
|
|
|
|
function ReadHistory:removeItem(item)
|
|
table.remove(self.hist, item.index)
|
|
os.remove(DocSettings:getHistoryPath(item.file))
|
|
self:_flush()
|
|
end
|
|
|
|
function ReadHistory:addItem(file)
|
|
if file ~= nil and lfs.attributes(file, "mode") == "file" then
|
|
table.insert(self.hist, 1, buildEntry(os.time(), file))
|
|
-- TODO(zijiehe): We do not need to sort if we can use binary insert and
|
|
-- binary search.
|
|
self:_sort()
|
|
self:_reduce()
|
|
self:_flush()
|
|
end
|
|
end
|
|
|
|
ReadHistory:_init()
|
|
|
|
return ReadHistory
|