Compare commits
28 Commits
ab0d370225
...
feat/teams
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
391df3bb41 | ||
|
|
a29bca1931 | ||
|
|
bc5da01735 | ||
|
|
914e276026 | ||
|
|
2e44012b8c | ||
|
|
0fe2e2bae6 | ||
|
|
c6518e81c9 | ||
|
|
289e11f3c5 | ||
| 8eef632ebb | |||
| ef88a6b69b | |||
|
|
a410208c62 | ||
|
|
d4a6028599 | ||
|
|
4888f93eac | ||
|
|
49921a26a9 | ||
|
|
3b6e0ec447 | ||
|
|
c16203110b | ||
|
|
60fcf08cbc | ||
|
|
701a433174 | ||
|
|
47b354d8b7 | ||
|
|
dfdb48920d | ||
|
|
3dac8ee685 | ||
|
|
09974721f3 | ||
|
|
8215ad8337 | ||
|
|
368ac50729 | ||
|
|
8f094ee89c | ||
|
|
0551cb078f | ||
|
|
26620fc043 | ||
|
|
f10d6daa6f |
26
.env.local
Normal file
26
.env.local
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
# Local Development Configuration
|
||||||
|
# Copy to .env.local and fill in your values.
|
||||||
|
|
||||||
|
# ── MinIO credentials ─────────────────────────────────────────────────────────
|
||||||
|
MINIO_KEY=your_minio_root_user
|
||||||
|
MINIO_SECRET=your_minio_root_password
|
||||||
|
|
||||||
|
# ── SSH tunnel (remote DB) ────────────────────────────────────────────────────
|
||||||
|
# Only needed when starting with --profile ssh-db.
|
||||||
|
# NOTE: no inline comments allowed after values — Docker reads them literally.
|
||||||
|
|
||||||
|
SSH_HOST=136.114.183.15
|
||||||
|
SSH_PORT=22
|
||||||
|
SSH_USER=webmaster
|
||||||
|
# Must be an absolute path — Docker Compose does NOT expand ~
|
||||||
|
SSH_KEY_PATH=/Users/webmaster/.ssh/id_ed25519_crew_webmaster
|
||||||
|
|
||||||
|
SSH_DB_REMOTE_HOST=127.0.0.1
|
||||||
|
SSH_DB_REMOTE_PORT=3306
|
||||||
|
|
||||||
|
# Tell the app to route DB traffic through the tunnel container:
|
||||||
|
DB_HOST=db-tunnel
|
||||||
|
DB_PORT=3306
|
||||||
|
DB_DATABASE=custom_designs
|
||||||
|
DB_USERNAME=root
|
||||||
|
DB_PASSWORD=VeryStrongRootPass2025!
|
||||||
26
.env.local.example
Normal file
26
.env.local.example
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
# Local Development Configuration
|
||||||
|
# Copy to .env.local and fill in your values.
|
||||||
|
|
||||||
|
# ── MinIO credentials ─────────────────────────────────────────────────────────
|
||||||
|
MINIO_KEY=your_minio_root_user
|
||||||
|
MINIO_SECRET=your_minio_root_password
|
||||||
|
|
||||||
|
# ── SSH tunnel (remote DB) ────────────────────────────────────────────────────
|
||||||
|
# Only needed when starting with --profile ssh-db.
|
||||||
|
# IMPORTANT: no inline comments after values — Docker Compose reads them literally.
|
||||||
|
# IMPORTANT: SSH_KEY_PATH must be an absolute path — ~ is NOT expanded by Docker Compose.
|
||||||
|
#
|
||||||
|
SSH_HOST=your.server.ip.or.hostname
|
||||||
|
SSH_PORT=22
|
||||||
|
SSH_USER=root
|
||||||
|
SSH_KEY_PATH=/absolute/path/to/your/private/key
|
||||||
|
#
|
||||||
|
SSH_DB_REMOTE_HOST=127.0.0.1 # DB host as seen from the SSH server
|
||||||
|
SSH_DB_REMOTE_PORT=3306 # DB port as seen from the SSH server
|
||||||
|
#
|
||||||
|
# Tell the app to route DB traffic through the tunnel container:
|
||||||
|
DB_HOST=db-tunnel
|
||||||
|
DB_PORT=3306
|
||||||
|
DB_DATABASE=your_remote_db_name
|
||||||
|
DB_USERNAME=your_remote_db_user
|
||||||
|
DB_PASSWORD=your_remote_db_password
|
||||||
21
.env.minio.example
Normal file
21
.env.minio.example
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
# MinIO S3 Storage Configuration
|
||||||
|
# Add these to your production .env file
|
||||||
|
|
||||||
|
# MinIO Endpoint (internal Docker network)
|
||||||
|
MINIO_ENDPOINT=http://crew-minio-prod:9000
|
||||||
|
|
||||||
|
# MinIO Credentials (get from /var/www/apps/minio-storage/.env)
|
||||||
|
MINIO_KEY=your_minio_root_user
|
||||||
|
MINIO_SECRET=your_minio_root_password
|
||||||
|
|
||||||
|
# Bucket name
|
||||||
|
MINIO_BUCKET=crewsportswear
|
||||||
|
|
||||||
|
# Region (required for S3 compatibility)
|
||||||
|
MINIO_REGION=us-east-1
|
||||||
|
|
||||||
|
# Use path-style endpoint (required for MinIO)
|
||||||
|
MINIO_USE_PATH_STYLE=true
|
||||||
|
|
||||||
|
# Public URL for accessing files (use your actual domain)
|
||||||
|
MINIO_URL=https://minio.crewsportswear.app
|
||||||
11
.gitignore
vendored
11
.gitignore
vendored
@@ -1,3 +1,14 @@
|
|||||||
/vendor
|
/vendor
|
||||||
/node_modules
|
/node_modules
|
||||||
.env
|
.env
|
||||||
|
|
||||||
|
# SSH Keys - Never commit private keys
|
||||||
|
*.ppk
|
||||||
|
*.pem
|
||||||
|
*.key
|
||||||
|
id_rsa
|
||||||
|
id_dsa
|
||||||
|
id_ecdsa
|
||||||
|
id_ed25519
|
||||||
|
_key/
|
||||||
|
.ssh/
|
||||||
|
|||||||
33
Dockerfile
33
Dockerfile
@@ -1,10 +1,10 @@
|
|||||||
# Use PHP 7.0 with Apache (has native mcrypt support for Laravel 5.0)
|
# Use PHP 7.2 with Apache (mcrypt available via PECL, compatible with Laravel 5.0)
|
||||||
FROM php:7.0-apache
|
FROM php:7.2-apache
|
||||||
|
|
||||||
# Update to use archived Debian repositories
|
# Redirect to archived Debian Buster repositories (EOL)
|
||||||
RUN sed -i 's|deb.debian.org|archive.debian.org|g' /etc/apt/sources.list \
|
RUN sed -i 's|deb.debian.org|archive.debian.org|g' /etc/apt/sources.list \
|
||||||
&& sed -i 's|security.debian.org|archive.debian.org|g' /etc/apt/sources.list \
|
&& sed -i 's|security.debian.org|archive.debian.org|g' /etc/apt/sources.list \
|
||||||
&& sed -i '/stretch-updates/d' /etc/apt/sources.list
|
&& sed -i '/buster-updates/d' /etc/apt/sources.list
|
||||||
|
|
||||||
# Install system dependencies
|
# Install system dependencies
|
||||||
RUN apt-get update && apt-get install -y --allow-unauthenticated \
|
RUN apt-get update && apt-get install -y --allow-unauthenticated \
|
||||||
@@ -18,17 +18,24 @@ RUN apt-get update && apt-get install -y --allow-unauthenticated \
|
|||||||
libfreetype6-dev \
|
libfreetype6-dev \
|
||||||
libjpeg62-turbo-dev \
|
libjpeg62-turbo-dev \
|
||||||
openssh-client \
|
openssh-client \
|
||||||
|
libzip-dev \
|
||||||
&& docker-php-ext-configure gd --with-freetype-dir=/usr/include/ --with-jpeg-dir=/usr/include/ \
|
&& docker-php-ext-configure gd --with-freetype-dir=/usr/include/ --with-jpeg-dir=/usr/include/ \
|
||||||
&& docker-php-ext-install -j$(nproc) gd
|
&& docker-php-ext-install -j$(nproc) gd
|
||||||
|
|
||||||
# Install PHP extensions (mcrypt is built-in for PHP 7.0)
|
# Install mcrypt via PECL (removed from core in PHP 7.2)
|
||||||
RUN docker-php-ext-install pdo_mysql mbstring exif pcntl bcmath mcrypt tokenizer zip
|
RUN pecl install mcrypt-1.0.4 && docker-php-ext-enable mcrypt
|
||||||
|
|
||||||
|
# Suppress E_DEPRECATED so PECL mcrypt functions don't trigger ErrorException in Laravel 5.0
|
||||||
|
RUN echo "error_reporting = E_ALL & ~E_DEPRECATED & ~E_STRICT" > /usr/local/etc/php/conf.d/suppress-deprecated.ini
|
||||||
|
|
||||||
|
# Install PHP extensions
|
||||||
|
RUN docker-php-ext-install pdo_mysql mbstring exif pcntl bcmath tokenizer zip
|
||||||
|
|
||||||
# Enable Apache mod_rewrite
|
# Enable Apache mod_rewrite
|
||||||
RUN a2enmod rewrite
|
RUN a2enmod rewrite
|
||||||
|
|
||||||
# Install Composer (version 1.x for better compatibility with Laravel 5.0)
|
# Install Composer 2.2 (LTS version supporting PHP 7.2+)
|
||||||
COPY --from=composer:1.10 /usr/bin/composer /usr/bin/composer
|
COPY --from=composer:2.2 /usr/bin/composer /usr/bin/composer
|
||||||
|
|
||||||
# Set working directory
|
# Set working directory
|
||||||
WORKDIR /var/www/html
|
WORKDIR /var/www/html
|
||||||
@@ -51,8 +58,8 @@ RUN chown -R www-data:www-data /var/www/html \
|
|||||||
# Create .env file if it doesn't exist
|
# Create .env file if it doesn't exist
|
||||||
RUN if [ ! -f .env ]; then cp .env.example .env; fi
|
RUN if [ ! -f .env ]; then cp .env.example .env; fi
|
||||||
|
|
||||||
# Install PHP dependencies (Laravel 5.0 compatible)
|
# Install PHP dependencies (--no-plugins skips kylekatarnls/update-helper which is Composer 1 only)
|
||||||
RUN composer install --no-dev --no-interaction --prefer-dist
|
RUN composer install --no-dev --no-interaction --prefer-dist --no-plugins
|
||||||
|
|
||||||
# Generate application key
|
# Generate application key
|
||||||
RUN php artisan key:generate || true
|
RUN php artisan key:generate || true
|
||||||
@@ -60,11 +67,7 @@ RUN php artisan key:generate || true
|
|||||||
# Run Laravel 5.0 optimization
|
# Run Laravel 5.0 optimization
|
||||||
RUN php artisan clear-compiled && php artisan optimize
|
RUN php artisan clear-compiled && php artisan optimize
|
||||||
|
|
||||||
# Note: yakpro-po obfuscation requires PHP 7.1+, incompatible with PHP 7.0
|
# Note: PHP 7.2 is compatible with Laravel 5.0 and yakpro-po obfuscation
|
||||||
# For code protection with PHP 7.0, consider:
|
|
||||||
# 1. ionCube Encoder (commercial, most secure)
|
|
||||||
# 2. Keeping source code private and using proper access controls
|
|
||||||
# 3. Using --optimize flag in composer (already done above)
|
|
||||||
|
|
||||||
# Configure Apache DocumentRoot to point to Laravel's public directory
|
# Configure Apache DocumentRoot to point to Laravel's public directory
|
||||||
ENV APACHE_DOCUMENT_ROOT=/var/www/html/public
|
ENV APACHE_DOCUMENT_ROOT=/var/www/html/public
|
||||||
|
|||||||
17
Makefile
Normal file
17
Makefile
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
COMPOSE_LOCAL = docker compose -f docker-compose.local.yml
|
||||||
|
|
||||||
|
# ── Local stack (local MariaDB) ───────────────────────────────────────────────
|
||||||
|
up:
|
||||||
|
$(COMPOSE_LOCAL) up --build
|
||||||
|
|
||||||
|
down:
|
||||||
|
$(COMPOSE_LOCAL) down
|
||||||
|
|
||||||
|
# ── Local stack with SSH tunnel to remote DB ──────────────────────────────────
|
||||||
|
up-ssh:
|
||||||
|
$(COMPOSE_LOCAL) --env-file .env.local --profile ssh-db up --build
|
||||||
|
|
||||||
|
down-ssh:
|
||||||
|
$(COMPOSE_LOCAL) --env-file .env.local --profile ssh-db down
|
||||||
|
|
||||||
|
.PHONY: up down up-ssh down-ssh
|
||||||
@@ -22,8 +22,11 @@ class Handler extends ExceptionHandler {
|
|||||||
* @param \Exception $e
|
* @param \Exception $e
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function report(Exception $e)
|
public function report($e)
|
||||||
{
|
{
|
||||||
|
if (!$e instanceof Exception) {
|
||||||
|
$e = new \ErrorException($e->getMessage(), $e->getCode(), E_ERROR, $e->getFile(), $e->getLine());
|
||||||
|
}
|
||||||
return parent::report($e);
|
return parent::report($e);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -31,11 +34,14 @@ class Handler extends ExceptionHandler {
|
|||||||
* Render an exception into an HTTP response.
|
* Render an exception into an HTTP response.
|
||||||
*
|
*
|
||||||
* @param \Illuminate\Http\Request $request
|
* @param \Illuminate\Http\Request $request
|
||||||
* @param \Exception $e
|
* @param mixed $e
|
||||||
* @return \Illuminate\Http\Response
|
* @return \Illuminate\Http\Response
|
||||||
*/
|
*/
|
||||||
public function render($request, Exception $e)
|
public function render($request, $e)
|
||||||
{
|
{
|
||||||
|
if (!$e instanceof Exception) {
|
||||||
|
$e = new \ErrorException($e->getMessage(), $e->getCode(), E_ERROR, $e->getFile(), $e->getLine());
|
||||||
|
}
|
||||||
return parent::render($request, $e);
|
return parent::render($request, $e);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -31,7 +31,7 @@ class MainController extends Controller {
|
|||||||
foreach ($fetchData as $row) {
|
foreach ($fetchData as $row) {
|
||||||
?>
|
?>
|
||||||
<div class="col-md-3 col-sm-6 col-xs-12 list-sport">
|
<div class="col-md-3 col-sm-6 col-xs-12 list-sport">
|
||||||
<a href="<?php echo url('sports') . "/" . $row->URL; ?>"><img src="<?php echo config('site_config.uploads') . 'sports-thumbnails/' . $row->Thumbnail; ?>" alt="" class="img img-responsive product-center" /></a>
|
<a href="<?php echo url('sports') . "/" . $row->URL; ?>"><img src="<?php echo minio_url('uploads/images/sports-thumbnails/' . $row->Thumbnail); ?>" alt="" class="img img-responsive product-center" /></a>
|
||||||
<h3 class="text-center sports-title"><?php echo $row->SportsName ?></h3>
|
<h3 class="text-center sports-title"><?php echo $row->SportsName ?></h3>
|
||||||
</div>
|
</div>
|
||||||
<?php
|
<?php
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ use App\Http\Controllers\Controller;
|
|||||||
|
|
||||||
use Illuminate\Support\Facades\Request1;
|
use Illuminate\Support\Facades\Request1;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
|
use Illuminate\Support\Facades\Storage;
|
||||||
use App\Models\PrintPatternModel;
|
use App\Models\PrintPatternModel;
|
||||||
use App\Models\SizesModel;
|
use App\Models\SizesModel;
|
||||||
|
|
||||||
@@ -46,7 +47,7 @@ class PrintPatternController extends Controller {
|
|||||||
$NewImageName = $templateSize.'.'.$imageExt;
|
$NewImageName = $templateSize.'.'.$imageExt;
|
||||||
|
|
||||||
|
|
||||||
$thumbnail = "uniform-templates/".$templatecode."/".$templateType."/SIZES/" . $NewImageName;
|
$thumbnail = "uploads/images/uniform-templates/".$templatecode."/".$templateType."/SIZES/" . $NewImageName;
|
||||||
|
|
||||||
$data = array(
|
$data = array(
|
||||||
'TemplateCode' => $templatecode,
|
'TemplateCode' => $templatecode,
|
||||||
@@ -58,9 +59,7 @@ class PrintPatternController extends Controller {
|
|||||||
$i = $m->insertPrintPattern($data);
|
$i = $m->insertPrintPattern($data);
|
||||||
//var_dump($data);
|
//var_dump($data);
|
||||||
if($i){
|
if($i){
|
||||||
$r = $request->file('preview_print_template')->move(
|
Storage::disk('minio')->put('uploads/images/uniform-templates/'.$templatecode.'/'.$templateType.'/SIZES/'.$NewImageName, file_get_contents($request->file('preview_print_template')->getRealPath()));
|
||||||
base_path() . "/public/images/uniform-templates/".$templatecode."/".$templateType."/SIZES/", $NewImageName
|
|
||||||
);
|
|
||||||
echo '<div class="alert alert-success alert-dismissible">
|
echo '<div class="alert alert-success alert-dismissible">
|
||||||
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
|
<button type="button" class="close" data-dismiss="alert" aria-hidden="true">×</button>
|
||||||
<h4><i class="icon fa fa-check"></i> Success!</h4>
|
<h4><i class="icon fa fa-check"></i> Success!</h4>
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ use App\Http\Requests;
|
|||||||
use App\Http\Controllers\Controller;
|
use App\Http\Controllers\Controller;
|
||||||
|
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
|
use Illuminate\Support\Facades\Storage;
|
||||||
use App\Models\TemplatesModel;
|
use App\Models\TemplatesModel;
|
||||||
use App\Models\SportsModel;
|
use App\Models\SportsModel;
|
||||||
use App\Models\PrintPatternModel;
|
use App\Models\PrintPatternModel;
|
||||||
@@ -48,7 +49,7 @@ class TemplatesController extends Controller {
|
|||||||
<h3><?php echo $row->TemplateName ?></h3>
|
<h3><?php echo $row->TemplateName ?></h3>
|
||||||
</div>
|
</div>
|
||||||
<div class="sports-border">
|
<div class="sports-border">
|
||||||
<a href=""><img src="<?php echo url('public') . "/" . $row->Thumbnail ?>" alt="Sports" height="400px;" class="img img-responsive product-center" /></a>
|
<a href=""><img src="<?php echo minio_url($row->Thumbnail) ?>" alt="Sports" height="400px;" class="img img-responsive product-center" /></a>
|
||||||
<div class="sport-edit-btn">
|
<div class="sport-edit-btn">
|
||||||
<a href="<?php echo url('admin/templates') . "/edit/" . $row->TemplateCode . "/" ?>" class="btn btn-primary btn-block"><i class="fa fa-edit"></i> Edit</a>
|
<a href="<?php echo url('admin/templates') . "/edit/" . $row->TemplateCode . "/" ?>" class="btn btn-primary btn-block"><i class="fa fa-edit"></i> Edit</a>
|
||||||
</div>
|
</div>
|
||||||
@@ -129,15 +130,13 @@ class TemplatesController extends Controller {
|
|||||||
|
|
||||||
|
|
||||||
if($i){
|
if($i){
|
||||||
$request->file('tempateImage')->move(
|
Storage::disk('minio')->put('images/templates/thumbnail/' . $NewImageName, file_get_contents($request->file('tempateImage')->getRealPath()));
|
||||||
base_path() . '/public/images/templates/thumbnail', $NewImageName
|
|
||||||
);
|
|
||||||
|
|
||||||
//for front jersey
|
//for front jersey
|
||||||
if(!empty($request->file('svgJerseyFront')->getClientOriginalName())){
|
if(!empty($request->file('svgJerseyFront')->getClientOriginalName())){
|
||||||
|
|
||||||
$svgName = $request->file('svgJerseyFront')->getClientOriginalName();
|
$svgName = $request->file('svgJerseyFront')->getClientOriginalName();
|
||||||
$svgThumbnail = "uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
$svgThumbnail = "uploads/images/uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
||||||
//var_dump($svgThumbnail);
|
//var_dump($svgThumbnail);
|
||||||
$Templatedata = array(
|
$Templatedata = array(
|
||||||
'TemplateCode' => $templateCode,
|
'TemplateCode' => $templateCode,
|
||||||
@@ -149,16 +148,14 @@ class TemplatesController extends Controller {
|
|||||||
|
|
||||||
$i = $m->insertTempaltePaths($Templatedata);
|
$i = $m->insertTempaltePaths($Templatedata);
|
||||||
if($i){
|
if($i){
|
||||||
$request->file('svgJerseyFront')->move(
|
Storage::disk('minio')->put('uploads/images/uniform-templates/'.$templateCode.'/DISPLAY/'.$svgName, file_get_contents($request->file('svgJerseyFront')->getRealPath()));
|
||||||
base_path() . '/public/images/uniform-templates/'.$templateCode. '/DISPLAY' , $svgName
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!empty($request->file('svgJerseyBack')->getClientOriginalName())){
|
if(!empty($request->file('svgJerseyBack')->getClientOriginalName())){
|
||||||
|
|
||||||
$svgName = $request->file('svgJerseyBack')->getClientOriginalName();
|
$svgName = $request->file('svgJerseyBack')->getClientOriginalName();
|
||||||
$svgThumbnail = "uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
$svgThumbnail = "uploads/images/uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
||||||
|
|
||||||
$Templatedata = array(
|
$Templatedata = array(
|
||||||
'TemplateCode' => $templateCode,
|
'TemplateCode' => $templateCode,
|
||||||
@@ -170,16 +167,14 @@ class TemplatesController extends Controller {
|
|||||||
|
|
||||||
$i = $m->insertTempaltePaths($Templatedata);
|
$i = $m->insertTempaltePaths($Templatedata);
|
||||||
if($i){
|
if($i){
|
||||||
$request->file('svgJerseyBack')->move(
|
Storage::disk('minio')->put('uploads/images/uniform-templates/'.$templateCode.'/DISPLAY/'.$svgName, file_get_contents($request->file('svgJerseyBack')->getRealPath()));
|
||||||
base_path() . '/public/images/uniform-templates/'.$templateCode. '/DISPLAY' , $svgName
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!empty($request->file('svgShortRight')->getClientOriginalName())){
|
if(!empty($request->file('svgShortRight')->getClientOriginalName())){
|
||||||
|
|
||||||
$svgName = $request->file('svgShortRight')->getClientOriginalName();
|
$svgName = $request->file('svgShortRight')->getClientOriginalName();
|
||||||
$svgThumbnail = "uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
$svgThumbnail = "uploads/images/uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
||||||
|
|
||||||
$Templatedata = array(
|
$Templatedata = array(
|
||||||
'TemplateCode' => $templateCode,
|
'TemplateCode' => $templateCode,
|
||||||
@@ -191,16 +186,14 @@ class TemplatesController extends Controller {
|
|||||||
|
|
||||||
$i = $m->insertTempaltePaths($Templatedata);
|
$i = $m->insertTempaltePaths($Templatedata);
|
||||||
if($i){
|
if($i){
|
||||||
$request->file('svgShortRight')->move(
|
Storage::disk('minio')->put('uploads/images/uniform-templates/'.$templateCode.'/DISPLAY/'.$svgName, file_get_contents($request->file('svgShortRight')->getRealPath()));
|
||||||
base_path() . '/public/images/uniform-templates/'.$templateCode. '/DISPLAY' , $svgName
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!empty($request->file('svgShortLeft')->getClientOriginalName())){
|
if(!empty($request->file('svgShortLeft')->getClientOriginalName())){
|
||||||
|
|
||||||
$svgName = $request->file('svgShortLeft')->getClientOriginalName();
|
$svgName = $request->file('svgShortLeft')->getClientOriginalName();
|
||||||
$svgThumbnail = "uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
$svgThumbnail = "uploads/images/uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
||||||
|
|
||||||
$Templatedata = array(
|
$Templatedata = array(
|
||||||
'TemplateCode' => $templateCode,
|
'TemplateCode' => $templateCode,
|
||||||
@@ -212,9 +205,7 @@ class TemplatesController extends Controller {
|
|||||||
|
|
||||||
$i = $m->insertTempaltePaths($Templatedata);
|
$i = $m->insertTempaltePaths($Templatedata);
|
||||||
if($i){
|
if($i){
|
||||||
$request->file('svgShortLeft')->move(
|
Storage::disk('minio')->put('uploads/images/uniform-templates/'.$templateCode.'/DISPLAY/'.$svgName, file_get_contents($request->file('svgShortLeft')->getRealPath()));
|
||||||
base_path() . '/public/images/uniform-templates/'.$templateCode. '/DISPLAY' , $svgName
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -270,9 +261,7 @@ class TemplatesController extends Controller {
|
|||||||
'PatternId' => $getSkins
|
'PatternId' => $getSkins
|
||||||
);
|
);
|
||||||
|
|
||||||
$request->file('tempateImage')->move(
|
Storage::disk('minio')->put('images/templates/thumbnail/' . $NewImageName, file_get_contents($request->file('tempateImage')->getRealPath()));
|
||||||
base_path() . '/public/images/templates/thumbnail', $NewImageName
|
|
||||||
);
|
|
||||||
|
|
||||||
}else{
|
}else{
|
||||||
|
|
||||||
@@ -298,7 +287,7 @@ class TemplatesController extends Controller {
|
|||||||
//echo 'meron jerset front';
|
//echo 'meron jerset front';
|
||||||
|
|
||||||
$svgName = $request->file('svgJerseyFront')->getClientOriginalName();
|
$svgName = $request->file('svgJerseyFront')->getClientOriginalName();
|
||||||
$svgThumbnail = "uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
$svgThumbnail = "uploads/images/uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
||||||
|
|
||||||
$Templatedata = array(
|
$Templatedata = array(
|
||||||
'Type' => 'Jersey',
|
'Type' => 'Jersey',
|
||||||
@@ -308,9 +297,7 @@ class TemplatesController extends Controller {
|
|||||||
|
|
||||||
$i = $m->updateTemplatePaths($Templatedata, $post['id_svgJerseyFront']);
|
$i = $m->updateTemplatePaths($Templatedata, $post['id_svgJerseyFront']);
|
||||||
if($i){
|
if($i){
|
||||||
$request->file('svgJerseyFront')->move(
|
Storage::disk('minio')->put('uploads/images/uniform-templates/'.$templateCode.'/DISPLAY/'.$svgName, file_get_contents($request->file('svgJerseyFront')->getRealPath()));
|
||||||
base_path() . '/public/images/uniform-templates/'.$templateCode. '/DISPLAY' , $svgName
|
|
||||||
);
|
|
||||||
//echo 'image move success';
|
//echo 'image move success';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -318,7 +305,7 @@ class TemplatesController extends Controller {
|
|||||||
if (array_key_exists('svgJerseyBack', $post)) {
|
if (array_key_exists('svgJerseyBack', $post)) {
|
||||||
|
|
||||||
$svgName = $request->file('svgJerseyBack')->getClientOriginalName();
|
$svgName = $request->file('svgJerseyBack')->getClientOriginalName();
|
||||||
$svgThumbnail = "uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
$svgThumbnail = "uploads/images/uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
||||||
|
|
||||||
$Templatedata = array(
|
$Templatedata = array(
|
||||||
'Type' => 'Jersey',
|
'Type' => 'Jersey',
|
||||||
@@ -327,16 +314,13 @@ class TemplatesController extends Controller {
|
|||||||
);
|
);
|
||||||
$i = $m->updateTemplatePaths($Templatedata, $post['id_svgJerseyBack']);
|
$i = $m->updateTemplatePaths($Templatedata, $post['id_svgJerseyBack']);
|
||||||
if($i){
|
if($i){
|
||||||
|
Storage::disk('minio')->put('uploads/images/uniform-templates/'.$templateCode.'/DISPLAY/'.$svgName, file_get_contents($request->file('svgJerseyBack')->getRealPath()));
|
||||||
$request->file('svgJerseyBack')->move(
|
|
||||||
base_path() . '/public/images/uniform-templates/'.$templateCode. '/DISPLAY' , $svgName
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (array_key_exists('svgShortRight', $post)) {
|
if (array_key_exists('svgShortRight', $post)) {
|
||||||
$svgName = $request->file('svgShortRight')->getClientOriginalName();
|
$svgName = $request->file('svgShortRight')->getClientOriginalName();
|
||||||
$svgThumbnail = "uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
$svgThumbnail = "uploads/images/uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
||||||
|
|
||||||
$Templatedata = array(
|
$Templatedata = array(
|
||||||
'Type' => 'Shorts',
|
'Type' => 'Shorts',
|
||||||
@@ -346,15 +330,13 @@ class TemplatesController extends Controller {
|
|||||||
|
|
||||||
$i = $m->updateTemplatePaths($Templatedata, $post['id_svgShortRight']);
|
$i = $m->updateTemplatePaths($Templatedata, $post['id_svgShortRight']);
|
||||||
if($i){
|
if($i){
|
||||||
$request->file('svgShortRight')->move(
|
Storage::disk('minio')->put('uploads/images/uniform-templates/'.$templateCode.'/DISPLAY/'.$svgName, file_get_contents($request->file('svgShortRight')->getRealPath()));
|
||||||
base_path() . '/public/images/uniform-templates/'.$templateCode. '/DISPLAY' , $svgName
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (array_key_exists('svgShortLeft', $post)) {
|
if (array_key_exists('svgShortLeft', $post)) {
|
||||||
$svgName = $request->file('svgShortLeft')->getClientOriginalName();
|
$svgName = $request->file('svgShortLeft')->getClientOriginalName();
|
||||||
$svgThumbnail = "uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
$svgThumbnail = "uploads/images/uniform-templates/".$templateCode."/DISPLAY/".$svgName;
|
||||||
|
|
||||||
$Templatedata = array(
|
$Templatedata = array(
|
||||||
'Type' => 'Shorts',
|
'Type' => 'Shorts',
|
||||||
@@ -364,9 +346,7 @@ class TemplatesController extends Controller {
|
|||||||
|
|
||||||
$i = $m->updateTemplatePaths($Templatedata, $post['id_svgShortLeft']);
|
$i = $m->updateTemplatePaths($Templatedata, $post['id_svgShortLeft']);
|
||||||
if($i){
|
if($i){
|
||||||
$request->file('svgShortLeft')->move(
|
Storage::disk('minio')->put('uploads/images/uniform-templates/'.$templateCode.'/DISPLAY/'.$svgName, file_get_contents($request->file('svgShortLeft')->getRealPath()));
|
||||||
base_path() . '/public/images/uniform-templates/'.$templateCode. '/DISPLAY' , $svgName
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
46
app/Http/Controllers/TestEmailController.php
Normal file
46
app/Http/Controllers/TestEmailController.php
Normal file
@@ -0,0 +1,46 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Http\Controllers;
|
||||||
|
|
||||||
|
use Illuminate\Http\Request;
|
||||||
|
use Illuminate\Support\Facades\Mail;
|
||||||
|
|
||||||
|
class TestEmailController extends Controller
|
||||||
|
{
|
||||||
|
|
||||||
|
public function show()
|
||||||
|
{
|
||||||
|
return view('test-email', ['token' => csrf_token()]);
|
||||||
|
}
|
||||||
|
|
||||||
|
public function send(Request $request)
|
||||||
|
{
|
||||||
|
$this->validate($request, [
|
||||||
|
'recipient' => 'required|email',
|
||||||
|
]);
|
||||||
|
|
||||||
|
$recipient = $request->input('recipient');
|
||||||
|
$config = [
|
||||||
|
'driver' => config('mail.driver'),
|
||||||
|
'host' => config('mail.host'),
|
||||||
|
'port' => config('mail.port'),
|
||||||
|
'username' => config('mail.username'),
|
||||||
|
'encryption' => config('mail.encryption'),
|
||||||
|
];
|
||||||
|
|
||||||
|
try {
|
||||||
|
Mail::send('emails.test', ['config' => $config, 'recipient' => $recipient], function ($message) use ($recipient) {
|
||||||
|
$message->from('no-reply@crewsportswear.com', 'CREW Sportswear');
|
||||||
|
$message->to($recipient)->subject('CREW Sportswear — Test Email');
|
||||||
|
});
|
||||||
|
|
||||||
|
$status = 'success';
|
||||||
|
$message = 'Test email sent successfully to ' . $recipient . '.';
|
||||||
|
} catch (\Throwable $e) {
|
||||||
|
$status = 'danger';
|
||||||
|
$message = 'Failed to send email: ' . $e->getMessage();
|
||||||
|
}
|
||||||
|
|
||||||
|
return redirect()->back()->with('status', $status)->with('message', $message);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -367,14 +367,11 @@ class DesignerController extends Controller {
|
|||||||
?>
|
?>
|
||||||
<div class="form-group col-md-3">
|
<div class="form-group col-md-3">
|
||||||
<div class="thumbnail clipart-thumnail">
|
<div class="thumbnail clipart-thumnail">
|
||||||
<a href="#" class="img-clipart" data-link="<?php echo $row->SVGFilename; ?>"><img src="<?php echo config('site_config.uploads') . 'cliparts/'. $row->SVGFilename; ?>" width="100%"></a>
|
<a href="#" class="img-clipart" data-link="<?php echo $row->SVGFilename; ?>"><img src="<?php echo minio_url('uploads/images/cliparts/') . $row->SVGFilename; ?>" width="100%"></a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<?php
|
<?php
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public function clipartProperties(Request $request)
|
public function clipartProperties(Request $request)
|
||||||
@@ -829,8 +826,9 @@ class DesignerController extends Controller {
|
|||||||
}
|
}
|
||||||
|
|
||||||
$arr = array(
|
$arr = array(
|
||||||
'small' => config('site_config.uploads') . $small ,
|
|
||||||
'large' => config('site_config.uploads') . $large
|
'small' => minio_url('uploads/images') . $small ,
|
||||||
|
'large' => minio_url('uploads/images') . $large
|
||||||
);
|
);
|
||||||
|
|
||||||
return json_encode($arr);
|
return json_encode($arr);
|
||||||
|
|||||||
@@ -761,10 +761,7 @@ class UserController extends Controller
|
|||||||
);
|
);
|
||||||
|
|
||||||
$u = $UserModel->insertNewProductThumbnails($thumbs);
|
$u = $UserModel->insertNewProductThumbnails($thumbs);
|
||||||
// var_dump($thumbs);
|
Storage::disk('minio')->put('images/' . $thumbnail, file_get_contents($request->file('imgupload')[$i]->getRealPath()));
|
||||||
Storage::disk('sftp')->put($thumbnail, fopen($request->file('imgupload')[$i], 'r+')); //live
|
|
||||||
//Storage::disk('localdir')->put($thumbnail, fopen($request->file('imgupload')[$i], 'r+'));
|
|
||||||
// var_dump($s);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
$prod_code = array('ProductCode' => $getYear . '-' . str_pad($id, 10, '0', STR_PAD_LEFT));
|
$prod_code = array('ProductCode' => $getYear . '-' . str_pad($id, 10, '0', STR_PAD_LEFT));
|
||||||
@@ -808,9 +805,7 @@ class UserController extends Controller
|
|||||||
);
|
);
|
||||||
|
|
||||||
$u = $UserModel->insertNewProductThumbnails($thumbs);
|
$u = $UserModel->insertNewProductThumbnails($thumbs);
|
||||||
Storage::disk('sftp')->put($thumbnail, fopen($request->file('upload_images')[$i], 'r+')); //live
|
Storage::disk('minio')->put('images/' . $thumbnail, file_get_contents($request->file('upload_images')[$i]->getRealPath()));
|
||||||
//Storage::disk('localdir')->put($thumbnail, fopen($request->file('upload_images')[$i], 'r+'));
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -826,9 +821,8 @@ class UserController extends Controller
|
|||||||
$id = $request->thumb_id;
|
$id = $request->thumb_id;
|
||||||
$UserModel = new UserModel;
|
$UserModel = new UserModel;
|
||||||
|
|
||||||
$storagePath = Storage::disk('sftp')->getDriver()->getAdapter()->getPathPrefix();
|
if (Storage::disk('minio')->exists('images/' . $file)) {
|
||||||
if (file_exists($storagePath . $file)) {
|
Storage::disk('minio')->delete('images/' . $file);
|
||||||
unlink($storagePath . $file);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
$i = $UserModel->deleteImageThumb('Id', $id);
|
$i = $UserModel->deleteImageThumb('Id', $id);
|
||||||
@@ -973,11 +967,11 @@ class UserController extends Controller
|
|||||||
// var_dump($res);
|
// var_dump($res);
|
||||||
// if($res){
|
// if($res){
|
||||||
if ($request->file('store_logo') != null) {
|
if ($request->file('store_logo') != null) {
|
||||||
Storage::disk('uploads')->put('/teamstore/' . $orig_store_url . '/' . $store_logo_name, fopen($request->file('store_logo'), 'r+'));
|
Storage::disk('minio')->put('uploads/images/teamstore/' . $orig_store_url . '/' . $store_logo_name, file_get_contents($request->file('store_logo')->getRealPath()));
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($request->file('store_banner') != null) {
|
if ($request->file('store_banner') != null) {
|
||||||
Storage::disk('uploads')->put('/teamstore/' . $orig_store_url . '/' . $store_banner_name, fopen($request->file('store_banner'), 'r+'));
|
Storage::disk('minio')->put('uploads/images/teamstore/' . $orig_store_url . '/' . $store_banner_name, file_get_contents($request->file('store_banner')->getRealPath()));
|
||||||
}
|
}
|
||||||
|
|
||||||
return response()->json(array(
|
return response()->json(array(
|
||||||
|
|||||||
@@ -41,6 +41,10 @@ Route::get('cart', ['as' => 'cart', 'uses' => 'teamstore\TeamStoreController@car
|
|||||||
Route::get('/checkout', 'teamstore\TeamStoreController@checkout');
|
Route::get('/checkout', 'teamstore\TeamStoreController@checkout');
|
||||||
Route::get('/mail', 'teamstore\TeamStoreController@mail');
|
Route::get('/mail', 'teamstore\TeamStoreController@mail');
|
||||||
|
|
||||||
|
// Test email page
|
||||||
|
Route::get('/test-email', 'TestEmailController@show');
|
||||||
|
Route::post('/test-email/send', 'TestEmailController@send');
|
||||||
|
|
||||||
Route::get('/designer/{templateid}', 'designer\DesignerController@index');
|
Route::get('/designer/{templateid}', 'designer\DesignerController@index');
|
||||||
|
|
||||||
Route::get('/designer/preview/{designCode}', 'designer\DesignerController@getDesign');
|
Route::get('/designer/preview/{designCode}', 'designer\DesignerController@getDesign');
|
||||||
|
|||||||
@@ -4,6 +4,8 @@ use Illuminate\Support\ServiceProvider;
|
|||||||
use Storage;
|
use Storage;
|
||||||
use League\Flysystem\Filesystem;
|
use League\Flysystem\Filesystem;
|
||||||
use League\Flysystem\Sftp\SftpAdapter;
|
use League\Flysystem\Sftp\SftpAdapter;
|
||||||
|
use League\Flysystem\AwsS3v3\AwsS3Adapter as AwsS3v3Adapter;
|
||||||
|
use Aws\S3\S3Client;
|
||||||
|
|
||||||
class AppServiceProvider extends ServiceProvider {
|
class AppServiceProvider extends ServiceProvider {
|
||||||
|
|
||||||
@@ -27,6 +29,21 @@ class AppServiceProvider extends ServiceProvider {
|
|||||||
Storage::extend('sftp', function ($app, $config) {
|
Storage::extend('sftp', function ($app, $config) {
|
||||||
return new Filesystem(new SftpAdapter($config));
|
return new Filesystem(new SftpAdapter($config));
|
||||||
});
|
});
|
||||||
|
|
||||||
|
Storage::extend('minio', function ($app, $config) {
|
||||||
|
$client = new S3Client([
|
||||||
|
'credentials' => [
|
||||||
|
'key' => $config['key'],
|
||||||
|
'secret' => $config['secret'],
|
||||||
|
],
|
||||||
|
'region' => $config['region'],
|
||||||
|
'version' => 'latest',
|
||||||
|
'endpoint' => $config['endpoint'],
|
||||||
|
'use_path_style_endpoint' => filter_var($config['use_path_style_endpoint'] ?? true, FILTER_VALIDATE_BOOLEAN),
|
||||||
|
]);
|
||||||
|
$adapter = new AwsS3v3Adapter($client, $config['bucket']);
|
||||||
|
return new Filesystem($adapter);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -40,6 +57,10 @@ class AppServiceProvider extends ServiceProvider {
|
|||||||
*/
|
*/
|
||||||
public function register()
|
public function register()
|
||||||
{
|
{
|
||||||
|
// Laravel's HandleExceptions sets error_reporting(-1) which causes PECL mcrypt
|
||||||
|
// deprecation notices to become ErrorExceptions. Override it here to suppress E_DEPRECATED.
|
||||||
|
error_reporting(E_ALL & ~E_DEPRECATED & ~E_STRICT);
|
||||||
|
|
||||||
$this->app->bind(
|
$this->app->bind(
|
||||||
'Illuminate\Contracts\Auth\Registrar',
|
'Illuminate\Contracts\Auth\Registrar',
|
||||||
'App\Services\Registrar'
|
'App\Services\Registrar'
|
||||||
|
|||||||
33
app/helpers.php
Normal file
33
app/helpers.php
Normal file
@@ -0,0 +1,33 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
if (!function_exists('minio_url')) {
|
||||||
|
/**
|
||||||
|
* Generate MinIO URL for a file
|
||||||
|
*
|
||||||
|
* @param string $path File path relative to bucket
|
||||||
|
* @return string Full MinIO URL
|
||||||
|
*/
|
||||||
|
function minio_url($path)
|
||||||
|
{
|
||||||
|
$bucket = env('MINIO_BUCKET', 'crewsportswear');
|
||||||
|
$baseUrl = env('MINIO_URL', 'https://minio.crewsportswear.app');
|
||||||
|
|
||||||
|
// Remove leading slash if present
|
||||||
|
$path = ltrim($path, '/');
|
||||||
|
|
||||||
|
return $baseUrl . '/' . $bucket . '/' . $path;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!function_exists('minio_image_url')) {
|
||||||
|
/**
|
||||||
|
* Generate MinIO URL for an image in uploads/images/
|
||||||
|
*
|
||||||
|
* @param string $filename Image filename
|
||||||
|
* @return string Full MinIO URL
|
||||||
|
*/
|
||||||
|
function minio_image_url($filename)
|
||||||
|
{
|
||||||
|
return minio_url('uploads/images/' . $filename);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -11,7 +11,11 @@
|
|||||||
"guzzlehttp/guzzle": "~5.0",
|
"guzzlehttp/guzzle": "~5.0",
|
||||||
"google/recaptcha": "~1.1",
|
"google/recaptcha": "~1.1",
|
||||||
"spatie/laravel-analytics": "^1.4",
|
"spatie/laravel-analytics": "^1.4",
|
||||||
"league/flysystem-sftp": "^1.0"
|
"league/flysystem-sftp": "^1.0",
|
||||||
|
"league/flysystem-aws-s3-v3": "~1.0",
|
||||||
|
"aws/aws-sdk-php": "~3.0",
|
||||||
|
"psr/http-message": "^1.0",
|
||||||
|
"guzzlehttp/psr7": "^1.4"
|
||||||
},
|
},
|
||||||
"require-dev": {
|
"require-dev": {
|
||||||
"phpunit/phpunit": "~4.0",
|
"phpunit/phpunit": "~4.0",
|
||||||
@@ -24,7 +28,10 @@
|
|||||||
],
|
],
|
||||||
"psr-4": {
|
"psr-4": {
|
||||||
"App\\": "app/"
|
"App\\": "app/"
|
||||||
}
|
},
|
||||||
|
"files": [
|
||||||
|
"app/helpers.php"
|
||||||
|
]
|
||||||
},
|
},
|
||||||
"autoload-dev": {
|
"autoload-dev": {
|
||||||
"classmap": [
|
"classmap": [
|
||||||
|
|||||||
647
composer.lock
generated
647
composer.lock
generated
@@ -4,8 +4,153 @@
|
|||||||
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
||||||
"This file is @generated automatically"
|
"This file is @generated automatically"
|
||||||
],
|
],
|
||||||
"content-hash": "9ad9cbf7c7c319c392284bef379f0004",
|
"content-hash": "0320d93525d3aeed0db29b492fe6f3cc",
|
||||||
"packages": [
|
"packages": [
|
||||||
|
{
|
||||||
|
"name": "aws/aws-crt-php",
|
||||||
|
"version": "v1.2.7",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/awslabs/aws-crt-php.git",
|
||||||
|
"reference": "d71d9906c7bb63a28295447ba12e74723bd3730e"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/awslabs/aws-crt-php/zipball/d71d9906c7bb63a28295447ba12e74723bd3730e",
|
||||||
|
"reference": "d71d9906c7bb63a28295447ba12e74723bd3730e",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"php": ">=5.5"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"phpunit/phpunit": "^4.8.35||^5.6.3||^9.5",
|
||||||
|
"yoast/phpunit-polyfills": "^1.0"
|
||||||
|
},
|
||||||
|
"suggest": {
|
||||||
|
"ext-awscrt": "Make sure you install awscrt native extension to use any of the functionality."
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"autoload": {
|
||||||
|
"classmap": [
|
||||||
|
"src/"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"Apache-2.0"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "AWS SDK Common Runtime Team",
|
||||||
|
"email": "aws-sdk-common-runtime@amazon.com"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "AWS Common Runtime for PHP",
|
||||||
|
"homepage": "https://github.com/awslabs/aws-crt-php",
|
||||||
|
"keywords": [
|
||||||
|
"amazon",
|
||||||
|
"aws",
|
||||||
|
"crt",
|
||||||
|
"sdk"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"issues": "https://github.com/awslabs/aws-crt-php/issues",
|
||||||
|
"source": "https://github.com/awslabs/aws-crt-php/tree/v1.2.7"
|
||||||
|
},
|
||||||
|
"time": "2024-10-18T22:15:13+00:00"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "aws/aws-sdk-php",
|
||||||
|
"version": "3.226.0",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/aws/aws-sdk-php.git",
|
||||||
|
"reference": "d76d4fe0fa603ddc3f5c54d9664438dc1a808859"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/aws/aws-sdk-php/zipball/d76d4fe0fa603ddc3f5c54d9664438dc1a808859",
|
||||||
|
"reference": "d76d4fe0fa603ddc3f5c54d9664438dc1a808859",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"aws/aws-crt-php": "^1.0.2",
|
||||||
|
"ext-json": "*",
|
||||||
|
"ext-pcre": "*",
|
||||||
|
"ext-simplexml": "*",
|
||||||
|
"guzzlehttp/guzzle": "^5.3.3 || ^6.2.1 || ^7.0",
|
||||||
|
"guzzlehttp/promises": "^1.4.0",
|
||||||
|
"guzzlehttp/psr7": "^1.7.0 || ^2.1.1",
|
||||||
|
"mtdowling/jmespath.php": "^2.6",
|
||||||
|
"php": ">=5.5"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"andrewsville/php-token-reflection": "^1.4",
|
||||||
|
"aws/aws-php-sns-message-validator": "~1.0",
|
||||||
|
"behat/behat": "~3.0",
|
||||||
|
"doctrine/cache": "~1.4",
|
||||||
|
"ext-dom": "*",
|
||||||
|
"ext-openssl": "*",
|
||||||
|
"ext-pcntl": "*",
|
||||||
|
"ext-sockets": "*",
|
||||||
|
"nette/neon": "^2.3",
|
||||||
|
"paragonie/random_compat": ">= 2",
|
||||||
|
"phpunit/phpunit": "^4.8.35 || ^5.6.3",
|
||||||
|
"psr/cache": "^1.0",
|
||||||
|
"psr/simple-cache": "^1.0",
|
||||||
|
"sebastian/comparator": "^1.2.3"
|
||||||
|
},
|
||||||
|
"suggest": {
|
||||||
|
"aws/aws-php-sns-message-validator": "To validate incoming SNS notifications",
|
||||||
|
"doctrine/cache": "To use the DoctrineCacheAdapter",
|
||||||
|
"ext-curl": "To send requests using cURL",
|
||||||
|
"ext-openssl": "Allows working with CloudFront private distributions and verifying received SNS messages",
|
||||||
|
"ext-sockets": "To use client-side monitoring"
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"extra": {
|
||||||
|
"branch-alias": {
|
||||||
|
"dev-master": "3.0-dev"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"autoload": {
|
||||||
|
"files": [
|
||||||
|
"src/functions.php"
|
||||||
|
],
|
||||||
|
"psr-4": {
|
||||||
|
"Aws\\": "src/"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"Apache-2.0"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Amazon Web Services",
|
||||||
|
"homepage": "http://aws.amazon.com"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "AWS SDK for PHP - Use Amazon Web Services in your PHP project",
|
||||||
|
"homepage": "http://aws.amazon.com/sdkforphp",
|
||||||
|
"keywords": [
|
||||||
|
"amazon",
|
||||||
|
"aws",
|
||||||
|
"cloud",
|
||||||
|
"dynamodb",
|
||||||
|
"ec2",
|
||||||
|
"glacier",
|
||||||
|
"s3",
|
||||||
|
"sdk"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"forum": "https://forums.aws.amazon.com/forum.jspa?forumID=80",
|
||||||
|
"issues": "https://github.com/aws/aws-sdk-php/issues",
|
||||||
|
"source": "https://github.com/aws/aws-sdk-php/tree/3.226.0"
|
||||||
|
},
|
||||||
|
"time": "2022-06-16T18:14:10+00:00"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "classpreloader/classpreloader",
|
"name": "classpreloader/classpreloader",
|
||||||
"version": "1.4.0",
|
"version": "1.4.0",
|
||||||
@@ -365,6 +510,190 @@
|
|||||||
],
|
],
|
||||||
"time": "2019-10-30T09:32:00+00:00"
|
"time": "2019-10-30T09:32:00+00:00"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "guzzlehttp/promises",
|
||||||
|
"version": "1.5.3",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/guzzle/promises.git",
|
||||||
|
"reference": "67ab6e18aaa14d753cc148911d273f6e6cb6721e"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/guzzle/promises/zipball/67ab6e18aaa14d753cc148911d273f6e6cb6721e",
|
||||||
|
"reference": "67ab6e18aaa14d753cc148911d273f6e6cb6721e",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"php": ">=5.5"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"symfony/phpunit-bridge": "^4.4 || ^5.1"
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"autoload": {
|
||||||
|
"files": [
|
||||||
|
"src/functions_include.php"
|
||||||
|
],
|
||||||
|
"psr-4": {
|
||||||
|
"GuzzleHttp\\Promise\\": "src/"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Graham Campbell",
|
||||||
|
"email": "hello@gjcampbell.co.uk",
|
||||||
|
"homepage": "https://github.com/GrahamCampbell"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Michael Dowling",
|
||||||
|
"email": "mtdowling@gmail.com",
|
||||||
|
"homepage": "https://github.com/mtdowling"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Tobias Nyholm",
|
||||||
|
"email": "tobias.nyholm@gmail.com",
|
||||||
|
"homepage": "https://github.com/Nyholm"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Tobias Schultze",
|
||||||
|
"email": "webmaster@tubo-world.de",
|
||||||
|
"homepage": "https://github.com/Tobion"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Guzzle promises library",
|
||||||
|
"keywords": [
|
||||||
|
"promise"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"issues": "https://github.com/guzzle/promises/issues",
|
||||||
|
"source": "https://github.com/guzzle/promises/tree/1.5.3"
|
||||||
|
},
|
||||||
|
"funding": [
|
||||||
|
{
|
||||||
|
"url": "https://github.com/GrahamCampbell",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://github.com/Nyholm",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://tidelift.com/funding/github/packagist/guzzlehttp/promises",
|
||||||
|
"type": "tidelift"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"time": "2023-05-21T12:31:43+00:00"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "guzzlehttp/psr7",
|
||||||
|
"version": "1.9.1",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/guzzle/psr7.git",
|
||||||
|
"reference": "e4490cabc77465aaee90b20cfc9a770f8c04be6b"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/guzzle/psr7/zipball/e4490cabc77465aaee90b20cfc9a770f8c04be6b",
|
||||||
|
"reference": "e4490cabc77465aaee90b20cfc9a770f8c04be6b",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"php": ">=5.4.0",
|
||||||
|
"psr/http-message": "~1.0",
|
||||||
|
"ralouphie/getallheaders": "^2.0.5 || ^3.0.0"
|
||||||
|
},
|
||||||
|
"provide": {
|
||||||
|
"psr/http-message-implementation": "1.0"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"ext-zlib": "*",
|
||||||
|
"phpunit/phpunit": "~4.8.36 || ^5.7.27 || ^6.5.14 || ^7.5.20 || ^8.5.8 || ^9.3.10"
|
||||||
|
},
|
||||||
|
"suggest": {
|
||||||
|
"laminas/laminas-httphandlerrunner": "Emit PSR-7 responses"
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"autoload": {
|
||||||
|
"files": [
|
||||||
|
"src/functions_include.php"
|
||||||
|
],
|
||||||
|
"psr-4": {
|
||||||
|
"GuzzleHttp\\Psr7\\": "src/"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Graham Campbell",
|
||||||
|
"email": "hello@gjcampbell.co.uk",
|
||||||
|
"homepage": "https://github.com/GrahamCampbell"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Michael Dowling",
|
||||||
|
"email": "mtdowling@gmail.com",
|
||||||
|
"homepage": "https://github.com/mtdowling"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "George Mponos",
|
||||||
|
"email": "gmponos@gmail.com",
|
||||||
|
"homepage": "https://github.com/gmponos"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Tobias Nyholm",
|
||||||
|
"email": "tobias.nyholm@gmail.com",
|
||||||
|
"homepage": "https://github.com/Nyholm"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Márk Sági-Kazár",
|
||||||
|
"email": "mark.sagikazar@gmail.com",
|
||||||
|
"homepage": "https://github.com/sagikazarmark"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Tobias Schultze",
|
||||||
|
"email": "webmaster@tubo-world.de",
|
||||||
|
"homepage": "https://github.com/Tobion"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "PSR-7 message implementation that also provides common utility methods",
|
||||||
|
"keywords": [
|
||||||
|
"http",
|
||||||
|
"message",
|
||||||
|
"psr-7",
|
||||||
|
"request",
|
||||||
|
"response",
|
||||||
|
"stream",
|
||||||
|
"uri",
|
||||||
|
"url"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"issues": "https://github.com/guzzle/psr7/issues",
|
||||||
|
"source": "https://github.com/guzzle/psr7/tree/1.9.1"
|
||||||
|
},
|
||||||
|
"funding": [
|
||||||
|
{
|
||||||
|
"url": "https://github.com/GrahamCampbell",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://github.com/Nyholm",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://tidelift.com/funding/github/packagist/guzzlehttp/psr7",
|
||||||
|
"type": "tidelift"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"time": "2023-04-17T16:00:37+00:00"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "guzzlehttp/ringphp",
|
"name": "guzzlehttp/ringphp",
|
||||||
"version": "1.1.1",
|
"version": "1.1.1",
|
||||||
@@ -907,6 +1236,71 @@
|
|||||||
],
|
],
|
||||||
"time": "2019-10-16T21:01:05+00:00"
|
"time": "2019-10-16T21:01:05+00:00"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "league/flysystem-aws-s3-v3",
|
||||||
|
"version": "1.0.30",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/thephpleague/flysystem-aws-s3-v3.git",
|
||||||
|
"reference": "af286f291ebab6877bac0c359c6c2cb017eb061d"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/thephpleague/flysystem-aws-s3-v3/zipball/af286f291ebab6877bac0c359c6c2cb017eb061d",
|
||||||
|
"reference": "af286f291ebab6877bac0c359c6c2cb017eb061d",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"aws/aws-sdk-php": "^3.20.0",
|
||||||
|
"league/flysystem": "^1.0.40",
|
||||||
|
"php": ">=5.5.0"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"henrikbjorn/phpspec-code-coverage": "~1.0.1",
|
||||||
|
"phpspec/phpspec": "^2.0.0"
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"extra": {
|
||||||
|
"branch-alias": {
|
||||||
|
"dev-master": "1.0-dev"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"autoload": {
|
||||||
|
"psr-4": {
|
||||||
|
"League\\Flysystem\\AwsS3v3\\": "src/"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Frank de Jonge",
|
||||||
|
"email": "info@frenky.net"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Flysystem adapter for the AWS S3 SDK v3.x",
|
||||||
|
"support": {
|
||||||
|
"issues": "https://github.com/thephpleague/flysystem-aws-s3-v3/issues",
|
||||||
|
"source": "https://github.com/thephpleague/flysystem-aws-s3-v3/tree/1.0.30"
|
||||||
|
},
|
||||||
|
"funding": [
|
||||||
|
{
|
||||||
|
"url": "https://offset.earth/frankdejonge",
|
||||||
|
"type": "custom"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://github.com/frankdejonge",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://tidelift.com/funding/github/packagist/league/flysystem",
|
||||||
|
"type": "tidelift"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"time": "2022-07-02T13:51:38+00:00"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "league/flysystem-sftp",
|
"name": "league/flysystem-sftp",
|
||||||
"version": "1.0.22",
|
"version": "1.0.22",
|
||||||
@@ -1071,6 +1465,72 @@
|
|||||||
],
|
],
|
||||||
"time": "2017-01-23T04:29:33+00:00"
|
"time": "2017-01-23T04:29:33+00:00"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "mtdowling/jmespath.php",
|
||||||
|
"version": "2.8.0",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/jmespath/jmespath.php.git",
|
||||||
|
"reference": "a2a865e05d5f420b50cc2f85bb78d565db12a6bc"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/jmespath/jmespath.php/zipball/a2a865e05d5f420b50cc2f85bb78d565db12a6bc",
|
||||||
|
"reference": "a2a865e05d5f420b50cc2f85bb78d565db12a6bc",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"php": "^7.2.5 || ^8.0",
|
||||||
|
"symfony/polyfill-mbstring": "^1.17"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"composer/xdebug-handler": "^3.0.3",
|
||||||
|
"phpunit/phpunit": "^8.5.33"
|
||||||
|
},
|
||||||
|
"bin": [
|
||||||
|
"bin/jp.php"
|
||||||
|
],
|
||||||
|
"type": "library",
|
||||||
|
"extra": {
|
||||||
|
"branch-alias": {
|
||||||
|
"dev-master": "2.8-dev"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"autoload": {
|
||||||
|
"files": [
|
||||||
|
"src/JmesPath.php"
|
||||||
|
],
|
||||||
|
"psr-4": {
|
||||||
|
"JmesPath\\": "src/"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Graham Campbell",
|
||||||
|
"email": "hello@gjcampbell.co.uk",
|
||||||
|
"homepage": "https://github.com/GrahamCampbell"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Michael Dowling",
|
||||||
|
"email": "mtdowling@gmail.com",
|
||||||
|
"homepage": "https://github.com/mtdowling"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Declaratively specify how to extract elements from a JSON document",
|
||||||
|
"keywords": [
|
||||||
|
"json",
|
||||||
|
"jsonpath"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"issues": "https://github.com/jmespath/jmespath.php/issues",
|
||||||
|
"source": "https://github.com/jmespath/jmespath.php/tree/2.8.0"
|
||||||
|
},
|
||||||
|
"time": "2024-09-04T18:46:31+00:00"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "nesbot/carbon",
|
"name": "nesbot/carbon",
|
||||||
"version": "1.39.1",
|
"version": "1.39.1",
|
||||||
@@ -1409,6 +1869,59 @@
|
|||||||
],
|
],
|
||||||
"time": "2019-09-17T03:41:22+00:00"
|
"time": "2019-09-17T03:41:22+00:00"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "psr/http-message",
|
||||||
|
"version": "1.1",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/php-fig/http-message.git",
|
||||||
|
"reference": "cb6ce4845ce34a8ad9e68117c10ee90a29919eba"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/php-fig/http-message/zipball/cb6ce4845ce34a8ad9e68117c10ee90a29919eba",
|
||||||
|
"reference": "cb6ce4845ce34a8ad9e68117c10ee90a29919eba",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"php": "^7.2 || ^8.0"
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"extra": {
|
||||||
|
"branch-alias": {
|
||||||
|
"dev-master": "1.1.x-dev"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"autoload": {
|
||||||
|
"psr-4": {
|
||||||
|
"Psr\\Http\\Message\\": "src/"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "PHP-FIG",
|
||||||
|
"homepage": "http://www.php-fig.org/"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Common interface for HTTP messages",
|
||||||
|
"homepage": "https://github.com/php-fig/http-message",
|
||||||
|
"keywords": [
|
||||||
|
"http",
|
||||||
|
"http-message",
|
||||||
|
"psr",
|
||||||
|
"psr-7",
|
||||||
|
"request",
|
||||||
|
"response"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"source": "https://github.com/php-fig/http-message/tree/1.1"
|
||||||
|
},
|
||||||
|
"time": "2023-04-04T09:50:52+00:00"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "psr/log",
|
"name": "psr/log",
|
||||||
"version": "1.1.2",
|
"version": "1.1.2",
|
||||||
@@ -1527,6 +2040,50 @@
|
|||||||
],
|
],
|
||||||
"time": "2015-03-26T18:43:54+00:00"
|
"time": "2015-03-26T18:43:54+00:00"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "ralouphie/getallheaders",
|
||||||
|
"version": "3.0.3",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/ralouphie/getallheaders.git",
|
||||||
|
"reference": "120b605dfeb996808c31b6477290a714d356e822"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/ralouphie/getallheaders/zipball/120b605dfeb996808c31b6477290a714d356e822",
|
||||||
|
"reference": "120b605dfeb996808c31b6477290a714d356e822",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"php": ">=5.6"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"php-coveralls/php-coveralls": "^2.1",
|
||||||
|
"phpunit/phpunit": "^5 || ^6.5"
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"autoload": {
|
||||||
|
"files": [
|
||||||
|
"src/getallheaders.php"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Ralph Khattar",
|
||||||
|
"email": "ralph.khattar@gmail.com"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "A polyfill for getallheaders.",
|
||||||
|
"support": {
|
||||||
|
"issues": "https://github.com/ralouphie/getallheaders/issues",
|
||||||
|
"source": "https://github.com/ralouphie/getallheaders/tree/develop"
|
||||||
|
},
|
||||||
|
"time": "2019-03-08T08:55:37+00:00"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "react/promise",
|
"name": "react/promise",
|
||||||
"version": "v2.7.1",
|
"version": "v2.7.1",
|
||||||
@@ -2158,6 +2715,91 @@
|
|||||||
],
|
],
|
||||||
"time": "2019-08-06T08:03:45+00:00"
|
"time": "2019-08-06T08:03:45+00:00"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "symfony/polyfill-mbstring",
|
||||||
|
"version": "v1.36.0",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/symfony/polyfill-mbstring.git",
|
||||||
|
"reference": "6a21eb99c6973357967f6ce3708cd55a6bec6315"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/6a21eb99c6973357967f6ce3708cd55a6bec6315",
|
||||||
|
"reference": "6a21eb99c6973357967f6ce3708cd55a6bec6315",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"ext-iconv": "*",
|
||||||
|
"php": ">=7.2"
|
||||||
|
},
|
||||||
|
"provide": {
|
||||||
|
"ext-mbstring": "*"
|
||||||
|
},
|
||||||
|
"suggest": {
|
||||||
|
"ext-mbstring": "For best performance"
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"extra": {
|
||||||
|
"thanks": {
|
||||||
|
"url": "https://github.com/symfony/polyfill",
|
||||||
|
"name": "symfony/polyfill"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"autoload": {
|
||||||
|
"files": [
|
||||||
|
"bootstrap.php"
|
||||||
|
],
|
||||||
|
"psr-4": {
|
||||||
|
"Symfony\\Polyfill\\Mbstring\\": ""
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Nicolas Grekas",
|
||||||
|
"email": "p@tchwork.com"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Symfony Community",
|
||||||
|
"homepage": "https://symfony.com/contributors"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "Symfony polyfill for the Mbstring extension",
|
||||||
|
"homepage": "https://symfony.com",
|
||||||
|
"keywords": [
|
||||||
|
"compatibility",
|
||||||
|
"mbstring",
|
||||||
|
"polyfill",
|
||||||
|
"portable",
|
||||||
|
"shim"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"source": "https://github.com/symfony/polyfill-mbstring/tree/v1.36.0"
|
||||||
|
},
|
||||||
|
"funding": [
|
||||||
|
{
|
||||||
|
"url": "https://symfony.com/sponsor",
|
||||||
|
"type": "custom"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://github.com/fabpot",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://github.com/nicolas-grekas",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
|
||||||
|
"type": "tidelift"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"time": "2026-04-10T17:25:58+00:00"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "symfony/polyfill-php56",
|
"name": "symfony/polyfill-php56",
|
||||||
"version": "v1.12.0",
|
"version": "v1.12.0",
|
||||||
@@ -3909,5 +4551,6 @@
|
|||||||
"prefer-stable": false,
|
"prefer-stable": false,
|
||||||
"prefer-lowest": false,
|
"prefer-lowest": false,
|
||||||
"platform": [],
|
"platform": [],
|
||||||
"platform-dev": []
|
"platform-dev": [],
|
||||||
|
"plugin-api-version": "2.2.0"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -77,7 +77,7 @@ return [
|
|||||||
'port' => 22,
|
'port' => 22,
|
||||||
'username' => 'root',
|
'username' => 'root',
|
||||||
'password' => '',
|
'password' => '',
|
||||||
'privateKey' => '/var/www/html/_key/instance2/root.ppk',
|
'privateKey' => '/var/keys/root.ppk',
|
||||||
'root' => '/var/www/html/images',
|
'root' => '/var/www/html/images',
|
||||||
'timeout' => 10
|
'timeout' => 10
|
||||||
],
|
],
|
||||||
@@ -86,6 +86,18 @@ return [
|
|||||||
'driver' => 'local',
|
'driver' => 'local',
|
||||||
'root' => '/var/www/html/uploads/images',
|
'root' => '/var/www/html/uploads/images',
|
||||||
],
|
],
|
||||||
|
|
||||||
|
'minio' => [
|
||||||
|
'driver' => 'minio',
|
||||||
|
'key' => env('MINIO_KEY'),
|
||||||
|
'secret' => env('MINIO_SECRET'),
|
||||||
|
'region' => env('MINIO_REGION', 'us-east-1'),
|
||||||
|
'bucket' => env('MINIO_BUCKET', 'crewsportswear'),
|
||||||
|
'endpoint' => env('MINIO_ENDPOINT'),
|
||||||
|
'use_path_style_endpoint' => env('MINIO_USE_PATH_STYLE', true),
|
||||||
|
'url' => env('MINIO_URL', 'https://minio.crewsportswear.app'),
|
||||||
|
],
|
||||||
|
|
||||||
],
|
],
|
||||||
|
|
||||||
];
|
];
|
||||||
@@ -18,6 +18,7 @@ return [
|
|||||||
|
|
||||||
'prod_private_server_ip' => env('https://crewsportswear.app', 'https://crewsportswear.app'),
|
'prod_private_server_ip' => env('https://crewsportswear.app', 'https://crewsportswear.app'),
|
||||||
'images_url' => env('https://crewsportswear.app:5955', 'https://crewsportswear.app:5955'),
|
'images_url' => env('https://crewsportswear.app:5955', 'https://crewsportswear.app:5955'),
|
||||||
|
'minio_url' => env('MINIO_URL', 'https://minio.crewsportswear.app/crewsportswear'),
|
||||||
'uploads' => env('https://crewsportswear.com/uploads/images/', 'https://crewsportswear.com/uploads/images/'), // local
|
'uploads' => env('https://crewsportswear.com/uploads/images/', 'https://crewsportswear.com/uploads/images/'), // local
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -31,6 +31,7 @@ services:
|
|||||||
volumes:
|
volumes:
|
||||||
- ./storage:/var/www/html/storage
|
- ./storage:/var/www/html/storage
|
||||||
- ./public/uploads:/var/www/html/public/uploads
|
- ./public/uploads:/var/www/html/public/uploads
|
||||||
|
- /var/crew-keys:/var/keys:ro
|
||||||
labels:
|
labels:
|
||||||
- "traefik.enable=true"
|
- "traefik.enable=true"
|
||||||
# Development environment (dev.crewsportswear.app)
|
# Development environment (dev.crewsportswear.app)
|
||||||
|
|||||||
@@ -1,3 +1,19 @@
|
|||||||
|
# ─────────────────────────────────────────────────────────────────────────────
|
||||||
|
# Local development stack
|
||||||
|
#
|
||||||
|
# Default (local MariaDB):
|
||||||
|
# docker compose -f docker-compose.local.yml up --build
|
||||||
|
#
|
||||||
|
# Remote DB via SSH private-key tunnel:
|
||||||
|
# 1. Set SSH_HOST, SSH_USER, SSH_KEY_PATH, SSH_DB_REMOTE_HOST,
|
||||||
|
# SSH_DB_REMOTE_PORT (and DB_* creds) in .env.local
|
||||||
|
# 2. docker compose -f docker-compose.local.yml --profile ssh-db up --build
|
||||||
|
# The app will talk to db-tunnel (port 3306) instead of the local db.
|
||||||
|
#
|
||||||
|
# App: http://localhost:8082
|
||||||
|
# phpMyAdmin: http://localhost:8083
|
||||||
|
# ─────────────────────────────────────────────────────────────────────────────
|
||||||
|
|
||||||
services:
|
services:
|
||||||
db:
|
db:
|
||||||
image: mariadb:10.6
|
image: mariadb:10.6
|
||||||
@@ -29,11 +45,7 @@ services:
|
|||||||
- APP_DEBUG=true
|
- APP_DEBUG=true
|
||||||
- APP_URL=http://localhost:8082
|
- APP_URL=http://localhost:8082
|
||||||
- DB_CONNECTION=mysql
|
- DB_CONNECTION=mysql
|
||||||
- DB_HOST=db
|
- DB_PORT=${DB_PORT:-3306}
|
||||||
- DB_PORT=3306
|
|
||||||
- DB_DATABASE=crewsportswear
|
|
||||||
- DB_USERNAME=crewsportswear
|
|
||||||
- DB_PASSWORD=secret
|
|
||||||
- PROD_PRIVATE=http://localhost:8082
|
- PROD_PRIVATE=http://localhost:8082
|
||||||
- IMAGES_URL=http://localhost:8082
|
- IMAGES_URL=http://localhost:8082
|
||||||
- UPLOAD_URL=http://localhost:8082/uploads/
|
- UPLOAD_URL=http://localhost:8082/uploads/
|
||||||
@@ -48,15 +60,73 @@ services:
|
|||||||
- ANALYTICS_SITE_ID=
|
- ANALYTICS_SITE_ID=
|
||||||
- ANALYTICS_CLIENT_ID=
|
- ANALYTICS_CLIENT_ID=
|
||||||
- ANALYTICS_SERVICE_EMAIL=
|
- ANALYTICS_SERVICE_EMAIL=
|
||||||
|
# MinIO S3 Storage (connect to production MinIO for testing)
|
||||||
|
- MINIO_ENDPOINT=https://minio.crewsportswear.app
|
||||||
|
- MINIO_KEY=${MINIO_KEY:-minioadmin}
|
||||||
|
- MINIO_SECRET=${MINIO_SECRET:-minioadmin}
|
||||||
|
- MINIO_BUCKET=crewsportswear
|
||||||
|
- MINIO_REGION=us-east-1
|
||||||
|
- MINIO_USE_PATH_STYLE=false
|
||||||
|
- MINIO_URL=https://minio.crewsportswear.app
|
||||||
|
# DB_HOST defaults to local container; set to db-tunnel in .env.local for SSH mode
|
||||||
|
- DB_HOST=${DB_HOST:-db}
|
||||||
|
- DB_DATABASE=${DB_DATABASE:-crewsportswear}
|
||||||
|
- DB_USERNAME=${DB_USERNAME:-crewsportswear}
|
||||||
|
- DB_PASSWORD=${DB_PASSWORD:-secret}
|
||||||
|
env_file:
|
||||||
|
- path: .env.local
|
||||||
|
required: false
|
||||||
volumes:
|
volumes:
|
||||||
- ./:/var/www/html
|
- ./:/var/www/html
|
||||||
- ./storage:/var/www/html/storage
|
- ./storage:/var/www/html/storage
|
||||||
- ./public/uploads:/var/www/html/public/uploads
|
- ./public/uploads:/var/www/html/public/uploads
|
||||||
|
# Keep the vendor/ directory from the image — prevents the bind-mount
|
||||||
|
# from wiping out the composer install done during docker build.
|
||||||
|
- vendor_local:/var/www/html/vendor
|
||||||
depends_on:
|
depends_on:
|
||||||
- db
|
- db
|
||||||
networks:
|
networks:
|
||||||
- crewsportswear-local
|
- crewsportswear-local
|
||||||
|
|
||||||
|
# ── SSH tunnel to a remote database ────────────────────────────────────────
|
||||||
|
# Activated only with: --profile ssh-db
|
||||||
|
# Requires SSH_HOST, SSH_USER, SSH_KEY_PATH (and optionally SSH_PORT,
|
||||||
|
# SSH_DB_REMOTE_HOST, SSH_DB_REMOTE_PORT) set in .env.local.
|
||||||
|
db-tunnel:
|
||||||
|
profiles:
|
||||||
|
- ssh-db
|
||||||
|
image: alpine:3.19
|
||||||
|
container_name: crewsportswear_db_tunnel
|
||||||
|
restart: unless-stopped
|
||||||
|
environment:
|
||||||
|
- SSH_HOST=${SSH_HOST}
|
||||||
|
- SSH_PORT=${SSH_PORT:-22}
|
||||||
|
- SSH_USER=${SSH_USER:-root}
|
||||||
|
- SSH_DB_REMOTE_HOST=${SSH_DB_REMOTE_HOST:-127.0.0.1}
|
||||||
|
- SSH_DB_REMOTE_PORT=${SSH_DB_REMOTE_PORT:-3306}
|
||||||
|
volumes:
|
||||||
|
# Mount your private key read-only; path configured in .env.local
|
||||||
|
- ${SSH_KEY_PATH:-~/.ssh/id_rsa}:/ssh/id_rsa:ro
|
||||||
|
command:
|
||||||
|
- sh
|
||||||
|
- -c
|
||||||
|
- |
|
||||||
|
apk add --no-cache openssh-client
|
||||||
|
cp /ssh/id_rsa /tmp/id_rsa
|
||||||
|
chmod 600 /tmp/id_rsa
|
||||||
|
echo "Starting SSH tunnel to $$SSH_HOST..."
|
||||||
|
exec ssh -N \
|
||||||
|
-o StrictHostKeyChecking=no \
|
||||||
|
-o ServerAliveInterval=30 \
|
||||||
|
-o ServerAliveCountMax=3 \
|
||||||
|
-o ExitOnForwardFailure=yes \
|
||||||
|
-i /tmp/id_rsa \
|
||||||
|
-L "0.0.0.0:3306:$$SSH_DB_REMOTE_HOST:$$SSH_DB_REMOTE_PORT" \
|
||||||
|
-p "$$SSH_PORT" \
|
||||||
|
"$$SSH_USER@$$SSH_HOST"
|
||||||
|
networks:
|
||||||
|
- crewsportswear-local
|
||||||
|
|
||||||
phpmyadmin:
|
phpmyadmin:
|
||||||
image: arm64v8/phpmyadmin
|
image: arm64v8/phpmyadmin
|
||||||
platform: linux/arm64
|
platform: linux/arm64
|
||||||
@@ -79,3 +149,4 @@ networks:
|
|||||||
|
|
||||||
volumes:
|
volumes:
|
||||||
db_data:
|
db_data:
|
||||||
|
vendor_local:
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ services:
|
|||||||
environment:
|
environment:
|
||||||
- APP_ENV=${APP_ENV:-production}
|
- APP_ENV=${APP_ENV:-production}
|
||||||
- APP_DEBUG=${APP_DEBUG:-false}
|
- APP_DEBUG=${APP_DEBUG:-false}
|
||||||
- APP_URL=${APP_URL:-https://dev-crew.crewsportswear.app}
|
- APP_URL=${APP_URL:-https://crewsportswear.com}
|
||||||
- DB_CONNECTION=mysql
|
- DB_CONNECTION=mysql
|
||||||
- DB_HOST=${DB_HOST}
|
- DB_HOST=${DB_HOST}
|
||||||
- DB_PORT=${DB_PORT:-3306}
|
- DB_PORT=${DB_PORT:-3306}
|
||||||
@@ -28,22 +28,31 @@ services:
|
|||||||
- ANALYTICS_SITE_ID=${ANALYTICS_SITE_ID}
|
- ANALYTICS_SITE_ID=${ANALYTICS_SITE_ID}
|
||||||
- ANALYTICS_CLIENT_ID=${ANALYTICS_CLIENT_ID}
|
- ANALYTICS_CLIENT_ID=${ANALYTICS_CLIENT_ID}
|
||||||
- ANALYTICS_SERVICE_EMAIL=${ANALYTICS_SERVICE_EMAIL}
|
- ANALYTICS_SERVICE_EMAIL=${ANALYTICS_SERVICE_EMAIL}
|
||||||
|
# MinIO S3 Storage
|
||||||
|
- MINIO_ENDPOINT=${MINIO_ENDPOINT:-http://crew-minio-prod:9000}
|
||||||
|
- MINIO_KEY=${MINIO_KEY}
|
||||||
|
- MINIO_SECRET=${MINIO_SECRET}
|
||||||
|
- MINIO_BUCKET=${MINIO_BUCKET:-crewsportswear}
|
||||||
|
- MINIO_REGION=${MINIO_REGION:-us-east-1}
|
||||||
|
- MINIO_USE_PATH_STYLE=${MINIO_USE_PATH_STYLE:-true}
|
||||||
|
- MINIO_URL=${MINIO_URL:-https://minio.crewsportswear.app}
|
||||||
volumes:
|
volumes:
|
||||||
- ./storage:/var/www/html/storage
|
- ./storage:/var/www/html/storage
|
||||||
- ./public/uploads:/var/www/html/public/uploads
|
- ./public/uploads:/var/www/html/public/uploads
|
||||||
|
- /var/crew-keys:/var/keys:ro
|
||||||
labels:
|
labels:
|
||||||
- "traefik.enable=true"
|
- "traefik.enable=true"
|
||||||
# Production environment (dev-crew.crewsportswear.app) - Uses Let's Encrypt
|
# Production environment (crewsportswear.com) - Uses paid SSL certificate
|
||||||
- "traefik.http.routers.crewsportswear-prod.rule=Host(`dev-crew.crewsportswear.app`)"
|
- "traefik.http.routers.crewsportswear-prod.rule=Host(`crewsportswear.com`)"
|
||||||
- "traefik.http.routers.crewsportswear-prod.entrypoints=websecure"
|
- "traefik.http.routers.crewsportswear-prod.entrypoints=websecure"
|
||||||
- "traefik.http.routers.crewsportswear-prod.tls=true"
|
- "traefik.http.routers.crewsportswear-prod.tls=true"
|
||||||
- "traefik.http.routers.crewsportswear-prod.tls.certresolver=le"
|
|
||||||
- "traefik.http.services.crewsportswear-prod.loadbalancer.server.port=80"
|
- "traefik.http.services.crewsportswear-prod.loadbalancer.server.port=80"
|
||||||
# HTTP to HTTPS redirect
|
# HTTP to HTTPS redirect
|
||||||
- "traefik.http.routers.crewsportswear-prod-http.rule=Host(`dev-crew.crewsportswear.app`)"
|
- "traefik.http.routers.crewsportswear-prod-http.rule=Host(`crewsportswear.com`)"
|
||||||
- "traefik.http.routers.crewsportswear-prod-http.entrypoints=web"
|
- "traefik.http.routers.crewsportswear-prod-http.entrypoints=web"
|
||||||
- "traefik.http.routers.crewsportswear-prod-http.middlewares=https-redirect"
|
- "traefik.http.routers.crewsportswear-prod-http.middlewares=https-redirect"
|
||||||
- "traefik.http.middlewares.https-redirect.redirectscheme.scheme=https"
|
- "traefik.http.middlewares.https-redirect.redirectscheme.scheme=https"
|
||||||
|
|
||||||
networks:
|
networks:
|
||||||
- traefik-public
|
- traefik-public
|
||||||
- crew-app-net
|
- crew-app-net
|
||||||
|
|||||||
@@ -13,5 +13,11 @@ mkdir -p bootstrap/cache
|
|||||||
chown -R www-data:www-data storage bootstrap/cache
|
chown -R www-data:www-data storage bootstrap/cache
|
||||||
chmod -R 775 storage bootstrap/cache
|
chmod -R 775 storage bootstrap/cache
|
||||||
|
|
||||||
|
# Install/update Composer dependencies if vendor is missing or composer.json changed
|
||||||
|
if [ ! -f vendor/autoload.php ]; then
|
||||||
|
echo "vendor/autoload.php not found — running composer install..."
|
||||||
|
composer install --no-interaction --prefer-dist
|
||||||
|
fi
|
||||||
|
|
||||||
# Execute the main command
|
# Execute the main command
|
||||||
exec "$@"
|
exec "$@"
|
||||||
|
|||||||
90
public/designer/js/centering_guidelines.js
Normal file
90
public/designer/js/centering_guidelines.js
Normal file
@@ -0,0 +1,90 @@
|
|||||||
|
/**
|
||||||
|
* Augments canvas by assigning to `onObjectMove` and `onAfterRender`.
|
||||||
|
* This kind of sucks because other code using those methods will stop functioning.
|
||||||
|
* Need to fix it by replacing callbacks with pub/sub kind of subscription model.
|
||||||
|
* (or maybe use existing fabric.util.fire/observe (if it won't be too slow))
|
||||||
|
*/
|
||||||
|
function initCenteringGuidelines(canvas) {
|
||||||
|
|
||||||
|
var canvasWidth = canvas.getWidth(),
|
||||||
|
canvasHeight = canvas.getHeight(),
|
||||||
|
canvasWidthCenter = canvasWidth / 2,
|
||||||
|
canvasHeightCenter = canvasHeight / 2,
|
||||||
|
canvasWidthCenterMap = { },
|
||||||
|
canvasHeightCenterMap = { },
|
||||||
|
centerLineMargin = 4,
|
||||||
|
centerLineColor = 'rgba(255,0,241,0.5)',
|
||||||
|
centerLineWidth = 1,
|
||||||
|
ctx = canvas.getSelectionContext(),
|
||||||
|
viewportTransform;
|
||||||
|
|
||||||
|
for (var i = canvasWidthCenter - centerLineMargin, len = canvasWidthCenter + centerLineMargin; i <= len; i++) {
|
||||||
|
canvasWidthCenterMap[Math.round(i)] = true;
|
||||||
|
}
|
||||||
|
for (var i = canvasHeightCenter - centerLineMargin, len = canvasHeightCenter + centerLineMargin; i <= len; i++) {
|
||||||
|
canvasHeightCenterMap[Math.round(i)] = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
function showVerticalCenterLine() {
|
||||||
|
showCenterLine(canvasWidthCenter + 0.5, 0, canvasWidthCenter + 0.5, canvasHeight);
|
||||||
|
}
|
||||||
|
|
||||||
|
function showHorizontalCenterLine() {
|
||||||
|
showCenterLine(0, canvasHeightCenter + 0.5, canvasWidth, canvasHeightCenter + 0.5);
|
||||||
|
}
|
||||||
|
|
||||||
|
function showCenterLine(x1, y1, x2, y2) {
|
||||||
|
ctx.save();
|
||||||
|
ctx.strokeStyle = centerLineColor;
|
||||||
|
ctx.lineWidth = centerLineWidth;
|
||||||
|
ctx.beginPath();
|
||||||
|
ctx.moveTo(x1 * viewportTransform[0], y1 * viewportTransform[3]);
|
||||||
|
ctx.lineTo(x2 * viewportTransform[0], y2 * viewportTransform[3]);
|
||||||
|
ctx.stroke();
|
||||||
|
ctx.restore();
|
||||||
|
}
|
||||||
|
|
||||||
|
var afterRenderActions = [],
|
||||||
|
isInVerticalCenter,
|
||||||
|
isInHorizontalCenter;
|
||||||
|
|
||||||
|
canvas.on('mouse:down', function () {
|
||||||
|
viewportTransform = canvas.viewportTransform;
|
||||||
|
});
|
||||||
|
|
||||||
|
canvas.on('object:moving', function(e) {
|
||||||
|
var object = e.target,
|
||||||
|
objectCenter = object.getCenterPoint(),
|
||||||
|
transform = canvas._currentTransform;
|
||||||
|
|
||||||
|
if (!transform) return;
|
||||||
|
|
||||||
|
isInVerticalCenter = Math.round(objectCenter.x) in canvasWidthCenterMap,
|
||||||
|
isInHorizontalCenter = Math.round(objectCenter.y) in canvasHeightCenterMap;
|
||||||
|
|
||||||
|
if (isInHorizontalCenter || isInVerticalCenter) {
|
||||||
|
object.setPositionByOrigin(new fabric.Point((isInVerticalCenter ? canvasWidthCenter : objectCenter.x), (isInHorizontalCenter ? canvasHeightCenter : objectCenter.y)), 'center', 'center');
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
canvas.on('before:render', function() {
|
||||||
|
if (canvas.contextTop) {
|
||||||
|
canvas.clearContext(canvas.contextTop);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
canvas.on('after:render', function() {
|
||||||
|
if (isInVerticalCenter) {
|
||||||
|
showVerticalCenterLine();
|
||||||
|
}
|
||||||
|
if (isInHorizontalCenter) {
|
||||||
|
showHorizontalCenterLine();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
canvas.on('mouse:up', function() {
|
||||||
|
// clear these values, to stop drawing guidelines once mouse is up
|
||||||
|
isInVerticalCenter = isInHorizontalCenter = null;
|
||||||
|
canvas.renderAll();
|
||||||
|
});
|
||||||
|
}
|
||||||
84
readme.md
84
readme.md
@@ -1,23 +1,79 @@
|
|||||||
## Laravel PHP Framework
|
# Crew Sportswear
|
||||||
|
|
||||||
[](https://travis-ci.org/laravel/framework)
|
A custom sportswear and apparel e-commerce platform built with Laravel.
|
||||||
[](https://packagist.org/packages/laravel/framework)
|
|
||||||
[](https://packagist.org/packages/laravel/framework)
|
|
||||||
[](https://packagist.org/packages/laravel/framework)
|
|
||||||
[](https://packagist.org/packages/laravel/framework)
|
|
||||||
|
|
||||||
Laravel is a web application framework with expressive, elegant syntax. We believe development must be an enjoyable, creative experience to be truly fulfilling. Laravel attempts to take the pain out of development by easing common tasks used in the majority of web projects, such as authentication, routing, sessions, queueing, and caching.
|
## Production URL
|
||||||
|
|
||||||
Laravel is accessible, yet powerful, providing powerful tools needed for large, robust applications. A superb inversion of control container, expressive migration system, and tightly integrated unit testing support give you the tools you need to build any application with which you are tasked.
|
https://crewsportswear.com
|
||||||
|
|
||||||
## Official Documentation
|
## Requirements
|
||||||
|
|
||||||
Documentation for the framework can be found on the [Laravel website](http://laravel.com/docs).
|
- Docker & Docker Compose
|
||||||
|
- PHP 7.4+
|
||||||
|
- MySQL 5.7+
|
||||||
|
- Composer
|
||||||
|
- Node.js & NPM
|
||||||
|
|
||||||
## Contributing
|
## Installation
|
||||||
|
|
||||||
Thank you for considering contributing to the Laravel framework! The contribution guide can be found in the [Laravel documentation](http://laravel.com/docs/contributions).
|
1. Clone the repository
|
||||||
|
2. Copy `.env.example` to `.env` and configure your environment variables
|
||||||
|
3. Install PHP dependencies:
|
||||||
|
```bash
|
||||||
|
composer install
|
||||||
|
```
|
||||||
|
4. Install Node dependencies:
|
||||||
|
```bash
|
||||||
|
npm install
|
||||||
|
```
|
||||||
|
5. Generate application key:
|
||||||
|
```bash
|
||||||
|
php artisan key:generate
|
||||||
|
```
|
||||||
|
6. Run migrations:
|
||||||
|
```bash
|
||||||
|
php artisan migrate
|
||||||
|
```
|
||||||
|
|
||||||
### License
|
## Docker Deployment
|
||||||
|
|
||||||
The Laravel framework is open-sourced software licensed under the [MIT license](http://opensource.org/licenses/MIT)
|
### Local Development
|
||||||
|
```bash
|
||||||
|
docker-compose -f docker-compose.local.yml up -d
|
||||||
|
```
|
||||||
|
|
||||||
|
### Development Environment
|
||||||
|
```bash
|
||||||
|
docker-compose -f docker-compose.dev.yml up -d
|
||||||
|
```
|
||||||
|
|
||||||
|
### Production Environment
|
||||||
|
```bash
|
||||||
|
docker-compose -f docker-compose.prod.yml up -d
|
||||||
|
```
|
||||||
|
|
||||||
|
The production environment uses Traefik as a reverse proxy with paid SSL certificate for crewsportswear.com.
|
||||||
|
|
||||||
|
## Features
|
||||||
|
|
||||||
|
- Custom sportswear design interface
|
||||||
|
- Product catalog and management
|
||||||
|
- Order processing and tracking
|
||||||
|
- User authentication and profiles
|
||||||
|
- Analytics integration
|
||||||
|
- Email notifications
|
||||||
|
- reCAPTCHA integration
|
||||||
|
|
||||||
|
## Environment Variables
|
||||||
|
|
||||||
|
Key environment variables (see `.env.example` for full list):
|
||||||
|
- `APP_ENV` - Application environment (local, development, production)
|
||||||
|
- `APP_URL` - Application URL
|
||||||
|
- `DB_*` - Database configuration
|
||||||
|
- `MAIL_*` - Mail server configuration
|
||||||
|
- `ANALYTICS_*` - Google Analytics configuration
|
||||||
|
- `CAPTCHA_*` - reCAPTCHA keys
|
||||||
|
|
||||||
|
## License
|
||||||
|
|
||||||
|
Proprietary - All rights reserved
|
||||||
|
|||||||
@@ -446,7 +446,7 @@
|
|||||||
@foreach ($pattern_arrays as $i => $val)
|
@foreach ($pattern_arrays as $i => $val)
|
||||||
<div class="item @if ($i == 0) active @endif">
|
<div class="item @if ($i == 0) active @endif">
|
||||||
<div class="btn-group patternBox ">
|
<div class="btn-group patternBox ">
|
||||||
<button type="button" data-pattern-path="{{ $val[0]->SVGPath }}" class="patternThumbs btn" data-id="{{ $val[0]->PatternId }}" style="background-image:url('{{ config('site_config.uploads') }}{{ $val[0]->PatternThumbnail }}'); background-size:cover; background-repeat: no-repeat;" @if ($i == 0) disabled @endif> @if ($i == 0) <i class="fa fa-2 fa-check" aria-hidden="true"></i> @endif</button>
|
<button type="button" data-pattern-path="{{ $val[0]->SVGPath }}" class="patternThumbs btn" data-id="{{ $val[0]->PatternId }}" style="background-image:url('{{ minio_url('uploads/images/' . $val[0]->PatternThumbnail) }}'); background-size:cover; background-repeat: no-repeat;" @if ($i == 0) disabled @endif> @if ($i == 0) <i class="fa fa-2 fa-check" aria-hidden="true"></i> @endif</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@endforeach
|
@endforeach
|
||||||
@@ -546,7 +546,7 @@
|
|||||||
@foreach ($pattern_arrays as $r => $val)
|
@foreach ($pattern_arrays as $r => $val)
|
||||||
<div class="item @if ($r == 0) active @endif">
|
<div class="item @if ($r == 0) active @endif">
|
||||||
<div class="btn-group patternBox ">
|
<div class="btn-group patternBox ">
|
||||||
<button type="button" data-pattern-path="{{ $val[0]->SVGPath }}" class="patternTrimThumbs patternTrim{{ $i }} btn" data-id="{{ $val[0]->PatternId }}" data-trim="{{ $i }}" style="background-image:url('{{ config('site_config.uploads') }}{{ $val[0]->PatternThumbnail }}'); background-size:cover; background-repeat: no-repeat;" @if ($r == 0) disabled @endif> @if ($r == 0) <i class="fa fa-2 fa-check" aria-hidden="true"></i> @endif</button>
|
<button type="button" data-pattern-path="{{ $val[0]->SVGPath }}" class="patternTrimThumbs patternTrim{{ $i }} btn" data-id="{{ $val[0]->PatternId }}" data-trim="{{ $i }}" style="background-image:url('{{ minio_url('uploads/images/' . $val[0]->PatternThumbnail) }}'); background-size:cover; background-repeat: no-repeat;" @if ($r == 0) disabled @endif> @if ($r == 0) <i class="fa fa-2 fa-check" aria-hidden="true"></i> @endif</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@endforeach
|
@endforeach
|
||||||
@@ -886,8 +886,8 @@
|
|||||||
<script src="{{asset('/designer/js/custom-script.js')}}"></script>
|
<script src="{{asset('/designer/js/custom-script.js')}}"></script>
|
||||||
<script src="https://gitcdn.github.io/bootstrap-toggle/2.2.2/js/bootstrap-toggle.min.js"></script>
|
<script src="https://gitcdn.github.io/bootstrap-toggle/2.2.2/js/bootstrap-toggle.min.js"></script>
|
||||||
<script src="https://ajax.aspnetcdn.com/ajax/jquery.validate/1.11.1/jquery.validate.min.js"></script>
|
<script src="https://ajax.aspnetcdn.com/ajax/jquery.validate/1.11.1/jquery.validate.min.js"></script>
|
||||||
<script src="https://rawgit.com/fabricjs/fabric.js/master/lib/centering_guidelines.js"></script>
|
<script src="{{asset('/designer/js/centering_guidelines.js')}}"></script>
|
||||||
<script src="https://rawgit.com/fabricjs/fabric.js/master/lib/aligning_guidelines.js"></script>
|
<script src="{{asset('/designer/js/aligning_guidelines.js')}}"></script>
|
||||||
<script>
|
<script>
|
||||||
|
|
||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
@@ -1306,7 +1306,7 @@
|
|||||||
|
|
||||||
var patternSVGPath = $(this).attr('data-pattern-path');
|
var patternSVGPath = $(this).attr('data-pattern-path');
|
||||||
|
|
||||||
var patternPath = "{{ config('site_config.uploads') }}" + patternSVGPath;
|
var patternPath = "{{ env('MINIO_URL', 'https://minio.crewsportswear.app') }}/{{ env('MINIO_BUCKET', 'crewsportswear') }}/" + patternSVGPath;
|
||||||
|
|
||||||
var SideAndPath = {!! json_encode($templatepaths_arrays) !!};
|
var SideAndPath = {!! json_encode($templatepaths_arrays) !!};
|
||||||
|
|
||||||
@@ -1383,7 +1383,7 @@
|
|||||||
$(document).on('button click', '.patternTrimThumbs', function(){
|
$(document).on('button click', '.patternTrimThumbs', function(){
|
||||||
|
|
||||||
var patternSVGPath = $(this).attr('data-pattern-path');
|
var patternSVGPath = $(this).attr('data-pattern-path');
|
||||||
var patternPath = "{{ config('site_config.uploads') }}" + patternSVGPath;
|
var patternPath = "{{ env('MINIO_URL', 'https://minio.crewsportswear.app') }}/{{ env('MINIO_BUCKET', 'crewsportswear') }}/" + patternSVGPath;
|
||||||
var getTrimId = $(this).attr('data-trim');
|
var getTrimId = $(this).attr('data-trim');
|
||||||
|
|
||||||
var SideAndPath = {!! json_encode($templatepaths_arrays) !!};
|
var SideAndPath = {!! json_encode($templatepaths_arrays) !!};
|
||||||
@@ -1527,7 +1527,7 @@
|
|||||||
var gradientIds = sideName+"_"+type+"_Gradients";
|
var gradientIds = sideName+"_"+type+"_Gradients";
|
||||||
var gradientPrefix = sideName+"_"+type+"_";
|
var gradientPrefix = sideName+"_"+type+"_";
|
||||||
|
|
||||||
var tempPath = "{{ config('site_config.uploads') }}" + pathLocation;
|
var tempPath = "{{ env('MINIO_URL', 'https://minio.crewsportswear.app') }}/{{ env('MINIO_BUCKET', 'crewsportswear') }}/" + pathLocation;
|
||||||
console.log(tempPath)
|
console.log(tempPath)
|
||||||
if(!document.getElementById(objectId))
|
if(!document.getElementById(objectId))
|
||||||
return false;
|
return false;
|
||||||
@@ -1711,7 +1711,7 @@
|
|||||||
var type = SideAndPath[i]['Type'];
|
var type = SideAndPath[i]['Type'];
|
||||||
var pathLocation = SideAndPath[i]['Path'];
|
var pathLocation = SideAndPath[i]['Path'];
|
||||||
var canvasName = "canvas_" + type + "_" + sideName;
|
var canvasName = "canvas_" + type + "_" + sideName;
|
||||||
var tempPath = "{{ config('site_config.uploads') }}" + pathLocation;
|
var tempPath = "{{ env('MINIO_URL', 'https://minio.crewsportswear.app') }}/{{ env('MINIO_BUCKET', 'crewsportswear') }}/" + pathLocation;
|
||||||
|
|
||||||
window['canvas_' + type + '_' + sideName] = new fabric.Canvas(canvasName);
|
window['canvas_' + type + '_' + sideName] = new fabric.Canvas(canvasName);
|
||||||
var templateFormat = SideAndPath[i]['TemplateFormat'];
|
var templateFormat = SideAndPath[i]['TemplateFormat'];
|
||||||
@@ -2043,9 +2043,9 @@
|
|||||||
|
|
||||||
if(objType == "curvedText"){
|
if(objType == "curvedText"){
|
||||||
if(obj.effect == "curved"){
|
if(obj.effect == "curved"){
|
||||||
$('#teamname_text_shape').html('Text Shape: <br><img src="{{ config('site_config.uploads') }}text-shapes-logo/curve-logo.png" height="30px">');
|
$('#teamname_text_shape').html('Text Shape: <br><img src="{{ minio_url('uploads/images/text-shapes-logo/curve-logo.png') }}" height="30px">');
|
||||||
}else if(obj.effect == "arc"){
|
}else if(obj.effect == "arc"){
|
||||||
$('#teamname_text_shape').html('Text Shape: <br><img src="{{ config('site_config.uploads') }}text-shapes-logo/arch-logo.png" height="30px">');
|
$('#teamname_text_shape').html('Text Shape: <br><img src="{{ minio_url('uploads/images/text-shapes-logo/arch-logo.png') }}" height="30px">');
|
||||||
}else{
|
}else{
|
||||||
$('#teamname_text_shape').html('Add text Shape');
|
$('#teamname_text_shape').html('Add text Shape');
|
||||||
}
|
}
|
||||||
@@ -3345,7 +3345,7 @@
|
|||||||
function loadSVGClipart(dataUrl){
|
function loadSVGClipart(dataUrl){
|
||||||
var k = 0;
|
var k = 0;
|
||||||
var arrayPathId = [];
|
var arrayPathId = [];
|
||||||
var svgUrl = "{{ config('site_config.uploads') }}cliparts/" + dataUrl;
|
var svgUrl = "{{ env('MINIO_URL', 'https://minio.crewsportswear.app') }}/{{ env('MINIO_BUCKET', 'crewsportswear') }}/uploads/images/cliparts/" + dataUrl;
|
||||||
fabric.loadSVGFromURL(svgUrl, function(objects, options) {
|
fabric.loadSVGFromURL(svgUrl, function(objects, options) {
|
||||||
var clipart = fabric.util.groupSVGElements(objects, options );
|
var clipart = fabric.util.groupSVGElements(objects, options );
|
||||||
clipart.set({
|
clipart.set({
|
||||||
|
|||||||
@@ -407,7 +407,7 @@
|
|||||||
<td align="left" style="width: 180px;">
|
<td align="left" style="width: 180px;">
|
||||||
@foreach($img_thumb as $img)
|
@foreach($img_thumb as $img)
|
||||||
@if($img->ProductId == $item->ProductId)
|
@if($img->ProductId == $item->ProductId)
|
||||||
<img style="height: 200px; overflow: hidden; object-fit: contain;" src="{{ config('site_config.images_url') }}/{{ $img->Image }}">
|
<img style="height: 200px; overflow: hidden; object-fit: contain;" src="{{ minio_url('images/' . $img->Image) }}">
|
||||||
@endif
|
@endif
|
||||||
@endforeach
|
@endforeach
|
||||||
</td>
|
</td>
|
||||||
|
|||||||
23
resources/views/emails/test.blade.php
Normal file
23
resources/views/emails/test.blade.php
Normal file
@@ -0,0 +1,23 @@
|
|||||||
|
<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<title>Test Email — CREW Sportswear</title>
|
||||||
|
</head>
|
||||||
|
<body style="font-family: Arial, sans-serif; color: #333; padding: 20px;">
|
||||||
|
<h2 style="color: #d9534f;">CREW Sportswear — Test Email</h2>
|
||||||
|
<p>This is a test email to verify that the mail configuration is working correctly.</p>
|
||||||
|
<p>Sent to: <strong>{{ $recipient }}</strong></p>
|
||||||
|
<hr>
|
||||||
|
<p style="font-size: 12px; color: #777;">
|
||||||
|
<strong>Mail Config Used:</strong><br>
|
||||||
|
Driver: {{ $config['driver'] }}<br>
|
||||||
|
Host: {{ $config['host'] }}<br>
|
||||||
|
Port: {{ $config['port'] }}<br>
|
||||||
|
Username: {{ $config['username'] }}<br>
|
||||||
|
Encryption: {{ $config['encryption'] }}
|
||||||
|
</p>
|
||||||
|
<hr>
|
||||||
|
<p style="font-size: 12px; color: #aaa;">This is an automated test message from CREW Sportswear.</p>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
@@ -122,13 +122,13 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div style="border: 1px solid #e2e2e2; padding: 10px;">
|
<div style="border: 1px solid #e2e2e2; padding: 10px;">
|
||||||
<a @if($getSubtotal <= 0 ) disabled @endif href="{{ url('getCheckout') }}" class="btn btn-primary btn-block" style="background-color: #ffc300; border-color: #e2ad00; text-align: -webkit-center;" ><img src="{{asset('/public/images/paypal1.png')}}" class="img img-responsive" style="height:30px;"></a><br>
|
<a @if($getSubtotal <= 0 ) disabled @endif href="{{ url('getCheckout') }}" class="btn btn-primary btn-block" style="background-color: #ffc300; border-color: #e2ad00; text-align: -webkit-center;" ><img src="{{asset('/images/paypal1.png')}}" class="img img-responsive" style="height:30px;"></a><br>
|
||||||
<a href="{{ url('teamstore') . '/' . $store_array[0]->StoreUrl }}" class="btn btn-default btn-block" type="submit">Continue Shopping</a>
|
<a href="{{ url('teamstore') . '/' . $store_array[0]->StoreUrl }}" class="btn btn-default btn-block" type="submit">Continue Shopping</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="col-md-8 col-md-pull-4">
|
<div class="col-md-8 col-md-pull-4">
|
||||||
<div style="border: 1px solid #e2e2e2; padding: 10px;">
|
<div style="border: 1px solid #e2e2e2; padding: 10px;">
|
||||||
<h4><img height="30px" class="store-logo" src="{{ config('site_config.uploads') . 'teamstore/'. $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreLogo }}"> {{ $store_array[0]->StoreName }}</h4>
|
<h4><img height="30px" class="store-logo" src="{{ minio_url('uploads/images/teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreLogo) }}"> {{ $store_array[0]->StoreName }}</h4>
|
||||||
</div>
|
</div>
|
||||||
@foreach($item_group as $item)
|
@foreach($item_group as $item)
|
||||||
@if($item->VoucherId == null)
|
@if($item->VoucherId == null)
|
||||||
@@ -138,7 +138,7 @@
|
|||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
@foreach($img_thumb as $img)
|
@foreach($img_thumb as $img)
|
||||||
@if($img->ProductId == $item->ProductId)
|
@if($img->ProductId == $item->ProductId)
|
||||||
<img class="previewImage" src="{{ config('site_config.images_url') }}/{{ $img->Image }}">
|
<img class="previewImage" src="{{ minio_url('images/' . $img->Image) }}">
|
||||||
@endif
|
@endif
|
||||||
@endforeach
|
@endforeach
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -64,7 +64,7 @@
|
|||||||
<table class="table">
|
<table class="table">
|
||||||
|
|
||||||
<tr>
|
<tr>
|
||||||
<td rowspan="2" class="text-center"><img class="previewImage" src="http://{{ config('site_config.images_url') }}/{{ $item->Image }} "></td>
|
<td rowspan="2" class="text-center"><img class="previewImage" src="{{ minio_url('images/' . $item->Image) }}"></td>
|
||||||
<td colspan="5">
|
<td colspan="5">
|
||||||
<h4>{{ $item->ProductName }} {{ $itemOrder }} <br>Price: ${{ $item->Price }}</h4>
|
<h4>{{ $item->ProductName }} {{ $itemOrder }} <br>Price: ${{ $item->Price }}</h4>
|
||||||
</td>
|
</td>
|
||||||
|
|||||||
@@ -19,7 +19,7 @@
|
|||||||
<div class="col-md-3 col-sm-6 col-xs-12 list-sport">
|
<div class="col-md-3 col-sm-6 col-xs-12 list-sport">
|
||||||
<div class="thumb-border">
|
<div class="thumb-border">
|
||||||
<a href="{{ url() }}/{{ Request::path() }}/{{ $r->Id }}">
|
<a href="{{ url() }}/{{ Request::path() }}/{{ $r->Id }}">
|
||||||
<img src="{{ config('site_config.uploads') . 'sports-category/' . $r->Thumbnail }}" alt="{{ $r->Category }}" class="image" />
|
<img src="{{ minio_url('uploads/images/sports-category/' . $r->Thumbnail) }}" alt="{{ $r->Category }}" class="image" />
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
|
|||||||
@@ -24,7 +24,7 @@
|
|||||||
|
|
||||||
<div class="thumb-border" style="border:1px solid #e2e2e2; padding: 5px;">
|
<div class="thumb-border" style="border:1px solid #e2e2e2; padding: 5px;">
|
||||||
<a href="{{ url('/designer') }}/{{ md5($r->TemplateCode) }}">
|
<a href="{{ url('/designer') }}/{{ md5($r->TemplateCode) }}">
|
||||||
<img src="{{ config('site_config.uploads') . $r->Thumbnail}}" alt="" class="image" />
|
<img src="{{ minio_url('uploads/images/' . $r->Thumbnail) }}" alt="" class="image" />
|
||||||
</a>
|
</a>
|
||||||
<!-- <div class="overlay">
|
<!-- <div class="overlay">
|
||||||
<div class="text" style="font-family:Academic M54;"><a href="">{{$r->TemplateName}}</a></div>
|
<div class="text" style="font-family:Academic M54;"><a href="">{{$r->TemplateName}}</a></div>
|
||||||
|
|||||||
@@ -7,14 +7,17 @@
|
|||||||
@endif
|
@endif
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
|
body {
|
||||||
|
background: #f4f6f8;
|
||||||
|
}
|
||||||
|
|
||||||
h2 {
|
h2 {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
margin: 0;
|
margin: 0;
|
||||||
padding: 0;
|
padding: 0;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
margin-top: 40px;
|
margin-top: 34px;
|
||||||
margin-bottom: 40px;
|
margin-bottom: 24px;
|
||||||
|
|
||||||
}
|
}
|
||||||
/* h2:after {
|
/* h2:after {
|
||||||
display: inline-block;
|
display: inline-block;
|
||||||
@@ -41,6 +44,15 @@
|
|||||||
font-size: 12px;
|
font-size: 12px;
|
||||||
margin-top: 5px;
|
margin-top: 5px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.featured-title {
|
||||||
|
font-size: 24px;
|
||||||
|
font-weight: 700;
|
||||||
|
letter-spacing: 0.6px;
|
||||||
|
color: #111827;
|
||||||
|
text-transform: uppercase;
|
||||||
|
}
|
||||||
|
|
||||||
.price{
|
.price{
|
||||||
font-size: 25px;
|
font-size: 25px;
|
||||||
margin: 0 auto;
|
margin: 0 auto;
|
||||||
@@ -51,19 +63,107 @@
|
|||||||
border-bottom: 2px solid #4B8E4B;
|
border-bottom: 2px solid #4B8E4B;
|
||||||
}
|
}
|
||||||
.thumbnail{
|
.thumbnail{
|
||||||
/* opacity:0.70; */
|
|
||||||
-webkit-transition: all 0.5s;
|
-webkit-transition: all 0.5s;
|
||||||
transition: all 0.5s;
|
transition: all 0.5s;
|
||||||
}
|
}
|
||||||
.thumbnail:hover{
|
|
||||||
opacity:1.00;
|
|
||||||
box-shadow: 0px 0px 10px #4bc6ff;
|
|
||||||
}
|
|
||||||
.line{
|
.line{
|
||||||
margin-bottom: 5px;
|
margin-bottom: 5px;
|
||||||
}
|
}
|
||||||
.thumbnail>img{
|
.products-grid {
|
||||||
height:201.84px;
|
margin-top: 6px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-col {
|
||||||
|
margin-bottom: 22px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-card {
|
||||||
|
height: 100%;
|
||||||
|
background: #ffffff;
|
||||||
|
border: 1px solid #e5e7eb;
|
||||||
|
border-radius: 12px;
|
||||||
|
overflow: hidden;
|
||||||
|
box-shadow: 0 1px 2px rgba(16, 24, 40, 0.04);
|
||||||
|
transition: transform 0.2s, box-shadow 0.2s, border-color 0.2s;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-card:hover {
|
||||||
|
transform: translateY(-2px);
|
||||||
|
border-color: #d1d5db;
|
||||||
|
box-shadow: 0 10px 24px rgba(2, 6, 23, 0.08);
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-image-link {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
padding: 16px;
|
||||||
|
min-height: 240px;
|
||||||
|
background: #f8fafc;
|
||||||
|
border-bottom: 1px solid #e5e7eb;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-image {
|
||||||
|
width: auto;
|
||||||
|
max-width: 100%;
|
||||||
|
height: auto;
|
||||||
|
max-height: 202px;
|
||||||
|
object-fit: contain;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-card-body {
|
||||||
|
padding: 12px 14px 14px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-name-holder {
|
||||||
|
margin: 0;
|
||||||
|
font-size: 14px;
|
||||||
|
font-weight: 700;
|
||||||
|
line-height: 1.35;
|
||||||
|
color: #111827;
|
||||||
|
white-space: nowrap;
|
||||||
|
overflow: hidden;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-card-footer {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
gap: 10px;
|
||||||
|
margin-top: 12px;
|
||||||
|
padding-top: 10px;
|
||||||
|
border-top: 1px solid #eef2f7;
|
||||||
|
}
|
||||||
|
|
||||||
|
.price {
|
||||||
|
margin: 0;
|
||||||
|
font-size: 22px;
|
||||||
|
line-height: 1;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #111827;
|
||||||
|
}
|
||||||
|
|
||||||
|
.price small,
|
||||||
|
.price-currency {
|
||||||
|
font-size: 13px;
|
||||||
|
color: #6b7280;
|
||||||
|
font-weight: 600;
|
||||||
|
}
|
||||||
|
|
||||||
|
.btn-view-details {
|
||||||
|
border-radius: 8px;
|
||||||
|
min-height: 36px;
|
||||||
|
font-weight: 600;
|
||||||
|
font-size: 12px;
|
||||||
|
padding: 8px 12px;
|
||||||
|
letter-spacing: 0.2px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.empty-state {
|
||||||
|
margin: 50px 0;
|
||||||
|
color: #6b7280;
|
||||||
|
font-size: 15px;
|
||||||
}
|
}
|
||||||
@media screen and (max-width: 770px) {
|
@media screen and (max-width: 770px) {
|
||||||
.right{
|
.right{
|
||||||
@@ -86,9 +186,9 @@
|
|||||||
padding-top: 20px;
|
padding-top: 20px;
|
||||||
padding-bottom: 20px;
|
padding-bottom: 20px;
|
||||||
@if($store_array[0]->StoreBanner == null)
|
@if($store_array[0]->StoreBanner == null)
|
||||||
background-image: url("{{ config('site_config.uploads') . 'teamstore/store-banner-dark.png' }}");
|
background-image: url("{{ minio_url('uploads/images/teamstore/store-banner-dark.png') }}");
|
||||||
@else
|
@else
|
||||||
background-image: url("{{ config('site_config.uploads') . 'teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreBanner }}");
|
background-image: url("{{ minio_url('uploads/images/teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreBanner) }}");
|
||||||
@endif
|
@endif
|
||||||
background-color: #f3f3f3;
|
background-color: #f3f3f3;
|
||||||
background-position: center;
|
background-position: center;
|
||||||
@@ -127,6 +227,164 @@
|
|||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
text-overflow: ellipsis;
|
text-overflow: ellipsis;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* ── Category nav ──────────────────────────────────────────────────────── */
|
||||||
|
.cat-nav {
|
||||||
|
background: #ffffff;
|
||||||
|
border: 1px solid #e5e7eb;
|
||||||
|
border-radius: 12px;
|
||||||
|
box-shadow: 0 1px 2px rgba(16, 24, 40, 0.04);
|
||||||
|
padding: 0;
|
||||||
|
margin-bottom: 24px;
|
||||||
|
overflow: visible;
|
||||||
|
}
|
||||||
|
.cat-nav ul {
|
||||||
|
list-style: none;
|
||||||
|
margin: 0;
|
||||||
|
padding: 0;
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
}
|
||||||
|
.cat-nav > ul > li {
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
.cat-nav > ul > li > a {
|
||||||
|
display: block;
|
||||||
|
padding: 14px 20px;
|
||||||
|
font-weight: 700;
|
||||||
|
font-size: 13px;
|
||||||
|
text-transform: uppercase;
|
||||||
|
color: #222;
|
||||||
|
text-decoration: none;
|
||||||
|
letter-spacing: .5px;
|
||||||
|
border-bottom: 3px solid transparent;
|
||||||
|
transition: border-color .2s, color .2s;
|
||||||
|
}
|
||||||
|
.cat-nav > ul > li > a:hover,
|
||||||
|
.cat-nav > ul > li > a.active {
|
||||||
|
color: #4B8E4B;
|
||||||
|
border-bottom-color: #4B8E4B;
|
||||||
|
}
|
||||||
|
/* sub-category dropdown */
|
||||||
|
.cat-nav .sub-menu {
|
||||||
|
display: none;
|
||||||
|
position: absolute;
|
||||||
|
top: 100%;
|
||||||
|
left: 0;
|
||||||
|
min-width: 200px;
|
||||||
|
background: #fff;
|
||||||
|
border: 1px solid #ddd;
|
||||||
|
border-top: 3px solid #4B8E4B;
|
||||||
|
box-shadow: 0 4px 12px rgba(0,0,0,.12);
|
||||||
|
z-index: 999;
|
||||||
|
list-style: none;
|
||||||
|
margin: 0;
|
||||||
|
padding: 6px 0;
|
||||||
|
}
|
||||||
|
.cat-nav > ul > li:hover .sub-menu {
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
.cat-nav .sub-menu li a {
|
||||||
|
display: block;
|
||||||
|
padding: 9px 18px;
|
||||||
|
font-size: 13px;
|
||||||
|
color: #333;
|
||||||
|
text-decoration: none;
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
.cat-nav .sub-menu li a:hover,
|
||||||
|
.cat-nav .sub-menu li a.active {
|
||||||
|
background: #f0f9f0;
|
||||||
|
color: #4B8E4B;
|
||||||
|
}
|
||||||
|
.cat-count {
|
||||||
|
display: inline-block;
|
||||||
|
background: #ddd;
|
||||||
|
border-radius: 10px;
|
||||||
|
font-size: 11px;
|
||||||
|
padding: 1px 7px;
|
||||||
|
margin-left: 4px;
|
||||||
|
vertical-align: middle;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ── League / conference pill filter (sub-sub-category) ─────────────────── */
|
||||||
|
.league-filter {
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 8px;
|
||||||
|
padding: 10px 12px 14px;
|
||||||
|
margin-bottom: 18px;
|
||||||
|
border: 1px solid #e5e7eb;
|
||||||
|
border-radius: 12px;
|
||||||
|
background: #fff;
|
||||||
|
align-items: center;
|
||||||
|
box-shadow: 0 1px 2px rgba(16, 24, 40, 0.04);
|
||||||
|
}
|
||||||
|
.league-filter .lf-label {
|
||||||
|
font-size: 11px;
|
||||||
|
font-weight: 700;
|
||||||
|
text-transform: uppercase;
|
||||||
|
color: #888;
|
||||||
|
letter-spacing: .5px;
|
||||||
|
margin-right: 4px;
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
.league-filter a {
|
||||||
|
display: inline-block;
|
||||||
|
padding: 5px 14px;
|
||||||
|
border-radius: 20px;
|
||||||
|
background: #f0f0f0;
|
||||||
|
color: #333;
|
||||||
|
font-size: 12px;
|
||||||
|
font-weight: 600;
|
||||||
|
text-decoration: none;
|
||||||
|
white-space: nowrap;
|
||||||
|
border: 1px solid #ddd;
|
||||||
|
transition: background .2s, color .2s, border-color .2s;
|
||||||
|
}
|
||||||
|
.league-filter a:hover {
|
||||||
|
background: #e0f2e0;
|
||||||
|
color: #4B8E4B;
|
||||||
|
border-color: #4B8E4B;
|
||||||
|
}
|
||||||
|
.league-filter a.active {
|
||||||
|
background: #4B8E4B;
|
||||||
|
color: #fff;
|
||||||
|
border-color: #4B8E4B;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media screen and (max-width: 991px) {
|
||||||
|
.product-image-link {
|
||||||
|
min-height: 220px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.btn-view-details {
|
||||||
|
padding: 7px 10px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@media screen and (max-width: 767px) {
|
||||||
|
h2 {
|
||||||
|
margin-top: 24px;
|
||||||
|
margin-bottom: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.featured-title {
|
||||||
|
font-size: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-card-footer {
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: stretch;
|
||||||
|
gap: 8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.btn-view-details {
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[v-cloak] { display: none; }
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
<div class="container">
|
<div class="container">
|
||||||
@@ -147,83 +405,277 @@
|
|||||||
</div>
|
</div>
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<h2>FEATURED PRODUCTS</h2>
|
<h2 class="featured-title">Featured Products</h2>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="row">
|
|
||||||
|
{{-- ── Vue category + product grid ─────────────────────────────────────── --}}
|
||||||
|
<script>
|
||||||
|
window._tsProducts = {!! json_encode(
|
||||||
|
collect($product_array)
|
||||||
|
->where('PrivacyStatus', 'public')
|
||||||
|
->map(function($p) use ($thumbnails) {
|
||||||
|
$thumbList = isset($thumbnails) ? $thumbnails : [];
|
||||||
|
$thumb = collect($thumbList)->filter(function($t) use ($p) {
|
||||||
|
return $t['product_id'] == $p->Id;
|
||||||
|
})->first();
|
||||||
|
return [
|
||||||
|
'id' => $p->Id,
|
||||||
|
'name' => $p->ProductName,
|
||||||
|
'price' => $p->ProductPrice,
|
||||||
|
'url' => $p->ProductURL,
|
||||||
|
'img' => $thumb ? $thumb['thumb'] : 'product-image-placeholder.png',
|
||||||
|
'folder'=> $thumb ? $thumb['folder'] : '',
|
||||||
|
];
|
||||||
|
})->values()->toArray(),
|
||||||
|
JSON_HEX_TAG | JSON_HEX_APOS | JSON_HEX_AMP | JSON_HEX_QUOT
|
||||||
|
) !!};
|
||||||
|
window._tsStore = {
|
||||||
|
url : {!! json_encode($store_array[0]->StoreUrl, JSON_HEX_TAG | JSON_HEX_APOS | JSON_HEX_AMP | JSON_HEX_QUOT) !!},
|
||||||
|
currency : {!! json_encode($store_array[0]->StoreCurrency, JSON_HEX_TAG | JSON_HEX_APOS | JSON_HEX_AMP | JSON_HEX_QUOT) !!},
|
||||||
|
minoBase : {!! json_encode(rtrim(config('filesystems.disks.minio.url', ''), '/') . '/' . env('MINIO_BUCKET', 'crewsportswear') . '/', JSON_HEX_TAG | JSON_HEX_APOS | JSON_HEX_AMP | JSON_HEX_QUOT) !!},
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div id="ts-app" v-cloak>
|
||||||
|
|
||||||
|
{{-- ── Category nav ── --}}
|
||||||
|
<nav class="cat-nav" v-if="categories.length > 0">
|
||||||
|
<ul>
|
||||||
|
<li>
|
||||||
|
<a href="#" :class="{active: activeCategory===null && activeSubCategory===null}"
|
||||||
|
@click.prevent="activeCategory=null; activeSubCategory=null">
|
||||||
|
All
|
||||||
|
<span class="cat-count">@{{ totalPublic }}</span>
|
||||||
|
</a>
|
||||||
|
</li>
|
||||||
|
<li v-for="cat in categories" :key="cat.name">
|
||||||
|
<a href="#"
|
||||||
|
:class="{active: activeCategory===cat.name}"
|
||||||
|
@click.prevent="selectCategory(cat.name)">
|
||||||
|
@{{ cat.name }}
|
||||||
|
<span class="cat-count">@{{ cat.count }}</span>
|
||||||
|
</a>
|
||||||
|
<ul class="sub-menu" v-if="cat.subs.length > 0">
|
||||||
|
<li v-for="sub in cat.subs" :key="sub.name">
|
||||||
|
<a href="#"
|
||||||
|
:class="{active: activeCategory===cat.name && activeSubCategory===sub.name}"
|
||||||
|
@click.prevent="selectSub(cat.name, sub.name)">
|
||||||
|
@{{ sub.name }}
|
||||||
|
<span class="cat-count">@{{ sub.count }}</span>
|
||||||
|
</a>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</nav>
|
||||||
|
|
||||||
|
{{-- ── League / conference pill filter ── --}}
|
||||||
|
<div class="league-filter" v-if="isLeagueStore && activeCategory !== null && leagues.length > 0">
|
||||||
|
<span class="lf-label">League / Conf:</span>
|
||||||
|
<a href="#"
|
||||||
|
:class="{active: activeLeague === null}"
|
||||||
|
@click.prevent="activeLeague = null">All</a>
|
||||||
|
<a href="#"
|
||||||
|
v-for="lg in leagues" :key="lg.name"
|
||||||
|
:class="{active: activeLeague === lg.name}"
|
||||||
|
@click.prevent="activeLeague = lg.name">
|
||||||
|
@{{ lg.name }}
|
||||||
|
<span class="cat-count">@{{ lg.count }}</span>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{{-- ── Announcements (kept outside loop) ── --}}
|
||||||
@if ($announcement->IsActive)
|
@if ($announcement->IsActive)
|
||||||
|
<div class="row">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<div class="alert alert-info">
|
<div class="alert alert-info">
|
||||||
<p><b>Shop Announcements:</b></p>
|
<p><b>Shop Announcements:</b></p>
|
||||||
{!! nl2br(e($announcement->Announcement)) !!}
|
{!! nl2br(e($announcement->Announcement)) !!}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
@endif
|
@endif
|
||||||
@if($store_array[0]->Id == 174 || $store_array[0]->Id == 175 || $store_array[0]->Id == 178 || $store_array[0]->Id == 179 || $store_array[0]->Id == 177 || $store_array[0]->Id == 189 || $store_array[0]->Id == 176 || $store_array[0]->Id == 190 || $store_array[0]->Id == 191 || $store_array[0]->Id == 192 || $store_array[0]->Id == 194)
|
@if($store_array[0]->Id == 174 || $store_array[0]->Id == 175 || $store_array[0]->Id == 178 || $store_array[0]->Id == 179 || $store_array[0]->Id == 177 || $store_array[0]->Id == 189 || $store_array[0]->Id == 176 || $store_array[0]->Id == 190 || $store_array[0]->Id == 191 || $store_array[0]->Id == 192 || $store_array[0]->Id == 194)
|
||||||
<div class="col-md-12">
|
<div class="row">
|
||||||
<div class="alert alert-warning">
|
<div class="col-md-12">
|
||||||
<p><b>Please read:</b></p>
|
<div class="alert alert-warning">
|
||||||
1. All orders will be batch shipped to your school for pick up.<br>
|
|
||||||
2. Orders will be batch processed on a weekly basis, please allow 2-3 weeks for delivery.<br>
|
|
||||||
3. Masks and gaiters sold on Crew are not intended for medical use. Crew does not make any medical or health claims.<br>
|
|
||||||
4. Refunds and exchanges are not allowed due to the hygenic nature of the product.<br>
|
|
||||||
@if($store_array[0]->Id == 175)
|
|
||||||
5. $1 from every item sold will benefit the 2020-2021 Maine South Schoolwide Fundraiser.
|
|
||||||
@endif
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
@else
|
|
||||||
<div class="col-md-12">
|
|
||||||
<div class="alert alert-warning">
|
|
||||||
<p><b>Please read:</b></p>
|
<p><b>Please read:</b></p>
|
||||||
1. Items purchased are made on demand. Orders will be shipped based on dates set by your store administrator.<br>
|
1. All orders will be batch shipped to your school for pick up.<br>
|
||||||
2. Store payments are processed through PayPal. A PayPal account is not required to make a purchase.<br>
|
2. Orders will be batch processed on a weekly basis, please allow 2-3 weeks for delivery.<br>
|
||||||
@if($store_array[0]->Id == 222)
|
3. Masks and gaiters sold on Crew are not intended for medical use. Crew does not make any medical or health claims.<br>
|
||||||
3. Orders will be batch processed on a monthly basis, please allow 4-6 weeks for delivery.<br>
|
4. Refunds and exchanges are not allowed due to the hygenic nature of the product.<br>
|
||||||
@else
|
@if($store_array[0]->Id == 175)
|
||||||
3. Orders will be batch processed on a weekly basis, please allow 2-3 weeks for delivery.<br>
|
5. $1 from every item sold will benefit the 2020-2021 Maine South Schoolwide Fundraiser.
|
||||||
@endif
|
@endif
|
||||||
4. We are currently only shipping to US locations. For international orders, please contact <b>orders@crewsportswear.com</b> if you'd like to place an order.<br>
|
|
||||||
5. Expect shipping delays due to COVID-19.<br>
|
|
||||||
6. All sales are final. No returns or exchanges will be accepted.<br><br>
|
|
||||||
|
|
||||||
<b>DISCLAIMER:</b> Masks and gaiters sold by Crew Sportswear are not intended for medical use. Crew Sportswear does not make any medical or health claims.
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
@endif
|
|
||||||
<!-- BEGIN PRODUCTS -->
|
|
||||||
|
|
||||||
@foreach($product_array as $i => $product)
|
|
||||||
@if($product->PrivacyStatus == "public")
|
|
||||||
@foreach($thumbnails as $t => $thumb)
|
|
||||||
@if($thumb['product_id'] == $product->Id)
|
|
||||||
@define $storeFolder = $thumb['folder']
|
|
||||||
@define $filename = $thumb['thumb']
|
|
||||||
@endif
|
|
||||||
@endforeach
|
|
||||||
|
|
||||||
<div class="col-md-3 col-sm-6">
|
|
||||||
<span class="thumbnail">
|
|
||||||
<a href="{{ url('teamstore') }}/{{ $store_array[0]->StoreUrl }}/product/{{ $product->ProductURL }}">
|
|
||||||
<img style="height: 201.84px;" src="{{ config('site_config.images_url') }}/{{ $filename }}" alt="{{ $product->ProductName }}" >
|
|
||||||
</a>
|
|
||||||
<h4 class="text-center product-name-holder">{{ $product->ProductName }}</h4>
|
|
||||||
<hr class="line">
|
|
||||||
<div class="row">
|
|
||||||
<div class="col-md-7 col-sm-7">
|
|
||||||
<p class="price">{{ $product->ProductPrice }} <small style="font-size: 15px;"> {{ $store_array[0]->StoreCurrency }}</small></p>
|
|
||||||
</div>
|
|
||||||
<div class="col-md-5 col-sm-5">
|
|
||||||
<a href="{{ url('teamstore') }}/{{ $store_array[0]->StoreUrl }}/product/{{ $product->ProductURL }}" class="btn btn-success right" > View Details</a>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</div>
|
|
||||||
</span>
|
|
||||||
</div>
|
</div>
|
||||||
@endif
|
</div>
|
||||||
@endforeach
|
</div>
|
||||||
<!-- END PRODUCTS -->
|
@endif
|
||||||
|
|
||||||
</div>
|
{{-- ── Product grid ── --}}
|
||||||
</div> <!-- cotainer -->
|
<div class="row products-grid">
|
||||||
|
<div class="col-md-12 text-center" v-if="filtered.length === 0">
|
||||||
|
<p class="empty-state">No products found in this category.</p>
|
||||||
|
</div>
|
||||||
|
<div class="col-md-3 col-sm-6 product-col" v-for="p in filtered" :key="p.id">
|
||||||
|
<div class="product-card">
|
||||||
|
<a :href="productUrl(p)" class="product-image-link">
|
||||||
|
<img class="product-image" :src="imgUrl(p)" :alt="p.name">
|
||||||
|
</a>
|
||||||
|
<div class="product-card-body">
|
||||||
|
<h4 class="text-center product-name-holder">@{{ p.name }}</h4>
|
||||||
|
<div class="product-card-footer">
|
||||||
|
<p class="price">@{{ p.price }} <small class="price-currency">@{{ store.currency }}</small></p>
|
||||||
|
<a :href="productUrl(p)" class="btn btn-success btn-view-details">View Details</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>{{-- /ts-app --}}
|
||||||
|
|
||||||
|
<script src="https://unpkg.com/vue@3/dist/vue.global.prod.js"></script>
|
||||||
|
<script>
|
||||||
|
(function () {
|
||||||
|
// ── sport & item-type keyword maps ──────────────────────────────────
|
||||||
|
const SPORTS = [
|
||||||
|
'Basketball','Football','Soccer','Baseball','Softball',
|
||||||
|
'Volleyball','Hockey','Lacrosse','Wrestling','Tennis',
|
||||||
|
'Swimming','Track','Cross Country','Golf','Cheerleading',
|
||||||
|
'Dance','Rugby','Bowling','Gymnastics','Cycling',
|
||||||
|
];
|
||||||
|
const ITEMS = [
|
||||||
|
'Jersey','T-Shirt','Tee','Hoodie','Sweatshirt','Jacket',
|
||||||
|
'Shorts','Pants','Tank','Top','Pullover','Zip-Up',
|
||||||
|
'Hat','Cap','Beanie','Polo','Uniform','Warmup','Pinnie',
|
||||||
|
];
|
||||||
|
// ── league / conference keyword map ──────────────────────────────────
|
||||||
|
// Order matters: more specific phrases first
|
||||||
|
const LEAGUES = [
|
||||||
|
{ key: 'WNBA', terms: ['\\bwnba\\b'] },
|
||||||
|
{ key: 'NBA', terms: ['\\bnba\\b'] },
|
||||||
|
{ key: 'NFL', terms: ['\\bnfl\\b'] },
|
||||||
|
{ key: 'MLB', terms: ['\\bmlb\\b'] },
|
||||||
|
{ key: 'NHL', terms: ['\\bnhl\\b'] },
|
||||||
|
{ key: 'MLS', terms: ['\\bmls\\b'] },
|
||||||
|
{ key: 'Big Ten', terms: ['\\bbig\\s*ten\\b','\\bbig\\s*10\\b','\\bbig10\\b'] },
|
||||||
|
{ key: 'ACC', terms: ['\\bacc\\b'] },
|
||||||
|
{ key: 'SEC', terms: ['\\bsec\\b'] },
|
||||||
|
{ key: 'Big 12', terms: ['\\bbig\\s*12\\b','\\bbig12\\b'] },
|
||||||
|
{ key: 'Pac-12', terms: ['\\bpac[-\\s]*12\\b','\\bpac12\\b'] },
|
||||||
|
{ key: 'AAC', terms: ['\\baac\\b'] },
|
||||||
|
{ key: 'CUSA', terms: ['\\bcusa\\b','\\bc-usa\\b'] },
|
||||||
|
{ key: 'MAC', terms: ['\\bmac\\b'] },
|
||||||
|
{ key: 'Sun Belt',terms: ['\\bsun\\s+belt\\b'] },
|
||||||
|
{ key: 'Mountain West', terms: ['\\bmountain\\s+west\\b','\\bmwc\\b'] },
|
||||||
|
];
|
||||||
|
|
||||||
|
function classify(name) {
|
||||||
|
const n = name.toLowerCase();
|
||||||
|
const sport = SPORTS.find(s => n.includes(s.toLowerCase())) || 'Other';
|
||||||
|
const item = ITEMS.find(i => n.includes(i.toLowerCase())) || 'Other';
|
||||||
|
let league = null;
|
||||||
|
for (const lg of LEAGUES) {
|
||||||
|
if (lg.terms.some(t => {
|
||||||
|
try { return new RegExp(t, 'i').test(n); } catch(e) { return n.includes(t); }
|
||||||
|
})) {
|
||||||
|
league = lg.key;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return { sport, item, league };
|
||||||
|
}
|
||||||
|
|
||||||
|
const { createApp } = Vue;
|
||||||
|
const store = window._tsStore || { url:'', currency:'', minoBase:'' };
|
||||||
|
const allProducts = Array.isArray(window._tsProducts) ? window._tsProducts : [];
|
||||||
|
|
||||||
|
createApp({
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
products : allProducts,
|
||||||
|
store : store,
|
||||||
|
activeCategory : null,
|
||||||
|
activeSubCategory: null,
|
||||||
|
activeLeague : null,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
computed: {
|
||||||
|
totalPublic() {
|
||||||
|
return this.products.length;
|
||||||
|
},
|
||||||
|
isLeagueStore() {
|
||||||
|
return this.store.url === 'hi-five-franchise-store';
|
||||||
|
},
|
||||||
|
// Build [ { name:'Basketball', count:N, subs:[{name:'Jersey',count:N},...] }, ... ]
|
||||||
|
categories() {
|
||||||
|
const map = {};
|
||||||
|
this.products.forEach(p => {
|
||||||
|
const { sport, item } = classify(p.name);
|
||||||
|
if (!map[sport]) map[sport] = {};
|
||||||
|
map[sport][item] = (map[sport][item] || 0) + 1;
|
||||||
|
});
|
||||||
|
return Object.entries(map)
|
||||||
|
.sort((a,b) => a[0].localeCompare(b[0]))
|
||||||
|
.map(([name, subs]) => ({
|
||||||
|
name,
|
||||||
|
count: Object.values(subs).reduce((a,b) => a+b, 0),
|
||||||
|
subs: Object.entries(subs)
|
||||||
|
.sort((a,b) => a[0].localeCompare(b[0]))
|
||||||
|
.map(([s, count]) => ({ name: s, count }))
|
||||||
|
.filter(s => s.name !== 'Other' || Object.keys(subs).length === 1),
|
||||||
|
}));
|
||||||
|
},
|
||||||
|
// Available leagues for the currently active category (+ optional sub)
|
||||||
|
// Only computed for hi-five-franchise-store
|
||||||
|
leagues() {
|
||||||
|
if (!this.isLeagueStore) return [];
|
||||||
|
const map = {};
|
||||||
|
this.products.forEach(p => {
|
||||||
|
const { sport, item, league } = classify(p.name);
|
||||||
|
if (!league) return;
|
||||||
|
if (this.activeCategory && sport !== this.activeCategory) return;
|
||||||
|
if (this.activeSubCategory && item !== this.activeSubCategory) return;
|
||||||
|
map[league] = (map[league] || 0) + 1;
|
||||||
|
});
|
||||||
|
return Object.entries(map)
|
||||||
|
.sort((a, b) => a[0].localeCompare(b[0]))
|
||||||
|
.map(([name, count]) => ({ name, count }));
|
||||||
|
},
|
||||||
|
filtered() {
|
||||||
|
if (!this.activeCategory && !this.activeLeague) return this.products;
|
||||||
|
return this.products.filter(p => {
|
||||||
|
const { sport, item, league } = classify(p.name);
|
||||||
|
if (this.activeCategory && sport !== this.activeCategory) return false;
|
||||||
|
if (this.activeSubCategory && item !== this.activeSubCategory) return false;
|
||||||
|
if (this.isLeagueStore && this.activeLeague && league !== this.activeLeague) return false;
|
||||||
|
return true;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
selectCategory(cat) {
|
||||||
|
this.activeCategory = cat;
|
||||||
|
this.activeSubCategory = null;
|
||||||
|
this.activeLeague = null;
|
||||||
|
},
|
||||||
|
selectSub(cat, sub) {
|
||||||
|
this.activeCategory = cat;
|
||||||
|
this.activeSubCategory = sub;
|
||||||
|
this.activeLeague = null;
|
||||||
|
},
|
||||||
|
productUrl(p) {
|
||||||
|
return '/teamstore/' + store.url + '/product/' + p.url;
|
||||||
|
},
|
||||||
|
imgUrl(p) {
|
||||||
|
return store.minoBase + 'images/' + p.img;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}).mount('#ts-app');
|
||||||
|
})();
|
||||||
|
</script>
|
||||||
|
|
||||||
|
</div>{{-- /container --}}
|
||||||
@endsection
|
@endsection
|
||||||
|
|||||||
@@ -7,6 +7,45 @@
|
|||||||
@endif
|
@endif
|
||||||
<style>
|
<style>
|
||||||
|
|
||||||
|
body {
|
||||||
|
background: #f4f6f8;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-page {
|
||||||
|
padding-top: 14px;
|
||||||
|
padding-bottom: 28px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-breadcrumb {
|
||||||
|
background: #fff;
|
||||||
|
border: 1px solid #e5e7eb;
|
||||||
|
border-radius: 10px;
|
||||||
|
margin-bottom: 18px;
|
||||||
|
padding: 10px 14px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-breadcrumb .breadcrumb {
|
||||||
|
margin: 0;
|
||||||
|
background: transparent;
|
||||||
|
padding: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-breadcrumb .breadcrumb > li,
|
||||||
|
.product-breadcrumb .breadcrumb > li.active,
|
||||||
|
.product-breadcrumb .breadcrumb > li + li:before {
|
||||||
|
color: #6b7280;
|
||||||
|
font-size: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-breadcrumb .breadcrumb > li > a {
|
||||||
|
color: #374151;
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-breadcrumb .breadcrumb > li > a:hover {
|
||||||
|
color: #111827;
|
||||||
|
}
|
||||||
|
|
||||||
p{
|
p{
|
||||||
font-size: 12px;
|
font-size: 12px;
|
||||||
margin-top: 5px;
|
margin-top: 5px;
|
||||||
@@ -30,7 +69,8 @@
|
|||||||
box-shadow: 0px 0px 10px #4bc6ff;
|
box-shadow: 0px 0px 10px #4bc6ff;
|
||||||
} */
|
} */
|
||||||
.line{
|
.line{
|
||||||
margin-bottom: 5px;
|
margin: 14px 0;
|
||||||
|
border-color: #e5e7eb;
|
||||||
}
|
}
|
||||||
@media screen and (max-width: 770px) {
|
@media screen and (max-width: 770px) {
|
||||||
.right{
|
.right{
|
||||||
@@ -117,18 +157,45 @@
|
|||||||
border: none;
|
border: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
.carousel-control.left {
|
#myCarousel {
|
||||||
margin-left: -35px;
|
position: relative;
|
||||||
margin-top: 7px;
|
width: 100%;
|
||||||
}
|
|
||||||
|
|
||||||
.carousel-control.right {
|
|
||||||
margin-right: -35px;
|
|
||||||
margin-top: 7px;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.carousel-control {
|
.carousel-control {
|
||||||
width: 0%;
|
width: 34px;
|
||||||
|
height: 34px;
|
||||||
|
top: 50%;
|
||||||
|
margin-top: -17px;
|
||||||
|
opacity: 1;
|
||||||
|
text-shadow: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.carousel-control.left {
|
||||||
|
left: -18px;
|
||||||
|
margin-left: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.carousel-control.right {
|
||||||
|
right: -18px;
|
||||||
|
margin-right: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.carousel-control .glyphicon {
|
||||||
|
width: 34px;
|
||||||
|
height: 34px;
|
||||||
|
line-height: 34px;
|
||||||
|
border-radius: 50%;
|
||||||
|
background: rgba(255, 255, 255, 0.95);
|
||||||
|
border: 1px solid #d1d5db;
|
||||||
|
color: #374151;
|
||||||
|
font-size: 14px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.carousel-control:hover .glyphicon {
|
||||||
|
background: #ffffff;
|
||||||
|
border-color: #9ca3af;
|
||||||
|
color: #111827;
|
||||||
}
|
}
|
||||||
|
|
||||||
.custom-chevron-left,
|
.custom-chevron-left,
|
||||||
@@ -139,11 +206,127 @@
|
|||||||
|
|
||||||
.hide-bullets {
|
.hide-bullets {
|
||||||
list-style:none;
|
list-style:none;
|
||||||
margin-left: -40px;
|
margin-left: 0;
|
||||||
margin-top:20px;
|
margin-top: 0;
|
||||||
|
margin-bottom: 0;
|
||||||
|
padding-left: 0;
|
||||||
}
|
}
|
||||||
|
.hide-bullets > li {
|
||||||
|
margin-bottom: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.main-gallery-card,
|
||||||
|
.product-info-card,
|
||||||
|
.description-card {
|
||||||
|
background: #fff;
|
||||||
|
border: 1px solid #e5e7eb;
|
||||||
|
border-radius: 12px;
|
||||||
|
box-shadow: 0 1px 2px rgba(16, 24, 40, 0.04);
|
||||||
|
}
|
||||||
|
|
||||||
|
.main-gallery-card {
|
||||||
|
padding: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.main-image-stage {
|
||||||
|
border: 1px solid #eef0f3;
|
||||||
|
border-radius: 10px;
|
||||||
|
background: #fcfcfd;
|
||||||
|
min-height: 430px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.main-product-image {
|
||||||
|
max-height: 400px;
|
||||||
|
width: auto;
|
||||||
|
max-width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.thumbnail {
|
||||||
|
border-radius: 10px;
|
||||||
|
border: 1px solid #d1d5db;
|
||||||
|
background: #fff;
|
||||||
|
margin-bottom: 0;
|
||||||
|
transition: border-color 0.2s, box-shadow 0.2s;
|
||||||
|
}
|
||||||
|
|
||||||
|
.thumbnail:hover {
|
||||||
|
border-color: #9ca3af;
|
||||||
|
box-shadow: 0 3px 12px rgba(0, 0, 0, 0.08);
|
||||||
|
}
|
||||||
|
|
||||||
|
.a_thumbnail.active {
|
||||||
|
border-color: #3b82f6;
|
||||||
|
box-shadow: 0 0 0 2px rgba(59, 130, 246, 0.2);
|
||||||
|
}
|
||||||
|
|
||||||
|
.image-thumbnails {
|
||||||
|
border-radius: 8px;
|
||||||
|
object-fit: contain;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-info-card {
|
||||||
|
padding: 22px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-title {
|
||||||
|
margin: 0;
|
||||||
|
font-size: 28px;
|
||||||
|
line-height: 1.2;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #111827;
|
||||||
|
}
|
||||||
|
|
||||||
|
.price {
|
||||||
|
font-size: 30px;
|
||||||
|
margin: 8px 0 18px;
|
||||||
|
color: #0f172a;
|
||||||
|
font-weight: 700;
|
||||||
|
}
|
||||||
|
|
||||||
|
.price small {
|
||||||
|
font-size: 14px;
|
||||||
|
color: #6b7280;
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
|
|
||||||
|
#frm-order-list {
|
||||||
|
padding-top: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#btn-add-to-cart {
|
||||||
|
min-height: 44px;
|
||||||
|
padding: 10px 18px;
|
||||||
|
border-radius: 9px;
|
||||||
|
font-weight: 600;
|
||||||
|
font-size: 14px;
|
||||||
|
letter-spacing: 0.2px;
|
||||||
|
margin-top: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.description-card {
|
||||||
|
margin-top: 18px;
|
||||||
|
padding: 18px 22px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.description-title {
|
||||||
|
margin: 0 0 10px;
|
||||||
|
font-size: 16px;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #111827;
|
||||||
|
}
|
||||||
|
|
||||||
|
.description-text {
|
||||||
|
margin: 0;
|
||||||
|
font-size: 14px;
|
||||||
|
line-height: 1.65;
|
||||||
|
color: #4b5563;
|
||||||
|
}
|
||||||
|
|
||||||
.spacer-top{
|
.spacer-top{
|
||||||
margin-top: 40px;
|
margin-top: 24px;
|
||||||
}
|
}
|
||||||
.roster-input{
|
.roster-input{
|
||||||
border-radius: 0px;
|
border-radius: 0px;
|
||||||
@@ -208,12 +391,49 @@
|
|||||||
overflow: auto;
|
overflow: auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@media screen and (max-width: 991px) {
|
||||||
|
.product-info-card {
|
||||||
|
margin-top: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.main-image-stage {
|
||||||
|
min-height: 350px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#btn-add-to-cart {
|
||||||
|
width: 100%;
|
||||||
|
float: none !important;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@media screen and (max-width: 768px) {
|
||||||
|
.main-image-stage {
|
||||||
|
min-height: 300px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.carousel-control.left {
|
||||||
|
left: -10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.carousel-control.right {
|
||||||
|
right: -10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.product-title {
|
||||||
|
font-size: 23px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.price {
|
||||||
|
font-size: 26px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
<div class="container">
|
<div class="container product-page">
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<nav aria-label="breadcrumb">
|
<nav aria-label="breadcrumb" class="product-breadcrumb">
|
||||||
<ol class="breadcrumb">
|
<ol class="breadcrumb">
|
||||||
<li class="breadcrumb-item"><a href="{{ url('teamstore') }}/{{ $store_array[0]->StoreUrl }}">Home</a></li>
|
<li class="breadcrumb-item"><a href="{{ url('teamstore') }}/{{ $store_array[0]->StoreUrl }}">Home</a></li>
|
||||||
<li class="breadcrumb-item active" aria-current="page">{{ $product_array[0]->ProductName }}</li>
|
<li class="breadcrumb-item active" aria-current="page">{{ $product_array[0]->ProductName }}</li>
|
||||||
@@ -224,68 +444,62 @@
|
|||||||
<div class="row">
|
<div class="row">
|
||||||
|
|
||||||
<div class="col-md-5 col-sm-5">
|
<div class="col-md-5 col-sm-5">
|
||||||
<div class="row">
|
<div class="main-gallery-card">
|
||||||
<div class="col-sm-12" id="carousel-bounding-box">
|
<div id="carousel-bounding-box">
|
||||||
<div class="carousel slide" id="myCarousel" data-interval="false">
|
<div class="main-image-stage">
|
||||||
<!-- Carousel items -->
|
<div class="carousel slide" id="myCarousel" data-interval="false">
|
||||||
<div class="carousel-inner">
|
<div class="carousel-inner">
|
||||||
@define $i = 0
|
@define $i = 0
|
||||||
@foreach($thumbnails_array as $thumbnail)
|
@foreach($thumbnails_array as $thumbnail)
|
||||||
@if($thumbnail->ImageClass == 'active')
|
@if($thumbnail->ImageClass == 'active')
|
||||||
<div class="active item text-center" data-slide-number="{{ $i }}">
|
<div class="active item text-center" data-slide-number="{{ $i }}">
|
||||||
<span class="zoom img-zoom">
|
<span class="zoom img-zoom">
|
||||||
<img style="height:400px;" src="{{ config('site_config.images_url') }}/{{ $thumbnail->Image }}">
|
<img class="main-product-image" src="{{ minio_url('images/' . $thumbnail->Image) }}">
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
@else
|
@else
|
||||||
<div class="item text-center" data-slide-number="{{ $i }}">
|
<div class="item text-center" data-slide-number="{{ $i }}">
|
||||||
<span class="zoom img-zoom">
|
<span class="zoom img-zoom">
|
||||||
<img style="height:400px;" src="{{ config('site_config.images_url') }}/{{ $thumbnail->Image }}">
|
<img class="main-product-image" src="{{ minio_url('images/' . $thumbnail->Image) }}">
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
@endif
|
@endif
|
||||||
@define $i++
|
@define $i++
|
||||||
@endforeach
|
@endforeach
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Carousel nav -->
|
<a class="left carousel-control" href="#myCarousel" role="button" data-slide="prev">
|
||||||
<a class="left carousel-control" href="#myCarousel" role="button" data-slide="prev">
|
<span class="glyphicon glyphicon-chevron-left"></span>
|
||||||
<span class="glyphicon glyphicon-chevron-left"></span>
|
</a>
|
||||||
</a>
|
<a class="right carousel-control" href="#myCarousel" role="button" data-slide="next">
|
||||||
<a class="right carousel-control" href="#myCarousel" role="button" data-slide="next">
|
<span class="glyphicon glyphicon-chevron-right"></span>
|
||||||
<span class="glyphicon glyphicon-chevron-right"></span>
|
</a>
|
||||||
</a>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<!-- </div> -->
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<hr class="line">
|
<hr class="line">
|
||||||
|
|
||||||
<div class="row">
|
<ul class="hide-bullets row">
|
||||||
<div class="col-md-12">
|
@define $j = 0
|
||||||
<ul class="hide-bullets">
|
@foreach($thumbnails_array as $thumbnail)
|
||||||
@define $j = 0
|
<li class="col-sm-3 col-xs-3">
|
||||||
@foreach($thumbnails_array as $thumbnail)
|
<a class="thumbnail a_thumbnail {{ $thumbnail->ImageClass }}" id="carousel-selector-{{ $j }}">
|
||||||
<li class="col-sm-3 col-xs-3">
|
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ minio_url('images/' . $thumbnail->Image) }}"/>
|
||||||
<a class="thumbnail a_thumbnail {{ $thumbnail->ImageClass }}" id="carousel-selector-{{ $j }}">
|
</a>
|
||||||
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ config('site_config.images_url') }}/{{ $thumbnail->Image }}"/>
|
</li>
|
||||||
</a>
|
@define $j++
|
||||||
</li>
|
@endforeach
|
||||||
@define $j++
|
</ul>
|
||||||
@endforeach
|
|
||||||
</ul>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="col-md-7 col-sm-7">
|
<div class="col-md-7 col-sm-7">
|
||||||
<div class="panel panel-default">
|
<div class="product-info-card">
|
||||||
<div class="panel-heading">
|
<h1 class="product-title">{{ $product_array[0]->ProductName }}</h1>
|
||||||
<h1>{{ $product_array[0]->ProductName }}</h1> <p class="price">{{ $product_array[0]->ProductPrice }} <small> {{ $store_array[0]->StoreCurrency }} </small></p>
|
<p class="price">{{ $product_array[0]->ProductPrice }} <small> {{ $store_array[0]->StoreCurrency }} </small></p>
|
||||||
</div>
|
|
||||||
<div class="panel-body">
|
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<form id="frm-order-list">
|
<form id="frm-order-list">
|
||||||
@@ -300,19 +514,23 @@
|
|||||||
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="spacer-top"></div>
|
|
||||||
<div class="row">
|
<div class="description-card">
|
||||||
<div class="col-md-12">
|
<h3 class="description-title">Description</h3>
|
||||||
<ul class="nav nav-tabs" role="tablist">
|
<p class="description-text">{{ $product_array[0]->ProductDescription }}</p>
|
||||||
<li role="presentation" class="active"><a href="#productDescription" aria-controls="productDescription" role="tab" data-toggle="tab">Description</a></li>
|
</div>
|
||||||
</ul>
|
|
||||||
<!-- Tab panes -->
|
<div class="spacer-top"></div>
|
||||||
<div class="tab-content">
|
<div class="row">
|
||||||
<div role="tabpanel" class="tab-pane active" id="productDescription">
|
<div class="col-md-12">
|
||||||
<div class="row">
|
<ul class="nav nav-tabs" role="tablist">
|
||||||
<div class="col-md-12">
|
<li role="presentation" class="active"><a href="#productDescription" aria-controls="productDescription" role="tab" data-toggle="tab">More Details</a></li>
|
||||||
<p>{{ $product_array[0]->ProductDescription }}</p>
|
</ul>
|
||||||
</div>
|
<div class="tab-content">
|
||||||
|
<div role="tabpanel" class="tab-pane active" id="productDescription">
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-md-12">
|
||||||
|
<p>{{ $product_array[0]->ProductDescription }}</p>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -2,108 +2,237 @@
|
|||||||
@section('content')
|
@section('content')
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
a.thumbnail>img {
|
body {
|
||||||
/* height: 250px; */
|
background: #f4f6f8;
|
||||||
}
|
}
|
||||||
|
|
||||||
.hide-bullets {
|
.store-page {
|
||||||
list-style:none;
|
padding-top: 14px;
|
||||||
margin-left: -40px;
|
padding-bottom: 26px;
|
||||||
margin-top:20px;
|
|
||||||
position: relative;
|
|
||||||
}
|
}
|
||||||
.thumbnail{
|
|
||||||
border: none;
|
.store-header {
|
||||||
display: unset;
|
margin-bottom: 14px;
|
||||||
background-color: transparent;
|
|
||||||
}
|
}
|
||||||
.li-custom{
|
|
||||||
padding:10px;
|
.store-title {
|
||||||
|
margin: 0;
|
||||||
|
font-size: 24px;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #111827;
|
||||||
}
|
}
|
||||||
.store-logo{
|
|
||||||
/* height: 250px;
|
.store-subtitle {
|
||||||
width: 250px;
|
margin: 6px 0 0;
|
||||||
|
font-size: 13px;
|
||||||
|
color: #6b7280;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-toolbar {
|
||||||
|
background: #fff;
|
||||||
|
border: 1px solid #e5e7eb;
|
||||||
|
border-radius: 12px;
|
||||||
|
box-shadow: 0 1px 2px rgba(16, 24, 40, 0.04);
|
||||||
|
padding: 14px;
|
||||||
|
margin-bottom: 18px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-toolbar label {
|
||||||
|
font-size: 12px;
|
||||||
|
color: #4b5563;
|
||||||
|
font-weight: 600;
|
||||||
|
margin-bottom: 6px;
|
||||||
|
text-transform: uppercase;
|
||||||
|
letter-spacing: 0.4px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-toolbar .form-control,
|
||||||
|
.store-toolbar .btn {
|
||||||
|
height: 40px;
|
||||||
|
border-radius: 8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-toolbar .form-control {
|
||||||
|
border-color: #d1d5db;
|
||||||
|
box-shadow: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-toolbar .form-control:focus {
|
||||||
|
border-color: #9ca3af;
|
||||||
|
box-shadow: 0 0 0 3px rgba(156, 163, 175, 0.18);
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-grid {
|
||||||
|
list-style: none;
|
||||||
|
padding-left: 0;
|
||||||
|
margin: 0 -10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-grid > li {
|
||||||
|
padding: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-card {
|
||||||
|
background: #fff;
|
||||||
|
border: 1px solid #e5e7eb;
|
||||||
|
border-radius: 12px;
|
||||||
|
box-shadow: 0 1px 2px rgba(16, 24, 40, 0.04);
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
object-fit: contain; */
|
height: 100%;
|
||||||
/* cursor: pointer; */
|
transition: transform 0.2s, box-shadow 0.2s, border-color 0.2s;
|
||||||
}
|
}
|
||||||
a.thumbnail>img{
|
|
||||||
height: 150px
|
.store-card:hover {
|
||||||
|
transform: translateY(-2px);
|
||||||
|
border-color: #d1d5db;
|
||||||
|
box-shadow: 0 8px 24px rgba(15, 23, 42, 0.08);
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-link {
|
||||||
|
display: block;
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-link:hover,
|
||||||
|
.store-link:focus {
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-logo-wrap {
|
||||||
|
height: 170px;
|
||||||
|
background: #f8fafc;
|
||||||
|
border-bottom: 1px solid #e5e7eb;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
padding: 14px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-logo {
|
||||||
|
max-width: 100%;
|
||||||
|
max-height: 100%;
|
||||||
|
width: auto;
|
||||||
|
height: auto;
|
||||||
|
object-fit: contain;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-meta {
|
||||||
|
padding: 12px;
|
||||||
|
min-height: 72px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-name {
|
||||||
|
margin: 0;
|
||||||
|
font-size: 15px;
|
||||||
|
line-height: 1.35;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #111827;
|
||||||
|
text-align: center;
|
||||||
|
text-transform: uppercase;
|
||||||
|
word-break: break-word;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-lock {
|
||||||
|
color: #6b7280;
|
||||||
|
margin-left: 4px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-pagination {
|
||||||
|
margin-top: 18px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-pagination .pagination {
|
||||||
|
margin: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (max-width: 767px) {
|
||||||
|
.store-title {
|
||||||
|
font-size: 21px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-toolbar {
|
||||||
|
padding: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.store-logo-wrap {
|
||||||
|
height: 155px;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
<div class="container">
|
<div class="container store-page">
|
||||||
<div class="row">
|
<div class="row store-header">
|
||||||
<div class="col-lg-12">
|
<div class="col-lg-12">
|
||||||
<h2 style="font-size: 20px; font-weight: bold; ">TEAM STORES</h2>
|
<h2 class="store-title">Team Stores</h2>
|
||||||
<hr>
|
<p class="store-subtitle">Browse and open your team store.</p>
|
||||||
</div>
|
</div>
|
||||||
</div><!-- /row -->
|
|
||||||
<div class="row">
|
|
||||||
<!-- <div class="col-sm-12"> -->
|
|
||||||
<!-- <div class="well"> -->
|
|
||||||
<form class="form-horizontal" role="search" id="frm_search_store">
|
|
||||||
<div class="col-lg-7">
|
|
||||||
<div class="form-group">
|
|
||||||
<div class="col-sm-12">
|
|
||||||
<label>Seach Store</label>
|
|
||||||
<div class="input-group">
|
|
||||||
<input type="text" class="form-control" placeholder="Search Store" value="{{ $keyword }}" name="q">
|
|
||||||
<div class="input-group-btn">
|
|
||||||
<button class="btn btn-default" type="submit"><i class="fa fa-search"></i></button>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="col-lg-5">
|
|
||||||
<div class="form-group">
|
|
||||||
<label class="col-sm-7 control-label hidden-xs"> </label>
|
|
||||||
<div class="col-sm-5">
|
|
||||||
<label>Sort by:</label>
|
|
||||||
<select class="form-control" name="s" id="select_sort_stores">
|
|
||||||
<option @if($filter == "al-asc") selected @endif value="al-asc">Store Name A → Z</option>
|
|
||||||
<option @if($filter == "al-desc") selected @endif value="al-desc">Store Name Z → A</option>
|
|
||||||
<option @if($filter == "latest") selected @endif value="latest">Newest → Oldest</option>
|
|
||||||
<option @if($filter == "oldest") selected @endif value="oldest">Oldest → Newest</option>
|
|
||||||
</select>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</form>
|
|
||||||
<div class="clearfix"></div>
|
|
||||||
<!-- </div> -->
|
|
||||||
<!-- </div> -->
|
|
||||||
</div>
|
</div>
|
||||||
<div class="row" id="slider-thumbs">
|
|
||||||
<!-- Bottom switcher of slider -->
|
<div class="store-toolbar">
|
||||||
<ul class="hide-bullets">
|
<form role="search" id="frm_search_store">
|
||||||
@foreach ($stores_array as $store)
|
<div class="row">
|
||||||
<li class="li-custom col-lg-3 col-md-3 col-sm-4 col-xs-12">
|
<div class="col-md-8 col-sm-7">
|
||||||
<div style="border: 1px solid #dddddd; padding: 5px;">
|
<label>Search Store</label>
|
||||||
@if($store->Password != null )
|
<div class="input-group">
|
||||||
<a class="thumbnail password-protected" href="#" data-store-id="{{ $store->Id }}" data-store-url="{{ $store->StoreUrl }}">
|
<input type="text" class="form-control" placeholder="Search store" value="{{ $keyword }}" name="q">
|
||||||
<img class="store-logo" src="{{ config('site_config.uploads') . 'teamstore/'. $store->ImageFolder . '/' . $store->StoreLogo }}">
|
<div class="input-group-btn">
|
||||||
</a>
|
<button class="btn btn-default" type="submit"><i class="fa fa-search"></i></button>
|
||||||
<h4 style="border-top: 1px solid #dddddd; padding: 10px; font-size: 16px; font-weight: bold; text-transform: uppercase;" class="text-center">{{ $store->StoreName }} <i class="fa fa-lock" title="This store is password protected."></i></h4>
|
</div>
|
||||||
@else
|
</div>
|
||||||
<a class="thumbnail" href="{{ url('teamstore') . '/' . $store->StoreUrl }}">
|
|
||||||
<img class="store-logo" src="{{ config('site_config.uploads') . 'teamstore/' . $store->ImageFolder . '/' . $store->StoreLogo }}">
|
|
||||||
</a>
|
|
||||||
<h4 style="border-top: 1px solid #dddddd; padding: 10px; font-size: 16px; font-weight: bold; text-transform: uppercase;" class="text-center">{{ $store->StoreName }}</h4>
|
|
||||||
@endif
|
|
||||||
</div>
|
</div>
|
||||||
</li>
|
<div class="col-md-4 col-sm-5">
|
||||||
|
<label>Sort by</label>
|
||||||
|
<select class="form-control" name="s" id="select_sort_stores">
|
||||||
|
<option @if($filter == "al-asc") selected @endif value="al-asc">Store Name A → Z</option>
|
||||||
|
<option @if($filter == "al-desc") selected @endif value="al-desc">Store Name Z → A</option>
|
||||||
|
<option @if($filter == "latest") selected @endif value="latest">Newest → Oldest</option>
|
||||||
|
<option @if($filter == "oldest") selected @endif value="oldest">Oldest → Newest</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div id="slider-thumbs">
|
||||||
|
<ul class="store-grid row">
|
||||||
|
@foreach ($stores_array as $store)
|
||||||
|
<li class="col-lg-3 col-md-4 col-sm-6 col-xs-12">
|
||||||
|
<div class="store-card">
|
||||||
|
@if($store->Password != null)
|
||||||
|
<a class="store-link password-protected" href="#" data-store-id="{{ $store->Id }}" data-store-url="{{ $store->StoreUrl }}">
|
||||||
|
<div class="store-logo-wrap">
|
||||||
|
<img class="store-logo" src="{{ minio_url('uploads/images/teamstore/' . $store->ImageFolder . '/' . $store->StoreLogo) }}">
|
||||||
|
</div>
|
||||||
|
</a>
|
||||||
|
<div class="store-meta">
|
||||||
|
<h4 class="store-name">{{ $store->StoreName }} <i class="fa fa-lock store-lock" title="This store is password protected."></i></h4>
|
||||||
|
</div>
|
||||||
|
@else
|
||||||
|
<a class="store-link" href="{{ url('teamstore') . '/' . $store->StoreUrl }}">
|
||||||
|
<div class="store-logo-wrap">
|
||||||
|
<img class="store-logo" src="{{ minio_url('uploads/images/teamstore/' . $store->ImageFolder . '/' . $store->StoreLogo) }}">
|
||||||
|
</div>
|
||||||
|
<div class="store-meta">
|
||||||
|
<h4 class="store-name">{{ $store->StoreName }}</h4>
|
||||||
|
</div>
|
||||||
|
</a>
|
||||||
|
@endif
|
||||||
|
</div>
|
||||||
|
</li>
|
||||||
@endforeach
|
@endforeach
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
<div class="row">
|
|
||||||
|
<div class="row store-pagination">
|
||||||
<div class="col-sm-12">
|
<div class="col-sm-12">
|
||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
{!! $stores_array->render() !!}
|
{!! $stores_array->render() !!}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div><!-- /container -->
|
</div>
|
||||||
|
|
||||||
|
|
||||||
<div id="team-store-login" class="modal fade" role="dialog">
|
<div id="team-store-login" class="modal fade" role="dialog">
|
||||||
|
|||||||
56
resources/views/test-email.blade.php
Normal file
56
resources/views/test-email.blade.php
Normal file
@@ -0,0 +1,56 @@
|
|||||||
|
@extends('layout.main')
|
||||||
|
|
||||||
|
@section('content')
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-md-6 col-md-offset-3" style="margin-top: 40px; margin-bottom: 40px;">
|
||||||
|
<div class="panel panel-default">
|
||||||
|
<div class="panel-heading">
|
||||||
|
<h3 class="panel-title"><strong>Send Test Email</strong></h3>
|
||||||
|
</div>
|
||||||
|
<div class="panel-body">
|
||||||
|
|
||||||
|
@if (session('message'))
|
||||||
|
<div class="alert alert-{{ session('status') }} alert-dismissible" role="alert">
|
||||||
|
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
|
||||||
|
<span aria-hidden="true">×</span>
|
||||||
|
</button>
|
||||||
|
{{ session('message') }}
|
||||||
|
</div>
|
||||||
|
@endif
|
||||||
|
|
||||||
|
<!-- Mail Config Info -->
|
||||||
|
<div class="well well-sm" style="font-size: 12px;">
|
||||||
|
<strong>Current Mail Config</strong><br>
|
||||||
|
Driver: <code>{{ config('mail.driver') ?: '(not set)' }}</code><br>
|
||||||
|
Host: <code>{{ config('mail.host') ?: '(not set)' }}</code><br>
|
||||||
|
Port: <code>{{ config('mail.port') ?: '(not set)' }}</code><br>
|
||||||
|
Username: <code>{{ config('mail.username') ?: '(not set)' }}</code><br>
|
||||||
|
Encryption: <code>{{ config('mail.encryption') ?: '(not set)' }}</code>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<form method="POST" action="{{ url('test-email/send') }}">
|
||||||
|
<input type="hidden" name="_token" value="{{ csrf_token() }}">
|
||||||
|
<input type="hidden" name="token" value="{{ $token }}">
|
||||||
|
<div class="form-group{{ $errors->has('recipient') ? ' has-error' : '' }}">
|
||||||
|
<label for="recipient">Recipient Email</label>
|
||||||
|
<input type="email"
|
||||||
|
name="recipient"
|
||||||
|
id="recipient"
|
||||||
|
class="form-control"
|
||||||
|
placeholder="you@example.com"
|
||||||
|
value="{{ old('recipient') }}"
|
||||||
|
required>
|
||||||
|
@if ($errors->has('recipient'))
|
||||||
|
<span class="help-block">{{ $errors->first('recipient') }}</span>
|
||||||
|
@endif
|
||||||
|
</div>
|
||||||
|
<button type="submit" class="btn btn-primary btn-block">
|
||||||
|
<i class="fa fa-envelope"></i> Send Test Email
|
||||||
|
</button>
|
||||||
|
</form>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
@endsection
|
||||||
@@ -42,7 +42,7 @@
|
|||||||
@foreach($array_client_designs as $row)
|
@foreach($array_client_designs as $row)
|
||||||
@foreach($array_template_paths as $key => $row1)
|
@foreach($array_template_paths as $key => $row1)
|
||||||
@if($key == 0)
|
@if($key == 0)
|
||||||
<img src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-front-thumbnail.png" alt="{{ $row->DesignName }}" id="main-thumbnail" class="img img-responsive">
|
<img src="{{ minio_url('images/' . $row->DesignCode . '-front-thumbnail.png') }}" alt="{{ $row->DesignName }}" id="main-thumbnail" class="img img-responsive">
|
||||||
@endif
|
@endif
|
||||||
@endforeach
|
@endforeach
|
||||||
@endforeach
|
@endforeach
|
||||||
@@ -56,7 +56,7 @@
|
|||||||
@if($key == 0)
|
@if($key == 0)
|
||||||
<li class="col-sm-3 col-xs-3">
|
<li class="col-sm-3 col-xs-3">
|
||||||
<a class="thumbnail a_thumbnail active">
|
<a class="thumbnail a_thumbnail active">
|
||||||
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-front-thumbnail.png"/>
|
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ minio_url('images/' . $row->DesignCode . '-front-thumbnail.png') }}"/>
|
||||||
</a>
|
</a>
|
||||||
<!-- <p>Select Default Thumbnail:</p>
|
<!-- <p>Select Default Thumbnail:</p>
|
||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
@@ -66,7 +66,7 @@
|
|||||||
@else
|
@else
|
||||||
<li class="col-sm-3 col-xs-3">
|
<li class="col-sm-3 col-xs-3">
|
||||||
<a class="thumbnail a_thumbnail">
|
<a class="thumbnail a_thumbnail">
|
||||||
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-{{ strtolower($row1->Side) }}-thumbnail.png"/>
|
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ minio_url('images/' . $row->DesignCode . '-' . strtolower($row1->Side) . '-thumbnail.png') }}"/>
|
||||||
</a>
|
</a>
|
||||||
<!-- <p> </p>
|
<!-- <p> </p>
|
||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
|
|||||||
@@ -18,7 +18,7 @@
|
|||||||
<!-- Control Sidebar Toggle Button -->
|
<!-- Control Sidebar Toggle Button -->
|
||||||
<li class="user user-menu">
|
<li class="user user-menu">
|
||||||
<a href="#">
|
<a href="#">
|
||||||
<img src="{{ config('site_config.uploads') . 'user/default-user.png' }}" class="user-image" alt="User Image">
|
<img src="{{ minio_url('uploads/images/user/default-user.png') }}" class="user-image" alt="User Image">
|
||||||
<span class="hidden-xs">{{ Auth::user()->username }}</span>
|
<span class="hidden-xs">{{ Auth::user()->username }}</span>
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
|
|||||||
@@ -32,7 +32,7 @@
|
|||||||
@foreach($array_client_designs as $row)
|
@foreach($array_client_designs as $row)
|
||||||
<div class="col-md-3 col-sm-6">
|
<div class="col-md-3 col-sm-6">
|
||||||
<span class="thumbnail">
|
<span class="thumbnail">
|
||||||
<img src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-front-thumbnail.png" alt="{{ $row->DesignName }}" >
|
<img src="{{ minio_url('images/' . $row->DesignCode . '-front-thumbnail.png') }}" alt="{{ $row->DesignName }}" >
|
||||||
<h4 class="design-name-holder">{{ $row->DesignName }}</h4>
|
<h4 class="design-name-holder">{{ $row->DesignName }}</h4>
|
||||||
<small>{{ date('F j, Y g:i a', strtotime($row->DateCreated)) }}</small>
|
<small>{{ date('F j, Y g:i a', strtotime($row->DateCreated)) }}</small>
|
||||||
<hr class="line">
|
<hr class="line">
|
||||||
|
|||||||
@@ -33,7 +33,7 @@
|
|||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-md-2">
|
<div class="col-md-2">
|
||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
<img class="previewImage" id="active_thumbnail" src="{{ config('site_config.images_url') . '/images/' . $array_thumbnail_display[0]->Image }}">
|
<img class="previewImage" id="active_thumbnail" src="{{ minio_url('images/' . $array_thumbnail_display[0]->Image) }}">
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="col-md-10">
|
<div class="col-md-10">
|
||||||
|
|||||||
@@ -93,7 +93,7 @@
|
|||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
@foreach($img_thumb as $img)
|
@foreach($img_thumb as $img)
|
||||||
@if($img->ProductId == $item->ProductId)
|
@if($img->ProductId == $item->ProductId)
|
||||||
<img class="previewImage" src="{{ config('site_config.images_url') }}/{{ $img->Image }}">
|
<img class="previewImage" src="{{ minio_url('images/' . $img->Image) }}">
|
||||||
@endif
|
@endif
|
||||||
@endforeach
|
@endforeach
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -42,7 +42,7 @@
|
|||||||
@foreach($array_client_designs as $row)
|
@foreach($array_client_designs as $row)
|
||||||
@foreach($array_template_paths as $key => $row1)
|
@foreach($array_template_paths as $key => $row1)
|
||||||
@if($key == 0)
|
@if($key == 0)
|
||||||
<img src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-front-thumbnail.png" alt="{{ $row->DesignName }}" id="main-thumbnail" class="img img-responsive">
|
<img src="{{ minio_url('images/' . $row->DesignCode . '-front-thumbnail.png') }}" alt="{{ $row->DesignName }}" id="main-thumbnail" class="img img-responsive">
|
||||||
@endif
|
@endif
|
||||||
@endforeach
|
@endforeach
|
||||||
@endforeach
|
@endforeach
|
||||||
@@ -56,7 +56,7 @@
|
|||||||
@if($key == 0)
|
@if($key == 0)
|
||||||
<li class="col-sm-3 col-xs-3">
|
<li class="col-sm-3 col-xs-3">
|
||||||
<a class="thumbnail a_thumbnail active">
|
<a class="thumbnail a_thumbnail active">
|
||||||
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-front-thumbnail.png"/>
|
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ minio_url('images/' . $row->DesignCode . '-front-thumbnail.png') }}"/>
|
||||||
</a>
|
</a>
|
||||||
<!-- <p>Select Default Thumbnail:</p>
|
<!-- <p>Select Default Thumbnail:</p>
|
||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
@@ -66,7 +66,7 @@
|
|||||||
@else
|
@else
|
||||||
<li class="col-sm-3 col-xs-3">
|
<li class="col-sm-3 col-xs-3">
|
||||||
<a class="thumbnail a_thumbnail">
|
<a class="thumbnail a_thumbnail">
|
||||||
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-{{ strtolower($row1->Side) }}-thumbnail.png"/>
|
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ minio_url('images/' . $row->DesignCode . '-' . strtolower($row1->Side) . '-thumbnail.png') }}"/>
|
||||||
</a>
|
</a>
|
||||||
<!-- <p> </p>
|
<!-- <p> </p>
|
||||||
<div class="text-center">
|
<div class="text-center">
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
<!-- Sidebar user panel -->
|
<!-- Sidebar user panel -->
|
||||||
<div class="user-panel">
|
<div class="user-panel">
|
||||||
<div class="pull-left image">
|
<div class="pull-left image">
|
||||||
<img src="{{ config('site_config.uploads') . 'user/default-user.png' }}" class="img-circle" alt="User Image">
|
<img src="{{ minio_url('uploads/images/user/default-user.png') }}" class="img-circle" alt="User Image">
|
||||||
</div>
|
</div>
|
||||||
<div class="pull-left info">
|
<div class="pull-left info">
|
||||||
<p>{{ Auth::user()->name }}</p>
|
<p>{{ Auth::user()->name }}</p>
|
||||||
|
|||||||
@@ -59,7 +59,7 @@
|
|||||||
<div class="col-md-3 col-sm-6">
|
<div class="col-md-3 col-sm-6">
|
||||||
<div class="thumbnail" >
|
<div class="thumbnail" >
|
||||||
<a href="{{ url('user/store-items/item') }}/{{ $product->ProductURL }}">
|
<a href="{{ url('user/store-items/item') }}/{{ $product->ProductURL }}">
|
||||||
<img style="height:200px" src="{{ config('site_config.images_url') }}/{{ $filename . '?t=' . time() }}" alt="{{ $product->ProductName }}" >
|
<img style="height:200px" src="{{ minio_url('images/' . $filename) . '?t=' . time() }}" alt="{{ $product->ProductName }}" >
|
||||||
</a>
|
</a>
|
||||||
<hr class="line">
|
<hr class="line">
|
||||||
<div class="pull-right">
|
<div class="pull-right">
|
||||||
|
|||||||
@@ -63,7 +63,7 @@
|
|||||||
<div id="{{ 'order_number_' . $product->Id }}">
|
<div id="{{ 'order_number_' . $product->Id }}">
|
||||||
<div class="thumbnail" >
|
<div class="thumbnail" >
|
||||||
<a href="#">
|
<a href="#">
|
||||||
<img style="height:200px" src="{{ config('site_config.images_url') }}/{{ $filename . '?t=' . time() }}" alt="{{ $product->ProductName }}" >
|
<img style="height:200px" src="{{ minio_url('images/' . $filename) . '?t=' . time() }}" alt="{{ $product->ProductName }}" >
|
||||||
</a>
|
</a>
|
||||||
<hr class="line">
|
<hr class="line">
|
||||||
<div class="pull-right">
|
<div class="pull-right">
|
||||||
|
|||||||
@@ -63,8 +63,8 @@
|
|||||||
<div class="col-sm-8">
|
<div class="col-sm-8">
|
||||||
<p>Store Logo Preview:</p>
|
<p>Store Logo Preview:</p>
|
||||||
<div class="store-logo-holder">
|
<div class="store-logo-holder">
|
||||||
<a href="{{ config('site_config.uploads') . 'teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreLogo }}?v={{ time() }}" class="img_store_logo_href" data-toggle="lightbox">
|
<a href="{{ minio_url('uploads/images/teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreLogo) }}?v={{ time() }}" class="img_store_logo_href" data-toggle="lightbox">
|
||||||
<img class="img_store_logo_img" id="img_store_logo" src="{{ config('site_config.uploads') . 'teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreLogo }}?v={{ time() }}" style="max-width: 100%; max-height: 100%; ">
|
<img class="img_store_logo_img" id="img_store_logo" src="{{ minio_url('uploads/images/teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreLogo) }}?v={{ time() }}" style="max-width: 100%; max-height: 100%; ">
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -82,8 +82,8 @@
|
|||||||
<div class="col-sm-8">
|
<div class="col-sm-8">
|
||||||
<p>Store Banner Preview:</p>
|
<p>Store Banner Preview:</p>
|
||||||
<div class="store-banner-holder">
|
<div class="store-banner-holder">
|
||||||
<a href="{{ config('site_config.uploads') . 'teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreBanner }}?v={{ time() }}" class="img_store_banner_href" data-toggle="lightbox">
|
<a href="{{ minio_url('uploads/images/teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreBanner) }}?v={{ time() }}" class="img_store_banner_href" data-toggle="lightbox">
|
||||||
<img class="img_store_banner_img" id="img_store_banner" src="{{ config('site_config.uploads') . 'teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreBanner }}?v={{ time() }}" style="max-width: 100%; max-height: 100%;">
|
<img class="img_store_banner_img" id="img_store_banner" src="{{ minio_url('uploads/images/teamstore/' . $store_array[0]->ImageFolder . '/' . $store_array[0]->StoreBanner) }}?v={{ time() }}" style="max-width: 100%; max-height: 100%;">
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -39,7 +39,7 @@
|
|||||||
@foreach($array_client_designs as $row)
|
@foreach($array_client_designs as $row)
|
||||||
@foreach($array_template_paths as $key => $row1)
|
@foreach($array_template_paths as $key => $row1)
|
||||||
@if($key == 0)
|
@if($key == 0)
|
||||||
<img src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-front-thumbnail.png" alt="{{ $row->DesignName }}" id="main-thumbnail" class="img img-responsive">
|
<img src="{{ minio_url('images/' . $row->DesignCode . '-front-thumbnail.png') }}" alt="{{ $row->DesignName }}" id="main-thumbnail" class="img img-responsive">
|
||||||
@endif
|
@endif
|
||||||
@endforeach
|
@endforeach
|
||||||
@endforeach
|
@endforeach
|
||||||
@@ -53,13 +53,13 @@
|
|||||||
@if($key == 0)
|
@if($key == 0)
|
||||||
<li class="col-sm-3 col-xs-3">
|
<li class="col-sm-3 col-xs-3">
|
||||||
<a class="thumbnail a_thumbnail active">
|
<a class="thumbnail a_thumbnail active">
|
||||||
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-front-thumbnail.png"/>
|
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ minio_url('images/' . $row->DesignCode . '-front-thumbnail.png') }}"/>
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
@else
|
@else
|
||||||
<li class="col-sm-3 col-xs-3">
|
<li class="col-sm-3 col-xs-3">
|
||||||
<a class="thumbnail a_thumbnail">
|
<a class="thumbnail a_thumbnail">
|
||||||
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ config('site_config.images_url') }}/{{ $row->DesignCode }}-{{ strtolower($row1->Side) }}-thumbnail.png"/>
|
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ minio_url('images/' . $row->DesignCode . '-' . strtolower($row1->Side) . '-thumbnail.png') }}"/>
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
@endif
|
@endif
|
||||||
|
|||||||
@@ -36,7 +36,7 @@
|
|||||||
<div class="col-md-12 text-center">
|
<div class="col-md-12 text-center">
|
||||||
@foreach($thumbnails_array as $thumbnail)
|
@foreach($thumbnails_array as $thumbnail)
|
||||||
@if($thumbnail->ImageClass == 'active')
|
@if($thumbnail->ImageClass == 'active')
|
||||||
<img style="height:400px" src="{{ config('site_config.images_url') }}/{{ $thumbnail->Image . '?t=' . time() }}" id="main-thumbnail">
|
<img style="height:400px" src="{{ minio_url('images/' . $thumbnail->Image) . '?t=' . time() }}" id="main-thumbnail">
|
||||||
@endif
|
@endif
|
||||||
@endforeach
|
@endforeach
|
||||||
</div>
|
</div>
|
||||||
@@ -58,7 +58,7 @@
|
|||||||
<li class="col-sm-3 col-xs-4">
|
<li class="col-sm-3 col-xs-4">
|
||||||
<a class="thumbnail a_thumbnail {{ $thumbnail->ImageClass }}" style="border-bottom-left-radius: 0px; border-bottom-right-radius: 0px; margin-bottom: -28px;">
|
<a class="thumbnail a_thumbnail {{ $thumbnail->ImageClass }}" style="border-bottom-left-radius: 0px; border-bottom-right-radius: 0px; margin-bottom: -28px;">
|
||||||
<!-- <span class="close">×</span> -->
|
<!-- <span class="close">×</span> -->
|
||||||
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ config('site_config.images_url') }}/{{ $thumbnail->Image . '?t=' . time() }}"/>
|
<img class="img img-responsive product-center image-thumbnails" style="height: 59.45px;" src="{{ minio_url('images/' . $thumbnail->Image) . '?t=' . time() }}"/>
|
||||||
</a>
|
</a>
|
||||||
<div class="funkyradio">
|
<div class="funkyradio">
|
||||||
<div class="funkyradio-primary">
|
<div class="funkyradio-primary">
|
||||||
@@ -200,7 +200,7 @@
|
|||||||
|
|
||||||
<tr id="{{ 'item-' . $thumbnail->Id }}">
|
<tr id="{{ 'item-' . $thumbnail->Id }}">
|
||||||
<td class="text-center" style="width: 50px"><i class="fa fa-bars"></i></td>
|
<td class="text-center" style="width: 50px"><i class="fa fa-bars"></i></td>
|
||||||
<td><img class="img img-responsive product-center" style="height: 59.45px;" src="{{ config('site_config.images_url') }}/{{ $thumbnail->Image . '?t=' . time() }}"/></td>
|
<td><img class="img img-responsive product-center" style="height: 59.45px;" src="{{ minio_url('images/' . $thumbnail->Image) . '?t=' . time() }}"/></td>
|
||||||
<td class="text-center">
|
<td class="text-center">
|
||||||
<!-- <button class="btn btn-default btn-xs btn-edit-clipart" data-id="#"><i class="fa fa-edit"></i></button> -->
|
<!-- <button class="btn btn-default btn-xs btn-edit-clipart" data-id="#"><i class="fa fa-edit"></i></button> -->
|
||||||
<button class="btn btn-default btn-sm btn-delete-item-image" data-id="{{ $thumbnail->Id }}" data-filename="{{ $thumbnail->Image }}" title="Delete Image"><i class="fa fa-trash"></i></button>
|
<button class="btn btn-default btn-sm btn-delete-item-image" data-id="{{ $thumbnail->Id }}" data-filename="{{ $thumbnail->Image }}" title="Delete Image"><i class="fa fa-trash"></i></button>
|
||||||
|
|||||||
Reference in New Issue
Block a user