diff --git a/plugins-data.json b/plugins-data.json index 23fbc26..2c08da5 100644 --- a/plugins-data.json +++ b/plugins-data.json @@ -144,7 +144,7 @@ "status": "revived", "accent": "#F97316", "tagline": "An expandable server grid with DMs, smarter folders, and mark-all-read built in.", - "note": "Fork of kmmiio99o's ServerDrawer. One lookup (useMobileQuestDock) was missing an optional-chaining guard - if that lookup came back empty, the whole onLoad threw and every patch after it in the sequence never got applied, not just that one surface. Fixed, plus every patch call is now wrapped so a single bad lookup only skips its own surface. Folder options (auto-collapse, hide preview icons) are adapted from fres621's BetterFolders - its icon-hiding half patched a \"GuildContainer\" component that no longer exists anywhere in current Discord builds (confirmed against decompiled source), and only applied to the native server rail anyway, which this plugin already replaces - so it's been rebuilt as a feature of the drawer's own folders instead. Two more bugs fixed after real device testing: guild icons that never loaded (GuildStore lookups weren't reactive to guild data streaming in after connect, so most servers just showed a bare unread dot with no icon) and taps in the drawer not navigating anywhere (several lookups - transitionToGuild, the create/join action, the root nav ref - were resolved once at plugin-load time, before Discord had necessarily required those modules yet, same class of bug as YouBar+'s startup race). Both fixed; DMs also moved from a leftover sidebar icon into the drawer itself, and a mark-all-servers-as-read button was added.", + "note": "Fork of kmmiio99o's ServerDrawer. One lookup (useMobileQuestDock) was missing an optional-chaining guard - if that lookup came back empty, the whole onLoad threw and every patch after it in the sequence never got applied, not just that one surface. Fixed, plus every patch call is now wrapped so a single bad lookup only skips its own surface. Folder options (auto-collapse, hide preview icons) are adapted from fres621's BetterFolders - its icon-hiding half patched a \"GuildContainer\" component that no longer exists anywhere in current Discord builds (confirmed against decompiled source), and only applied to the native server rail anyway, which this plugin already replaces - so it's been rebuilt as a feature of the drawer's own folders instead. Two more bugs fixed after real device testing: guild icons that never loaded (GuildStore lookups weren't reactive to guild data streaming in after connect, so most servers just showed a bare unread dot with no icon) and taps in the drawer not navigating anywhere (several lookups - transitionToGuild, the create/join action, the root nav ref - were resolved once at plugin-load time, before Discord had necessarily required those modules yet, same class of bug as YouBar+'s startup race). Both fixed; DMs also moved from a leftover sidebar icon into the drawer itself, and a mark-all-servers-as-read button was added. Two more rounds after that: the Quest Dock hijack (10 separate internal lookups just to force it to render) used to be attempted once at onLoad, so if any single one of them wasn't registered in Metro yet the drawer could just silently not show up for the whole session - it now retries whatever hasn't landed on a fast 200ms interval until everything's applied. And mark-all-read was rebuilt to match Discord's own markGuildsAsRead action exactly (getSelectableChannelIds + getVocalChannelIds per guild, confirmed against decompiled source) instead of a less certain guild-enumeration method.", "howItWorks": "Hijacks the Quest Dock - the strip Discord normally uses for daily quests, right above the tab bar - and puts a grid of your servers there instead. Tap it to expand, tap a server to jump to it, long-press for the usual context menu (mark as read, notification settings, leave, etc). A + button opens Discord's own create/join-server modal. Optionally hides the left server rail down to a single DMs icon, since your servers now live in the drawer instead.", "features": [ "Tap-to-expand server grid with folders, unread badges, and mention counts", diff --git a/server-drawer/install/index.js b/server-drawer/install/index.js index 4353378..8998e85 100644 --- a/server-drawer/install/index.js +++ b/server-drawer/install/index.js @@ -1 +1 @@ -(function(Q,de,d,s,u,n,o,K,M,Y,Z,Je){"use strict";function Ke(e){const t=s.findByProps("useIsMobileQuestDockRendered");if(!t?.useIsMobileQuestDockRendered)return!1;const r=t.useIsMobileQuestDockRendered;return t.useIsMobileQuestDockRendered=function(...i){return r.apply(this,i),!0},e.push(function(){t.useIsMobileQuestDockRendered=r}),!0}function Ye(e){const t=s.findByProps("useIsMobileQuestDockRenderedBase");if(!t?.useIsMobileQuestDockRenderedBase)return!1;const r=t.useIsMobileQuestDockRenderedBase;return t.useIsMobileQuestDockRenderedBase=function(...i){return r.apply(this,i),!0},e.push(function(){t.useIsMobileQuestDockRenderedBase=r}),!0}function Ze(e){const t=s.findByProps("useMobileQuestDock");if(!t?.useMobileQuestDock)return!1;const r=t.useMobileQuestDock;return t.useMobileQuestDock=function(...i){return r.apply(this,i)||{id:"server-drawer",config:{quest_content_type:0,assets:{questBarHeroVideo:null,questBarHero:null},features:[]},userStatus:{enrolledAt:"2099-01-01",claimedAt:null},benefits:{rewards:[]},guildId:"0",tasks:[]}},e.push(function(){t.useMobileQuestDock=r}),!0}const $e="[ServerDrawer]";function Ne(e){const t=s.findByProps("getQuestAsset");if(!t?.getQuestAsset)return console.log($e,"WARN: getQuestAsset not found"),!1;const r=t.getQuestAsset;return t.getQuestAsset=function(...i){try{return r.apply(this,i)}catch{return{url:null,isAnimated:!1}}},e.push(function(){t.getQuestAsset=r}),!0}function k(e){let t,r=!1;return function(){if(r)return t;const i=e();return i!=null&&(t=i,r=!0),i??void 0}}const fe=s.findByStoreName("GuildStore"),et=s.findByProps("useStateFromStores"),tt=s.findByProps("colors","unsafe_rawColors")?.colors;function he({id:e,size:t=48}){const r=et?.useStateFromStores?.([fe],function(){return fe?.getGuild?.(e)},[e])??null;if(!r)return null;const i=t>=40?16:8;return r.icon?n.createElement(o.Image,{source:{uri:`https://cdn.discordapp.com/icons/${r.id}/${r.icon}.png?size=${t*2}`},style:{width:t,height:t,borderRadius:i}}):n.createElement(o.View,{style:[pe.fallback,{width:t,height:t,borderRadius:i,backgroundColor:tt?.BG_ACCENT??"#5865f2"}]},n.createElement(o.Text,{style:[pe.letter,{fontSize:Math.max(10,t*.4)}]},r.name?.split(" ").map(function(l){return l[0]}).join("").slice(0,2).toUpperCase()||"?"))}const pe=o.StyleSheet.create({fallback:{alignItems:"center",justifyContent:"center"},letter:{color:"#fff",fontWeight:"700"}}),nt=s.findByStoreName("ThemeStore"),ot=s.find(function(e){return e?.default?.internal?.resolveSemanticColor})?.default?.internal?.resolveSemanticColor??s.find(function(e){return e?.meta?.resolveSemanticColor})?.meta?.resolveSemanticColor??function(){};function rt(e,t=nt?.theme){if(e)try{return ot(t,e)}catch{return}}const ge=s.findByProps("TextStyleSheet")?.TextStyleSheet,ye=s.findByProps("triggerHapticFeedback","HapticFeedbackTypes");function L(e,t){return rt(e)??t}const I=12,$=12,me=42,N=220,be=4,A=16,O=20,Ce={tension:200,friction:20};function st({visible:e,items:t,title:r,anchorX:i,anchorY:l,onClose:a}){const{width:f,height:y}=o.Dimensions.get("window"),R=(r?$+20+be:0)+t.length*me;let C=i,m=l+48+10;C+N>f-I&&(C=f-N-I),Cy-I&&(m=l-R-10),m0?n.createElement(o.View,{style:T.outline},n.createElement(o.View,{style:T.badge},n.createElement(o.Text,{style:T.text},t>99?"99+":String(t)))):r?n.createElement(o.View,{style:T.dotOutline},n.createElement(o.View,{style:T.dot})):null:null}function ke({node:e,onPick:t}){const r=n.useRef(null),i=n.useRef(new o.Animated.Value(1)).current,l=function(){return o.Animated.spring(i,{toValue:.85,useNativeDriver:!0}).start()},a=function(){return o.Animated.spring(i,{toValue:1,useNativeDriver:!0}).start()},[f,y]=n.useState({visible:!1,items:[],title:"",x:0,y:0}),R=n.useCallback(function(){const D=e.id,c=it?.getGuild?.(D),p=s.find(function(b){return b?.default?.name==="getGuildsBarGuildMenuItems"})?.default??s.find(function(b){return typeof b?.default=="function"&&b.default.length<=2&&/guild/i.test(b.default.name??"")})?.default;if(!c||!p)return;const x=lt?.getGuildsTree?.()?.version,P=p(D,x);if(!P?.length)return;const F=r.current;F?.measure&&F.measure(function(b,le,ue,H,V,S){y({visible:!0,items:P.map(function(E){return{label:E.label??E.title??"Unknown",action:E.action,danger:E.variant==="destructive",iconSource:E.iconSource,IconComponent:E.IconComponent}}),title:c.name,x:V,y:S})})},[e.id]),C=n.useCallback(function(){Ee?.triggerHapticFeedback?.(Ee.HapticFeedbackTypes.IMPACT_MEDIUM),R()},[R]),m=e.id;return n.createElement(n.Fragment,null,n.createElement(o.Pressable,{onPressIn:l,onPressOut:a,onPress:function(){return t(m)},onLongPress:C,delayLongPress:500},n.createElement(o.View,{ref:r,style:we.outer,collapsable:!1},n.createElement(o.Animated.View,{style:[we.icon,{transform:[{scale:i}]}]},n.createElement(he,{id:m})),n.createElement(ut,{guildId:m}))),n.createElement(st,{visible:f.visible,items:f.items,title:f.title,anchorX:f.x,anchorY:f.y,onClose:function(){return y(function(D){return{...D,visible:!1}})}}))}const we=o.StyleSheet.create({outer:{width:_,height:_},icon:{width:_,height:_,borderRadius:16,overflow:"hidden"}}),T=o.StyleSheet.create({outline:{position:"absolute",bottom:-3,right:-3,minWidth:23,minHeight:23,borderRadius:12,backgroundColor:"#1a1a2e",alignItems:"center",justifyContent:"center"},badge:{minWidth:19,height:19,borderRadius:9,backgroundColor:"#ed4245",alignItems:"center",justifyContent:"center",paddingHorizontal:5},text:{color:"#fff",fontSize:10,fontWeight:"700",lineHeight:19},dotOutline:{position:"absolute",bottom:-2,right:-2,width:14,height:14,borderRadius:7,backgroundColor:"#1a1a2e",alignItems:"center",justifyContent:"center"},dot:{width:10,height:10,borderRadius:5,backgroundColor:"#ed4245"}}),at=s.findByProps("useStateFromStores");s.findByProps("colors","unsafe_rawColors")?.colors;const Be=s.findByStoreName("ExpandedGuildFolderStore");function ct(e){return at?.useStateFromStores?.([Be],function(){const t=Be?.getExpandedFolders?.();return t instanceof Set?t.has(e):!1},[e])??!1}const dt=s.findByProps("toggleGuildFolderExpand"),ft=s.findByProps("useStateFromStores"),Re=s.findByStoreName("GuildReadStateStore"),w=48,te=16,ht=[{top:6,left:6},{top:6,right:6},{bottom:6,left:6},{bottom:6,right:6}],De=Y.getAssetIDByName("FolderIcon");function Ie(e){return e==null?"#5865f2":`#${e.toString(16).padStart(6,"0")}`}function pt({node:e}){const t=ft?.useStateFromStores?.([Re],function(){let r=0;for(const i of e.children)r+=Re?.getMentionCount?.(i.id)??0;return r},[e.children])??0;return t>0?n.createElement(o.View,{style:oe.outline},n.createElement(o.View,{style:oe.badge},n.createElement(o.Text,{style:oe.text},t>99?"99+":String(t)))):null}function gt({node:e}){K.useProxy(d.storage);const t=Ie(e.color);return n.createElement(o.View,{style:v.outer},n.createElement(o.View,{style:[v.icon,{backgroundColor:t}]},d.storage.hideFolderIcons?n.createElement(o.View,{style:v.plainIcon},n.createElement(o.Image,{source:De,style:ne.folderImg,tintColor:"#fff"})):e.children.slice(0,4).map(function(r,i){return n.createElement(o.View,{key:r.id,style:[v.cell,ht[i]]},n.createElement(he,{id:r.id,size:te}))})),n.createElement(pt,{node:e}))}const v=o.StyleSheet.create({outer:{width:w,height:w},icon:{width:w,height:w,borderRadius:16,overflow:"hidden"},cell:{position:"absolute",width:te,height:te,borderRadius:8,overflow:"hidden"},plainIcon:{width:w,height:w,alignItems:"center",justifyContent:"center"}});function yt({children:e}){const t=n.useRef(new o.Animated.Value(0)).current;return n.useEffect(function(){o.Animated.timing(t,{toValue:1,duration:180,useNativeDriver:!0}).start()},[]),n.createElement(o.Animated.View,{style:{opacity:t}},e)}function mt({node:e,onPick:t}){const r=ct(e.id),i=function(){dt?.toggleGuildFolderExpand?.(e.id)};return r?n.createElement(n.Fragment,null,n.createElement(o.Pressable,{onPress:i},n.createElement(o.View,{style:[ne.openIcon,{backgroundColor:Ie(e.color)}]},n.createElement(o.Image,{source:De,style:ne.folderImg,tintColor:"#fff"}))),e.children.map(function(l){return n.createElement(yt,{key:l.id},n.createElement(ke,{node:l,onPick:t}))})):n.createElement(o.Pressable,{onPress:i},n.createElement(gt,{node:e}))}const ne=o.StyleSheet.create({openIcon:{width:w,height:w,borderRadius:16,alignItems:"center",justifyContent:"center"},folderImg:{width:24,height:24}}),oe=o.StyleSheet.create({outline:{position:"absolute",bottom:-3,right:-3,minWidth:23,minHeight:23,borderRadius:12,backgroundColor:"#1a1a2e",alignItems:"center",justifyContent:"center"},badge:{minWidth:19,height:19,borderRadius:9,backgroundColor:"#ed4245",alignItems:"center",justifyContent:"center",paddingHorizontal:5},text:{color:"#fff",fontSize:10,fontWeight:"700",lineHeight:19}}),W=48,bt=Y.getAssetIDByName("ChatIcon"),Pe=s.findByProps("triggerHapticFeedback","HapticFeedbackTypes"),Fe=s.findByProps("selectPrivateChannel"),Ct=s.findByName("SelectedChannelStore"),St=s.findByProps("useStateFromStores"),xe=s.findByProps("getGuildId"),Et=s.findByProps("colors","unsafe_rawColors")?.colors;function kt(){if(Pe?.triggerHapticFeedback(Pe.HapticFeedbackTypes.SOFT),Fe?.selectPrivateChannel){const e=Ct?.getLastSelectedChannelId?.();Fe.selectPrivateChannel(e)}}function wt(){const e=St?.useStateFromStores?.([xe],function(){return xe?.getGuildId?.()==null})??!1;return n.createElement(o.Pressable,{onPress:kt,style:Ae.outer},n.createElement(o.View,{style:[Ae.icon,{backgroundColor:e?Et?.BG_ACCENT??"#5865f2":"rgba(128,128,128,0.24)"}]},n.createElement(o.Image,{source:bt,style:{width:24,height:24,tintColor:"#fff"}})))}const Ae=o.StyleSheet.create({outer:{width:W,height:W},icon:{width:W,height:W,borderRadius:16,alignItems:"center",justifyContent:"center"}}),Te=48,Bt=Y.getAssetIDByName("CheckmarkLargeIcon"),Ge=s.findByStoreName("GuildStore"),He=s.findByStoreName("GuildChannelStore"),Rt=k(function(){return s.findByProps("triggerHapticFeedback","HapticFeedbackTypes")}),Dt=k(function(){return s.findByProps("bulkAck","ackChannel")}),It=k(function(){return s.findByProps("ReadStateTypes","UnreadSetting")?.ReadStateTypes});function Pt(){const e=Dt(),t=It();if(!e?.bulkAck||t?.CHANNEL==null||!Ge?.getGuilds||!He?.getChannels){Z.showToast("Couldn't find Discord's read-state action - this may be unavailable on your version.",void 0);return}const r=[];for(const i of Object.keys(Ge.getGuilds())){const l=He.getChannels(i)??{};for(const a of Object.values(l))if(Array.isArray(a))for(const f of a){const y=f?.channel;y?.id&&r.push({channelId:y.id,readStateType:t.CHANNEL,messageId:y.lastMessageId??null})}}if(r.length===0){Z.showToast("Nothing to mark as read.",void 0);return}e.bulkAck(r),Z.showToast(`Marked ${r.length} channel${r.length===1?"":"s"} as read`,void 0)}function Ft(){const e=n.useCallback(function(){const t=Rt();t?.triggerHapticFeedback?.(t.HapticFeedbackTypes.SOFT),Pt()},[]);return n.createElement(o.Pressable,{onPress:e,style:xt.outer},n.createElement(o.Image,{source:Bt,style:{width:24,height:24,tintColor:"#80848e"}}))}const xt=o.StyleSheet.create({outer:{width:Te,height:Te,alignItems:"center",justifyContent:"center"}}),At=s.findByProps("useStateFromStores"),Ve=s.findByStoreName("SortedGuildStore"),Tt=k(function(){return s.findByProps("getRootNavigationRef")}),Qe=k(function(){return s.findByProps("triggerHapticFeedback","HapticFeedbackTypes")}),Gt=k(function(){return s.findByProps("transitionToGuild")}),Ht=k(function(){return s.find(function(e){return typeof e?.handleCreateJoinGuildPress=="function"})}),Vt=k(function(){return s.find(function(e){return e?.CirclePlusIcon})?.CirclePlusIcon}),Qt=k(function(){return s.findByProps("colors","unsafe_rawColors")?.unsafe_rawColors}),Mt=s.find(function(e){return e?.QuestDockExternalCoordinationContext}),Me=Mt?.QuestDockExternalCoordinationContext,Le=s.find(function(e){return e?.QuestDockMode?.COLLAPSED!=null})?.QuestDockMode,U=48,z=6,Lt=12;function Ot(){const e=n.useRef(new o.Animated.Value(1)).current,t=n.useCallback(function(){o.Animated.spring(e,{toValue:.9,useNativeDriver:!0}).start()},[e]),r=n.useCallback(function(){o.Animated.spring(e,{toValue:1,useNativeDriver:!0}).start()},[e]),i=n.useCallback(function(){const f=Qe();f?.triggerHapticFeedback?.(f.HapticFeedbackTypes.SOFT),Ht()?.handleCreateJoinGuildPress?.()},[]),l=Vt(),a=Qt();return n.createElement(o.Pressable,{onPress:i,onPressIn:t,onPressOut:r},n.createElement(o.Animated.View,{style:[q.createJoin,{backgroundColor:a?.GREEN_360,transform:[{scale:e}]}]},l?n.createElement(l,{size:"md",color:a?.WHITE}):n.createElement(o.Text,{style:[q.createJoinFallback,{color:a?.WHITE}]},"+")))}function Oe({gestureContext:e}){const t=n.useCallback(function(c){const p=Qe();p?.triggerHapticFeedback?.(p.HapticFeedbackTypes.SOFT);const x=Gt();x?.transitionToGuild?x.transitionToGuild(c):Tt()?.getRootNavigationRef?.()?.navigate("guilds",{guildId:c})},[]),r=At?.useStateFromStores?.([Ve],function(){return(Ve?.getGuildsTree()?.root?.children||[]).filter(function(c){return c.type!=="root"})})??[],i=e?n.useContext(e):null,l=i?.minExpandedContentHeight,a=n.useCallback(function(c){if(!l)return;const p=c.nativeEvent.layout.height;l.get()!==p&&l.set(p)},[l]),f=(Me?n.useContext(Me):null)?.setRestingQuestDockMode,y=i?.questDockWrapperSpecs;n.useEffect(function(){if(!f||!Le||!y)return;const c=o.BackHandler.addEventListener("hardwareBackPress",function(){return(y.get()?.height??56)>80?(f(Le.COLLAPSED),!0):!1});return function(){return c.remove()}},[f,y]);const{width:R}=o.Dimensions.get("window"),C=Math.max(3,Math.floor((R-Lt*2+z)/(U+z))),m=C*U+(C-1)*z,D=Math.max(0,(R-m)/2);return n.createElement(o.View,{style:q.alignTop},n.createElement(o.View,{style:[q.grid,{paddingHorizontal:D,gap:z}],onLayout:a},n.createElement(wt,null),r.map(function(c){return c.type==="folder"?n.createElement(mt,{key:c.id,node:c,onPick:t}):n.createElement(ke,{key:c.id,node:c,onPick:t})}),n.createElement(Ot,null),n.createElement(Ft,null)))}const q=o.StyleSheet.create({alignTop:{flex:1,justifyContent:"flex-start",alignItems:"flex-start"},grid:{flexDirection:"row",flexWrap:"wrap",paddingTop:4,paddingBottom:16},createJoin:{width:U,height:U,borderRadius:16,alignItems:"center",justifyContent:"center"},createJoinFallback:{fontSize:28,fontWeight:"700",lineHeight:30}}),re=new Map;let B=null,X=!1;function _e(e,t,r){re.set(e,{replacement:t,extraProps:r})}function _t(e){if(X)return;if(B=u.React.createElement,!B){console.warn("[ServerDrawer] React.createElement is null, skipping patch");return}const t=function(r,i,...l){if(!B)return u.React.createElement(r,i,...l);const a=re.get(r);if(a){const f=a.extraProps?{...i,...a.extraProps}:i;return B.call(u.React,a.replacement,f,...l)}return B.call(u.React,r,i,...l)};Object.assign(t,B),u.React.createElement=t,X=!0,e.push(function(){X&&B&&(u.React.createElement=B,X=!1),re.clear()})}const se="[ServerDrawer]";let ie=null;function je(){return ie||(ie=s.find(function(e){return e?.QuestDockGestureContext})?.QuestDockGestureContext??null),ie}function jt(e){const t=s.find(function(i){return i?.type?.displayName==="QuestDockContentExpanded"||i?.type?.name==="QuestDockContentExpanded"});if(!t?.type)return console.log(se,"WARN: QuestDockContentExpanded not found (will retry)"),!1;const r=t.type;return _e(r,Oe,{gestureContext:je()}),t.type=function(){return u.React.createElement(Oe,{gestureContext:je()})},e.push(function(){t.type=r}),console.log(se,"PATCH: QuestDockContentExpanded replaced"),!0}function G(e,t){const r=s.find(function(a){return a?.type?.displayName===e||a?.type?.name===e});if(!r?.type)return console.log(se,`WARN: ${e} not found`),!1;const i=r.type,l=i;return r.type=function(){return null},l&&(Object.defineProperties(r.type,Object.getOwnPropertyDescriptors(l)),r.type.displayName=e),t.push(function(){r.type=i}),!0}const vt="[ServerDrawer]";function ve(){return null}function Wt(){const e=s.findByName("GuildsBar");if(e)return{default:e};let t=s.find(function(r){try{return r?.default?.type?.name==="GuildsBar"}catch{return!1}});return t?.default||(t=s.find(function(r){try{return r?.default?.displayName==="GuildsBar"}catch{return!1}}),t?.default)?t:null}function Ut(e){const t=Wt();if(!t?.default)return console.log(vt,"WARN: GuildsBar not found"),!1;const r=t.default;return _e(r,ve),t.default=function(){return n.createElement(ve)},t.default.displayName="GuildsBar",e.push(function(){t.default=r}),!0}function zt(e){const t=s.findByStoreName("ExpandedGuildFolderStore");if(!t?.getExpandedFolders)return!1;const r=function({folderId:i}){if(!d.storage.autoCollapseFolders||i==null)return;const l=t.getExpandedFolders();if(!(!(l instanceof Set)||!l.has(i)))for(const a of l)a!==i&&u.FluxDispatcher.dispatch({type:"TOGGLE_GUILD_FOLDER_EXPAND",folderId:a})};return u.FluxDispatcher.subscribe("TOGGLE_GUILD_FOLDER_EXPAND",r),e.push(function(){return u.FluxDispatcher.unsubscribe("TOGGLE_GUILD_FOLDER_EXPAND",r)}),!0}const{ScrollView:qt,View:Xt}=u.ReactNative;function Jt({children:e}){return u.React.createElement(qt,{style:{flex:1}},e,u.React.createElement(Xt,{style:{height:24}}))}const{View:Kt,Text:Yt}=u.ReactNative;function We({children:e,style:t}){return u.React.createElement(Kt,{style:[{marginHorizontal:16,marginVertical:8,padding:10,borderRadius:8,borderWidth:1,borderColor:"rgba(128,128,128,0.25)"},t]},u.React.createElement(Yt,{style:{fontSize:12.5,lineHeight:18,opacity:.75}},e))}const{FormSection:Ue,FormSwitchRow:J}=Je.Forms;function Zt(){return K.useProxy(d.storage),u.React.createElement(Jt,null,u.React.createElement(We,null,"Server Drawer takes over the Quest Dock (the strip above the tab bar) to show your servers as a grid instead - tap to expand, long-press a server for its usual context menu, the chat bubble jumps to DMs, the + button creates or joins a server through Discord's own modal, and the check button marks every channel in every server as read."),u.React.createElement(Ue,{title:"Layout"},u.React.createElement(J,{label:"Hide the left server rail",subLabel:"Your servers and DMs already live in the drawer, so the rail is redundant",value:d.storage.hideGuildsBar!==!1,onValueChange:function(e){d.storage.hideGuildsBar=e,Xe()}}),u.React.createElement(J,{label:"Unread badges",subLabel:"Show mention counts and unread dots on server icons in the drawer",value:d.storage.showUnreadBadges!==!1,onValueChange:function(e){d.storage.showUnreadBadges=e}})),u.React.createElement(Ue,{title:"Folders"},u.React.createElement(J,{label:"Auto-collapse other folders",subLabel:"Opening a folder collapses any other folder that was already open",value:!!d.storage.autoCollapseFolders,onValueChange:function(e){d.storage.autoCollapseFolders=e}}),u.React.createElement(J,{label:"Hide icons in collapsed folders",subLabel:"Show a plain folder icon instead of a 4-server preview",value:!!d.storage.hideFolderIcons,onValueChange:function(e){d.storage.hideFolderIcons=e}})),u.React.createElement(We,null,"The folder options above are ported from fres621's BetterFolders - its other half (hiding icons in the native left server rail) patched a component that no longer exists in current Discord builds, so it's been rebuilt here instead, where it actually applies to what you see."))}let h=[];function g(e,t){try{return t()}catch(r){return de.logger.error(`[ServerDrawer] "${e}" patch threw, skipping: ${r}`),!1}}function ze(){const e=[];_t(h),g("questDockRender",function(){return Ke(h)})&&e.push("questDockRender"),g("questDockBase",function(){return Ye(h)})&&e.push("questDockBase"),g("mobileQuestDock",function(){return Ze(h)})&&e.push("mobileQuestDock"),g("getQuestAsset",function(){return Ne(h)})&&e.push("getQuestAsset"),g("expanded",function(){return jt(h)})&&e.push("expanded"),g("collapsed",function(){return G("QuestDockContentCollapsed",h)})&&e.push("collapsed"),g("enrolledHeader",function(){return G("QuestDockEnrolledHeader",h)})&&e.push("enrolledHeader"),g("unenrolledHeader",function(){return G("QuestDockUnenrolledHeader",h)})&&e.push("unenrolledHeader"),g("enrolledBody",function(){return G("QuestDockEnrolledBody",h)})&&e.push("enrolledBody"),g("unenrolledBody",function(){return G("QuestDockUnenrolledBody",h)})&&e.push("unenrolledBody"),d.storage.hideGuildsBar&&g("hideGuildsBar",function(){return Ut(h)})&&e.push("hideGuildsBar"),g("autoCollapseFolders",function(){return zt(h)})&&e.push("autoCollapseFolders"),de.logger.log(`[ServerDrawer] onLoad done - ${e.length}/12 patches applied (${e.join(", ")||"none"})`)}function qe(){for(const e of h)try{e()}catch{}h=[]}function Xe(){qe(),ze()}var $t={onLoad:function(){d.storage.hideGuildsBar??=!0,d.storage.showUnreadBadges??=!0,d.storage.autoCollapseFolders??=!1,d.storage.hideFolderIcons??=!1,ze()},onUnload:function(){return qe()},settings:Zt};return Q.default=$t,Q.restart=Xe,Object.defineProperty(Q,"__esModule",{value:!0}),Q})({},vendetta,vendetta.plugin,vendetta.metro,vendetta.metro.common,window.React,vendetta.metro.common.ReactNative,vendetta.storage,vendetta.ui,vendetta.ui.assets,vendetta.ui.toasts,vendetta.ui.components); +(function(Q,Z,f,i,a,n,o,$,M,N,v,Xe){"use strict";function Je(e){const t=i.findByProps("useIsMobileQuestDockRendered");if(!t?.useIsMobileQuestDockRendered)return!1;const r=t.useIsMobileQuestDockRendered;return t.useIsMobileQuestDockRendered=function(...s){return r.apply(this,s),!0},e.push(function(){t.useIsMobileQuestDockRendered=r}),!0}function Ke(e){const t=i.findByProps("useIsMobileQuestDockRenderedBase");if(!t?.useIsMobileQuestDockRenderedBase)return!1;const r=t.useIsMobileQuestDockRenderedBase;return t.useIsMobileQuestDockRenderedBase=function(...s){return r.apply(this,s),!0},e.push(function(){t.useIsMobileQuestDockRenderedBase=r}),!0}function Ye(e){const t=i.findByProps("useMobileQuestDock");if(!t?.useMobileQuestDock)return!1;const r=t.useMobileQuestDock;return t.useMobileQuestDock=function(...s){return r.apply(this,s)||{id:"server-drawer",config:{quest_content_type:0,assets:{questBarHeroVideo:null,questBarHero:null},features:[]},userStatus:{enrolledAt:"2099-01-01",claimedAt:null},benefits:{rewards:[]},guildId:"0",tasks:[]}},e.push(function(){t.useMobileQuestDock=r}),!0}const Ze="[ServerDrawer]";function $e(e){const t=i.findByProps("getQuestAsset");if(!t?.getQuestAsset)return console.log(Ze,"WARN: getQuestAsset not found"),!1;const r=t.getQuestAsset;return t.getQuestAsset=function(...s){try{return r.apply(this,s)}catch{return{url:null,isAnimated:!1}}},e.push(function(){t.getQuestAsset=r}),!0}function E(e){let t,r=!1;return function(){if(r)return t;const s=e();return s!=null&&(t=s,r=!0),s??void 0}}const he=i.findByStoreName("GuildStore"),Ne=i.findByProps("useStateFromStores"),et=i.findByProps("colors","unsafe_rawColors")?.colors;function ge({id:e,size:t=48}){const r=Ne?.useStateFromStores?.([he],function(){return he?.getGuild?.(e)},[e])??null;if(!r)return null;const s=t>=40?16:8;return r.icon?n.createElement(o.Image,{source:{uri:`https://cdn.discordapp.com/icons/${r.id}/${r.icon}.png?size=${t*2}`},style:{width:t,height:t,borderRadius:s}}):n.createElement(o.View,{style:[pe.fallback,{width:t,height:t,borderRadius:s,backgroundColor:et?.BG_ACCENT??"#5865f2"}]},n.createElement(o.Text,{style:[pe.letter,{fontSize:Math.max(10,t*.4)}]},r.name?.split(" ").map(function(l){return l[0]}).join("").slice(0,2).toUpperCase()||"?"))}const pe=o.StyleSheet.create({fallback:{alignItems:"center",justifyContent:"center"},letter:{color:"#fff",fontWeight:"700"}}),tt=i.findByStoreName("ThemeStore"),nt=i.find(function(e){return e?.default?.internal?.resolveSemanticColor})?.default?.internal?.resolveSemanticColor??i.find(function(e){return e?.meta?.resolveSemanticColor})?.meta?.resolveSemanticColor??function(){};function rt(e,t=tt?.theme){if(e)try{return nt(t,e)}catch{return}}const ye=i.findByProps("TextStyleSheet")?.TextStyleSheet,me=i.findByProps("triggerHapticFeedback","HapticFeedbackTypes");function L(e,t){return rt(e)??t}const I=12,ee=12,be=42,te=220,Se=4,A=16,O=20,Ce={tension:200,friction:20};function ot({visible:e,items:t,title:r,anchorX:s,anchorY:l,onClose:u}){const{width:d,height:R}=o.Dimensions.get("window"),B=(r?ee+20+Se:0)+t.length*be;let b=s,p=l+48+10;b+te>d-I&&(b=d-te-I),bR-I&&(p=l-B-10),p0?n.createElement(o.View,{style:T.outline},n.createElement(o.View,{style:T.badge},n.createElement(o.Text,{style:T.text},t>99?"99+":String(t)))):r?n.createElement(o.View,{style:T.dotOutline},n.createElement(o.View,{style:T.dot})):null:null}function we({node:e,onPick:t}){const r=n.useRef(null),s=n.useRef(new o.Animated.Value(1)).current,l=function(){return o.Animated.spring(s,{toValue:.85,useNativeDriver:!0}).start()},u=function(){return o.Animated.spring(s,{toValue:1,useNativeDriver:!0}).start()},[d,R]=n.useState({visible:!1,items:[],title:"",x:0,y:0}),B=n.useCallback(function(){const D=e.id,c=st?.getGuild?.(D),g=i.find(function(y){return y?.default?.name==="getGuildsBarGuildMenuItems"})?.default??i.find(function(y){return typeof y?.default=="function"&&y.default.length<=2&&/guild/i.test(y.default.name??"")})?.default;if(!c||!g)return;const x=it?.getGuildsTree?.()?.version,P=g(D,x);if(!P?.length)return;const F=r.current;F?.measure&&F.measure(function(y,ue,ce,V,H,S){R({visible:!0,items:P.map(function(C){return{label:C.label??C.title??"Unknown",action:C.action,danger:C.variant==="destructive",iconSource:C.iconSource,IconComponent:C.IconComponent}}),title:c.name,x:H,y:S})})},[e.id]),b=n.useCallback(function(){ke?.triggerHapticFeedback?.(ke.HapticFeedbackTypes.IMPACT_MEDIUM),B()},[B]),p=e.id;return n.createElement(n.Fragment,null,n.createElement(o.Pressable,{onPressIn:l,onPressOut:u,onPress:function(){return t(p)},onLongPress:b,delayLongPress:500},n.createElement(o.View,{ref:r,style:Re.outer,collapsable:!1},n.createElement(o.Animated.View,{style:[Re.icon,{transform:[{scale:s}]}]},n.createElement(ge,{id:p})),n.createElement(lt,{guildId:p}))),n.createElement(ot,{visible:d.visible,items:d.items,title:d.title,anchorX:d.x,anchorY:d.y,onClose:function(){return R(function(D){return{...D,visible:!1}})}}))}const Re=o.StyleSheet.create({outer:{width:j,height:j},icon:{width:j,height:j,borderRadius:16,overflow:"hidden"}}),T=o.StyleSheet.create({outline:{position:"absolute",bottom:-3,right:-3,minWidth:23,minHeight:23,borderRadius:12,backgroundColor:"#1a1a2e",alignItems:"center",justifyContent:"center"},badge:{minWidth:19,height:19,borderRadius:9,backgroundColor:"#ed4245",alignItems:"center",justifyContent:"center",paddingHorizontal:5},text:{color:"#fff",fontSize:10,fontWeight:"700",lineHeight:19},dotOutline:{position:"absolute",bottom:-2,right:-2,width:14,height:14,borderRadius:7,backgroundColor:"#1a1a2e",alignItems:"center",justifyContent:"center"},dot:{width:10,height:10,borderRadius:5,backgroundColor:"#ed4245"}}),at=i.findByProps("useStateFromStores");i.findByProps("colors","unsafe_rawColors")?.colors;const Be=i.findByStoreName("ExpandedGuildFolderStore");function ut(e){return at?.useStateFromStores?.([Be],function(){const t=Be?.getExpandedFolders?.();return t instanceof Set?t.has(e):!1},[e])??!1}const ct=i.findByProps("toggleGuildFolderExpand"),dt=i.findByProps("useStateFromStores"),De=i.findByStoreName("GuildReadStateStore"),k=48,re=16,ft=[{top:6,left:6},{top:6,right:6},{bottom:6,left:6},{bottom:6,right:6}],Ie=N.getAssetIDByName("FolderIcon");function Pe(e){return e==null?"#5865f2":`#${e.toString(16).padStart(6,"0")}`}function ht({node:e}){const t=dt?.useStateFromStores?.([De],function(){let r=0;for(const s of e.children)r+=De?.getMentionCount?.(s.id)??0;return r},[e.children])??0;return t>0?n.createElement(o.View,{style:se.outline},n.createElement(o.View,{style:se.badge},n.createElement(o.Text,{style:se.text},t>99?"99+":String(t)))):null}function gt({node:e}){$.useProxy(f.storage);const t=Pe(e.color);return n.createElement(o.View,{style:z.outer},n.createElement(o.View,{style:[z.icon,{backgroundColor:t}]},f.storage.hideFolderIcons?n.createElement(o.View,{style:z.plainIcon},n.createElement(o.Image,{source:Ie,style:oe.folderImg,tintColor:"#fff"})):e.children.slice(0,4).map(function(r,s){return n.createElement(o.View,{key:r.id,style:[z.cell,ft[s]]},n.createElement(ge,{id:r.id,size:re}))})),n.createElement(ht,{node:e}))}const z=o.StyleSheet.create({outer:{width:k,height:k},icon:{width:k,height:k,borderRadius:16,overflow:"hidden"},cell:{position:"absolute",width:re,height:re,borderRadius:8,overflow:"hidden"},plainIcon:{width:k,height:k,alignItems:"center",justifyContent:"center"}});function pt({children:e}){const t=n.useRef(new o.Animated.Value(0)).current;return n.useEffect(function(){o.Animated.timing(t,{toValue:1,duration:180,useNativeDriver:!0}).start()},[]),n.createElement(o.Animated.View,{style:{opacity:t}},e)}function yt({node:e,onPick:t}){const r=ut(e.id),s=function(){ct?.toggleGuildFolderExpand?.(e.id)};return r?n.createElement(n.Fragment,null,n.createElement(o.Pressable,{onPress:s},n.createElement(o.View,{style:[oe.openIcon,{backgroundColor:Pe(e.color)}]},n.createElement(o.Image,{source:Ie,style:oe.folderImg,tintColor:"#fff"}))),e.children.map(function(l){return n.createElement(pt,{key:l.id},n.createElement(we,{node:l,onPick:t}))})):n.createElement(o.Pressable,{onPress:s},n.createElement(gt,{node:e}))}const oe=o.StyleSheet.create({openIcon:{width:k,height:k,borderRadius:16,alignItems:"center",justifyContent:"center"},folderImg:{width:24,height:24}}),se=o.StyleSheet.create({outline:{position:"absolute",bottom:-3,right:-3,minWidth:23,minHeight:23,borderRadius:12,backgroundColor:"#1a1a2e",alignItems:"center",justifyContent:"center"},badge:{minWidth:19,height:19,borderRadius:9,backgroundColor:"#ed4245",alignItems:"center",justifyContent:"center",paddingHorizontal:5},text:{color:"#fff",fontSize:10,fontWeight:"700",lineHeight:19}}),W=48,mt=N.getAssetIDByName("ChatIcon"),Fe=i.findByProps("triggerHapticFeedback","HapticFeedbackTypes"),xe=i.findByProps("selectPrivateChannel"),bt=i.findByName("SelectedChannelStore"),St=i.findByProps("useStateFromStores"),Ae=i.findByProps("getGuildId"),Ct=i.findByProps("colors","unsafe_rawColors")?.colors;function Et(){if(Fe?.triggerHapticFeedback(Fe.HapticFeedbackTypes.SOFT),xe?.selectPrivateChannel){const e=bt?.getLastSelectedChannelId?.();xe.selectPrivateChannel(e)}}function kt(){const e=St?.useStateFromStores?.([Ae],function(){return Ae?.getGuildId?.()==null})??!1;return n.createElement(o.Pressable,{onPress:Et,style:Te.outer},n.createElement(o.View,{style:[Te.icon,{backgroundColor:e?Ct?.BG_ACCENT??"#5865f2":"rgba(128,128,128,0.24)"}]},n.createElement(o.Image,{source:mt,style:{width:24,height:24,tintColor:"#fff"}})))}const Te=o.StyleSheet.create({outer:{width:W,height:W},icon:{width:W,height:W,borderRadius:16,alignItems:"center",justifyContent:"center"}}),Ge=48,wt=N.getAssetIDByName("CheckmarkLargeIcon"),Rt=i.findByStoreName("SortedGuildStore"),U=i.findByStoreName("GuildChannelStore"),Bt=i.findByStoreName("ChannelStore"),Dt=E(function(){return i.findByProps("triggerHapticFeedback","HapticFeedbackTypes")}),It=E(function(){return i.findByProps("bulkAck","ackChannel")}),Pt=E(function(){return i.findByProps("ReadStateTypes","UnreadSetting")?.ReadStateTypes});function Ft(){const e=(Rt?.getGuildsTree?.()?.root?.children??[]).filter(function(s){return s?.type!=="root"}),t=[],r=function(s){for(const l of s)l.type==="folder"?r(l.children??[]):l.id!=null&&t.push(String(l.id))};return r(e),t}function xt(){const e=It(),t=Pt();if(!e?.bulkAck||t?.CHANNEL==null||!U?.getSelectableChannelIds||!U?.getVocalChannelIds){v.showToast("Couldn't find Discord's read-state action - this may be unavailable on your version.",void 0);return}const r=Ft();if(r.length===0){v.showToast("Nothing to mark as read.",void 0);return}const s=[];for(const l of r){const u=[...U.getSelectableChannelIds(l)??[],...U.getVocalChannelIds(l)??[]];for(const d of u)s.push({channelId:d,readStateType:t.CHANNEL,messageId:Bt?.getChannel?.(d)?.lastMessageId??null})}if(s.length===0){v.showToast("Nothing to mark as read.",void 0);return}e.bulkAck(s),v.showToast(`Marked ${s.length} channel${s.length===1?"":"s"} as read`,void 0)}function At(){const e=n.useCallback(function(){const t=Dt();t?.triggerHapticFeedback?.(t.HapticFeedbackTypes.SOFT),xt()},[]);return n.createElement(o.Pressable,{onPress:e,style:Tt.outer},n.createElement(o.Image,{source:wt,style:{width:24,height:24,tintColor:"#80848e"}}))}const Tt=o.StyleSheet.create({outer:{width:Ge,height:Ge,alignItems:"center",justifyContent:"center"}}),Gt=i.findByProps("useStateFromStores"),Ve=i.findByStoreName("SortedGuildStore"),Vt=E(function(){return i.findByProps("getRootNavigationRef")}),He=E(function(){return i.findByProps("triggerHapticFeedback","HapticFeedbackTypes")}),Ht=E(function(){return i.findByProps("transitionToGuild")}),Qt=E(function(){return i.find(function(e){return typeof e?.handleCreateJoinGuildPress=="function"})}),Mt=E(function(){return i.find(function(e){return e?.CirclePlusIcon})?.CirclePlusIcon}),vt=E(function(){return i.findByProps("colors","unsafe_rawColors")?.unsafe_rawColors}),Lt=i.find(function(e){return e?.QuestDockExternalCoordinationContext}),Qe=Lt?.QuestDockExternalCoordinationContext,Me=i.find(function(e){return e?.QuestDockMode?.COLLAPSED!=null})?.QuestDockMode,q=48,X=6,Ot=12;function jt(){const e=n.useRef(new o.Animated.Value(1)).current,t=n.useCallback(function(){o.Animated.spring(e,{toValue:.9,useNativeDriver:!0}).start()},[e]),r=n.useCallback(function(){o.Animated.spring(e,{toValue:1,useNativeDriver:!0}).start()},[e]),s=n.useCallback(function(){const d=He();d?.triggerHapticFeedback?.(d.HapticFeedbackTypes.SOFT),Qt()?.handleCreateJoinGuildPress?.()},[]),l=Mt(),u=vt();return n.createElement(o.Pressable,{onPress:s,onPressIn:t,onPressOut:r},n.createElement(o.Animated.View,{style:[J.createJoin,{backgroundColor:u?.GREEN_360,transform:[{scale:e}]}]},l?n.createElement(l,{size:"md",color:u?.WHITE}):n.createElement(o.Text,{style:[J.createJoinFallback,{color:u?.WHITE}]},"+")))}function ve({gestureContext:e}){const t=n.useCallback(function(c){const g=He();g?.triggerHapticFeedback?.(g.HapticFeedbackTypes.SOFT);const x=Ht();x?.transitionToGuild?x.transitionToGuild(c):Vt()?.getRootNavigationRef?.()?.navigate("guilds",{guildId:c})},[]),r=Gt?.useStateFromStores?.([Ve],function(){return(Ve?.getGuildsTree()?.root?.children||[]).filter(function(c){return c.type!=="root"})})??[],s=e?n.useContext(e):null,l=s?.minExpandedContentHeight,u=n.useCallback(function(c){if(!l)return;const g=c.nativeEvent.layout.height;l.get()!==g&&l.set(g)},[l]),d=(Qe?n.useContext(Qe):null)?.setRestingQuestDockMode,R=s?.questDockWrapperSpecs;n.useEffect(function(){if(!d||!Me||!R)return;const c=o.BackHandler.addEventListener("hardwareBackPress",function(){return(R.get()?.height??56)>80?(d(Me.COLLAPSED),!0):!1});return function(){return c.remove()}},[d,R]);const{width:B}=o.Dimensions.get("window"),b=Math.max(3,Math.floor((B-Ot*2+X)/(q+X))),p=b*q+(b-1)*X,D=Math.max(0,(B-p)/2);return n.createElement(o.View,{style:J.alignTop},n.createElement(o.View,{style:[J.grid,{paddingHorizontal:D,gap:X}],onLayout:u},n.createElement(kt,null),r.map(function(c){return c.type==="folder"?n.createElement(yt,{key:c.id,node:c,onPick:t}):n.createElement(we,{key:c.id,node:c,onPick:t})}),n.createElement(jt,null),n.createElement(At,null)))}const J=o.StyleSheet.create({alignTop:{flex:1,justifyContent:"flex-start",alignItems:"flex-start"},grid:{flexDirection:"row",flexWrap:"wrap",paddingTop:4,paddingBottom:16},createJoin:{width:q,height:q,borderRadius:16,alignItems:"center",justifyContent:"center"},createJoinFallback:{fontSize:28,fontWeight:"700",lineHeight:30}}),ie=new Map;let w=null,K=!1;function Le(e,t,r){ie.set(e,{replacement:t,extraProps:r})}function _t(e){if(K)return;if(w=a.React.createElement,!w){console.warn("[ServerDrawer] React.createElement is null, skipping patch");return}const t=function(r,s,...l){if(!w)return a.React.createElement(r,s,...l);const u=ie.get(r);if(u){const d=u.extraProps?{...s,...u.extraProps}:s;return w.call(a.React,u.replacement,d,...l)}return w.call(a.React,r,s,...l)};Object.assign(t,w),a.React.createElement=t,K=!0,e.push(function(){K&&w&&(a.React.createElement=w,K=!1),ie.clear()})}const le="[ServerDrawer]";let ae=null;function Oe(){return ae||(ae=i.find(function(e){return e?.QuestDockGestureContext})?.QuestDockGestureContext??null),ae}function zt(e){const t=i.find(function(s){return s?.type?.displayName==="QuestDockContentExpanded"||s?.type?.name==="QuestDockContentExpanded"});if(!t?.type)return console.log(le,"WARN: QuestDockContentExpanded not found (will retry)"),!1;const r=t.type;return Le(r,ve,{gestureContext:Oe()}),t.type=function(){return a.React.createElement(ve,{gestureContext:Oe()})},e.push(function(){t.type=r}),console.log(le,"PATCH: QuestDockContentExpanded replaced"),!0}function G(e,t){const r=i.find(function(u){return u?.type?.displayName===e||u?.type?.name===e});if(!r?.type)return console.log(le,`WARN: ${e} not found`),!1;const s=r.type,l=s;return r.type=function(){return null},l&&(Object.defineProperties(r.type,Object.getOwnPropertyDescriptors(l)),r.type.displayName=e),t.push(function(){r.type=s}),!0}const Wt="[ServerDrawer]";function je(){return null}function Ut(){const e=i.findByName("GuildsBar");if(e)return{default:e};let t=i.find(function(r){try{return r?.default?.type?.name==="GuildsBar"}catch{return!1}});return t?.default||(t=i.find(function(r){try{return r?.default?.displayName==="GuildsBar"}catch{return!1}}),t?.default)?t:null}function qt(e){const t=Ut();if(!t?.default)return console.log(Wt,"WARN: GuildsBar not found"),!1;const r=t.default;return Le(r,je),t.default=function(){return n.createElement(je)},t.default.displayName="GuildsBar",e.push(function(){t.default=r}),!0}function Xt(e){const t=i.findByStoreName("ExpandedGuildFolderStore");if(!t?.getExpandedFolders)return!1;const r=function({folderId:s}){if(!f.storage.autoCollapseFolders||s==null)return;const l=t.getExpandedFolders();if(!(!(l instanceof Set)||!l.has(s)))for(const u of l)u!==s&&a.FluxDispatcher.dispatch({type:"TOGGLE_GUILD_FOLDER_EXPAND",folderId:u})};return a.FluxDispatcher.subscribe("TOGGLE_GUILD_FOLDER_EXPAND",r),e.push(function(){return a.FluxDispatcher.unsubscribe("TOGGLE_GUILD_FOLDER_EXPAND",r)}),!0}const{ScrollView:Jt,View:Kt}=a.ReactNative;function Yt({children:e}){return a.React.createElement(Jt,{style:{flex:1}},e,a.React.createElement(Kt,{style:{height:24}}))}const{View:Zt,Text:$t}=a.ReactNative;function _e({children:e,style:t}){return a.React.createElement(Zt,{style:[{marginHorizontal:16,marginVertical:8,padding:10,borderRadius:8,borderWidth:1,borderColor:"rgba(128,128,128,0.25)"},t]},a.React.createElement($t,{style:{fontSize:12.5,lineHeight:18,opacity:.75}},e))}const{FormSection:ze,FormSwitchRow:Y}=Xe.Forms;function Nt(){return $.useProxy(f.storage),a.React.createElement(Yt,null,a.React.createElement(_e,null,"Server Drawer takes over the Quest Dock (the strip above the tab bar) to show your servers as a grid instead - tap to expand, long-press a server for its usual context menu, the chat bubble jumps to DMs, the + button creates or joins a server through Discord's own modal, and the check button marks every channel in every server as read."),a.React.createElement(ze,{title:"Layout"},a.React.createElement(Y,{label:"Hide the left server rail",subLabel:"Your servers and DMs already live in the drawer, so the rail is redundant",value:f.storage.hideGuildsBar!==!1,onValueChange:function(e){f.storage.hideGuildsBar=e,qe()}}),a.React.createElement(Y,{label:"Unread badges",subLabel:"Show mention counts and unread dots on server icons in the drawer",value:f.storage.showUnreadBadges!==!1,onValueChange:function(e){f.storage.showUnreadBadges=e}})),a.React.createElement(ze,{title:"Folders"},a.React.createElement(Y,{label:"Auto-collapse other folders",subLabel:"Opening a folder collapses any other folder that was already open",value:!!f.storage.autoCollapseFolders,onValueChange:function(e){f.storage.autoCollapseFolders=e}}),a.React.createElement(Y,{label:"Hide icons in collapsed folders",subLabel:"Show a plain folder icon instead of a 4-server preview",value:!!f.storage.hideFolderIcons,onValueChange:function(e){f.storage.hideFolderIcons=e}})),a.React.createElement(_e,null,"The folder options above are ported from fres621's BetterFolders - its other half (hiding icons in the native left server rail) patched a component that no longer exists in current Discord builds, so it's been rebuilt here instead, where it actually applies to what you see."))}let h=[],m;function en(e,t){try{return t()}catch(r){return Z.logger.error(`[ServerDrawer] "${e}" patch threw, skipping: ${r}`),!1}}function We(){const e={questDockRender:function(){return Je(h)},questDockBase:function(){return Ke(h)},mobileQuestDock:function(){return Ye(h)},getQuestAsset:function(){return $e(h)},expanded:function(){return zt(h)},collapsed:function(){return G("QuestDockContentCollapsed",h)},enrolledHeader:function(){return G("QuestDockEnrolledHeader",h)},unenrolledHeader:function(){return G("QuestDockUnenrolledHeader",h)},enrolledBody:function(){return G("QuestDockEnrolledBody",h)},unenrolledBody:function(){return G("QuestDockUnenrolledBody",h)},autoCollapseFolders:function(){return Xt(h)},...f.storage.hideGuildsBar?{hideGuildsBar:function(){return qt(h)}}:{}};_t(h);const t=new Set(Object.keys(e)),r=new Set,s=function(){for(const l of t)en(l,e[l])&&(r.add(l),t.delete(l));t.size===0&&m&&(clearInterval(m),m=void 0)};if(s(),t.size>0){let l=0;m=setInterval(function(){s(),++l>=50&&m&&(clearInterval(m),m=void 0,t.size>0&&Z.logger.error(`[ServerDrawer] Gave up waiting on: ${[...t].join(", ")}`))},200)}Z.logger.log(`[ServerDrawer] onLoad: applied immediately - ${[...r].join(", ")||"none"}${t.size?`, still waiting on ${[...t].join(", ")}`:""}`)}function Ue(){m&&(clearInterval(m),m=void 0);for(const e of h)try{e()}catch{}h=[]}function qe(){Ue(),We()}var tn={onLoad:function(){f.storage.hideGuildsBar??=!0,f.storage.showUnreadBadges??=!0,f.storage.autoCollapseFolders??=!1,f.storage.hideFolderIcons??=!1,We()},onUnload:function(){return Ue()},settings:Nt};return Q.default=tn,Q.restart=qe,Object.defineProperty(Q,"__esModule",{value:!0}),Q})({},vendetta,vendetta.plugin,vendetta.metro,vendetta.metro.common,window.React,vendetta.metro.common.ReactNative,vendetta.storage,vendetta.ui,vendetta.ui.assets,vendetta.ui.toasts,vendetta.ui.components); diff --git a/server-drawer/install/manifest.json b/server-drawer/install/manifest.json index 474fcba..c6d99f8 100644 --- a/server-drawer/install/manifest.json +++ b/server-drawer/install/manifest.json @@ -1 +1 @@ -{"name":"ServerDrawer","description":"Replaces the Quest Dock with a server grid drawer above the YouBar - tap to expand, long-press a server for its context menu, plus a one-tap create/join button.","authors":[{"name":"everestmcarthur"},{"name":"kmmiio99o"},{"name":"fres"}],"main":"index.js","vendetta":{"icon":"ServerIcon"},"hash":"c4faaed1ba1d9ba08a56168d07c43f02b23af1ec7fdc449fb55de5eb37604ce9"} \ No newline at end of file +{"name":"ServerDrawer","description":"Replaces the Quest Dock with a server grid drawer above the YouBar - tap to expand, long-press a server for its context menu, plus a one-tap create/join button.","authors":[{"name":"everestmcarthur"},{"name":"kmmiio99o"},{"name":"fres"}],"main":"index.js","vendetta":{"icon":"ServerIcon"},"hash":"25b67abaaf23f7755deb448176f5f2d2fb41f87c355daaed375df15e73df82fd"} \ No newline at end of file