Add option to turn off cache (#263)
This commit is contained in:
parent
1d904a858e
commit
17f97bd958
|
@ -2,7 +2,7 @@ use std::fs::{File, Metadata, OpenOptions};
|
|||
use std::io::prelude::*;
|
||||
use std::path::{Path, PathBuf};
|
||||
use std::time::{Duration, SystemTime, UNIX_EPOCH};
|
||||
use std::{fs, thread};
|
||||
use std::{fs, mem, thread};
|
||||
|
||||
use crate::common::Common;
|
||||
use crate::common_directory::Directories;
|
||||
|
@ -78,6 +78,7 @@ pub struct BrokenFiles {
|
|||
recursive_search: bool,
|
||||
delete_method: DeleteMethod,
|
||||
stopped_search: bool,
|
||||
use_cache: bool,
|
||||
}
|
||||
|
||||
impl BrokenFiles {
|
||||
|
@ -93,6 +94,7 @@ impl BrokenFiles {
|
|||
delete_method: DeleteMethod::None,
|
||||
stopped_search: false,
|
||||
broken_files: Default::default(),
|
||||
use_cache: true,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -130,6 +132,10 @@ impl BrokenFiles {
|
|||
self.delete_method = delete_method;
|
||||
}
|
||||
|
||||
pub fn set_use_cache(&mut self, use_cache: bool) {
|
||||
self.use_cache = use_cache;
|
||||
}
|
||||
|
||||
pub fn set_recursive_search(&mut self, recursive_search: bool) {
|
||||
self.recursive_search = recursive_search;
|
||||
}
|
||||
|
@ -297,27 +303,35 @@ impl BrokenFiles {
|
|||
fn look_for_broken_files(&mut self, stop_receiver: Option<&Receiver<()>>, progress_sender: Option<&futures::channel::mpsc::Sender<ProgressData>>) -> bool {
|
||||
let system_time = SystemTime::now();
|
||||
|
||||
let loaded_hash_map = match load_cache_from_file(&mut self.text_messages) {
|
||||
Some(t) => t,
|
||||
None => Default::default(),
|
||||
};
|
||||
let loaded_hash_map;
|
||||
|
||||
let mut records_already_cached: HashMap<String, FileEntry> = Default::default();
|
||||
let mut non_cached_files_to_check: HashMap<String, FileEntry> = Default::default();
|
||||
for (name, file_entry) in &self.files_to_check {
|
||||
#[allow(clippy::collapsible_if)]
|
||||
if !loaded_hash_map.contains_key(name) {
|
||||
// If loaded data doesn't contains current image info
|
||||
non_cached_files_to_check.insert(name.clone(), file_entry.clone());
|
||||
} else {
|
||||
if file_entry.size != loaded_hash_map.get(name).unwrap().size || file_entry.modified_date != loaded_hash_map.get(name).unwrap().modified_date {
|
||||
// When size or modification date of image changed, then it is clear that is different image
|
||||
|
||||
if self.use_cache {
|
||||
loaded_hash_map = match load_cache_from_file(&mut self.text_messages) {
|
||||
Some(t) => t,
|
||||
None => Default::default(),
|
||||
};
|
||||
|
||||
for (name, file_entry) in &self.files_to_check {
|
||||
#[allow(clippy::collapsible_if)]
|
||||
if !loaded_hash_map.contains_key(name) {
|
||||
// If loaded data doesn't contains current image info
|
||||
non_cached_files_to_check.insert(name.clone(), file_entry.clone());
|
||||
} else {
|
||||
// Checking may be omitted when already there is entry with same size and modification date
|
||||
records_already_cached.insert(name.clone(), loaded_hash_map.get(name).unwrap().clone());
|
||||
if file_entry.size != loaded_hash_map.get(name).unwrap().size || file_entry.modified_date != loaded_hash_map.get(name).unwrap().modified_date {
|
||||
// When size or modification date of image changed, then it is clear that is different image
|
||||
non_cached_files_to_check.insert(name.clone(), file_entry.clone());
|
||||
} else {
|
||||
// Checking may be omitted when already there is entry with same size and modification date
|
||||
records_already_cached.insert(name.clone(), loaded_hash_map.get(name).unwrap().clone());
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
loaded_hash_map = Default::default();
|
||||
mem::swap(&mut self.files_to_check, &mut non_cached_files_to_check);
|
||||
}
|
||||
|
||||
let check_was_breaked = AtomicBool::new(false); // Used for breaking from GUI and ending check thread
|
||||
|
@ -430,16 +444,18 @@ impl BrokenFiles {
|
|||
|
||||
self.broken_files = vec_file_entry.iter().filter_map(|f| if f.error_string.is_empty() { None } else { Some(f.clone()) }).collect();
|
||||
|
||||
// Must save all results to file, old loaded from file with all currently counted results
|
||||
let mut all_results: HashMap<String, FileEntry> = self.files_to_check.clone();
|
||||
if self.use_cache {
|
||||
// Must save all results to file, old loaded from file with all currently counted results
|
||||
let mut all_results: HashMap<String, FileEntry> = self.files_to_check.clone();
|
||||
|
||||
for file_entry in vec_file_entry {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry);
|
||||
for file_entry in vec_file_entry {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry);
|
||||
}
|
||||
for (_name, file_entry) in loaded_hash_map {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry);
|
||||
}
|
||||
save_cache_to_file(&all_results, &mut self.text_messages);
|
||||
}
|
||||
for (_name, file_entry) in loaded_hash_map {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry);
|
||||
}
|
||||
save_cache_to_file(&all_results, &mut self.text_messages);
|
||||
|
||||
self.information.number_of_broken_files = self.broken_files.len();
|
||||
|
||||
|
|
|
@ -10,7 +10,7 @@ use std::io::{self, Error, ErrorKind};
|
|||
use std::os::unix::fs::MetadataExt;
|
||||
use std::path::{Path, PathBuf};
|
||||
use std::time::{Duration, SystemTime, UNIX_EPOCH};
|
||||
use std::{fs, thread};
|
||||
use std::{fs, mem, thread};
|
||||
|
||||
use crate::common::Common;
|
||||
use crate::common_directory::Directories;
|
||||
|
@ -151,6 +151,7 @@ pub struct DuplicateFinder {
|
|||
ignore_hard_links: bool,
|
||||
dryrun: bool,
|
||||
stopped_search: bool,
|
||||
use_cache: bool,
|
||||
}
|
||||
|
||||
impl DuplicateFinder {
|
||||
|
@ -172,6 +173,7 @@ impl DuplicateFinder {
|
|||
ignore_hard_links: true,
|
||||
hash_type: HashType::Blake3,
|
||||
dryrun: false,
|
||||
use_cache: true,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -221,6 +223,10 @@ impl DuplicateFinder {
|
|||
&self.files_with_identical_names
|
||||
}
|
||||
|
||||
pub fn set_use_cache(&mut self, use_cache: bool) {
|
||||
self.use_cache = use_cache;
|
||||
}
|
||||
|
||||
pub const fn get_files_sorted_by_size(&self) -> &BTreeMap<u64, Vec<FileEntry>> {
|
||||
&self.files_with_identical_size
|
||||
}
|
||||
|
@ -795,38 +801,46 @@ impl DuplicateFinder {
|
|||
.collect();
|
||||
}
|
||||
CheckingMethod::Hash => {
|
||||
let loaded_hash_map = match load_hashes_from_file(&mut self.text_messages, &self.hash_type) {
|
||||
Some(t) => t,
|
||||
None => Default::default(),
|
||||
};
|
||||
let loaded_hash_map;
|
||||
|
||||
let mut records_already_cached: HashMap<u64, Vec<FileEntry>> = Default::default();
|
||||
let mut non_cached_files_to_check: HashMap<u64, Vec<FileEntry>> = Default::default();
|
||||
for (size, vec_file_entry) in pre_checked_map {
|
||||
#[allow(clippy::collapsible_if)]
|
||||
if !loaded_hash_map.contains_key(&size) {
|
||||
// If loaded data doesn't contains current info
|
||||
non_cached_files_to_check.insert(size, vec_file_entry);
|
||||
} else {
|
||||
let loaded_vec_file_entry = loaded_hash_map.get(&size).unwrap();
|
||||
let mut records_already_cached: BTreeMap<u64, Vec<FileEntry>> = Default::default();
|
||||
let mut non_cached_files_to_check: BTreeMap<u64, Vec<FileEntry>> = Default::default();
|
||||
|
||||
for file_entry in vec_file_entry {
|
||||
let mut found: bool = false;
|
||||
for loaded_file_entry in loaded_vec_file_entry {
|
||||
if file_entry.path == loaded_file_entry.path && file_entry.modified_date == loaded_file_entry.modified_date {
|
||||
records_already_cached.entry(file_entry.size).or_insert_with(Vec::new);
|
||||
records_already_cached.get_mut(&file_entry.size).unwrap().push(loaded_file_entry.clone());
|
||||
found = true;
|
||||
break;
|
||||
if self.use_cache {
|
||||
loaded_hash_map = match load_hashes_from_file(&mut self.text_messages, &self.hash_type) {
|
||||
Some(t) => t,
|
||||
None => Default::default(),
|
||||
};
|
||||
|
||||
for (size, vec_file_entry) in pre_checked_map {
|
||||
#[allow(clippy::collapsible_if)]
|
||||
if !loaded_hash_map.contains_key(&size) {
|
||||
// If loaded data doesn't contains current info
|
||||
non_cached_files_to_check.insert(size, vec_file_entry);
|
||||
} else {
|
||||
let loaded_vec_file_entry = loaded_hash_map.get(&size).unwrap();
|
||||
|
||||
for file_entry in vec_file_entry {
|
||||
let mut found: bool = false;
|
||||
for loaded_file_entry in loaded_vec_file_entry {
|
||||
if file_entry.path == loaded_file_entry.path && file_entry.modified_date == loaded_file_entry.modified_date {
|
||||
records_already_cached.entry(file_entry.size).or_insert_with(Vec::new);
|
||||
records_already_cached.get_mut(&file_entry.size).unwrap().push(loaded_file_entry.clone());
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if !found {
|
||||
non_cached_files_to_check.entry(file_entry.size).or_insert_with(Vec::new);
|
||||
non_cached_files_to_check.get_mut(&file_entry.size).unwrap().push(file_entry);
|
||||
if !found {
|
||||
non_cached_files_to_check.entry(file_entry.size).or_insert_with(Vec::new);
|
||||
non_cached_files_to_check.get_mut(&file_entry.size).unwrap().push(file_entry);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
loaded_hash_map = Default::default();
|
||||
mem::swap(&mut pre_checked_map, &mut non_cached_files_to_check);
|
||||
}
|
||||
|
||||
full_hash_results = non_cached_files_to_check
|
||||
|
@ -860,43 +874,43 @@ impl DuplicateFinder {
|
|||
.while_some()
|
||||
.collect();
|
||||
|
||||
// Size, Vec
|
||||
|
||||
'main: for (size, vec_file_entry) in records_already_cached {
|
||||
// Check if size already exists, if exists we must to change it outside because cannot have mut and non mut reference to full_hash_results
|
||||
for (full_size, full_hashmap, _errors, _bytes_read) in &mut full_hash_results {
|
||||
if size == *full_size {
|
||||
for file_entry in vec_file_entry {
|
||||
full_hashmap.entry(file_entry.hash.clone()).or_insert_with(Vec::new);
|
||||
full_hashmap.get_mut(&file_entry.hash).unwrap().push(file_entry);
|
||||
if self.use_cache {
|
||||
'main: for (size, vec_file_entry) in records_already_cached {
|
||||
// Check if size already exists, if exists we must to change it outside because cannot have mut and non mut reference to full_hash_results
|
||||
for (full_size, full_hashmap, _errors, _bytes_read) in &mut full_hash_results {
|
||||
if size == *full_size {
|
||||
for file_entry in vec_file_entry {
|
||||
full_hashmap.entry(file_entry.hash.clone()).or_insert_with(Vec::new);
|
||||
full_hashmap.get_mut(&file_entry.hash).unwrap().push(file_entry);
|
||||
}
|
||||
continue 'main;
|
||||
}
|
||||
continue 'main;
|
||||
}
|
||||
}
|
||||
// Size doesn't exists add results to files
|
||||
let mut temp_hashmap: HashMap<String, Vec<FileEntry>> = Default::default();
|
||||
for file_entry in vec_file_entry {
|
||||
temp_hashmap.entry(file_entry.hash.clone()).or_insert_with(Vec::new);
|
||||
temp_hashmap.get_mut(&file_entry.hash).unwrap().push(file_entry);
|
||||
}
|
||||
full_hash_results.push((size, temp_hashmap, Vec::new(), 0));
|
||||
}
|
||||
|
||||
// Must save all results to file, old loaded from file with all currently counted results
|
||||
let mut all_results: HashMap<String, FileEntry> = Default::default();
|
||||
for (_size, vec_file_entry) in loaded_hash_map {
|
||||
for file_entry in vec_file_entry {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry);
|
||||
}
|
||||
}
|
||||
for (_size, hashmap, _errors, _bytes_read) in &full_hash_results {
|
||||
for vec_file_entry in hashmap.values() {
|
||||
// Size doesn't exists add results to files
|
||||
let mut temp_hashmap: HashMap<String, Vec<FileEntry>> = Default::default();
|
||||
for file_entry in vec_file_entry {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry.clone());
|
||||
temp_hashmap.entry(file_entry.hash.clone()).or_insert_with(Vec::new);
|
||||
temp_hashmap.get_mut(&file_entry.hash).unwrap().push(file_entry);
|
||||
}
|
||||
full_hash_results.push((size, temp_hashmap, Vec::new(), 0));
|
||||
}
|
||||
|
||||
// Must save all results to file, old loaded from file with all currently counted results
|
||||
let mut all_results: HashMap<String, FileEntry> = Default::default();
|
||||
for (_size, vec_file_entry) in loaded_hash_map {
|
||||
for file_entry in vec_file_entry {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry);
|
||||
}
|
||||
}
|
||||
for (_size, hashmap, _errors, _bytes_read) in &full_hash_results {
|
||||
for vec_file_entry in hashmap.values() {
|
||||
for file_entry in vec_file_entry {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry.clone());
|
||||
}
|
||||
}
|
||||
}
|
||||
save_hashes_to_file(&all_results, &mut self.text_messages, &self.hash_type);
|
||||
}
|
||||
save_hashes_to_file(&all_results, &mut self.text_messages, &self.hash_type);
|
||||
}
|
||||
_ => panic!("What"),
|
||||
}
|
||||
|
|
|
@ -20,7 +20,7 @@ use std::sync::atomic::{AtomicBool, AtomicUsize, Ordering};
|
|||
use std::sync::Arc;
|
||||
use std::thread::sleep;
|
||||
use std::time::{Duration, SystemTime, UNIX_EPOCH};
|
||||
use std::{fs, thread};
|
||||
use std::{fs, mem, thread};
|
||||
|
||||
/// Type to store for each entry in the similarity BK-tree.
|
||||
type Node = [u8; 8];
|
||||
|
@ -79,6 +79,7 @@ pub struct SimilarImages {
|
|||
stopped_search: bool,
|
||||
similarity: Similarity,
|
||||
images_to_check: HashMap<String, FileEntry>,
|
||||
use_cache: bool,
|
||||
}
|
||||
|
||||
/// Info struck with helpful information's about results
|
||||
|
@ -111,6 +112,7 @@ impl SimilarImages {
|
|||
stopped_search: false,
|
||||
similarity: Similarity::High,
|
||||
images_to_check: Default::default(),
|
||||
use_cache: true,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -130,6 +132,10 @@ impl SimilarImages {
|
|||
&self.information
|
||||
}
|
||||
|
||||
pub fn set_use_cache(&mut self, use_cache: bool) {
|
||||
self.use_cache = use_cache;
|
||||
}
|
||||
|
||||
pub fn set_recursive_search(&mut self, recursive_search: bool) {
|
||||
self.recursive_search = recursive_search;
|
||||
}
|
||||
|
@ -321,27 +327,35 @@ impl SimilarImages {
|
|||
fn sort_images(&mut self, stop_receiver: Option<&Receiver<()>>, progress_sender: Option<&futures::channel::mpsc::Sender<ProgressData>>) -> bool {
|
||||
let hash_map_modification = SystemTime::now();
|
||||
|
||||
let loaded_hash_map = match load_hashes_from_file(&mut self.text_messages) {
|
||||
Some(t) => t,
|
||||
None => Default::default(),
|
||||
};
|
||||
let loaded_hash_map;
|
||||
|
||||
let mut records_already_cached: HashMap<String, FileEntry> = Default::default();
|
||||
let mut non_cached_files_to_check: HashMap<String, FileEntry> = Default::default();
|
||||
for (name, file_entry) in &self.images_to_check {
|
||||
#[allow(clippy::collapsible_if)]
|
||||
if !loaded_hash_map.contains_key(name) {
|
||||
// If loaded data doesn't contains current image info
|
||||
non_cached_files_to_check.insert(name.clone(), file_entry.clone());
|
||||
} else {
|
||||
if file_entry.size != loaded_hash_map.get(name).unwrap().size || file_entry.modified_date != loaded_hash_map.get(name).unwrap().modified_date {
|
||||
// When size or modification date of image changed, then it is clear that is different image
|
||||
|
||||
if self.use_cache {
|
||||
loaded_hash_map = match load_hashes_from_file(&mut self.text_messages) {
|
||||
Some(t) => t,
|
||||
None => Default::default(),
|
||||
};
|
||||
|
||||
for (name, file_entry) in &self.images_to_check {
|
||||
#[allow(clippy::collapsible_if)]
|
||||
if !loaded_hash_map.contains_key(name) {
|
||||
// If loaded data doesn't contains current image info
|
||||
non_cached_files_to_check.insert(name.clone(), file_entry.clone());
|
||||
} else {
|
||||
// Checking may be omitted when already there is entry with same size and modification date
|
||||
records_already_cached.insert(name.clone(), loaded_hash_map.get(name).unwrap().clone());
|
||||
if file_entry.size != loaded_hash_map.get(name).unwrap().size || file_entry.modified_date != loaded_hash_map.get(name).unwrap().modified_date {
|
||||
// When size or modification date of image changed, then it is clear that is different image
|
||||
non_cached_files_to_check.insert(name.clone(), file_entry.clone());
|
||||
} else {
|
||||
// Checking may be omitted when already there is entry with same size and modification date
|
||||
records_already_cached.insert(name.clone(), loaded_hash_map.get(name).unwrap().clone());
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
loaded_hash_map = Default::default();
|
||||
mem::swap(&mut self.images_to_check, &mut non_cached_files_to_check);
|
||||
}
|
||||
|
||||
Common::print_time(hash_map_modification, SystemTime::now(), "sort_images - reading data from cache and preparing them".to_string());
|
||||
|
@ -426,12 +440,14 @@ impl SimilarImages {
|
|||
self.image_hashes.get_mut(buf).unwrap().push(file_entry.clone());
|
||||
}
|
||||
|
||||
// Must save all results to file, old loaded from file with all currently counted results
|
||||
let mut all_results: HashMap<String, FileEntry> = loaded_hash_map;
|
||||
for (file_entry, _hash) in vec_file_entry {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry);
|
||||
if self.use_cache {
|
||||
// Must save all results to file, old loaded from file with all currently counted results
|
||||
let mut all_results: HashMap<String, FileEntry> = loaded_hash_map;
|
||||
for (file_entry, _hash) in vec_file_entry {
|
||||
all_results.insert(file_entry.path.to_string_lossy().to_string(), file_entry);
|
||||
}
|
||||
save_hashes_to_file(&all_results, &mut self.text_messages);
|
||||
}
|
||||
save_hashes_to_file(&all_results, &mut self.text_messages);
|
||||
|
||||
Common::print_time(hash_map_modification, SystemTime::now(), "sort_images - saving data to files".to_string());
|
||||
let hash_map_modification = SystemTime::now();
|
||||
|
|
|
@ -2485,6 +2485,21 @@ This program is free to use and will always be.
|
|||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="check_button_settings_save_at_exit">
|
||||
<property name="label" translatable="yes">Save configuration at exit</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
<property name="receives-default">False</property>
|
||||
<property name="active">True</property>
|
||||
<property name="draw-indicator">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="check_button_settings_confirm_deletion">
|
||||
<property name="label" translatable="yes">Show confirm dialog when deleting</property>
|
||||
|
@ -2497,7 +2512,7 @@ This program is free to use and will always be.
|
|||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">3</property>
|
||||
<property name="position">2</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
|
@ -2512,12 +2527,12 @@ This program is free to use and will always be.
|
|||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">False</property>
|
||||
<property name="position">5</property>
|
||||
<property name="position">3</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="check_button_settings_save_at_exit">
|
||||
<property name="label" translatable="yes">Save configuration at exit</property>
|
||||
<object class="GtkCheckButton" id="check_button_settings_use_cache">
|
||||
<property name="label" translatable="yes">Use cache</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
<property name="receives-default">False</property>
|
||||
|
|
|
@ -91,6 +91,7 @@ pub fn connect_button_search(
|
|||
let radio_button_hash_type_crc32 = gui_data.main_notebook.radio_button_hash_type_crc32.clone();
|
||||
let radio_button_hash_type_xxh3 = gui_data.main_notebook.radio_button_hash_type_xxh3.clone();
|
||||
let check_button_settings_hide_hard_links = gui_data.settings.check_button_settings_hide_hard_links.clone();
|
||||
let check_button_settings_use_cache = gui_data.settings.check_button_settings_use_cache.clone();
|
||||
|
||||
buttons_search_clone.connect_clicked(move |_| {
|
||||
let included_directories = get_path_buf_from_vector_of_strings(get_string_from_list_store(&tree_view_included_directories));
|
||||
|
@ -99,6 +100,7 @@ pub fn connect_button_search(
|
|||
let excluded_items = entry_excluded_items.get_text().as_str().to_string().split(',').map(|e| e.to_string()).collect::<Vec<String>>();
|
||||
let allowed_extensions = entry_allowed_extensions.get_text().as_str().to_string();
|
||||
let hide_hard_links = check_button_settings_hide_hard_links.get_active();
|
||||
let use_cache = check_button_settings_use_cache.get_active();
|
||||
|
||||
let show_dialog = Arc::new(AtomicBool::new(true));
|
||||
|
||||
|
@ -167,6 +169,7 @@ pub fn connect_button_search(
|
|||
df.set_check_method(check_method);
|
||||
df.set_hash_type(hash_type);
|
||||
df.set_ignore_hard_links(hide_hard_links);
|
||||
df.set_use_cache(use_cache);
|
||||
df.find_duplicates(Some(&stop_receiver), Some(&futures_sender_duplicate_files));
|
||||
let _ = glib_stop_sender.send(Message::Duplicates(df));
|
||||
});
|
||||
|
@ -292,6 +295,7 @@ pub fn connect_button_search(
|
|||
sf.set_excluded_items(excluded_items);
|
||||
sf.set_minimal_file_size(minimal_file_size);
|
||||
sf.set_similarity(similarity);
|
||||
sf.set_use_cache(use_cache);
|
||||
sf.find_similar_images(Some(&stop_receiver), Some(&futures_sender_similar_images));
|
||||
let _ = glib_stop_sender.send(Message::SimilarImages(sf));
|
||||
});
|
||||
|
@ -402,6 +406,7 @@ pub fn connect_button_search(
|
|||
br.set_excluded_directory(excluded_directories);
|
||||
br.set_recursive_search(recursive_search);
|
||||
br.set_excluded_items(excluded_items);
|
||||
br.set_use_cache(use_cache);
|
||||
br.find_broken_files(Some(&stop_receiver), Some(&futures_sender_broken_files));
|
||||
let _ = glib_stop_sender.send(Message::BrokenFiles(br));
|
||||
});
|
||||
|
|
|
@ -9,6 +9,7 @@ pub struct GUISettings {
|
|||
pub check_button_settings_load_at_start: gtk::CheckButton,
|
||||
pub check_button_settings_confirm_deletion: gtk::CheckButton,
|
||||
pub check_button_settings_show_text_view: gtk::CheckButton,
|
||||
pub check_button_settings_use_cache: gtk::CheckButton,
|
||||
|
||||
// Duplicates
|
||||
pub check_button_settings_hide_hard_links: gtk::CheckButton,
|
||||
|
@ -31,6 +32,7 @@ impl GUISettings {
|
|||
let check_button_settings_load_at_start: gtk::CheckButton = builder.get_object("check_button_settings_load_at_start").unwrap();
|
||||
let check_button_settings_confirm_deletion: gtk::CheckButton = builder.get_object("check_button_settings_confirm_deletion").unwrap();
|
||||
let check_button_settings_show_text_view: gtk::CheckButton = builder.get_object("check_button_settings_show_text_view").unwrap();
|
||||
let check_button_settings_use_cache: gtk::CheckButton = builder.get_object("check_button_settings_use_cache").unwrap();
|
||||
|
||||
// Duplicates
|
||||
let check_button_settings_hide_hard_links: gtk::CheckButton = builder.get_object("check_button_settings_hide_hard_links").unwrap();
|
||||
|
@ -54,6 +56,7 @@ impl GUISettings {
|
|||
button_settings_reset_configuration,
|
||||
check_button_settings_show_preview_similar_images,
|
||||
check_button_settings_hide_hard_links,
|
||||
check_button_settings_use_cache,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -112,10 +112,15 @@ pub fn save_configuration(gui_data: &GuiData, manual_execution: bool) {
|
|||
let check_button_settings_show_text_view = gui_data.settings.check_button_settings_show_text_view.clone();
|
||||
data_to_save.push(check_button_settings_show_text_view.get_active().to_string());
|
||||
|
||||
//// Show bottom text panel with errors
|
||||
//// Hide/Show hard linked files, with same inodes
|
||||
data_to_save.push("--hide_hard_links:".to_string());
|
||||
let check_button_settings_hide_hard_links = gui_data.settings.check_button_settings_hide_hard_links.clone();
|
||||
data_to_save.push(check_button_settings_hide_hard_links.get_active().to_string());
|
||||
|
||||
//// Use cache system
|
||||
data_to_save.push("--use_cache:".to_string());
|
||||
let check_button_settings_use_cache = gui_data.settings.check_button_settings_use_cache.clone();
|
||||
data_to_save.push(check_button_settings_use_cache.get_active().to_string());
|
||||
}
|
||||
|
||||
// Creating/Opening config file
|
||||
|
@ -143,9 +148,9 @@ pub fn save_configuration(gui_data: &GuiData, manual_execution: bool) {
|
|||
}
|
||||
}
|
||||
if data_saved {
|
||||
add_text_to_text_view(&text_view_errors, format!("Saved configuration to file {}", config_dir.display()).as_str());
|
||||
add_text_to_text_view(&text_view_errors, format!("Saved configuration to file {}", config_file.display()).as_str());
|
||||
} else {
|
||||
add_text_to_text_view(&text_view_errors, format!("Failed to save configuration data to file {}", config_dir.display()).as_str());
|
||||
add_text_to_text_view(&text_view_errors, format!("Failed to save configuration data to file {}", config_file.display()).as_str());
|
||||
}
|
||||
} else {
|
||||
add_text_to_text_view(&text_view_errors, "Failed to get home directory, so can't save file.");
|
||||
|
@ -164,6 +169,7 @@ enum TypeOfLoadedData {
|
|||
ShowPreviews,
|
||||
BottomTextPanel,
|
||||
HideHardLinks,
|
||||
UseCache,
|
||||
}
|
||||
|
||||
pub fn load_configuration(gui_data: &GuiData, manual_execution: bool) {
|
||||
|
@ -207,6 +213,7 @@ pub fn load_configuration(gui_data: &GuiData, manual_execution: bool) {
|
|||
let mut show_previews: bool = true;
|
||||
let mut bottom_text_panel: bool = true;
|
||||
let mut hide_hard_links: bool = true;
|
||||
let mut use_cache: bool = true;
|
||||
|
||||
let mut current_type = TypeOfLoadedData::None;
|
||||
for (line_number, line) in loaded_data.replace("\r\n", "\n").split('\n').enumerate() {
|
||||
|
@ -234,6 +241,8 @@ pub fn load_configuration(gui_data: &GuiData, manual_execution: bool) {
|
|||
current_type = TypeOfLoadedData::BottomTextPanel;
|
||||
} else if line.starts_with("--hide_hard_links") {
|
||||
current_type = TypeOfLoadedData::HideHardLinks;
|
||||
} else if line.starts_with("--use_cache") {
|
||||
current_type = TypeOfLoadedData::UseCache;
|
||||
} else if line.starts_with("--") {
|
||||
current_type = TypeOfLoadedData::None;
|
||||
add_text_to_text_view(
|
||||
|
@ -338,6 +347,19 @@ pub fn load_configuration(gui_data: &GuiData, manual_execution: bool) {
|
|||
);
|
||||
}
|
||||
}
|
||||
TypeOfLoadedData::UseCache => {
|
||||
let line = line.to_lowercase();
|
||||
if line == "1" || line == "true" {
|
||||
use_cache = true;
|
||||
} else if line == "0" || line == "false" {
|
||||
use_cache = false;
|
||||
} else {
|
||||
add_text_to_text_view(
|
||||
&text_view_errors,
|
||||
format!("Found invalid data in line {} \"{}\" isn't proper value(0/1/true/false) when loading file {:?}", line_number, line, config_file).as_str(),
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -389,6 +411,7 @@ pub fn load_configuration(gui_data: &GuiData, manual_execution: bool) {
|
|||
gui_data.scrolled_window_errors.show();
|
||||
}
|
||||
gui_data.settings.check_button_settings_hide_hard_links.set_active(hide_hard_links);
|
||||
gui_data.settings.check_button_settings_use_cache.set_active(use_cache);
|
||||
} else {
|
||||
gui_data.settings.check_button_settings_load_at_start.set_active(false);
|
||||
}
|
||||
|
@ -469,6 +492,7 @@ pub fn reset_configuration(gui_data: &GuiData, manual_clearing: bool) {
|
|||
gui_data.settings.check_button_settings_show_preview_similar_images.set_active(true);
|
||||
gui_data.settings.check_button_settings_show_text_view.set_active(true);
|
||||
gui_data.settings.check_button_settings_hide_hard_links.set_active(true);
|
||||
gui_data.settings.check_button_settings_use_cache.set_active(true);
|
||||
}
|
||||
if manual_clearing {
|
||||
add_text_to_text_view(&text_view_errors, "Current configuration was cleared.");
|
||||
|
|
Loading…
Reference in New Issue