mirror of
https://github.com/LaCasemate/fab-manager.git
synced 2025-02-20 14:54:15 +01:00
(ui) Update layout
This commit is contained in:
parent
b9d86aecdc
commit
554ed083d0
@ -30,6 +30,7 @@ import ProductLib from '../../lib/product';
|
||||
import { UIRouter } from '@uirouter/angularjs';
|
||||
import SettingAPI from '../../api/setting';
|
||||
import { SelectOption } from '../../models/select';
|
||||
import { CaretDoubleUp } from 'phosphor-react';
|
||||
|
||||
declare const Application: IApplication;
|
||||
|
||||
@ -66,7 +67,6 @@ const Store: React.FC<StoreProps> = ({ onError, onSuccess, currentUser, uiRouter
|
||||
const [resources, setResources] = useImmer<ProductResourcesFetching>(storeInitialResources);
|
||||
const [machinesModule, setMachinesModule] = useState<boolean>(false);
|
||||
const [categoriesTree, setCategoriesTree] = useState<CategoryTree[]>([]);
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
const [filtersPanel, setFiltersPanel] = useState<boolean>(false);
|
||||
const [pageCount, setPageCount] = useState<number>(0);
|
||||
const [productsCount, setProductsCount] = useState<number>(0);
|
||||
@ -241,11 +241,14 @@ const Store: React.FC<StoreProps> = ({ onError, onSuccess, currentUser, uiRouter
|
||||
}
|
||||
</ul>
|
||||
<aside className={`store-filters ${filtersPanel ? '' : 'collapsed'}`}>
|
||||
<header>
|
||||
<h3>{t('app.public.store.products.filter_categories')}</h3>
|
||||
<div className="grpBtn">
|
||||
<CaretDoubleUp className='filters-toggle' size={16} weight="bold" onClick={() => setFiltersPanel(!filtersPanel)} />
|
||||
</div>
|
||||
</header>
|
||||
<div className='grp'>
|
||||
<div className="categories">
|
||||
<header>
|
||||
<h3>{t('app.public.store.products.filter_categories')}</h3>
|
||||
</header>
|
||||
<div className="group u-scrollbar">
|
||||
{categoriesTree.map(c =>
|
||||
<div key={c.parent.id} className={`parent ${selectedCategory?.id === c.parent.id || selectedCategory?.parent_id === c.parent.id ? 'is-active' : ''}`}>
|
||||
|
@ -103,7 +103,9 @@
|
||||
@import "modules/profile-completion/completion-header-info";
|
||||
@import "modules/profile-completion/profile-form-option";
|
||||
@import "modules/profile-custom-fields/profile-custom-fields-list";
|
||||
@import "modules/projects/project-card";
|
||||
@import "modules/projects/projects-setting.scss";
|
||||
@import "modules/projects/projects";
|
||||
@import "modules/select-gateway-modal";
|
||||
@import "modules/settings/boolean-setting";
|
||||
@import "modules/settings/check-list-setting";
|
||||
|
@ -1,6 +1,6 @@
|
||||
.machine-card {
|
||||
background-color: #fff;
|
||||
border: 1px solid #ddd;
|
||||
background-color: var(--gray-soft-lightest);
|
||||
border: 1px solid var(--gray-soft-dark);
|
||||
border-radius: var(--border-radius);
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
|
@ -0,0 +1,48 @@
|
||||
.project-card {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
background-color: var(--gray-soft-lightest);
|
||||
border: 1px solid var(--gray-soft-dark);
|
||||
border-radius: var(--border-radius);
|
||||
overflow: hidden;
|
||||
&:hover {
|
||||
border-color: var(--gray-hard);
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.project-image {
|
||||
@include imageRatio(50%);
|
||||
background-size: cover;
|
||||
background-position: center;
|
||||
border-bottom: 1px solid var(--gray-soft-dark);
|
||||
}
|
||||
.project-info {
|
||||
flex: 1;
|
||||
position: relative;
|
||||
padding: 1.6rem;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
gap: 0.4rem;
|
||||
.badge {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 50%;
|
||||
transform: translate(-50%, -50%);
|
||||
}
|
||||
.name {
|
||||
margin: 0;
|
||||
font-size: 1.6rem;
|
||||
text-transform: uppercase;
|
||||
font-weight: 600;
|
||||
text-align: center;
|
||||
}
|
||||
.openlab {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 0.8rem;
|
||||
font-size: 1.2rem;
|
||||
color: var(--main);
|
||||
}
|
||||
}
|
||||
}
|
47
app/frontend/src/stylesheets/modules/projects/projects.scss
Normal file
47
app/frontend/src/stylesheets/modules/projects/projects.scss
Normal file
@ -0,0 +1,47 @@
|
||||
.projects {
|
||||
max-width: calc(1600px + 6rem);
|
||||
margin: 0 auto;
|
||||
padding: 3rem 3rem 6rem;
|
||||
display: grid;
|
||||
grid-template-columns: 1fr;
|
||||
align-items: flex-start;
|
||||
gap: 2.4rem 3.2rem;
|
||||
|
||||
&-filters,
|
||||
.grp {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 1.6rem;
|
||||
header {
|
||||
@include header();
|
||||
padding-top: 0;
|
||||
}
|
||||
.switch {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
}
|
||||
.keywords {
|
||||
display: flex;
|
||||
input {
|
||||
border-top-right-radius: 0;
|
||||
border-bottom-right-radius: 0;
|
||||
}
|
||||
button {
|
||||
border-top-left-radius: 0;
|
||||
border-bottom-left-radius: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-list {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(auto-fill, minmax(290px, 1fr));
|
||||
gap: 3.2rem;
|
||||
& > span { grid-column: 1/-1;}
|
||||
}
|
||||
|
||||
@media (min-width: 1200px) {
|
||||
grid-template-columns: 1fr 3fr;
|
||||
&-list { grid-column: 2/-1; }
|
||||
}
|
||||
}
|
@ -9,7 +9,7 @@
|
||||
}
|
||||
|
||||
&.collapsed {
|
||||
header .grpBtn svg { transform: rotateZ(-180deg); }
|
||||
header .grpBtn .filters-toggle { transform: rotateZ(-180deg); }
|
||||
header .grpBtn button { display: flex; }
|
||||
.grp {
|
||||
max-height: 100vh;
|
||||
@ -26,7 +26,7 @@
|
||||
display: flex;
|
||||
align-items: center;
|
||||
button { display: none; }
|
||||
svg {
|
||||
.filters-toggle {
|
||||
cursor: pointer;
|
||||
transition: transform 250ms ease-in-out;
|
||||
}
|
||||
|
@ -63,6 +63,37 @@
|
||||
line-height: 1.18;
|
||||
}
|
||||
|
||||
@mixin header($sticky: false) {
|
||||
padding: 2.4rem 0;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
@if $sticky {
|
||||
position: sticky;
|
||||
top: 0;
|
||||
margin-top: 1px;
|
||||
padding: 2.4rem 0 4rem;
|
||||
background: linear-gradient(180deg, var(--gray-soft-lightest) 80%, transparent);
|
||||
z-index: 1;
|
||||
}
|
||||
h2 {
|
||||
margin: 0;
|
||||
@include title-lg;
|
||||
color: var(--gray-hard-darkest) !important;
|
||||
}
|
||||
h3 {
|
||||
margin: 0;
|
||||
@include text-lg(600);
|
||||
color: var(--gray-hard-darkest) !important;
|
||||
}
|
||||
.grpBtn {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 1.6rem;
|
||||
}
|
||||
}
|
||||
|
||||
// Text Editor
|
||||
@mixin editor {
|
||||
*:first-child {
|
||||
|
@ -19,108 +19,70 @@
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<section class="projects">
|
||||
<div class="projects-filters">
|
||||
<header>
|
||||
<h3>Filter</h3>
|
||||
<a href="javascript:void(0);" class="fab-button is-black" name="button" ng-click="resetFiltersAndTriggerSearch()" ng-show="!openlab.searchOverWholeNetwork">{{ 'app.public.projects_list.reset_all_filters' | translate }}</a>
|
||||
</header>
|
||||
<span class="switch" ng-if="openlab.projectsActive" uib-tooltip="{{ 'app.public.projects_list.tooltip_openlab_projects_switch' | translate }}" tooltip-trigger="mouseenter">
|
||||
<label for="searchOverWholeNetwork" class="control-label text-sm" translate>{{ 'app.public.projects_list.network_search' }}</label>
|
||||
<input bs-switch
|
||||
ng-model="openlab.searchOverWholeNetwork"
|
||||
type="checkbox"
|
||||
class="form-control"
|
||||
switch-on-text="{{ 'app.shared.buttons.yes' | translate }}"
|
||||
switch-off-text="{{ 'app.shared.buttons.no' | translate }}"
|
||||
switch-animate="true"
|
||||
ng-change="searchOverWholeNetworkChanged()"
|
||||
/>
|
||||
</span>
|
||||
|
||||
<section class="m-lg">
|
||||
<div class="row m-b-md">
|
||||
<div class="col-md-12 m-b">
|
||||
<a href="javascript:void(0);" class="text-sm pull-right reinit-filters" name="button" ng-click="resetFiltersAndTriggerSearch()" ng-show="!openlab.searchOverWholeNetwork"><i class="fa fa-refresh"></i> {{ 'app.public.projects_list.reset_all_filters' | translate }}</a>
|
||||
<form role="form" ng-submit="setUrlQueryParams(search) && triggerSearch()">
|
||||
<div class="keywords">
|
||||
<input type="search" class="form-control" placeholder="{{ 'app.public.projects_list.keywords' | translate }}" ng-model="search.q"/>
|
||||
<button type="submit" class="fab-button fab-button--icon-only is-secondary"><i class="fas fa-search"></i></button>
|
||||
<!--<button type="submit" class="btn btn-warning" translate>{{ 'app.public.projects_list.search' }}</button>-->
|
||||
</div>
|
||||
</form>
|
||||
|
||||
<span ng-if="openlab.projectsActive" uib-tooltip="{{ 'app.public.projects_list.tooltip_openlab_projects_switch' | translate }}" tooltip-trigger="mouseenter">
|
||||
<label for="searchOverWholeNetwork" class="control-label m-r text-sm" translate>{{ 'app.public.projects_list.search_over_the_whole_network' }}</label>
|
||||
<input bs-switch
|
||||
ng-model="openlab.searchOverWholeNetwork"
|
||||
type="checkbox"
|
||||
class="form-control"
|
||||
switch-on-text="{{ 'app.shared.buttons.yes' | translate }}"
|
||||
switch-off-text="{{ 'app.shared.buttons.no' | translate }}"
|
||||
switch-animate="true"
|
||||
ng-change="searchOverWholeNetworkChanged()"
|
||||
/>
|
||||
{{ searchOverWholeNetwork }}
|
||||
</span>
|
||||
<form class="form-inline m-t text-center" role="form" ng-submit="setUrlQueryParams(search) && triggerSearch()">
|
||||
<div class="form-group">
|
||||
<div class="input-group">
|
||||
<div class="input-group-addon"><i class="fa fa-search"></i></div>
|
||||
<input type="search" class="form-control" placeholder="{{ 'app.public.projects_list.keywords' | translate }}" ng-model="search.q"/>
|
||||
<div class="input-group-btn">
|
||||
<button type="submit" class="btn btn-warning" translate>{{ 'app.public.projects_list.search' }}</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
<div class="col-md-12" ng-if="!openlab.searchOverWholeNetwork">
|
||||
<div class="col-md-3 m-b" ng-show="isAuthenticated()">
|
||||
<select ng-model="search.from" ng-change="setUrlQueryParams(search) && triggerSearch()" class="form-control">
|
||||
<option value="" translate>{{ 'app.public.projects_list.all_projects' }}</option>
|
||||
<option value="mine" translate>{{ 'app.public.projects_list.my_projects' }}</option>
|
||||
<option value="collaboration" translate>{{ 'app.public.projects_list.projects_to_whom_i_take_part_in' }}</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="col-md-3 m-b">
|
||||
<select ng-model="search.machine_id" ng-change="setUrlQueryParams(search) && triggerSearch()" class="form-control" ng-options="m.id as m.name for m in machines">
|
||||
<option value="" translate>{{ 'app.public.projects_list.all_machines' }}</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="grp" ng-if="!openlab.searchOverWholeNetwork">
|
||||
<select ng-show="isAuthenticated()" ng-model="search.from" ng-change="setUrlQueryParams(search) && triggerSearch()" class="form-control">
|
||||
<option value="" translate>{{ 'app.public.projects_list.all_projects' }}</option>
|
||||
<option value="mine" translate>{{ 'app.public.projects_list.my_projects' }}</option>
|
||||
<option value="collaboration" translate>{{ 'app.public.projects_list.projects_to_whom_i_take_part_in' }}</option>
|
||||
</select>
|
||||
|
||||
<div class="col-md-2 m-b">
|
||||
<select ng-model="search.theme_id" ng-change="setUrlQueryParams(search) && triggerSearch()" class="form-control" ng-options="t.id as t.name for t in themes">
|
||||
<option value="" translate>{{ 'app.public.projects_list.all_themes' }}</option>
|
||||
</select>
|
||||
</div>
|
||||
<select ng-model="search.machine_id" ng-change="setUrlQueryParams(search) && triggerSearch()" class="form-control" ng-options="m.id as m.name for m in machines">
|
||||
<option value="" translate>{{ 'app.public.projects_list.all_machines' }}</option>
|
||||
</select>
|
||||
|
||||
<div class="col-md-2 m-b">
|
||||
<select ng-model="search.component_id" ng-change="setUrlQueryParams(search) && triggerSearch()" class="form-control" ng-options="t.id as t.name for t in components">
|
||||
<option value="" translate>{{ 'app.public.projects_list.all_materials' }}</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="col-md-2 m-b">
|
||||
<status-filter on-filter-change="onStatusChange" current-status-index="search.status_id"/>
|
||||
</div>
|
||||
<select ng-model="search.theme_id" ng-change="setUrlQueryParams(search) && triggerSearch()" class="form-control" ng-options="t.id as t.name for t in themes">
|
||||
<option value="" translate>{{ 'app.public.projects_list.all_themes' }}</option>
|
||||
</select>
|
||||
|
||||
<select ng-model="search.component_id" ng-change="setUrlQueryParams(search) && triggerSearch()" class="form-control" ng-options="t.id as t.name for t in components">
|
||||
<option value="" translate>{{ 'app.public.projects_list.all_materials' }}</option>
|
||||
</select>
|
||||
|
||||
<status-filter on-filter-change="onStatusChange" current-status-index="search.status_id"/>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row">
|
||||
<span class="col-md-12" ng-show="projects && (projects.length == 0)"> {{ 'app.public.projects_list.project_search_result_is_empty' | translate }} </span>
|
||||
<div class="col-xs-12 col-sm-6 col-md-3" ng-repeat="project in projects" ng-click="showProject(project)">
|
||||
|
||||
<div class="card card-project">
|
||||
|
||||
<div class="card-header">
|
||||
<div class="card-header-bg" style="background-image: url({{project.project_image}});">
|
||||
<img src="data:image/png;base64," data-src="holder.js/100%x100%/text:/font:'Font Awesome 5 Free'/icon" bs-holder ng-if="!project.project_image">
|
||||
</div>
|
||||
|
||||
<div class="projects-list">
|
||||
<span ng-show="projects && (projects.length == 0)"> {{ 'app.public.projects_list.project_search_result_is_empty' | translate }} </span>
|
||||
<div class="project-card" ng-repeat="project in projects" ng-click="showProject(project)">
|
||||
<div class="project-image" style="background-image: url({{project.project_image}});">
|
||||
<img src="data:image/png;base64," data-src="holder.js/100%x100%/text:/font:'Font Awesome 5 Free'/icon" bs-holder ng-if="!project.project_image">
|
||||
</div>
|
||||
|
||||
<div class="card-block">
|
||||
<h3 class="card-meta" ng-if="openlab.searchOverWholeNetwork"><i class="fa fa-tag"></i> {{ project.app_name }}</h3>
|
||||
<h1 class="card-title">{{project.name}}</h1>
|
||||
</div>
|
||||
|
||||
<div class="text-center">
|
||||
<div class="project-info">
|
||||
<span class="badge" ng-if="project.state == 'draft'" translate>{{ 'app.public.projects_list.rough_draft' }}</span>
|
||||
<p class="name">{{project.name}}</p>
|
||||
<span class="openlab" ng-if="openlab.searchOverWholeNetwork"><i class="fa fa-tag"></i> {{ project.app_name }}</span>
|
||||
</div>
|
||||
|
||||
<div class="card-overlay">
|
||||
<div class="btn-group">
|
||||
<div class="btn btn-default" ng-click="showProject(project)">
|
||||
<i ng-class="{'fa fa-external-link' : (openlab.searchOverWholeNetwork && project.app_id != openlabAppId) }"></i> {{ 'app.shared.buttons.consult' | translate }}
|
||||
</div>
|
||||
<div class="btn btn-default" ui-sref="app.logged.projects_edit({id:project.id})" ng-if="isAuthorized('admin') && !openlab.searchOverWholeNetwork">
|
||||
<i class="fa fa-edit"></i>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row">
|
||||
<div class="col-lg-12 text-center">
|
||||
<a class="btn btn-warning" ng-click="loadMore()" ng-if="projectsPagination.hasNextPage()" translate>{{ 'app.public.projects_list.load_next_projects' }}</a>
|
||||
</div>
|
||||
<a class="btn btn-warning" ng-click="loadMore()" ng-if="projectsPagination.hasNextPage()" translate>{{ 'app.public.projects_list.load_next_projects' }}</a>
|
||||
</div>
|
||||
</section>
|
||||
|
@ -169,13 +169,12 @@ en:
|
||||
projects_list:
|
||||
the_fablab_projects: "The projects"
|
||||
add_a_project: "Add a project"
|
||||
search_over_the_whole_network: "Search over the whole Fab-manager network"
|
||||
network_search: "Fab-manager network"
|
||||
tooltip_openlab_projects_switch: "The search over the whole network lets you search over the projects of every Fab-manager using this feature !"
|
||||
openlab_search_not_available_at_the_moment: "Search over the whole network is not available at the moment. You still can search over the projects of this platform."
|
||||
project_search_result_is_empty: "Sorry, we found no results matching your search criteria."
|
||||
reset_all_filters: "Reset all filters"
|
||||
reset_all_filters: "Clear all"
|
||||
keywords: "Keywords"
|
||||
search: "Search"
|
||||
all_projects: "All projects"
|
||||
my_projects: "My projects"
|
||||
projects_to_whom_i_take_part_in: "Projects to whom I take part in"
|
||||
|
Loading…
x
Reference in New Issue
Block a user