Skip to content

Commit

Permalink
Merge branch 'main' into nm/coin-flip
Browse files Browse the repository at this point in the history
  • Loading branch information
nunom27 committed Jan 8, 2025
2 parents 5d002e3 + 611182b commit 7090cc5
Show file tree
Hide file tree
Showing 97 changed files with 3,584 additions and 438 deletions.
2 changes: 2 additions & 0 deletions .env.dev.sample
Original file line number Diff line number Diff line change
Expand Up @@ -5,3 +5,5 @@ DB_PORT=5432
DB_NAME=safira_dev
HOST_URL=http://localhost:4000
ASSET_HOST=http://localhost:4000
UMAMI_SCRIPT_URL=
UMAMI_WEBSITE_ID=
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -37,4 +37,5 @@ safira-*.tar
npm-debug.log
/assets/node_modules/

.env.dev
.env.*
.env
6 changes: 5 additions & 1 deletion assets/css/app.css
Original file line number Diff line number Diff line change
Expand Up @@ -24,5 +24,9 @@ input:-webkit-autofill:active {

@font-face {
font-family: "Terminal";
src: url("/fonts/TerminalGrotesque.ttf") format("truetype");
src: url("/fonts/Terminal/TerminalGrotesque.ttf") format("truetype");
}
@font-face {
font-family: "Inter-Regular";
src: url("/fonts/Inter/Inter-Regular.ttf") format("truetype");
}
1 change: 1 addition & 0 deletions assets/css/components.css
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
@import "components/avatar.css";
@import "components/field.css";
@import "components/dropdown.css";
@import "components/coinflip.css";
35 changes: 35 additions & 0 deletions assets/css/components/dropdown.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
/* Dropdown */

.safira-dropdown {
@apply relative inline-block text-left;
}
.safira-dropdown__chevron {
@apply w-5 h-5 ml-2 -mr-1 dark:text-gray-100;
}
.safira-dropdown__menu-items-wrapper {
@apply absolute z-30 w-56 mt-2 bg-white rounded-md shadow-lg dark:bg-gray-800 ring-1 ring-black ring-opacity-5 focus:outline-none;
}
.safira-dropdown__menu-items-wrapper-placement--left {
@apply right-0 origin-top-right;
}
.safira-dropdown__menu-items-wrapper-placement--right {
@apply left-0 origin-top-left;
}
.safira-dropdown__menu-item {
@apply flex items-center self-start justify-start w-full gap-2 px-4 py-2 text-sm text-left text-gray-700 transition duration-150 ease-in-out dark:hover:bg-gray-700 dark:text-gray-300 dark:bg-gray-800 hover:bg-gray-100;
}
.safira-dropdown__trigger-button--no-label {
@apply flex items-center text-gray-400 rounded-full hover:text-gray-600 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-offset-gray-100 focus:ring-blue-500;
}
.safira-dropdown__trigger-button--with-label {
@apply inline-flex justify-center w-full px-4 py-2 text-sm font-medium text-gray-700 bg-white border border-gray-300 rounded-md shadow-sm dark:text-gray-300 dark:bg-gray-800 hover:dark:bg-gray-700 dark:border-gray-700 dark:focus:bg-gray-800 hover:bg-gray-50 focus:outline-none;
}
.safira-dropdown__trigger-button--with-label-and-trigger-element {
@apply align-middle;
}
.safira-dropdown__menu-item--disabled {
@apply text-gray-500 hover:bg-transparent;
}
.safira-dropdown__ellipsis {
@apply w-5 h-5;
}
12 changes: 6 additions & 6 deletions assets/css/components/field.css
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
}

.safira-checkbox {
@apply w-5 h-5 transition-all duration-150 ease-linear border-gray-300 rounded cursor-pointer text-primary-500 dark:bg-gray-800 dark:border-gray-600 disabled:bg-gray-300 dark:disabled:bg-gray-600 disabled:cursor-not-allowed focus:ring-primary-500;
@apply w-5 h-5 transition-all duration-150 ease-linear border-gray-300 rounded cursor-pointer text-secondary-500 dark:bg-gray-800 dark:border-gray-600 disabled:bg-gray-300 dark:disabled:bg-gray-600 disabled:cursor-not-allowed focus:ring-secondary-500;
}

