From a8dda17b9c5d1908b359d6dccd3ce1e6f0b32234 Mon Sep 17 00:00:00 2001 From: Reinhard Pointner Date: Wed, 6 Apr 2016 18:56:39 +0000 Subject: [PATCH] Add AutoDetectMatcher --- source/net/filebot/media/AutoDetection.java | 10 +-- source/net/filebot/resources/action.auto.png | Bin 0 -> 1218 bytes .../net/filebot/resources/action.auto@2x.png | Bin 0 -> 2513 bytes .../filebot/ui/rename/AutoDetectMatcher.java | 78 ++++++++++++++++++ source/net/filebot/ui/rename/RenamePanel.java | 5 +- 5 files changed, 87 insertions(+), 6 deletions(-) create mode 100644 source/net/filebot/resources/action.auto.png create mode 100644 source/net/filebot/resources/action.auto@2x.png create mode 100644 source/net/filebot/ui/rename/AutoDetectMatcher.java diff --git a/source/net/filebot/media/AutoDetection.java b/source/net/filebot/media/AutoDetection.java index 8abd8701..53660fe1 100644 --- a/source/net/filebot/media/AutoDetection.java +++ b/source/net/filebot/media/AutoDetection.java @@ -44,8 +44,8 @@ public class AutoDetection { private File[] files; private Locale locale; - public AutoDetection(Collection root, Locale locale) { - this.files = resolve(root.stream().map(FastFile::new), getSystemFilesFilter()).toArray(File[]::new); + public AutoDetection(Collection root, boolean resolve, Locale locale) { + this.files = (resolve ? resolve(root.stream().map(FastFile::new), getSystemFilesFilter()) : root.stream()).toArray(File[]::new); this.locale = locale; } @@ -135,10 +135,10 @@ public class AutoDetection { if (isMusic(f)) return group.music(f); - if (isEpisode(f)) - return group.series(getSeriesMatches(f, false)); // episode characteristics override movie characteristics (e.g. episodes in Movies folder) - if (isMovie(f)) + if (isMovie(f) && !isEpisode(f)) // episode characteristics override movie characteristics (e.g. episodes in Movies folder) return group.movie(getMovieMatches(f, false)); + if (isEpisode(f)) + return group.series(getSeriesMatches(f, false)); if (isAnime(f)) return group.anime(getSeriesMatches(f, true)); diff --git a/source/net/filebot/resources/action.auto.png b/source/net/filebot/resources/action.auto.png new file mode 100644 index 0000000000000000000000000000000000000000..640f890dae40532980d1b2e7b93c3916d0004fc8 GIT binary patch literal 1218 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`Y)RhkE**7r~Dz7=iaW$&qYRn}hYtKnSZ#n+s? zG$VAf0}oFXa*`{TJ#uk&*c&d%C6)12GmG|YdKFV#{Q2mcf9kA@B%e*>xRkqdg>caH zDyPONwb~6VldF$^kW|}$e)(@ni#tEA?6WnmT(kZ9(a$w2{gzwL4E2A{Bw@}N&!Kq! z-;XPuKP;YdH0L?h*^2xQb-WP!BP;)I{^q$WBBV5mcg8TC-jwUNJeZS(seOZ&*ZM1K zINMuUEx$Cq{rK|!ls9KiD;~}NE)la_$n%oRX?IEPx$CX}=54n=dZM`Yan-%T9CN|j z*;}4()vQ@NE&R*phXp$;8g^Z{KJRhh{q*+qxT#`6UKfL&`xwtYyOQD4s&1XDTfgn- z^JZPJ&`oXCJ!1_o>F)=sxo<^0Oj)qo=;Ev|f1B$H^|XzaEEL?|7Wy?t zFJB}bzab>ORjl7^i{17BukhuJow^)~5<9g*RWf*fy3CP%Q6)ZSkMR^;_GU-VX-{XJ zIpeeZ`fK0CQ`oKxm{}M?{+oLyxdin`E2hmkOI}?)RTqGW`8?bMGO0>KKe#_hWgR{HpwtILY#*b3I@iyhL$0Q z23Dpy=MP+(wo`PpG(DiR5*1Z5qt0Sc2LxX%^UIiJJ4_2+42~rLA>wEK6r-51+ NJYD@<);T3K0RYfJ;zv75b zDecT$Id>(+CV@;WHq!N(8Y9meO>?)p*Dp>JF_*XVgHkq#c>JqWv3+WDj)jE371`Z# zv4fT8Z-mh8f_U-ogj)uqCQG4>FE&;`rXSCRd%sLR=s<6&ZZ|*;0$ zvj0@_-ye6>{5rX{DZ)qxTK(lJ+ft!qbuM!Yks2swgLx9ZePH%=U6QWaSe>Maln0uq zb>5|hj_834ny9O*>yg^iR56#A-QdVbLa9Sli(UTseb=Wmf+DTS0HOiIc;ry~&l!KV+= z7d&!!t0AMU%P1ke_v_9VH10;(XEWW;<4e6-66Jdoe+`?vz2^W@v8b@{UUfC{TtGm& zgoK1LIR!CHi;{iRvo^`>zY1RM$q+KS6~&#qR2T5!m%FV{Jkz{6I#7&Lf>zJKWo9eC z@vkmxZf>^1VliYgtE8%Gbuuw=_pP+F%UzlJ^%d0V?mgT9R7>xLL-p{Zoo*6W%!@WA zlivM`GnMDburNN?eO&%FRxOHJlKOmSp?)PRh&w+zSWdDfM@6yQCYQhvNY|Ue!EpCf zmCI&FR8&>ji#cj)N;7m!j2GkHCC_4!mBRq@w#Z@7o;a*CN2~CfL-f?>TE1jA&Cj8s za-pfFBR3^*q+o-$0WLwQIV)MbrINjG<3@Jn9q@> zn{ug!ci*uY7bSrihgf9i0kp?$12MTs2oF;Br$3U3BX3+qAm2r%#42`Oa8D4q+diwI zp%L6aFkq2!>(-ys%Z>+8l<|bTJT*)KO52p_$h9$cZhL*)#d{#wn0anc6S?&jc3M@5 zk_cb1YS-KxoSiDghYECvto?N3Ic37EOmosr|Els^q`7+55@q04@_)~>{*;syBqSshWME)W0bpI~BG(DIea^z; zLz|nM=|HOotat6x8?hHEN@koCPl-8r*3HM|qz#qqcPYkn` zPbB(z%;@{R3Gs>S`}oX?Uh3^lqm#I-dX1MKWrVi_ z`HnY<_1N{BJ=_&i1G8dDiLNhBb4KUW3*9K|r&D|4K(ZbA?CcFfJ9oFIsMJa2)??Vl zSn)QRQM}XEa{D@*i>|D%(-Nz?#dCxJ(%LrIa4q-2%85$sTGkDHnIG z5;MnN?{A#AK6CHLla7yLj-1A=d1^*zbGu^!|C1Lyd-iO`w1y(V=sUNIQCn&2>=l&v zHBR|qynI^rBhmzJc?_T}c?mo)Krb#*-z7PfX0=qwxZ@2GP9bS`<)5GZ)? z;IbSMdJKl_Ge2b&*NP7-qxCNvXH#AZ3WDn zsiFvh-h5g+UF>vVCEReVwY7DB^5ll1r08xDp_j{>c)%Xy`{9C7MIKJUkoQy$kZw~3 z55IX+3)ycQ9UWbtL(u3EFtM~0EpqyJjw7Wr4fG0zD=@mtAh<1OU_@A25H`c*u}|dx z6`-fUOSd5z0eX6RU}NKpHqGgmB4L$+fSi?P{Igu*FLjZ_znXlJC))h>bGBj60s5Vk z2~>%D>I01FPo*U_=ImDQQ@bh05Zjw?-`4K>!rIES5G=L8V4fHC`Dy^YUzR4-)ztF# z0o<9FixbWOLjag>XlOv*nf{1MzR7a06{#3fq*Z*SRlO7(SBtxm_k4aS+*L-rc|e+y zSSG`@*hU>>h`%7T4D!UU#8kRMW>+JmfKS^+!cPKxK_&;J9hr?2Cg7hKU=SLB8cT~D zhf9l&vl8L2&Q%GIckc7_NDCD}nPC=rTL8?qknrJ-oRGdtub}S~y^dX4x+qKIP2Fvd z*NKi`stxgf;i@4P&LPBLl4l4Ba+bdUIxv_41P+J55d^qC8m5ER)rY|NH!!ADTFMV# z$BF(<@c}pt0@H!$zz90JXdNUPj`|Mx%o&;f4-h~;>*r1X7vOh*6JQ2tT^JhnZwHc7 zC7KWT>_o!)5lMkm65tyWLP0~J-+K9lk%;7g0CFHzn;h%|_5W_6LcQn^swY%e8wLfF zgTem~fwi>9LUpv^P`4CA;*X5q`)q1hBR^fhjTbi1`PZ5^UW7 literal 0 HcmV?d00001 diff --git a/source/net/filebot/ui/rename/AutoDetectMatcher.java b/source/net/filebot/ui/rename/AutoDetectMatcher.java new file mode 100644 index 00000000..7bdcb352 --- /dev/null +++ b/source/net/filebot/ui/rename/AutoDetectMatcher.java @@ -0,0 +1,78 @@ + +package net.filebot.ui.rename; + +import static java.util.Collections.*; +import static java.util.stream.Collectors.*; +import static net.filebot.Logging.*; +import static net.filebot.WebServices.*; + +import java.awt.Component; +import java.io.File; +import java.util.ArrayList; +import java.util.Collection; +import java.util.List; +import java.util.Locale; +import java.util.Map; +import java.util.Map.Entry; +import java.util.Objects; +import java.util.Set; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.logging.Level; + +import net.filebot.media.AutoDetection; +import net.filebot.media.AutoDetection.Group; +import net.filebot.media.AutoDetection.Type; +import net.filebot.similarity.Match; +import net.filebot.web.SortOrder; + +class AutoDetectMatcher implements AutoCompleteMatcher { + + private AutoCompleteMatcher movie = new MovieMatcher(TheMovieDB); + private AutoCompleteMatcher episode = new EpisodeListMatcher(TheTVDB, false); + private AutoCompleteMatcher anime = new EpisodeListMatcher(AniDB, false); + private AutoCompleteMatcher music = new MusicMatcher(MediaInfoID3, AcoustID); + + @Override + public List> match(Collection files, boolean strict, SortOrder order, Locale locale, boolean autodetection, Component parent) throws Exception { + Map> groups = new AutoDetection(files, false, locale).group(); + + // can't use parallel stream because default fork/join pool doesn't play well with the security manager + ExecutorService executor = Executors.newWorkStealingPool(); + List> result = new ArrayList>(); + + groups.entrySet().stream().collect(toMap(Entry::getKey, it -> { + return executor.submit(() -> match(it.getKey(), it.getValue(), strict, order, locale, autodetection, parent)); + })).forEach((group, matches) -> { + try { + result.addAll(matches.get()); + } catch (Exception e) { + log.log(Level.WARNING, "Failed to process group: " + group, e); + } + }); + + executor.shutdown(); + return result; + } + + private List> match(Group group, Collection files, boolean strict, SortOrder order, Locale locale, boolean autodetection, Component parent) throws Exception { + if (group.values().stream().filter(Objects::nonNull).count() == 1) { + for (Type key : group.keySet()) { + switch (key) { + case Movie: + return movie.match(files, strict, order, locale, autodetection, parent); + case Series: + return episode.match(files, strict, order, locale, autodetection, parent); + case Anime: + return anime.match(files, strict, order, locale, autodetection, parent); + case Music: + return music.match(files, strict, order, locale, autodetection, parent); + } + } + } + + debug.info(format("Ignore group: %s", group)); + return emptyList(); + } + +} diff --git a/source/net/filebot/ui/rename/RenamePanel.java b/source/net/filebot/ui/rename/RenamePanel.java index d610d380..21ca55b3 100644 --- a/source/net/filebot/ui/rename/RenamePanel.java +++ b/source/net/filebot/ui/rename/RenamePanel.java @@ -426,7 +426,7 @@ public class RenamePanel extends JComponent { } protected ActionPopup createFetchPopup() { - final ActionPopup actionPopup = new ActionPopup("Fetch & Match Data", ResourceManager.getIcon("action.fetch")); + ActionPopup actionPopup = new ActionPopup("Fetch & Match Data", ResourceManager.getIcon("action.fetch")); actionPopup.addDescription(new JLabel("Episode Mode:")); @@ -449,6 +449,9 @@ public class RenamePanel extends JComponent { actionPopup.add(new AutoCompleteAction(it.getName(), it.getIcon(), new MusicMatcher(it))); } + actionPopup.addDescription(new JLabel("Smart Mode:")); + actionPopup.add(new AutoCompleteAction("Autodetect", ResourceManager.getIcon("action.auto"), new AutoDetectMatcher())); + actionPopup.addSeparator(); actionPopup.addDescription(new JLabel("Options:"));