@@ -39,6 +39,14 @@ use std::{
3939 path:: { Path , PathBuf } ,
4040} ;
4141
42+ #[ derive( PartialEq , Eq , PartialOrd , Ord ) ]
43+ pub struct DebIcon {
44+ pub width : u32 ,
45+ pub height : u32 ,
46+ pub is_high_density : bool ,
47+ pub path : PathBuf ,
48+ }
49+
4250/// Bundles the project.
4351/// Returns a vector of PathBuf that shows where the DEB was created.
4452pub fn bundle_project ( settings : & Settings ) -> crate :: Result < Vec < PathBuf > > {
@@ -63,7 +71,7 @@ pub fn bundle_project(settings: &Settings) -> crate::Result<Vec<PathBuf>> {
6371 }
6472 let package_path = base_dir. join ( package_name) ;
6573
66- let data_dir = generate_data ( settings, & package_dir)
74+ let ( data_dir, _ ) = generate_data ( settings, & package_dir)
6775 . with_context ( || "Failed to build data folders and files" ) ?;
6876 // Generate control files.
6977 let control_dir = package_dir. join ( "control" ) ;
@@ -91,7 +99,10 @@ pub fn bundle_project(settings: &Settings) -> crate::Result<Vec<PathBuf>> {
9199}
92100
93101/// Generate the debian data folders and files.
94- pub fn generate_data ( settings : & Settings , package_dir : & Path ) -> crate :: Result < PathBuf > {
102+ pub fn generate_data (
103+ settings : & Settings ,
104+ package_dir : & Path ,
105+ ) -> crate :: Result < ( PathBuf , BTreeSet < DebIcon > ) > {
95106 // Generate data files.
96107 let data_dir = package_dir. join ( "data" ) ;
97108 let bin_dir = data_dir. join ( "usr/bin" ) ;
@@ -108,7 +119,8 @@ pub fn generate_data(settings: &Settings, package_dir: &Path) -> crate::Result<P
108119 . copy_binaries ( & bin_dir)
109120 . with_context ( || "Failed to copy external binaries" ) ?;
110121
111- generate_icon_files ( settings, & data_dir) . with_context ( || "Failed to create icon files" ) ?;
122+ let icons =
123+ generate_icon_files ( settings, & data_dir) . with_context ( || "Failed to create icon files" ) ?;
112124 generate_desktop_file ( settings, & data_dir) . with_context ( || "Failed to create desktop file" ) ?;
113125
114126 let use_bootstrapper = settings. deb ( ) . use_bootstrapper . unwrap_or_default ( ) ;
@@ -117,7 +129,7 @@ pub fn generate_data(settings: &Settings, package_dir: &Path) -> crate::Result<P
117129 . with_context ( || "Failed to generate bootstrap file" ) ?;
118130 }
119131
120- Ok ( data_dir)
132+ Ok ( ( data_dir, icons ) )
121133}
122134
123135/// Generates the bootstrap script file.
@@ -307,7 +319,7 @@ fn transfer_resource_files(settings: &Settings, data_dir: &Path) -> crate::Resul
307319}
308320
309321/// Generate the icon files and store them under the `data_dir`.
310- fn generate_icon_files ( settings : & Settings , data_dir : & Path ) -> crate :: Result < ( ) > {
322+ fn generate_icon_files ( settings : & Settings , data_dir : & Path ) -> crate :: Result < BTreeSet < DebIcon > > {
311323 let base_dir = data_dir. join ( "usr/share/icons/hicolor" ) ;
312324 let get_dest_path = |width : u32 , height : u32 , is_high_density : bool | {
313325 base_dir. join ( format ! (
@@ -318,7 +330,7 @@ fn generate_icon_files(settings: &Settings, data_dir: &Path) -> crate::Result<()
318330 settings. main_binary_name( )
319331 ) )
320332 } ;
321- let mut sizes = BTreeSet :: new ( ) ;
333+ let mut icons = BTreeSet :: new ( ) ;
322334 // Prefer PNG files.
323335 for icon_path in settings. icon_files ( ) {
324336 let icon_path = icon_path?;
@@ -329,10 +341,16 @@ fn generate_icon_files(settings: &Settings, data_dir: &Path) -> crate::Result<()
329341 let width = decoder. dimensions ( ) . 0 ;
330342 let height = decoder. dimensions ( ) . 1 ;
331343 let is_high_density = common:: is_retina ( & icon_path) ;
332- if !sizes. contains ( & ( width, height, is_high_density) ) {
333- sizes. insert ( ( width, height, is_high_density) ) ;
334- let dest_path = get_dest_path ( width, height, is_high_density) ;
335- common:: copy_file ( & icon_path, & dest_path) ?;
344+ let dest_path = get_dest_path ( width, height, is_high_density) ;
345+ let deb_icon = DebIcon {
346+ width,
347+ height,
348+ is_high_density,
349+ path : dest_path,
350+ } ;
351+ if !icons. contains ( & deb_icon) {
352+ common:: copy_file ( & icon_path, & deb_icon. path ) ?;
353+ icons. insert ( deb_icon) ;
336354 }
337355 }
338356 // Fall back to non-PNG files for any missing sizes.
@@ -346,28 +364,40 @@ fn generate_icon_files(settings: &Settings, data_dir: &Path) -> crate::Result<()
346364 let width = icon_type. screen_width ( ) ;
347365 let height = icon_type. screen_height ( ) ;
348366 let is_high_density = icon_type. pixel_density ( ) > 1 ;
349- if !sizes. contains ( & ( width, height, is_high_density) ) {
350- sizes. insert ( ( width, height, is_high_density) ) ;
351- let dest_path = get_dest_path ( width, height, is_high_density) ;
367+ let dest_path = get_dest_path ( width, height, is_high_density) ;
368+ let deb_icon = DebIcon {
369+ width,
370+ height,
371+ is_high_density,
372+ path : dest_path,
373+ } ;
374+ if !icons. contains ( & deb_icon) {
352375 let icon = icon_family. get_icon_with_type ( icon_type) ?;
353- icon. write_png ( common:: create_file ( & dest_path) ?) ?;
376+ icon. write_png ( common:: create_file ( & deb_icon. path ) ?) ?;
377+ icons. insert ( deb_icon) ;
354378 }
355379 }
356380 } else {
357381 let icon = image:: open ( & icon_path) ?;
358382 let ( width, height) = icon. dimensions ( ) ;
359383 let is_high_density = common:: is_retina ( & icon_path) ;
360- if !sizes. contains ( & ( width, height, is_high_density) ) {
361- sizes. insert ( ( width, height, is_high_density) ) ;
362- let dest_path = get_dest_path ( width, height, is_high_density) ;
384+ let dest_path = get_dest_path ( width, height, is_high_density) ;
385+ let deb_icon = DebIcon {
386+ width,
387+ height,
388+ is_high_density,
389+ path : dest_path,
390+ } ;
391+ if !icons. contains ( & deb_icon) {
363392 icon. write_to (
364- & mut common:: create_file ( & dest_path ) ?,
393+ & mut common:: create_file ( & deb_icon . path ) ?,
365394 image:: ImageOutputFormat :: Png ,
366395 ) ?;
396+ icons. insert ( deb_icon) ;
367397 }
368398 }
369399 }
370- Ok ( ( ) )
400+ Ok ( icons )
371401}
372402
373403/// Create an empty file at the given path, creating any parent directories as
0 commit comments