.safira-checkbox-label {
Expand Down Expand Up @@ -47,7 +47,7 @@
/* Text input */

.safira-text-input {
@apply block w-full border-gray-300 rounded-md shadow-sm focus:border-primary-500 focus:ring-primary-500 dark:border-gray-600 dark:focus:border-primary-500 sm:text-sm disabled:cursor-not-allowed dark:text-gray-300 focus:outline-none;
@apply block w-full border-gray-300 rounded-md shadow-sm focus:border-secondary-500 focus:ring-secondary-500 dark:border-gray-600 dark:focus:border-secondary-500 sm:text-sm disabled:cursor-not-allowed dark:text-gray-300 focus:outline-none;
}

/* Switch */
Expand Down Expand Up @@ -75,7 +75,7 @@
/* Radio */

.safira-radio {
@apply w-4 h-4 border-gray-300 cursor-pointer text-primary-600 focus:ring-primary-500 dark:border-gray-600;
@apply w-4 h-4 border-gray-300 cursor-pointer text-secondary-600 focus:ring-secondary-500 dark:border-gray-600;
}

.safira-radio-label {
Expand Down Expand Up @@ -111,19 +111,19 @@
/* Color */

.safira-color-input {
@apply border-gray-300 cursor-pointer focus:border-primary-500 focus:ring-primary-500 dark:border-gray-600 dark:focus:border-primary-500;
@apply border-gray-300 cursor-pointer focus:border-secondary-500 focus:ring-secondary-500 dark:border-gray-600 dark:focus:border-secondary-500;
}

/* File */

.safira-file-input {
@apply text-sm rounded-md cursor-pointer focus:outline-none file:border-0 text-slate-500 file:text-primary-700 file:font-semibold file:px-4 file:py-2 file:mr-6 file:rounded-md hover:file:bg-primary-100 file:bg-primary-200 dark:file:bg-primary-300 hover:dark:file:bg-primary-200;
@apply text-sm rounded-md cursor-pointer focus:outline-none file:border-0 text-slate-500 file:text-secondary-700 file:font-semibold file:px-4 file:py-2 file:mr-6 file:rounded-md hover:file:bg-secondary-100 file:bg-secondary-200 dark:file:bg-secondary-300 hover:dark:file:bg-secondary-200;
}

/* Range */

.safira-range-input {
@apply w-full border-gray-300 cursor-pointer focus:border-primary-500 focus:ring-primary-500 dark:border-gray-600 dark:focus:border-primary-500;
@apply w-full border-gray-300 cursor-pointer focus:border-secondary-500 focus:ring-secondary-500 dark:border-gray-600 dark:focus:border-secondary-500;
}

/* Text */
Expand Down
5 changes: 3 additions & 2 deletions assets/js/app.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,12 +22,13 @@ import {Socket} from "phoenix"
import {LiveSocket} from "phoenix_live_view"
import topbar from "../vendor/topbar"
import live_select from "live_select"
import { QrScanner, Wheel, Confetti, Sorting, CoinFlip } from "./hooks";
import { QrScanner, Wheel, Confetti, Countdown, Sorting, CoinFlip } from "./hooks";

let Hooks = {
QrScanner: QrScanner,
Wheel: Wheel,
Confetti: Confetti,
Countdown: Countdown,
Sorting: Sorting,
CoinFlip: CoinFlip,
...live_select
Expand All @@ -41,7 +42,7 @@ let liveSocket = new LiveSocket("/live", Socket, {
})

// Show progress bar on live navigation and form submits
topbar.config({barColors: {0: "#29d"}, shadowColor: "rgba(0, 0, 0, .3)"})
topbar.config({barColors: {0: "#ffdb0d"}, shadowColor: "rgba(0, 0, 0, .3)"})
window.addEventListener("phx:page-loading-start", _info => topbar.show(300))
window.addEventListener("phx:page-loading-stop", _info => topbar.hide())

Expand Down
50 changes: 50 additions & 0 deletions assets/js/hooks/countdown.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
export const Countdown = {
mounted() {
let countdownInterval = null;

const startCountdown = (startTime) => {
if (countdownInterval) {
clearInterval(countdownInterval);
}

const textElement = document.getElementById("seconds-remaining");
if (!textElement) {
console.warn("Countdown element not found!");
return;
}

countdownInterval = setInterval(() => {
const now = Date.now();
const secondsLeft = Math.round((startTime - now) / 1000);

if (secondsLeft >= 0) {
textElement.textContent = formatTime(secondsLeft);
} else {
clearInterval(countdownInterval);
textElement.textContent = "00";
window.location.reload();
}
}, 100);
};

window.addEventListener("phx:highlight", (e) => {
const startTime = new Date(e.detail.start_time).getTime();
startCountdown(startTime);
});
}
};

function formatTime(totalSeconds) {
const dayToSeconds = 86400;
const days = Math.floor(totalSeconds / dayToSeconds);
const hours = Math.floor((totalSeconds % dayToSeconds) / 3600);
const minutes = Math.floor((totalSeconds % 3600) / 60);
const seconds = totalSeconds % 60;

const formattedTime = [
days > 0 ? `${days} days` : null,
`${String(hours).padStart(2, '0')}:${String(minutes).padStart(2, '0')}:${String(seconds).padStart(2, '0')}`
].filter(Boolean).join(", ");

return formattedTime;
}
1 change: 1 addition & 0 deletions assets/js/hooks/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,5 @@ export { QrScanner } from "./qr_reading.js";
export { Wheel } from "./wheel.js";
export { Confetti } from "./confetti.js";
export { Sorting } from "./sorting.js";
export { Countdown } from "./countdown.js";
export { CoinFlip } from "./coinflip.js";
62 changes: 55 additions & 7 deletions assets/tailwind.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ const path = require("path")
const colors = require("tailwindcss/colors");

module.exports = {
//darkMode: "selector",
darkMode: "selector",
content: [
"./js/**/*.js",
"../lib/safira_web.ex",
Expand All @@ -13,9 +13,8 @@ module.exports = {
theme: {
extend: {
colors: {
primary: colors.blue,
primaryDark: "#04041C",
accent: "#ff800d",
primary: "#04041C",
accent: "#ffdb0d",
light: "#ffffff",
lightMuted: "#a1a1aa",
lightShade: "#e5e7eb",
Expand All @@ -30,8 +29,24 @@ module.exports = {
gray: colors.gray
},
fontFamily: {
terminal: ["Terminal"]
}
terminal: ["Terminal"],
iregular: ["Inter-Regular"]
},
animation: {
"slide-in": "slide-in 1.5s ease-in-out",
"fade-in": "fade-in 0.5s ease-in-out",
"fade-in-slow": "fade-in 1.5s ease-in-out"
},
keyframes: {
"slide-in": {
"0%": { transform: "translateY(20%)", opacity: 0},
"100%": { transform: "translateY(0)", opacity: 1},
},
"fade-in": {
"0%": { opacity: 0},
"100%": { opacity: 1},
}
},
},
},
plugins: [
Expand Down Expand Up @@ -86,6 +101,39 @@ module.exports = {
}
}
}, {values})
}),

// Embeds FontAwesome icons (https://fontawesome.com/) into app.css bundle
plugin(function ({ matchComponents, theme }) {
let iconsDir = path.join(__dirname, "../deps/fontawesome/svgs")
let values = {}
let icons = [
["", "", "/regular"],
["-solid", "", "/solid"],
["", "brand-", "/brands"]
]
icons.forEach(([suffix, prefix, dir]) => {
fs.readdirSync(path.join(iconsDir, dir)).forEach(file => {
let name = prefix + path.basename(file, ".svg") + suffix
values[name] = { name, fullPath: path.join(iconsDir, dir, file) }
})
})
matchComponents({
"fa": ({ name, fullPath }) => {
let content = fs.readFileSync(fullPath).toString().replace(/\r?\n|\r/g, "")
return {
[`--fa-${name}`]: `url('data:image/svg+xml;utf8,${content}')`,
"-webkit-mask": `var(--fa-${name})`,
"mask": `var(--fa-${name})`,
"mask-repeat": "no-repeat",
"background-color": "currentColor",
"vertical-align": "middle",
"display": "inline-block",
"width": theme("spacing.5"),
"height": theme("spacing.5")
}
}
}, { values })
})
]
}
}
6 changes: 4 additions & 2 deletions config/config.exs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,9 @@ import Config

