Generic (non-5e) ruleset mode + UI polish + combat switch fix #7
+27
-1
@@ -2330,6 +2330,7 @@ function AdminView({ userId }) {
|
||||
const { data: initialActiveInfo } = useFirestoreDocument(getPath.activeDisplay());
|
||||
|
||||
const [campaignsWithDetails, setCampaignsWithDetails] = useState([]);
|
||||
const [draggedCampaignId, setDraggedCampaignId] = useState(null);
|
||||
const [selectedCampaignId, setSelectedCampaignId] = useState(null);
|
||||
const encounterStartedRef = useRef(false);
|
||||
const encounterActiveRef = useRef(false);
|
||||
@@ -2390,6 +2391,10 @@ function AdminView({ userId }) {
|
||||
fetchDetails();
|
||||
} else if (campaignsData) {
|
||||
const sorted = [...campaignsData].sort((a, b) => {
|
||||
const ao = a.order ?? null, bo = b.order ?? null;
|
||||
if (ao !== null && bo !== null) return ao - bo;
|
||||
if (ao !== null) return -1;
|
||||
if (bo !== null) return 1;
|
||||
const at = a.createdAt || 0;
|
||||
const bt = b.createdAt || 0;
|
||||
if (at === bt) return (a.name || '').localeCompare(b.name || '');
|
||||
@@ -2433,6 +2438,7 @@ function AdminView({ userId }) {
|
||||
createdAt: new Date().toISOString(),
|
||||
players: [],
|
||||
ruleset: ruleset || '5e',
|
||||
order: (campaignsWithDetails || []).reduce((max, c) => Math.max(max, c.order ?? -1), -1) + 1,
|
||||
});
|
||||
|
||||
setShowCreateModal(false);
|
||||
@@ -2579,11 +2585,28 @@ function AdminView({ userId }) {
|
||||
? { backgroundImage: `url(${campaign.playerDisplayBackgroundUrl})` }
|
||||
: {};
|
||||
|
||||
const cardClasses = `h-40 flex flex-col justify-between rounded-lg shadow-md cursor-pointer transition-all relative overflow-hidden bg-cover bg-center ${selectedCampaignId === campaign.id ? 'ring-4 ring-amber-500' : ''} ${!campaign.playerDisplayBackgroundUrl ? 'bg-stone-800 hover:bg-stone-700' : 'hover:shadow-xl'}`;
|
||||
const cardClasses = `h-40 flex flex-col justify-between rounded-lg shadow-md cursor-grab transition-all relative overflow-hidden bg-cover bg-center ${selectedCampaignId === campaign.id ? 'ring-4 ring-amber-500' : ''} ${!campaign.playerDisplayBackgroundUrl ? 'bg-stone-800 hover:bg-stone-700' : 'hover:shadow-xl'} ${draggedCampaignId === campaign.id ? 'opacity-50 ring-2 ring-yellow-400' : ''}`;
|
||||
|
||||
return (
|
||||
<div
|
||||
key={campaign.id}
|
||||
draggable
|
||||
onDragStart={(e) => { setDraggedCampaignId(campaign.id); e.dataTransfer.effectAllowed = 'move'; }}
|
||||
onDragOver={(e) => { e.preventDefault(); e.dataTransfer.dropEffect = 'move'; }}
|
||||
onDrop={async (e) => {
|
||||
e.preventDefault();
|
||||
if (!db || !draggedCampaignId || draggedCampaignId === campaign.id) { setDraggedCampaignId(null); return; }
|
||||
const reordered = [...campaignsWithDetails];
|
||||
const fromIdx = reordered.findIndex(c => c.id === draggedCampaignId);
|
||||
const toIdx = reordered.findIndex(c => c.id === campaign.id);
|
||||
if (fromIdx === -1 || toIdx === -1) { setDraggedCampaignId(null); return; }
|
||||
const [moved] = reordered.splice(fromIdx, 1);
|
||||
reordered.splice(toIdx, 0, moved);
|
||||
const ops = reordered.map((c, i) => ({ type: 'update', path: getPath.campaign(c.id), data: { order: i } }));
|
||||
try { await storage.batchWrite(ops); } catch (err) {}
|
||||
setDraggedCampaignId(null);
|
||||
}}
|
||||
onDragEnd={() => setDraggedCampaignId(null)}
|
||||
onClick={() => {
|
||||
if (encounterStartedRef.current) {
|
||||
showToast('End or pause active encounter before switching campaigns.');
|
||||
@@ -2599,7 +2622,10 @@ function AdminView({ userId }) {
|
||||
className={`relative z-10 flex flex-col justify-between h-full ${campaign.playerDisplayBackgroundUrl ? 'bg-black bg-opacity-60 p-3' : 'p-4'}`}
|
||||
>
|
||||
<div>
|
||||
<div className="flex items-center gap-1">
|
||||
<ChevronsUpDown size={14} className="text-white/60 flex-shrink-0" title="Drag to reorder" />
|
||||
<h3 className="text-xl font-semibold text-white">{campaign.name}</h3>
|
||||
</div>
|
||||
<div className="text-xs text-stone-100 mt-1 space-x-3">
|
||||
<span className="inline-flex items-center">
|
||||
<Users size={12} className="mr-1" /> {campaign.characters?.length || 0} Characters
|
||||
|
||||
Reference in New Issue
Block a user