aboutsummaryrefslogtreecommitdiff
path: root/Hotline/macOS
diff options
context:
space:
mode:
authorDustin Mierau <dustin@mierau.me>2023-12-20 15:33:33 -0800
committerDustin Mierau <dustin@mierau.me>2023-12-20 15:33:33 -0800
commit5658209bd322449f4b54fa4a3047a485cc2ed32c (patch)
tree1eb82432ffb95873f1ff1b275e8eabfb74f1e14c /Hotline/macOS
parentcc19df82bab213bd628792e0b3eca8c2ee986506 (diff)
Add refresh button to Servers window. Fix styling on disclosure arrow. Remove icons from news list. Trying tooltips on some buttons.
Diffstat (limited to 'Hotline/macOS')
-rw-r--r--Hotline/macOS/FilesView.swift47
-rw-r--r--Hotline/macOS/NewsView.swift26
-rw-r--r--Hotline/macOS/ServerView.swift34
-rw-r--r--Hotline/macOS/TrackerView.swift138
4 files changed, 136 insertions, 109 deletions
diff --git a/Hotline/macOS/FilesView.swift b/Hotline/macOS/FilesView.swift
index 8482dd9..19dde94 100644
--- a/Hotline/macOS/FilesView.swift
+++ b/Hotline/macOS/FilesView.swift
@@ -18,19 +18,20 @@ struct FileView: View {
file.expanded.toggle()
}
} label: {
- Image(systemName: file.expanded ? "chevron.down" : "chevron.right")
- .renderingMode(.template)
- .frame(width: 10, height: 10)
- .aspectRatio(contentMode: .fit)
+ Text(Image(systemName: file.expanded ? "chevron.down" : "chevron.right"))
+ .bold()
+ .font(.system(size: 10))
.opacity(0.5)
}
.buttonStyle(.plain)
- .frame(width: 12)
+ .frame(width: 10)
+ .padding(.leading, 4)
}
else {
HStack {
- }.frame(width: 12)
+ }.frame(width: 10)
+ .padding(.leading, 4)
}
HStack(alignment: .center) {
if file.isFolder {
@@ -39,17 +40,18 @@ struct FileView: View {
else {
fileIcon(name: file.name)
.resizable()
- .scaledToFill()
+ .aspectRatio(contentMode: .fit)
+// .scaledToFill()
.frame(width: 16, height: 16)
}
}
.frame(width: 15)
Text(file.name).lineLimit(1).truncationMode(.tail)
+ if file.isFolder && loading {
+ ProgressView().controlSize(.small).padding([.leading, .trailing], 1)
+ }
Spacer()
if file.isFolder {
- if loading {
- ProgressView().controlSize(.small).padding(.trailing, 4)
- }
Text("^[\(file.fileSize) file](inflect: true)")
.foregroundStyle(.secondary)
.lineLimit(1)
@@ -154,6 +156,31 @@ struct FilesView: View {
.frame(maxWidth: .infinity)
}
}
+ .toolbar {
+ ToolbarItem(placement: .primaryAction) {
+ Button {
+ } label: {
+ Label("Download File", systemImage: "square.and.arrow.down")
+ }
+ .help("Download")
+ }
+
+ ToolbarItem(placement: .primaryAction) {
+ Button {
+ } label: {
+ Label("Preview File", systemImage: "eye")
+ }
+ .help("Preview")
+ }
+
+ ToolbarItem(placement: .primaryAction) {
+ Button {
+ } label: {
+ Label("Delete File", systemImage: "trash")
+ }
+ .help("Delete")
+ }
+ }
}
}
}
diff --git a/Hotline/macOS/NewsView.swift b/Hotline/macOS/NewsView.swift
index c59b446..3c35b1b 100644
--- a/Hotline/macOS/NewsView.swift
+++ b/Hotline/macOS/NewsView.swift
@@ -31,20 +31,26 @@ struct NewsItemView: View {
Button {
news.expanded.toggle()
} label: {
- Image(systemName: news.expanded ? "chevron.down" : "chevron.right")
- .renderingMode(.template)
- .frame(width: 10, height: 10)
- .aspectRatio(contentMode: .fit)
+ Text(Image(systemName: news.expanded ? "chevron.down" : "chevron.right"))
+ .bold()
+ .font(.system(size: 10))
.opacity(0.5)
+ .frame(alignment: .center)
}
.buttonStyle(.plain)
- .frame(width: 12)
+ .frame(width: 10)
+ .padding(.leading, 4)
}
- if news.type == .article {
- HStack(alignment: .center) {
- Image(systemName: "quote.opening")
- }
- .frame(width: 15)
+ else if news.type == .article {
+// HStack(alignment: .center) {
+// Text(Image(systemName: "quote.opening"))
+// .font(.system(size: 12))
+// .opacity(0.5)
+// .frame(alignment: .centerFirstTextBaseline)
+
+// Image(systemName: "quote.opening")
+// }
+// .frame(width: 14)
}
Text(news.name)
.fontWeight((news.type == .bundle || news.type == .category) ? .bold : .regular)
diff --git a/Hotline/macOS/ServerView.swift b/Hotline/macOS/ServerView.swift
index eca6f54..d858c6e 100644
--- a/Hotline/macOS/ServerView.swift
+++ b/Hotline/macOS/ServerView.swift
@@ -2,6 +2,7 @@ import SwiftUI
enum MenuItemType {
case banner
+ case progress
case chat
case news
case messageBoard
@@ -70,6 +71,7 @@ private func connectionStatusToProgress(status: HotlineClientStatus) -> Double {
struct ServerView: View {
@Environment(Hotline.self) private var model: Hotline
@State private var selectedCategoryId: MenuItem.ID?
+ @Environment(\.dismiss) var dismiss
let server: Server
@@ -89,8 +91,6 @@ struct ServerView: View {
var body: some View {
NavigationSplitView {
-// Divider()
-
List(selection: $selection) {
HStack {
@@ -111,9 +111,13 @@ struct ServerView: View {
.padding(.bottom, 16)
if model.status != .loggedIn {
- ProgressView(value: connectionStatusToProgress(status: model.status))
- .padding()
- .selectionDisabled()
+ HStack {
+ ProgressView(value: connectionStatusToProgress(status: model.status))
+ .padding()
+ }
+ .tag(MenuItem(name: "progress", image: "", type: .progress))
+ .frame(maxWidth: .infinity, minHeight: 60)
+ .selectionDisabled()
}
if model.status == .loggedIn {
@@ -137,8 +141,14 @@ struct ServerView: View {
Text("🙂")
.font(.headline)
if user.status.contains(.admin) {
- Text(user.name)
- .foregroundStyle(.red, .red.opacity(0.3))
+ if user.status.contains(.idle) {
+ Text(user.name)
+ .foregroundStyle(.red.opacity(0.5))
+ }
+ else {
+ Text(user.name)
+ .foregroundStyle(.red)
+ }
}
else if user.status.contains(.idle) {
Text(user.name)
@@ -155,11 +165,15 @@ struct ServerView: View {
}
}
}
+ .frame(minWidth: 200, idealWidth: 200)
} detail: {
if let selection = self.selection {
switch selection.type {
case .banner:
EmptyView()
+ case .progress
+ :
+ EmptyView()
case .chat:
ChatView()
case .news:
@@ -184,11 +198,15 @@ struct ServerView: View {
}
}
.onDisappear {
- print("DISCONNECTING FROM SERVER")
Task {
model.disconnect()
}
}
+ .onChange(of: model.status) {
+ if model.status == .disconnected {
+ dismiss()
+ }
+ }
}
}
diff --git a/Hotline/macOS/TrackerView.swift b/Hotline/macOS/TrackerView.swift
index d6473d9..02e0c5e 100644
--- a/Hotline/macOS/TrackerView.swift
+++ b/Hotline/macOS/TrackerView.swift
@@ -46,16 +46,6 @@ class TrackerItem: Identifiable, Hashable {
hasher.combine(self.id)
}
- func setServers(_ servers: [Server]) {
- var newServers: [TrackerItem] = []
-
- for server in servers {
- newServers.append(TrackerItem(server: server))
- }
-
- self.servers = newServers
- }
-
@MainActor
func loadServers() async {
guard
@@ -112,19 +102,29 @@ struct TrackerItemView: View {
Button {
item.expanded.toggle()
} label: {
- Image(systemName: item.expanded ? "chevron.down" : "chevron.right")
- .renderingMode(.template)
- .frame(width: 10, height: 10)
- .aspectRatio(contentMode: .fit)
+ Text(Image(systemName: item.expanded ? "chevron.down" : "chevron.right"))
+ .bold()
+ .font(.system(size: 10))
.opacity(0.5)
+ .frame(alignment: .center)
}
.buttonStyle(.plain)
- .frame(width: 12)
+ .frame(width: 10)
+ .padding(.leading, 4)
}
else {
HStack {
-
- }.frame(width: 12)
+ if let bookmark = item.bookmark, bookmark.type == .server {
+ Image(systemName: "bookmark.fill")
+ .resizable()
+ .renderingMode(.template)
+ .aspectRatio(contentMode: .fit)
+ .frame(width: 11, height: 11, alignment: .center)
+ .opacity(0.5)
+ }
+ }
+ .frame(width: 10)
+ .padding(.leading, 4)
}
HStack(alignment: .center) {
@@ -215,8 +215,10 @@ struct TrackerView: View {
// @AppStorage("servers", store: .standard)
var bookmarks: [TrackerBookmark] = [
TrackerBookmark(type: .server, name: "Bob Kiwi's House", address: "73.132.92.104"),
+ TrackerBookmark(type: .server, name: "System 7 Today", address: "158.174.146.146"),
TrackerBookmark(type: .tracker, name: "Featured Servers", address: "hltracker.com"),
- TrackerBookmark(type: .tracker, name: "Ubersoft", address: "hotline.ubersoft.org")
+ TrackerBookmark(type: .tracker, name: "Ubersoft", address: "hotline.ubersoft.org"),
+ TrackerBookmark(type: .tracker, name: "Preterhuman", address: "tracker.preterhuman.net"),
// "hltracker.com"
// "tracker.preterhuman.net"
@@ -227,23 +229,38 @@ struct TrackerView: View {
]
- private var client = HotlineTrackerClient()
-
@MainActor
func refresh() async {
-// self.servers = []
-//
-// let fetchedServers: [HotlineServer] = await self.client.fetchServers(address: "hltracker.com", port: Tracker.defaultPort)
-//
-// var newServers: [Server] = []
-//
-// for s in fetchedServers {
-// if let serverName = s.name {
-// newServers.append(Server(name: serverName, description: s.description, address: s.address, port: Int(s.port), users: Int(s.users)))
-// }
-// }
-//
-// self.servers = newServers
+
+ // When a tracker is selected, refresh only that tracker.
+ if
+ let selectedItem = selection,
+ let bookmark = selectedItem.bookmark,
+ bookmark.type == .tracker {
+ if !selectedItem.expanded {
+ selectedItem.expanded.toggle()
+ }
+ else {
+ await selectedItem.loadServers()
+ }
+ return
+ }
+
+ // Otherwise refresh/expand all trackers.
+ for server in self.servers {
+ if
+ let bookmark = server.bookmark,
+ bookmark.type == .tracker {
+ if !server.expanded {
+ server.expanded.toggle()
+ }
+ else {
+ Task {
+ await server.loadServers()
+ }
+ }
+ }
+ }
}
@State private var servers: [TrackerItem] = []
@@ -259,43 +276,6 @@ struct TrackerView: View {
@State private var connectDismissed = true
@State private var serverVisible = false
- func shouldDisplayDescription(server: Server) -> Bool {
- guard let desc = server.description else {
- return false
- }
-
- return desc.count > 0 && desc != server.name
- }
-
- func connectionStatusToProgress(status: HotlineClientStatus) -> Double {
- switch status {
- case .disconnected:
- return 0.0
- case .connecting:
- return 0.1
- case .connected:
- return 0.25
- case .loggingIn:
- return 0.5
- case .loggedIn:
- return 1.0
- }
- }
-
- func inverseLerp(lower: Double, upper: Double, v: Double) -> Double {
- return (v - lower) / (upper - lower)
- }
-
-// func updateServers() async {
- // "hltracker.com"
- // "tracker.preterhuman.net"
- // "hotline.ubersoft.org"
- // "tracked.nailbat.com"
- // "hotline.duckdns.org"
- // "tracked.agent79.org"
-// self.servers = await model.getServerList(tracker: "hltracker.com")
-// }
-
var body: some View {
List(self.servers, id: \.self, selection: $selection) { item in
TrackerItemView(item: item, depth: 0)
@@ -367,30 +347,26 @@ struct TrackerView: View {
} label: {
Label("Refresh", systemImage: "arrow.clockwise")
}
+ .help("Refresh")
}
ToolbarItem(placement: .primaryAction) {
Button {
- // Task {
- // initialLoadComplete = false
- // await updateServers()
- // initialLoadComplete = true
- // }
} label: {
- Label("Add Tracker", systemImage: "point.3.connected.trianglepath.dotted")
+ Label("Add Tracker", systemImage: "point.3.filled.connected.trianglepath.dotted")
}
+ .help("Add Tracker")
}
ToolbarItem(placement: .primaryAction) {
Button {
- // Task {
- // initialLoadComplete = false
- // await updateServers()
- // initialLoadComplete = true
- // }
+ Task {
+ await refresh()
+ }
} label: {
Label("Add Server", systemImage: "plus")
}
+ .help("Add Server")
}
}
.onAppear {