config :safira,
ecto_repos: [Safira.Repo],
generators: [timestamp_type: :utc_datetime]
generators: [timestamp_type: :utc_datetime],
umami_script_url: System.get_env("UMAMI_SCRIPT_URL") || "",
umami_website_id: System.get_env("UMAMI_WEBSITE_ID") || ""

# Flop configuration
config :flop,
Expand All @@ -27,7 +29,7 @@ config :safira, SafiraWeb.Endpoint,
adapter: Bandit.PhoenixAdapter,
render_errors: [
formats: [html: SafiraWeb.ErrorHTML, json: SafiraWeb.ErrorJSON],
layout: false
layout: {SafiraWeb.Layouts, :landing}
],
pubsub_server: Safira.PubSub,
live_view: [signing_salt: "TzWGKiXG"]
Expand Down
1 change: 1 addition & 0 deletions lib/safira/accounts/roles/permissions.ex
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ defmodule Safira.Accounts.Roles.Permissions do
"purchases" => ["show", "redeem", "refund"],
"badges" => ["show", "edit", "delete", "give", "revoke", "give_without_restrictions"],
"minigames" => ["show", "edit", "simulate"],
"event" => ["show", "edit", "edit_faqs"],
"spotlights" => ["edit"],
"schedule" => ["edit"],
"statistics" => ["show"],
Expand Down
47 changes: 47 additions & 0 deletions lib/safira/activities.ex
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,37 @@ defmodule Safira.Activities do
|> Flop.validate_and_run(params, for: Activity)
end

@doc """
Returns the count of activities.
## Examples
iex> get_activities_count()
42
"""
def get_activities_count do
Activity
|> Repo.aggregate(:count, :id)
end

@doc """
Returns the list of daily activities.
## Examples
iex> list_daily_activities(~D[2022-01-01])
[%Activity{}, ...]
"""
def list_daily_activities(day) do
Activity
|> where([a], a.date == ^day)
|> order_by([a], a.time_start)
|> preload([:speakers, :category])
|> Repo.all()
end

@doc """
Gets a single activity.
Expand Down Expand Up @@ -374,4 +405,20 @@ defmodule Safira.Activities do
def change_speaker(%Speaker{} = speaker, attrs \\ %{}) do
Speaker.changeset(speaker, attrs)
end

@doc """
Returns the list of highlighted speakers.
## Examples
iex> list_highlighted_speakers()
[%Speaker{}, ...]
"""
def list_highlighted_speakers(opts \\ []) do
Speaker
|> apply_filters(opts)
|> where([s], s.highlighted)
|> Repo.all()
end
end
Loading

0 comments on commit 7090cc5

Please sign in to comment.