added season edits
This commit is contained in:
@@ -146,7 +146,7 @@ func formatDateLong(t time.Time) string {
|
||||
func formatDuration(start, end time.Time) string {
|
||||
days := int(end.Sub(start).Hours() / 24)
|
||||
if days == 0 {
|
||||
return "Same day"
|
||||
return "1 day"
|
||||
} else if days == 1 {
|
||||
return "1 day"
|
||||
} else if days < 7 {
|
||||
|
||||
177
internal/view/seasonsview/edit_form.templ
Normal file
177
internal/view/seasonsview/edit_form.templ
Normal file
@@ -0,0 +1,177 @@
|
||||
package seasonsview
|
||||
|
||||
import "git.haelnorr.com/h/oslstats/internal/view/datepicker"
|
||||
import "git.haelnorr.com/h/oslstats/internal/db"
|
||||
import "time"
|
||||
|
||||
templ EditForm(season *db.Season) {
|
||||
{{
|
||||
// Format dates for display (DD/MM/YYYY)
|
||||
startDateStr := formatDateInput(season.StartDate)
|
||||
endDateStr := ""
|
||||
if !season.EndDate.IsZero() {
|
||||
endDateStr = formatDateInput(season.EndDate.Time)
|
||||
}
|
||||
finalsStartDateStr := ""
|
||||
if !season.FinalsStartDate.IsZero() {
|
||||
finalsStartDateStr = formatDateInput(season.FinalsStartDate.Time)
|
||||
}
|
||||
finalsEndDateStr := ""
|
||||
if !season.FinalsEndDate.IsZero() {
|
||||
finalsEndDateStr = formatDateInput(season.FinalsEndDate.Time)
|
||||
}
|
||||
}}
|
||||
<form
|
||||
hx-post={ "/seasons/" + season.ShortName + "/edit" }
|
||||
hx-swap="none"
|
||||
x-data={ templ.JSFuncCall("editSeasonFormData", startDateStr, endDateStr, finalsStartDateStr, finalsEndDateStr).CallInline }
|
||||
@submit="handleSubmit()"
|
||||
@htmx:after-request="if(submitTimeout) clearTimeout(submitTimeout); const redirect = $event.detail.xhr.getResponseHeader('HX-Redirect'); if(redirect) return; if(!$event.detail.successful) { isSubmitting=false; buttonText='Save Changes'; generalError='An error occurred. Please try again.'; }"
|
||||
>
|
||||
<script>
|
||||
function editSeasonFormData(
|
||||
initialStart,
|
||||
initialEnd,
|
||||
initialFinalsStart,
|
||||
initialFinalsEnd,
|
||||
) {
|
||||
return {
|
||||
canSubmit: true,
|
||||
buttonText: "Save Changes",
|
||||
// Date validation state
|
||||
startDateError: "",
|
||||
startDateIsEmpty: initialStart === "",
|
||||
endDateError: "",
|
||||
finalsStartDateError: "",
|
||||
finalsEndDateError: "",
|
||||
// Form state
|
||||
isSubmitting: false,
|
||||
generalError: "",
|
||||
submitTimeout: null,
|
||||
// Reset date errors
|
||||
resetStartDateErr() {
|
||||
this.startDateError = "";
|
||||
},
|
||||
resetEndDateErr() {
|
||||
this.endDateError = "";
|
||||
},
|
||||
resetFinalsStartDateErr() {
|
||||
this.finalsStartDateError = "";
|
||||
},
|
||||
resetFinalsEndDateErr() {
|
||||
this.finalsEndDateError = "";
|
||||
},
|
||||
// Check if form can be submitted
|
||||
updateCanSubmit() {
|
||||
this.canSubmit = !this.startDateIsEmpty;
|
||||
},
|
||||
// Handle form submission
|
||||
handleSubmit() {
|
||||
this.isSubmitting = true;
|
||||
this.buttonText = "Saving...";
|
||||
this.generalError = "";
|
||||
// Set timeout for 10 seconds
|
||||
this.submitTimeout = setTimeout(() => {
|
||||
this.isSubmitting = false;
|
||||
this.buttonText = "Save Changes";
|
||||
this.generalError = "Request timed out. Please try again.";
|
||||
}, 10000);
|
||||
},
|
||||
};
|
||||
}
|
||||
</script>
|
||||
<div class="bg-mantle border border-surface1 rounded-lg">
|
||||
<!-- Header Section -->
|
||||
<div class="bg-surface0 border-b border-surface1 px-6 py-8 rounded-t-lg">
|
||||
<div class="flex flex-col sm:flex-row justify-between items-start sm:items-center gap-4">
|
||||
<div>
|
||||
<h1 class="text-4xl font-bold text-text mb-2">Edit { season.Name }</h1>
|
||||
<span class="inline-block bg-blue px-3 py-1 rounded-full text-sm font-semibold text-mantle">
|
||||
{ season.ShortName }
|
||||
</span>
|
||||
</div>
|
||||
<div class="flex gap-2">
|
||||
<button
|
||||
x-bind:disabled="!canSubmit || isSubmitting"
|
||||
x-text="buttonText"
|
||||
type="submit"
|
||||
class="rounded-lg px-4 py-2 hover:cursor-pointer text-center
|
||||
bg-blue hover:bg-blue/75 text-mantle transition font-semibold
|
||||
disabled:bg-blue/40 disabled:cursor-not-allowed"
|
||||
></button>
|
||||
<a
|
||||
href={ templ.SafeURL("/seasons/" + season.ShortName) }
|
||||
class="rounded-lg px-4 py-2 hover:cursor-pointer text-center
|
||||
bg-surface1 hover:bg-surface2 text-text transition"
|
||||
>
|
||||
Cancel
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<!-- Information Grid -->
|
||||
<div class="grid grid-cols-1 md:grid-cols-2 gap-6 p-6">
|
||||
<!-- Regular Season Section -->
|
||||
<div class="bg-surface0 border border-surface1 rounded-lg p-6">
|
||||
<h2 class="text-2xl font-bold text-text mb-4 flex items-center gap-2">
|
||||
<span class="text-blue">●</span>
|
||||
Regular Season
|
||||
</h2>
|
||||
<div class="space-y-4">
|
||||
@datepicker.DatePickerWithDefault("start_date", "start_date", "Start Date", "DD/MM/YYYY", true, "startDateIsEmpty = $el.value === ''; resetStartDateErr(); if(startDateIsEmpty) { startDateError='Start date is required'; } updateCanSubmit();", startDateStr)
|
||||
<p
|
||||
class="text-xs text-red -mt-2"
|
||||
x-show="startDateError && !isSubmitting"
|
||||
x-cloak
|
||||
x-text="startDateError"
|
||||
></p>
|
||||
@datepicker.DatePickerWithDefault("end_date", "end_date", "End Date (Optional)", "DD/MM/YYYY", false, "resetEndDateErr();", endDateStr)
|
||||
<p
|
||||
class="text-xs text-red -mt-2"
|
||||
x-show="endDateError && !isSubmitting"
|
||||
x-cloak
|
||||
x-text="endDateError"
|
||||
></p>
|
||||
</div>
|
||||
</div>
|
||||
<!-- Finals Section -->
|
||||
<div class="bg-surface0 border border-surface1 rounded-lg p-6">
|
||||
<h2 class="text-2xl font-bold text-text mb-4 flex items-center gap-2">
|
||||
<span class="text-yellow">★</span>
|
||||
Finals
|
||||
</h2>
|
||||
<div class="space-y-4">
|
||||
@datepicker.DatePickerWithDefault("finals_start_date", "finals_start_date", "Start Date (Optional)", "DD/MM/YYYY", false, "resetFinalsStartDateErr();", finalsStartDateStr)
|
||||
<p
|
||||
class="text-xs text-red -mt-2"
|
||||
x-show="finalsStartDateError && !isSubmitting"
|
||||
x-cloak
|
||||
x-text="finalsStartDateError"
|
||||
></p>
|
||||
@datepicker.DatePickerWithDefault("finals_end_date", "finals_end_date", "End Date (Optional)", "DD/MM/YYYY", false, "resetFinalsEndDateErr();", finalsEndDateStr)
|
||||
<p
|
||||
class="text-xs text-red -mt-2"
|
||||
x-show="finalsEndDateError && !isSubmitting"
|
||||
x-cloak
|
||||
x-text="finalsEndDateError"
|
||||
></p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<!-- General Error Message -->
|
||||
<div
|
||||
class="px-6 pb-6"
|
||||
x-show="generalError"
|
||||
x-cloak
|
||||
>
|
||||
<div class="bg-red/10 border border-red rounded-lg p-4">
|
||||
<p class="text-sm text-red text-center" x-text="generalError"></p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
}
|
||||
|
||||
func formatDateInput(t time.Time) string {
|
||||
return t.Format("02/01/2006")
|
||||
}
|
||||
12
internal/view/seasonsview/edit_page.templ
Normal file
12
internal/view/seasonsview/edit_page.templ
Normal file
@@ -0,0 +1,12 @@
|
||||
package seasonsview
|
||||
|
||||
import "git.haelnorr.com/h/oslstats/internal/view/baseview"
|
||||
import "git.haelnorr.com/h/oslstats/internal/db"
|
||||
|
||||
templ EditPage(season *db.Season) {
|
||||
@baseview.Layout("Edit " + season.Name) {
|
||||
<div class="max-w-screen-2xl mx-auto px-4 py-8">
|
||||
@EditForm(season)
|
||||
</div>
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user