diff --git a/addons/website_slides/static/src/scss/website_slides.scss b/addons/website_slides/static/src/scss/website_slides.scss index 708acd252b00d33a47d460e0e193bdb2fb641c68..86f8db440a40f0832383b93048a55f8f55abb7e2 100644 --- a/addons/website_slides/static/src/scss/website_slides.scss +++ b/addons/website_slides/static/src/scss/website_slides.scss @@ -81,6 +81,25 @@ $o-wslides-fs-side-width: 300px; .o_wslides_entry_muted { opacity: 0.5; } + + // Truncate text descriptions to a specific number of lines. + // If '-webkit-line-clamp' is not supported, a less effective + // 'line-height' fallback will be used instead. + $truncate-limits: 2, 3, 5, 10; + + @each $limit in $truncate-limits { + .o_wslides_desc_truncate_#{$limit} { + $line-height: 1.3; + max-height: $limit * $line-height * 1em; + overflow: hidden; + text-overflow: ellipsis; + white-space: normal; + line-height: $line-height; + display: -webkit-box; + -webkit-box-orient: vertical; + -webkit-line-clamp: $limit; + } + } } @@ -99,6 +118,37 @@ $o-wslides-fs-side-width: 300px; // New course page // ************************************************** +@mixin o-wslides-tabs($tab-active-color: $o-wslides-color-bg) { + margin-top: $o-wslides-tabs-height * -1; + border-bottom: 0; + + .nav-link { + border-radius: 0; + border-width: 0 1px; + @include o-hover-text-color(rgba(white, 0.8), white); + + &, &:hover { + border-color: #875A7B; + background: transparent; + } + + &.active { + color: $headings-color; + background: $tab-active-color; + border-color: $tab-active-color; + } + } +} + +@mixin o-wslides-header-bar() { + &:before { + content: ""; + @include o-position-absolute(auto, 0, 0, 0); + height: $o-wslides-tabs-height; + background: rgba(black, 0.2); + } +} + .o_wslides_course_nav { @include o-position-absolute(0,0,auto,0); border-width: 1px 0; @@ -122,42 +172,27 @@ $o-wslides-fs-side-width: 300px; } } -.o_wslides_course_header:before { + +.o_wslides_course_header { @include media-breakpoint-up(md) { - content: ""; - @include o-position-absolute(auto, 0, 0, 0); - height: $o-wslides-tabs-height; - background: rgba(black, 0.2); + @include o-wslides-header-bar(); } } +.o_wslides_course_doc_header { + @include o-wslides-header-bar(); +} + .o_wslides_course_main { .o_wslides_nav_tabs { @include media-breakpoint-up(md) { - margin-top: $o-wslides-tabs-height * -1; - border-bottom: 0; - - .nav-link { - border-radius: 0; - border-width: 0 1px; - @include o-hover-text-color(rgba(white, 0.8), white); - - &, &:hover { - border-color: #875A7B; - background: transparent; - } - - &.active { - color: $headings-color; - background: $o-wslides-color-bg; - border-color: $o-wslides-color-bg; - } - } + @include o-wslides-tabs(); } @include media-breakpoint-only(xs) { overflow-x: auto; overflow-y: hidden; + line-height: 1.51; li { white-space: nowrap; @@ -165,6 +200,10 @@ $o-wslides-fs-side-width: 300px; } } + .o_wslides_doc_nav_tabs { + @include o-wslides-tabs($gray-100); + } + .o_wslides_tabs_content { @include media-breakpoint-down(sm) { background-color: $nav-tabs-link-active-bg; @@ -236,42 +275,32 @@ $o-wslides-fs-side-width: 300px; // New lesson page // ************************************************** -.o_wslides_lesson_header { - margin: auto; - - .o_wslides_lesson_header_container { - a:hover { - text-decoration: none; - } - - .fa-trophy { - font-size: 2em; - } - } -} - .o_wslides_lesson_main { .o_wslides_lesson_aside { - .o_wslides_lesson_aside_list, - .o_wslides_lesson_aside_doc { - border: 0; - border-bottom: 3px solid $border-color; - position: relative; - top: -50px; - - .nav-tabs .nav-link { - border-top: 0; - border-top-left-radius: 0; - border-top-right-radius: 0; + .o_wslides_lesson_aside_collapse.collapsed { + transform: rotate(90deg); + } + + .o_wslides_lesson_aside_list { + @include media-breakpoint-up (lg) { + top: -58px; } } .o_wslides_lesson_aside_list { .o_wslides_lesson_aside_list_link { - text-decoration: none; + @include o-hover-text-color($gray-600, $headings-color ); + + .o_wslides_lesson_link_name { + line-height: 1.2; + } &.active { - background-color: $gray-200; + box-shadow:inset 2px 0 theme-color('primary'); + } + + &:hover .o_wslides_lesson_link_name { + color: $headings-color; } } } diff --git a/addons/website_slides/views/website_slides_templates_course.xml b/addons/website_slides/views/website_slides_templates_course.xml index c47969b0c7e6b12c55c2bc6cc4ab011435062c9c..1b835af6335c1f2f2e69c480fe2928a076b9deab 100644 --- a/addons/website_slides/views/website_slides_templates_course.xml +++ b/addons/website_slides/views/website_slides_templates_course.xml @@ -31,37 +31,15 @@ </nav> <div class="col d-none d-md-flex flex-row align-items-center justify-content-end"> - <!-- karma / profile --> - <a t-if="not is_public_user" t-att-href="'/profile/user/%s?channel_id=%s' % (user.id, channel.id)" class="btn btn-link text-white text-nowrap"> - <i class="fa fa-diamond" /> <t t-esc="user_id.karma"/> - </a> - <!-- sort / filter --> - <div class="dropdown ml-1"> - <button class="btn btn-link text-white dropdown-toggle" type="button" id="slidesChannelDropdownSort" - data-toggle="dropdown" aria-haspopup="true" aria-expanded="false"> - <t t-if="sorting == 'most_voted'">Most Voted</t> - <t t-elif="sorting == 'most_viewed'">Most Viewed</t> - <t t-else="">Newest</t> - </button> - <div class="dropdown-menu" aria-labelledby="slidesChannelDropdownSort" role="menu"> - <h6 class="dropdown-header">Sort by</h6> - <a role="menuitem" t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', 'slide_type', sorting='latest'))" - t-att-class="'dropdown-item %s' % ('active' if sorting and sorting == 'latest' else '')">Newest</a> - <a role="menuitem" t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', 'slide_type', sorting='most_voted'))" - t-att-class="'dropdown-item %s' % ('active' if sorting and sorting == 'most_voted' else '')">Most Voted</a> - <a role="menuitem" t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', 'slide_type', sorting='most_viewed'))" - t-att-class="'dropdown-item %s' % ('active' if sorting and sorting == 'most_viewed' else '')">Most Viewed</a> - </div> - </div> <!-- search --> - <form t-attf-action="/slides/#{slug(channel)}" role="search" method="get"> + <form t-attf-action="/slides/all" role="search" method="get"> <div class="input-group o_wslides_course_nav_search ml-1 position-relative"> <span class="input-group-prepend"> <button class="btn btn-link text-white rounded-0 pr-1" type="submit" aria-label="Search" title="Search"> <i class="fa fa-search"></i> </button> </span> - <input type="text" class="form-control border-0 rounded-0 bg-transparent text-white" name="search" t-attf-placeholder="Search in #{channel.name}" t-att-value="search"/> + <input type="text" class="form-control border-0 rounded-0 bg-transparent text-white" name="search" placeholder="Search courses"/> </div> </form> </div> @@ -93,11 +71,11 @@ </div> <div class="btn-group ml-1 position-static"> - <a class="btn bg-black-25 text-white dropdown-toggle" href="#" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false"><i class="fa fa-search"></i>Search and sort</a> + <a class="btn bg-black-25 text-white dropdown-toggle" href="#" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false"><i class="fa fa-search"></i></a> <div class="dropdown-menu dropdown-menu-right w-100" style="right: 10px;"> - <form class="px-4 py-3" t-attf-action="/slides/#{slug(channel)}" role="search" method="get"> + <form class="px-3" t-attf-action="/slides/#{slug(channel)}" role="search" method="get"> <div class="input-group"> - <input type="text" class="form-control" name="search" t-attf-placeholder="Search in #{channel.name}" t-att-value="search"/> + <input type="text" class="form-control" name="search" placeholder="Search courses"/> <span class="input-group-append"> <button class="btn btn-primary" type="submit" aria-label="Search" title="Search"> <i class="fa fa-search"/> @@ -105,14 +83,6 @@ </span> </div> </form> - <div class="dropdown-divider"/> - <h6 class="dropdown-header">Sort by:</h6> - <a role="menuitem" t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', 'slide_type', sorting='latest'))" - t-att-class="'dropdown-item %s' % ('active' if sorting and sorting == 'latest' else '')">Newest</a> - <a role="menuitem" t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', 'slide_type', sorting='most_voted'))" - t-att-class="'dropdown-item %s' % ('active' if sorting and sorting == 'most_voted' else '')">Most Voted</a> - <a role="menuitem" t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', 'slide_type', sorting='most_viewed'))" - t-att-class="'dropdown-item %s' % ('active' if sorting and sorting == 'most_viewed' else '')">Most Viewed</a> </div> </div> </div> @@ -133,26 +103,35 @@ <div class="wrap o_wslides_wrap"> <t t-set="main_object" t-value="channel"/> - <div class="o_wslides_course_header o_wslides_gradient position-relative text-white pb-3 pb-md-0 pt-2 pt-md-5"> + <div t-attf-class="o_wslides_course_header o_wslides_gradient position-relative text-white pb-md-0 pt-2 pt-md-5 #{'pb-3' if channel.channel_type == 'training' else 'o_wslides_course_doc_header pb-5'}"> <t t-call="website_slides.course_nav"/> <div class="container mt-5 mt-md-3 mt-xl-4"> <div class="row align-items-end align-items-md-stretch"> <!-- ==== Header Left ==== --> <div class="col-12 col-md-4 col-lg-3"> - <div class="d-flex align-items-start justify-content-around"> - <div class="o_wslides_course_pict d-inline-block mb-3 mb-md-0" t-attf-style="background-image:url(/web/image/slide.channel/#{channel.id}/image)"/> + <div class="d-flex align-items-start justify-content-around h-100"> + <div class="o_wslides_course_pict d-inline-block mb-2 mt-3 my-md-0" t-attf-style="background-image:url(/web/image/slide.channel/#{channel.id}/image)"/> </div> </div> <!-- ==== Header Right ==== --> <div class="col-12 col-md-8 col-lg-9 d-flex flex-column"> - <div class="d-flex flex-column align-items-start"> + <div class="d-flex flex-column"> <h1 t-field="channel.name"/> - <p t-field="channel.description"/> + <p class="mb-0 mb-xl-3" t-field="channel.description"/> + + <div t-if="channel.channel_type == 'documentation'" class="my-1"> + <button role="button" class="btn text-white pl-0" title="Share Channel" + aria-label="Share Channel" + data-toggle="modal" data-target="#slideChannelShareModal"> + <i class="fa fa-share-square"></i> Share + </button> + </div> </div> - <div class="d-flex flex-column justify-content-center flex-grow-1 mb-0 mb-md-5" t-if="channel.allow_comment"> + <div class="d-flex flex-column justify-content-center h5 flex-grow-1 mb-md-5" t-if="channel.allow_comment"> <t t-call="website_rating.rating_stars_static_popup_composer"> + <t t-set="btn_classes" t-value="'btn-warning'"/> <t t-set="rating_avg" t-value="rating_avg"/> <t t-set="rating_total" t-value="rating_count"/> <t t-set="object" t-value="channel"/> @@ -170,33 +149,71 @@ </div> </div> - <div class="o_wslides_course_main container"> - <div class="row"> + <div class="o_wslides_course_main"> + <!-- ========== TRAINING COURSE ========== --> + <div t-if="channel.channel_type == 'training'" class="container"> + <div class="row"> + <!-- Training Sidebar --> + <div class="col-12 col-md-4 col-lg-3 mt-3 mt-md-0"> + <t t-call="website_slides.course_sidebar"/> + </div> - <!-- ========== SIDEBAR ========== --> - <div class="col-12 col-md-4 col-lg-3 mt-3 mt-md-0"> - <t t-call="website_slides.course_sidebar"/> - </div> + <!-- Training Content --> + <div class="col-12 col-md-8 col-lg-9"> + <ul class="nav nav-tabs o_wslides_nav_tabs flex-nowrap" role="tablist" id="profile_extra_info_tablist"> + <li class="nav-item o_wslides_course_header_nav_home"> + <a t-att-class="'nav-link %s' % ('' if search_slide_type else 'active')" id="home-tab" data-toggle="pill" href="#home" role="tab" aria-controls="home" aria-selected="true"> + <i class="fa fa-home"/> Course + </a> + </li> + <li class="nav-item"> + <a class="nav-link" id="review-tab" data-toggle="pill" href="#review" role="tab" aria-controls="review" aria-selected="false">Review</a> + </li> + </ul> - <!-- ========== COURSE CONTENT ========== --> - <div class="col-12 col-md-8 col-lg-9"> - <ul class="nav nav-tabs o_wslides_nav_tabs flex-nowrap" role="tablist" id="profile_extra_info_tablist"> - <li class="nav-item o_wslides_course_header_nav_home"> - <a t-att-class="'nav-link %s' % ('' if search_slide_type else 'active')" id="home-tab" data-toggle="pill" href="#home" role="tab" aria-controls="home" aria-selected="true"> - <i class="fa fa-home"/> Course - </a> - </li> - <li class="nav-item"> - <a class="nav-link" id="review-tab" data-toggle="pill" href="#review" role="tab" aria-controls="review" aria-selected="false">Review</a> - </li> - </ul> + <div class="tab-content py-4 o_wslides_tabs_content mb-4" id="courseMainTabContent"> + <div class="tab-pane fade show active" id="home" role="tabpanel" aria-labelledby="home-tab"> + <t t-if="channel.channel_type == 'training'" t-call="website_slides.course_slides_list"/> + </div> + <div class="tab-pane fade" id="review" role="tabpanel" aria-labelledby="review-tab"> + <t t-call="portal.message_thread"> + <t t-set="object" t-value="channel"/> + <t t-set="hash" t-value="message_post_hash"/> + <t t-set="pid" t-value="message_post_pid"/> + <t t-set="display_rating" t-value="True"/> + <t t-set="disable_composer" t-value="True"/> + </t> + </div> + </div> + </div> + </div> + </div> - <div class="tab-content py-4 o_wslides_tabs_content mb-4" id="courseMainTabContent"> - <div class="tab-pane fade show active" id="home" role="tabpanel" aria-labelledby="home-tab"> - <t t-if="channel.channel_type == 'training'" t-call="website_slides.course_slides_list"/> - <t t-if="channel.channel_type == 'documentation'" t-call="website_slides.course_slides_cards"/> + <!-- ========== DOCUMENTATION COURSE ========== --> + <t t-if="channel.channel_type == 'documentation'"> + <div class="container"> + <div class="row"> + <div class="col-12 col-md-8 offset-md-4 col-lg-9 offset-lg-3"> + <ul class="nav nav-tabs o_wslides_nav_tabs o_wslides_doc_nav_tabs flex-nowrap" role="tablist" id="profile_extra_info_tablist"> + <li class="nav-item o_wslides_course_header_nav_home"> + <a class="nav-link active" id="home-tab" data-toggle="pill" href="#home" role="tab" aria-controls="home" aria-selected="true"> + <i class="fa fa-home"/> Course + </a> + </li> + <li class="nav-item"> + <a class="nav-link" id="review-tab" data-toggle="pill" href="#review" role="tab" aria-controls="review" aria-selected="false">Review</a> + </li> + </ul> </div> - <div class="tab-pane fade" id="review" role="tabpanel" aria-labelledby="review-tab"> + </div> + </div> + + <div class="tab-content pb-5" id="courseMainTabContent"> + <div class="tab-pane fade show active" id="home" role="tabpanel" aria-labelledby="home-tab"> + <t t-if="channel.channel_type == 'documentation'" t-call="website_slides.course_slides_cards"/> + </div> + <div class="tab-pane fade" id="review" role="tabpanel" aria-labelledby="review-tab"> + <div class="container pt-4"> <t t-call="portal.message_thread"> <t t-set="object" t-value="channel"/> <t t-set="hash" t-value="message_post_hash"/> @@ -207,14 +224,14 @@ </div> </div> </div> - </div> + </t> </div> </div> </t> </template> <template id="course_sidebar" name="Course Sidebar (infos, CTA)"> - <!-- Channel presentation, aka general information + CTAs --> + <!-- Training-only: Channel sidebar (aka general information + CTAs) --> <div class="bg-white px-3 py-2 py-md-3 mb-3 mb-md-5"> <div class="o_wslides_sidebar_top d-flex justify-content-between"> @@ -256,27 +273,6 @@ <th>Members</th> <td><t t-esc="channel.members_count"/></td> </tr> - <t t-if="channel.channel_type == 'documentation'"> - <t t-set="slide_type_keys" t-value="slide_types.keys()"/> - <t t-foreach="slide_type_keys" t-as="slide_type_key"> - <tr t-if="search_category"> - <th> - <a t-att-href="'/slides/%s/category/%s?%s' % (slug(channel), slug(search_category), keep_query('debug', slide_type=slide_type_key))" - t-att-class="'%s' % ('active' if search_slide_type == slide_type_key else '')"><t t-esc="slide_types[slide_type_key]"/> - </a> - </th> - <td><span class="badge badge-pill badge-info" t-esc="search_category['nbr_%s' % slide_type_key]"/></td> - </tr> - <tr t-else=""> - <th> - <a t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', slide_type=slide_type_key))" - t-att-class="'%s' % ('active' if search_slide_type == slide_type_key else '')"><t t-esc="slide_types[slide_type_key]"/> - </a> - </th> - <td><span class="badge badge-pill badge-info" t-esc="channel['nbr_%s' % slide_type_key]"/></td> - </tr> - </t> - </t> </table> <div class="mt-3"> @@ -422,58 +418,175 @@ </li> </template> +<!-- ======= Documentation Course content: cards / categories======= --> <template id="course_slides_cards" name="Documentation Course content: cards / categories"> - <div t-if="not search" class="row mb-5"> - <div class="col-lg-8"> - <div class="mt-3 w-100"> - <h5 class="m-0"> Featured lesson</h5> - <hr class="mt-2"/> + <nav class="navbar navbar-expand-lg navbar-light mb-4 border-bottom"> + <div class="container"> + <a class="navbar-brand d-lg-none" href="#">Filter & order</a> + + <div class="form-inline ml-auto d-lg-none" t-if="search_slide_type or search"> + <a t-att-href="'/slides/%s' % (slug(channel))" class="btn btn-info mr-3"> + <i class="fa fa-eraser mr-1"/>Clear filters + </a> </div> - <div class="row" t-if="slide_promoted"> - <div class="col-4"> - <img class="img img-fluid" style="" - t-att-src="'/slides/slide/%s/get_image?field=image_large' % slide_promoted.id" - t-att-alt="slide_promoted.name"/> - </div> - <div class="col-8"> - <h3 class="w-100" t-att-title="slide_promoted.name"> - <a t-if="slide_promoted.is_preview or channel.is_member or channel.can_publish" - t-attf-href="/slides/slide/#{slug(slide_promoted)}" class="font-weight-bold text-muted" t-field="slide_promoted.name"/> - <span t-else="" class="font-weight-bold text-muted" t-field="slide_promoted.name"/> - </h3> - <div t-field="slide_promoted.description"/> + + <button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation"> + <span class="navbar-toggler-icon"></span> + </button> + + <div class="collapse navbar-collapse" id="navbarSupportedContent"> + <ul class="navbar-nav mr-lg-auto align-items-lg-center"> + + <t t-set="slide_type_keys" t-value="slide_types.keys()"/> + <t t-foreach="slide_type_keys" t-as="slide_type_key"> + <t t-if="search_category"> + <li t-if="search_category['nbr_%s' % slide_type_key] > 0" class="nav-item"> + <a t-att-href="'/slides/%s/category/%s?%s' % (slug(channel), slug(search_category), keep_query('debug', slide_type=slide_type_key))" + t-att-class="'nav-link d-flex align-items-center justify-content-between pl-0 mr-1 %s' % ('active' if search_slide_type == slide_type_key else '')"> + <t t-esc="slide_types[slide_type_key]"/> + <span t-attf-class="badge badge-pill ml-1 #{'badge-info' if search_slide_type == slide_type_key else 'bg-400'}" t-esc="search_category['nbr_%s' % slide_type_key]"/> + </a> + </li> + </t> + <t t-else=""> + <li t-if="channel['nbr_%s' % slide_type_key] > 0" class="nav-item"> + <a t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', slide_type=slide_type_key))" + t-att-class="'nav-link d-flex align-items-center justify-content-between pl-0 mr-1 %s' % ('active' if search_slide_type == slide_type_key else '')"> + <t t-esc="slide_types[slide_type_key]"/> + <span t-attf-class="badge badge-pill ml-1 #{'badge-info' if search_slide_type == slide_type_key else 'bg-400'}" t-esc="channel['nbr_%s' % slide_type_key]"/> + </a> + </li> + </t> + </t> + </ul> + + <ul class="navbar-nav mr-auto"> + <li class="nav-item dropdown ml-lg-auto"> + <a class="nav-link dropdown-toggle dropdown-toggle align-items-center d-flex" type="button" id="slidesChannelDropdownSort" + data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" href="#"> + <b>Order by</b> + <span class="d-none d-xl-inline">: + <t t-if="sorting == 'most_voted'">Most Voted</t> + <t t-elif="sorting == 'most_viewed'">Most Viewed</t> + <t t-else="">Newest</t> + </span> + </a> + <div class="dropdown-menu" aria-labelledby="slidesChannelDropdownSort" role="menu"> + <h6 class="dropdown-header">Sort by</h6> + <a role="menuitem" t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', 'slide_type', sorting='latest'))" + t-att-class="'dropdown-item %s' % ('active' if sorting and sorting == 'latest' else '')">Newest</a> + <a role="menuitem" t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', 'slide_type', sorting='most_voted'))" + t-att-class="'dropdown-item %s' % ('active' if sorting and sorting == 'most_voted' else '')">Most Voted</a> + <a role="menuitem" t-att-href="'/slides/%s?%s' % (slug(channel), keep_query('debug', 'slide_type', sorting='most_viewed'))" + t-att-class="'dropdown-item %s' % ('active' if sorting and sorting == 'most_viewed' else '')">Most Viewed</a> + </div> + </li> + </ul> + + <div class="form-inline mr-3"> + <a t-if="search_slide_type or search" t-att-href="'/slides/%s' % (slug(channel))" class="btn btn-sm btn-info ml-1"> + <i class="fa fa-eraser mr-1"/>Clear filters + </a> </div> + + <form t-attf-action="/slides/#{slug(channel)}" role="search" method="get" class="form-inline my-2 my-lg-0"> + <div class="input-group position-relative"> + <input type="text" class="form-control border" name="search" placeholder="Search in content" t-att-value="search"/> + <div class="input-group-append"> + <button class="btn border" type="submit" aria-label="Search" title="Search"> + <i class="fa fa-search"/> + </button> + </div> + </div> + </form> </div> </div> + </nav> + + <div t-if="channel.can_upload" class="text-right container pb-2"> + <a class="btn btn-primary py-1 o_wslides_js_slide_upload" + title="Upload Presentation" role="button" + aria-label="Upload Presentation" href="#" + t-att-data-channel-id="channel.id" + t-att-data-can-upload="channel.can_upload" + t-att-data-can-publish="channel.can_publish"> + <i class="fa fa-cloud-upload mr-1"/>Upload new content + </a> </div> - <div t-if="search and not category_data" class="row mt16 justify-content-end"> - <div class="col-12"> - <p class="text-center">No content was found using your search <span class="font-weight-bold" t-esc="search"/>.</p> + <!-- Featured lesson --> + <div t-if="not search and not search_slide_type and slide_promoted" class="container mb-3"> + <div class="card"> + <div class="card-body d-flex flex-column flex-lg-row"> + <t t-set="image_url" t-value="'/web/image/slide.slide/%s/image' % slide_promoted.id"/> + + <t t-if="slide_promoted.is_preview or channel.is_member or is_slides_publisher"> + <a t-attf-href="/slides/slide/#{slug(slide_promoted)}" class="w-100 w-lg-50 mr-0 mr-lg-4 mb-3 mb-lg-0 flex-shrink-0 rounded border"> + <div t-attf-style="background-image:url(#{image_url}); background-size: cover; background-position:center; padding-bottom: 35%;" class="h-lg-100"/> + </a> + </t> + <t t-else=""> + <div class="w-100 w-lg-50 mr-0 mr-lg-4 mb-3 mb-lg-0 flex-shrink-0 rounded border"> + <div t-attf-style="background-image:url(#{image_url}); background-size: cover; background-position:center; padding-bottom: 35%;" class="h-lg-100"/> + </div> + </t> + + <div> + <a t-if="slide_promoted.is_preview or channel.is_member or is_slides_publisher" + t-attf-href="/slides/slide/#{slug(slide_promoted)}" + class="h4 d-block" t-att-title="slide_promoted.name" t-field="slide_promoted.name"/> + <h4 t-else="" class="text-muted" t-field="slide_promoted.name"/> + + <div t-if="slide_promoted.tag_ids" class="border-top mt-2 pt-1"> + <t t-foreach="slide_promoted.tag_ids" t-as="tag"> + <a t-att-href="'/slides/%s/tag/%s' % (slug(slide_promoted.channel_id), slug(tag))" class="badge badge-light" t-esc="tag.name"/> + </t> + </div> + <div class="o_wslides_desc_truncate_10 mt-3" t-field="slide_promoted.description"/> + </div> + </div> </div> </div> - <t t-foreach="category_data" t-as="category"> - <div class="mb-5" t-if="(category['slides'] or channel.can_publish) and (search_category and search_category.id == category['id'] or not search_category)"> - <div class="row align-items-center"> - <div class="col"> - <t t-if="category['id']"> - <a t-att-href="'/slides/%s/category/%s' % (slug(channel), category['slug_name'])" class="float-right">View all</a> - </t> - <t t-else=""> - <a t-att-href="'/slides/%s?uncategorized=1' % (slug(channel))" class="float-right">View all</a> - </t> + + <div class="container py-2"> + <t t-if="search"> + <t t-set="search_results_number" t-value="0"/> + <t t-foreach="category_data" t-as="category"> + <t t-set="search_results_number" t-value="search_results_number + category['total_slides']"/> + </t> + <div t-if="search_results_number == 0" class="alert alert-info mt-4 mb-5 text-center"> + No content was found using your search <span class="font-weight-bold" t-esc="search"/>. + </div> + </t> + + <t t-foreach="category_data" t-as="category"> + <div class="mb-2" t-if="(category['slides'] or channel.can_publish) and (search_category and search_category.id == category['id'] or not search_category)"> + <div class="d-flex align-items-center justify-content-between border-bottom pb-2 mb-3" t-if="category['name'] != 'Uncategorized'"> <h5 class="m-0"><t t-esc="category['name']"/></h5> - <hr class="mt-2"/> + <a t-if="category['id']" t-att-href="'/slides/%s/category/%s' % (slug(channel), category['slug_name'])">View all</a> + <a t-else="" t-att-href="'/slides/%s?uncategorized=1' % (slug(channel))">View all</a> + </div> + <div class="row mx-n2"> + <t t-foreach="category['slides']" t-as="slide"> + <t t-if="(slide.id != slide_promoted.id) and (slide_promoted and not search) "> + <div class="col-12 col-sm-6 col-lg-3 px-2 d-flex flex-grow-1" t-call="website_slides.lesson_card"/> + </t> + <t t-elif="search_slide_type or search"> + <div class="col-12 col-sm-6 col-lg-3 px-2 d-flex flex-grow-1" t-call="website_slides.lesson_card"/> + </t> + </t> </div> </div> - <div class="row mx-n2 mt8"> - <t t-foreach="category['slides']" t-as="slide"> - <div class="col-md-3 col-sm-6 px-2 col-xs-12 d-flex flex-grow-1" t-call="website_slides.lesson_card"/> - </t> - </div> + </t> + + <div class="row"> + <div class="col" t-field="channel.description_html"/> </div> - </t> - <div class="row"> - <div class="col" t-field="channel.description_html"/> + + <t t-if="search_category"> + <div class="form-inline justify-content-center"> + <t t-call="website_profile.pager_nobox"></t> + </div> + </t> </div> <t t-if="search_category"> <div class="form-inline justify-content-center pb-5"> @@ -484,18 +597,26 @@ <template id='lesson_card' name="Lesson Card"> <div class="card w-100 o_wslides_lesson_card mb-4"> - <t t-set="lesson_image" t-value="'/slides/slide/%s/get_image?field=image_large' % slide.id"/> <t t-set="can_access" t-value="slide.is_preview or channel.is_member or channel.can_publish"/> - <a t-if="can_access" t-attf-href="/slides/slide/#{slug(slide)}" t-title="slide.name"> - <div class="card-img-top" t-attf-style="padding-top: 50%; background-image: url(#{lesson_image}); background-size: cover; background-position:center"/> - </a> + + <t t-if="slide.image"> + <t t-set="lesson_image" t-value="'/web/image/slide.slide/%s/image' % slide.id"/> + <a t-if="can_access" t-attf-href="/slides/slide/#{slug(slide)}" t-title="slide.name"> + <div class="card-img-top border-bottom" t-attf-style="padding-top: 50%; background-image: url(#{lesson_image}); background-size: cover; background-position:center"/> + </a> + <div t-else="" class="card-img-top border-bottom" t-attf-style="padding-top: 50%; background-image: url(#{lesson_image}); background-size: cover; background-position:center"/> + </t> <t t-else=""> - <div class="card-img-top" t-attf-style="padding-top: 50%; background-image: url(#{lesson_image}); background-size: cover; background-position:center"/> + <a t-if="can_access" t-attf-href="/slides/slide/#{slug(slide)}" t-title="slide.name"> + <div class="card-img-top border-bottom o_wslides_gradient" t-attf-style="padding-top: 50%;"/> + </a> + <div t-else="" class="card-img-top border-bottom o_wslides_gradient" t-attf-style="padding-top: 50%;"/> </t> + <div class="card-body"> <a t-if="can_access" class="card-title h5" t-attf-href="/slides/slide/#{slug(slide)}" t-esc="slide.name"/> <span t-else="" class="card-title h5 text-muted" t-esc="slide.name"/> - <div class="card-subtitle mb-2 text-muted"> + <div class="card-subtitle mb-2 text-muted" t-if="slide.is_preview or (not slide.is_published and user.has_group('website.group_website_publisher'))"> <t t-if="slide.is_preview"> <span class="badge badge-info">Free preview</span> </t> @@ -503,8 +624,8 @@ <span class="badge badge-danger">Unpublished</span> </t> </div> - <div class="card-text mt-1"> - <div class="font-weight-light oe_no_empty" t-field="slide.description"/> + <div class="card-text pt-2"> + <div class="o_wslides_desc_truncate_3 font-weight-light oe_no_empty" t-field="slide.description"/> <div t-if="slide.tag_ids" class="border-top mt-2 pt-1"> <t t-foreach="slide.tag_ids" t-as="tag"> <a t-att-href="'/slides/%s/tag/%s' % (slug(slide.channel_id), slug(tag))" class="badge badge-light" t-esc="tag.name"/> diff --git a/addons/website_slides/views/website_slides_templates_lesson.xml b/addons/website_slides/views/website_slides_templates_lesson.xml index 88e32fb27ae09dba188710b0ddded2696b847374..4fc2644b820b35cd31eb7f9e5150e59c772f6632 100644 --- a/addons/website_slides/views/website_slides_templates_lesson.xml +++ b/addons/website_slides/views/website_slides_templates_lesson.xml @@ -6,27 +6,31 @@ <t t-call="website.layout"> <t t-set="main_object" t-value="slide"/> <div class="wrap o_wslides_wrap"> - <t t-call="website_slides.course_nav"> - <t t-set="channel" t-value="slide.channel_id"/> - </t> - <div class="o_wslides_lesson_header o_wslides_gradient"> - <div class="container o_wslides_lesson_header_container pt-3 pb-3"> - <div class="row align-items-end d-flex"> - <div class="col-md-9 offset-md-3 col-xs-12"> - <h3 class="font-weight-bold w-100"> - <a t-att-href="'/slides/%s' % (slug(slide.channel_id))" - class="text-white" - t-field="slide.channel_id.name"/> - </h3> - <div t-if="not is_public_user" class="d-flex align-items-center"> - <div class="progress w-50" style="height: 8px;"> - <div class="progress-bar rounded" role="progressbar" + <div class="o_wslides_lesson_header o_wslides_gradient position-relative text-white pb-0 pt-2 pt-md-5"> + <t t-call="website_slides.course_nav"> + <t t-set="channel" t-value="slide.channel_id"/> + </t> + <div class="container o_wslides_lesson_header_container mt-5 mt-md-3 mt-xl-4"> + <div class="row align-items-end align-items-md-stretch"> + <div t-attf-class="col-12 col-lg-9 d-flex flex-column #{'offset-lg-3' if slide.channel_id.channel_type == 'training' else ''}"> + <h2 class="font-weight-medium w-100"> + <a t-att-href="'/slides/%s' % (slug(slide.channel_id))" class="text-white text-decoration-none" t-field="slide.channel_id.name"/> + </h2> + + <div t-if="slide.channel_id.channel_type == 'documentation'" class="mb-3 small"> + <span class="font-weight-normal">Last update:</span> + <t t-esc="slide.date_published" t-options="{'widget': 'date'}"/> + </div> + + <div t-else="" class="d-flex align-items-center pb-3"> + <div class="progress w-50 bg-black-25" style="height: 10px;"> + <div class="progress-bar rounded-left" role="progressbar" t-att-aria-valuenow="slide.channel_id.completion" aria-valuemin="0" aria-valuemax="100" t-attf-style="width: #{slide.channel_id.completion}%;"> - <span><t t-esc="slide.channel_id.completion"/> %</span> </div> </div> - <i t-att-class="'fa fa-trophy m-0 ml-2 p-0 %s' % ('text-success' if slide.channel_id.completed else 'text-warning')"></i> + <i t-att-class="'fa fa-trophy m-0 ml-2 p-0 %s' % ('text-warning' if slide.channel_id.completed else 'text-black-50')"></i> + <small class="ml-2 text-white-50"><t t-esc="slide.channel_id.completion"/> %</small> </div> </div> </div> @@ -34,13 +38,11 @@ </div> <div class="container o_wslides_lesson_main"> <div class="row"> - <div class="col-lg-3 o_wslides_lesson_aside"> - <t t-if="slide.channel_id.channel_type == 'training'" - t-call="website_slides.slide_aside_training"/> - <t t-if="slide.channel_id.channel_type == 'documentation'" - t-call="website_slides.slide_aside_documentation"/> + <div t-attf-class="o_wslides_lesson_aside col-lg-3 #{'order-2' if slide.channel_id.channel_type == 'documentation' else ''}"> + <t t-if="slide.channel_id.channel_type == 'training'" t-call="website_slides.slide_aside_training"/> + <t t-if="slide.channel_id.channel_type == 'documentation'" t-call="website_slides.slide_aside_documentation"/> </div> - <div class="col-lg-9 o_wslides_lesson_content"> + <div t-attf-class="o_wslides_lesson_content col-lg-9 #{'order-1' if slide.channel_id.channel_type == 'documentation' else ''}"> <t t-call="website_slides.slide_content_detailed"/> </div> </div> @@ -51,14 +53,14 @@ <!-- Slide: sidebar documentation mode --> <template id="slide_aside_documentation" name="Slide: Sidebar in Documentation"> - <div class="o_wslides_lesson_aside_doc bg-white"> - <ul class="nav nav-tabs" role="tablist"> - <li class="nav-item"><a aria-controls="related" href="#related" class="nav-link active" data-toggle="tab">Related</a></li> - <li class="nav-item"><a aria-controls="most_viewed" href="#most_viewed" class="nav-link" data-toggle="tab">Most Viewed</a></li> + <div class="o_wslides_lesson_aside_doc position-relative bg-white pb-1 my-3 border-bottom"> + <ul class="nav nav-tabs nav-fill" role="tablist"> + <li class="nav-item"><a aria-controls="related" href="#related" class="nav-link rounded-0 border-top-0 border-left-0 py-2 active" data-toggle="tab">Related</a></li> + <li class="nav-item"><a aria-controls="most_viewed" href="#most_viewed" class="nav-link rounded-0 border-top-0 border-right-0 py-2" data-toggle="tab">Most Viewed</a></li> </ul> <div class="tab-content"> - <div role="tabpanel" id="related" class="tab-pane active"> - <ul class="list-unstyled card-body px-2 py-0"> + <div role="tabpanel" id="related" class="tab-pane active bg-100"> + <ul class="list-group list-group-flush"> <t t-set="related_slides_list" t-value="list(related_slides)"/> <t t-if="not related_slides_list"> No presentation available. @@ -68,8 +70,8 @@ </t> </ul> </div> - <div role="tabpanel" id="most_viewed" class="tab-pane"> - <ul class="list-unstyled card-body px-2 py-0"> + <div role="tabpanel" id="most_viewed" class="tab-pane bg-100"> + <ul class="list-group list-group-flush"> <t t-set="most_viewed_slides_list" t-value="list(most_viewed_slides)"/> <t t-if="not list(most_viewed_slides_list)"> No presentation available. @@ -85,27 +87,30 @@ <!-- Slide sub-template: display an item in a list of related slides (Related, Most Viewed, ...) --> <template id="slide_aside_card" name="Related Slide"> - <li class="media mt-2 row"> - <t t-set="slide_image" t-value="'/web/image/slide.slide/%s/image_medium' % aside_slide.id"/> - <a t-att-href="'/slides/slide/%s' % (slug(aside_slide))" t-att-title="aside_slide.name" class="col-4"> - <div class="img" t-attf-style="padding-top: 50%; background-image: url(#{slide_image}); background-size: cover; background-position:center"/> - </a> - <div class="media-body col-8 pl-0"> - <a t-att-href="'/slides/slide/%s' % (slug(aside_slide))"> - <h6 t-esc="aside_slide.name" class="mb-1"/> - </a> - <small class="text-muted"> + <a class="list-group-item list-group-item-action d-flex align-items-start px-2" t-att-href="'/slides/slide/%s' % (slug(aside_slide))"> + <t t-set="slide_image" t-value="'/web/image/slide.slide/%s/image' % aside_slide.id"/> + + <div t-if="aside_slide.image" class="flex-shrink-0 mr-1 border" t-attf-style="width: 20%; padding-top: 20%; background-image: url(#{slide_image}); background-size: cover; background-position:center"/> + <div t-else="" class="o_wslides_gradient flex-shrink-0 mr-1" t-attf-style="width: 20%; padding-top: 20%;"/> + <div class="overflow-hidden d-flex flex-column justify-content-start"> + <h6 t-esc="aside_slide.name" class="o_wslides_desc_truncate_2 mb-1" style="line-height: 1.15"/> + <small class="text-600"> <t t-esc="aside_slide.total_views"/> Views • <timeago class="timeago" t-att-datetime="aside_slide.create_date"></timeago> </small> </div> - </li> + </a> </template> <!-- Slide: sidebar training mode --> <template id="slide_aside_training" name="Slide: Sidebar in Training"> - <div class="o_wslides_lesson_aside_list bg-white"> - <h5 class="bg-100 text-600 pl-2 py-2 border-bottom">Course content</h5> - <ul class="p-0 list-unstyled"> + <div class="o_wslides_lesson_aside_list position-relative bg-white border-bottom mt-4"> + <div class="bg-100 text-600 h6 my-0 text-decoration-none border-bottom d-flex align-items-center justify-content-between"> + <span class="p-2">Course content</span> + <a href="#collapse_slide_aside" data-toggle="collapse" class="d-lg-none p-2 text-decoration-none o_wslides_lesson_aside_collapse"> + <i class="fa fa-chevron-down d-lg-none"/> + </a> + </div> + <ul id="collapse_slide_aside" class="list-unstyled my-0 pb-3 collapse d-lg-block"> <t t-set="i" t-value="0"/> <t t-if="uncategorized_slides" t-call="website_slides.slide_aside_training_category"> <t t-set="category_slide_ids" t-value="uncategorized_slides"/> @@ -120,45 +125,49 @@ </template> <template id="slide_aside_training_category" name="Category item for the slide detailed view list"> - <li class="mt-3"> + <li class="o_wslides_fs_sidebar_section mt-2"> <a t-att-href="('#collapse-%s') % (category.id if category else 0)" data-toggle="collapse" role="button" aria-expanded="true" - class="o_wslides_lesson_aside_list_link pl-2 text-600" + class="o_wslides_lesson_aside_list_link pl-2 text-600 text-uppercase text-decoration-none py-1 small d-block" t-att-aria-controls="('collapse-%s') % (category.id if category else 0)"> <t t-if="category"> - <span t-field="category.name" class="text-uppercase"/> + <b t-field="category.name"/> </t> <t t-else=""> - <span class="text-uppercase">Uncategorized</span> + <b>Uncategorized</b> </t> </a> <ul class="collapse show p-0 m-0 list-unstyled" t-att-id="('collapse-%s') % (category.id if category else 0)" > <t t-foreach="category_slide_ids" t-as="aside_slide"> - <li class="p-0"> + <li class="p-0 pb-1"> <a t-att-href="'/slides/slide/%s' % (slug(aside_slide))" - t-att-class="'o_wslides_lesson_aside_list_link d-flex align-items-center pl-2 %s' % ('bg-200 border-left border-primary' if aside_slide == slide else '')"> - <i t-att-id="'o_wslides_lesson_aside_slide_check_%s' % (aside_slide.id)" - t-att-class="'mr-2 fa %s' % ('text-success fa-check-circle' if channel_progress[aside_slide.id].get('completed') else 'text-600 fa-circle-o')"> - </i> - <t t-call="website_slides.slide_icon"> - <t t-set="icon_class" t-value="'mr-2 %s' % ('text-800' if aside_slide == slide else 'text-600')"/> - <t t-set="slide" t-value="aside_slide"/> - </t> - <span t-esc="aside_slide.name" t-att-class="'mr-2 %s' % ('text-800' if aside_slide == slide else 'text-600')"/> - <span t-if="aside_slide.question_ids" - t-att-class="'ml-auto badge badge-pill %s' % ('badge-success' if channel_progress[aside_slide.id].get('completed') else 'badge-light text-600')"> - <t t-esc="channel_progress[aside_slide.id].get('quiz_karma_won') if channel_progress[aside_slide.id].get('completed') else channel_progress[aside_slide.id].get('quiz_karma_gain')"/> xp - </span> + t-att-class="'o_wslides_lesson_aside_list_link d-flex align-items-top px-2 pt-1 text-decoration-none %s' % ('bg-100 py-1 active' if aside_slide == slide else '')"> + <div> + <i t-att-id="'o_wslides_lesson_aside_slide_check_%s' % (aside_slide.id)" + t-att-class="'mr-1 fa fa-fw %s' % ('text-success fa-check-circle' if channel_progress[aside_slide.id].get('completed') else 'text-600 fa-circle-o')"> + </i> + </div> + <div class="o_wslides_lesson_link_name"> + <span t-esc="aside_slide.name" class="mr-2"/> + </div> + <div class="ml-auto" t-if="aside_slide.question_ids"> + <span t-att-class="'badge badge-pill %s' % ('badge-success' if channel_progress[aside_slide.id].get('completed') else 'badge-light text-600')"> + <t t-esc="channel_progress[aside_slide.id].get('quiz_karma_won') if channel_progress[aside_slide.id].get('completed') else channel_progress[aside_slide.id].get('quiz_karma_gain')"/> xp + </span> + </div> </a> - <ul t-if="aside_slide.link_ids or aside_slide.question_ids" class="list-group ml-5 list-unstyled"> + <ul t-if="aside_slide.link_ids or aside_slide.question_ids" class="list-group px-2 mb-1 list-unstyled"> <t t-foreach="aside_slide.link_ids" t-as="resource"> - <a t-attf-href="#{resource.link}" target="new"> - <li><small><i class="fa fa-link mr-1"></i><span t-field="resource.name"/></small></li> - </a> + <li class="pl-4"> + <a t-attf-href="#{resource.link}" target="new" class="text-decoration-none small"> + <i class="fa fa-link mr-1"/><span t-field="resource.name"/> + </a> + </li> </t> - <a t-if="aside_slide.question_ids" t-att-href="'/slides/slide/%s#lessonQuiz' % (slug(aside_slide))" - class="o_wslides_lesson_aside_list_link text-600"> - <li><small><i class="fa fa-flag-o text-warning"></i> Quiz</small></li> - </a> + <li class="pl-4"> + <a t-if="aside_slide.question_ids" t-att-href="'/slides/slide/%s#lessonQuiz' % (slug(aside_slide))" class="o_wslides_lesson_aside_list_link text-decoration-none small text-600"> + <i class="fa fa-flag text-warning"/> Quiz + </a> + </li> </ul> </li> </t> @@ -168,13 +177,15 @@ <!-- Slide: all its content, not fullscreen mode --> <template id="slide_content_detailed" name="Slide: Detailed Content"> - <div class="row"> - <div class="col-12 d-flex mt-3"> + <div class="row align-items-center my-3"> + <div class="col-12 col-md order-2 order-md-1 d-flex"> <div class="d-flex align-items-center"> - <h5 class="m-0 ml-2"> - <t t-call="website_slides.slide_icon"/> + <h4 class="my-0"> + <t t-call="website_slides.slide_icon"> + <t t-set="icon_class">mr-1</t> + </t> <span t-field="slide.name"/> - </h5> + </h4> <span t-if="slide.question_ids" t-att-class="'ml-2 badge %s' % ('badge-success' if channel_progress[slide.id].get('completed') else 'badge-info')"> <span t-if="channel_progress[slide.id].get('completed')"> @@ -185,11 +196,13 @@ <span>XP</span> </span> </div> - <div class="ml-auto"> + </div> + <div class="col-12 col-md order-1 order-md-2 text-nowrap flex-grow-0 d-flex justify-content-end mb-3 mb-md-0"> + <div class="btn-group flex-grow-1 flex-sm-0" role="group" aria-label="Lesson Nav"> <a t-att-class="'btn btn-light border %s' % ('disabled' if not previous_slide else '')" role="button" t-att-aria-disabled="'disabled' if not previous_slide else None" t-att-href="'/slides/slide/%s' % (slug(previous_slide)) if previous_slide else '#'"> - <i class="fa fa-chevron-left mr-2"></i> Prev + <i class="fa fa-chevron-left mr-2"></i> <span class="d-none d-sm-inline-block">Prev</span> </a> <t t-set="allow_done_btn" t-value="slide.slide_type in ['infographic', 'presentation', 'document', 'webpage'] and not slide.question_ids and not channel_progress[slide.id].get('completed')"/> <a t-att-class="'btn btn-primary border text-white %s' % ('disabled' if not allow_done_btn else '')" @@ -200,20 +213,21 @@ <a t-att-class="'btn btn-light border %s' % ('disabled' if not next_slide else '')" role="button" t-att-aria-disabled="'disabled' if not next_slide else None" t-att-href="'/slides/slide/%s' % (slug(next_slide)) if next_slide else '#'"> - Next <i class="fa fa-chevron-right ml-2"></i> + <span class="d-none d-sm-inline-block">Next</span> <i class="fa fa-chevron-right ml-2"></i> </a> - <a t-att-class="'btn btn-light border ml-2 %s' % ('disabled' if slide.channel_id.channel_type != 'training' else '')" - role="button" t-att-aria-disabled="'disabled' if slide.channel_id.channel_type != 'training' else None" - t-att-href="'/slides/slide/%s?fullscreen=1' % (slug(slide)) if slide.channel_id.channel_type == 'training' else '#'"><i class="fa fa-desktop mr-2"></i> Fullscreen</a> </div> + <a t-if="slide.channel_id.channel_type == 'training'" class="btn btn-light border ml-2" role="button" t-att-href="'/slides/slide/%s?fullscreen=1' % (slug(slide))"> + <i class="fa fa-desktop mr-2"/> + <span class="d-none d-sm-inline-block">Fullscreen</span> + </a> </div> - <div t-if="slide.tag_ids" class="col"> - <t t-foreach="slide.tag_ids" t-as="tag"> - <a t-att-href="'/slides/%s/tag/%s' % (slug(slide.channel_id), slug(tag))" class="badge badge-light" t-esc="tag.name"/> - </t> - </div> </div> - <div class="row o_wslides_lesson_content_type"> + <div t-if="slide.tag_ids" class="pb-2"> + <t t-foreach="slide.tag_ids" t-as="tag"> + <a t-att-href="'/slides/%s/tag/%s' % (slug(slide.channel_id), slug(tag))" class="badge badge-light py-1 px-2" t-esc="tag.name"/> + </t> + </div> + <div class="o_wslides_lesson_content_type"> <img t-if="slide.slide_type == 'infographic'" t-attf-src="/web/image/slide.slide/#{slide.id}/image" class="img-fluid" style="width:100%" t-att-alt="slide.name"/> <div t-if="slide.slide_type in ('presentation', 'document')" class="embed-responsive embed-responsive-4by3 embed-responsive-item mb8" style="height: 600px;"> @@ -222,7 +236,7 @@ <div t-if="slide.slide_type == 'video' and slide.document_id" class="embed-responsive embed-responsive-16by9 embed-responsive-item mb8"> <t t-raw="slide.embed_code"/> </div> - <div t-if="slide.slide_type == 'webpage'" class="bg-white"> + <div t-if="slide.slide_type == 'webpage'" class="bg-white p-3"> <div t-field="slide.html_content"/> </div> </div> @@ -230,33 +244,33 @@ <t t-call="website_slides.lesson_content_quiz"/> </div> <div class="row mt-3 mb-3"> - <div class="col d-flex align-items-start"> + <div class="col-12 col-md d-flex align-items-start mb-4 mb-md-0" t-if="len(slide.link_ids)"> <span t-if="slide.link_ids" class="text-muted font-weight-bold mr-3">External sources</span> <div class="text-muted mr-auto border-left pl-3"> <t t-foreach="slide.link_ids" t-as="link"> <a t-att-href="link.link" t-esc="link.name"/><br /> </t> </div> - - <t t-if="slide.channel_id.allow_comment and slide.channel_id.channel_type == 'documentation'"> - <span class="text-muted font-weight-bold mr-3">Rating</span> - <div class="text-muted border-left pl-3"> - <div class="o_wslides_js_slide_like mr-2"> - <span t-att-class="('o_wslides_js_slide_like_up %s') % ('disabled' if not slide.channel_id.can_vote else '')" tabindex="0" data-toggle="popover" t-att-data-slide-id="slide.id"> - <i class="fa fa-thumbs-up fa-1x" role="img" aria-label="Likes" title="Likes"></i> - <span t-esc="slide.likes"/> - </span> - <span t-att-class="('o_wslides_js_slide_like_down ml-3 %s') % ('disabled' if not slide.channel_id.can_vote else '')" tabindex="0" data-toggle="popover" t-att-data-slide-id="slide.id"> - <i class="fa fa-thumbs-down fa-1x" role="img" aria-label="Dislikes" title="Dislikes"></i> - <span t-esc="slide.dislikes"/> - </span> - </div> + </div> + <div t-if="slide.channel_id.allow_comment and slide.channel_id.channel_type == 'documentation'" + class="col-12 col-md d-flex align-items-start justify-content-md-end mb-2 mb-md-0"> + <span class="text-muted font-weight-bold mr-3">Rating</span> + <div class="text-muted border-left pl-3"> + <div class="o_wslides_js_slide_like mr-2"> + <span t-att-class="('o_wslides_js_slide_like_up %s') % ('disabled' if not slide.channel_id.can_vote else '')" tabindex="0" data-toggle="popover" t-att-data-slide-id="slide.id"> + <i class="fa fa-thumbs-up fa-1x" role="img" aria-label="Likes" title="Likes"></i> + <span t-esc="slide.likes"/> + </span> + <span t-att-class="('o_wslides_js_slide_like_down ml-3 %s') % ('disabled' if not slide.channel_id.can_vote else '')" tabindex="0" data-toggle="popover" t-att-data-slide-id="slide.id"> + <i class="fa fa-thumbs-down fa-1x" role="img" aria-label="Dislikes" title="Dislikes"></i> + <span t-esc="slide.dislikes"/> + </span> </div> - </t> + </div> </div> </div> - <div class="row mb-5"> - <ul class="col-lg-12 nav nav-tabs o_wslides_lesson_nav" role="tablist"> + <div class="mb-5"> + <ul class="nav nav-tabs o_wslides_lesson_nav" role="tablist"> <li class="nav-item"> <a href="#about" aria-controls="about" class="nav-link active" role="tab" data-toggle="tab"> <i class="fa fa-home"></i> About @@ -267,7 +281,7 @@ <i class="fa fa-comments-o"></i> Comments </a> </li> - <li class="nav-item"> + <li class="nav-item" t-if="slide.index_content"> <a href="#transcript" aria-controls="transcript" class="nav-link" role="tab" data-toggle="tab"> <i class="fa fa-align-justify"></i> Transcript </a> @@ -283,7 +297,7 @@ </a> </li> </ul> - <div class="col tab-content mt-3"> + <div class="tab-content mt-3"> <div role="tabpanel" t-att-class="not comments and 'tab-pane fade in show active' or 'tab-pane fade'" id="about"> <div t-field="slide.description"/> </div> @@ -294,59 +308,75 @@ <t t-set="display_rating" t-value="False"/> </t> </div> - <div role="tabpanel" class="tab-pane fade oe_slides_transcript" id="transcript"> - <t t-if="slide.index_content"> - <t t-foreach="slide.index_content.split('\n')" t-as="line"> - <p t-esc="line"></p> - </t> + <div role="tabpanel" class="tab-pane fade oe_slides_transcript" id="transcript" t-if="slide.index_content"> + <t t-foreach="slide.index_content.split('\n')" t-as="line"> + <p t-esc="line"></p> </t> </div> <div role="tabpanel" class="tab-pane fade" id="statistic" t-att-slide-url="slide.website_url"> <div class="row"> - <div class="col-lg-4 d-flex flex-column"> - <span class="font-weight-bold mb-3 mt-3">Views</span> - <span class="d-flex pl-3"> - <span class="badge badge-pill" t-esc="slide.total_views"/> - <span class="mr-5 ml-auto">Total Views</span> - </span> - <span class="d-flex pl-3"> - <span class="badge badge-pill" t-esc="slide.slide_views"/> - <span class="mr-5 ml-auto">Members Views</span> - </span> - <span class="d-flex pl-3"> - <span class="badge badge-pill" t-esc="slide.public_views"/> - <span class="mr-5 ml-auto">Public Views</span> - </span> + <div class="col-12 col-md"> + <table class="table table-sm"> + <tbody> + <tr> + <th colspan="2" class="border-top-0">Views</th> + </tr> + <tr class="border-top-0"> + <th class="border-top-0"><span t-esc="slide.total_views"/></th> + <td class="border-top-0 w-100">Total Views</td> + </tr> + <tr> + <th><span t-esc="slide.slide_views"/></th> + <td>Members Views</td> + </tr> + <tr> + <th><span t-esc="slide.public_views"/></th> + <td>Public Views</td> + </tr> + </tbody> + </table> </div> - <div class="col-lg-4 d-flex flex-column"> - <span class="font-weight-bold mb-3 mt-3">Actions</span> - <span class="d-flex pl-3"> - <span class="badge badge-pill" t-esc="slide.likes"/> - <span class="mr-5 ml-auto">Likes</span> - </span> - <span class="d-flex pl-3"> - <span class="badge badge-pill" t-esc="slide.dislikes"/> - <span class="mr-5 ml-auto">Dislikes</span> - </span> - <span class="d-flex pl-3"> - <span class="badge badge-pill" t-esc="len(slide.website_message_ids)"/> - <span class="mr-5 ml-auto">Comments</span> - </span> + <div class="col-12 col-md"> + <table class="table table-sm"> + <tbody> + <tr> + <th colspan="2" class="border-top-0">Actions</th> + </tr> + <tr class="border-top-0"> + <th class="border-top-0"><span t-esc="slide.likes"/></th> + <td class="border-top-0 w-100">Likes</td> + </tr> + <tr> + <th><span t-esc="slide.dislikes"/></th> + <td>Dislikes</td> + </tr> + <tr> + <th><span t-esc="len(slide.website_message_ids)"/></th> + <td>Comments</td> + </tr> + </tbody> + </table> </div> - <div class="col-lg-4 d-flex flex-column"> - <span class="font-weight-bold mb-3 mt-3">Share Count</span> - <span class="d-flex pl-3"> - <span class="badge badge-pill" id="facebook-badge">0</span> - <span class="mr-5 ml-auto">Facebook</span> - </span> - <span class="d-flex pl-3"> - <span class="badge badge-pill" id="twitter-badge">0</span> - <span class="mr-5 ml-auto">Twitter</span> - </span> - <span class="d-flex pl-3"> - <span class="badge badge-pill" id="linkedin-badge">0</span> - <span class="mr-5 ml-auto">LinkedIn</span> - </span> + <div class="col-12 col-md"> + <table class="table table-sm"> + <tbody> + <tr> + <th colspan="2" class="border-top-0">Share count</th> + </tr> + <tr class="border-top-0"> + <th class="border-top-0"><span id="facebook-badge">0</span></th> + <td class="border-top-0 w-100">Facebook</td> + </tr> + <tr> + <th><span id="twitter-badge">0</span></th> + <td>Twitter</td> + </tr> + <tr> + <th><span id="linkedin-badge"/></th> + <td>LinkedIn</td> + </tr> + </tbody> + </table> </div> </div> </div> @@ -358,14 +388,18 @@ <t t-call="website_slides.slide_social_media"> <t t-set="slide" t-value="slide"/> </t> - <t t-call="website_slides.slide_social_email"> - <t t-set="slide" t-value="slide"/> - </t> - <t t-if="not slide.document_id"> - <t t-call="website_slides.slide_social_embed"> - <t t-set="slide" t-value="slide"/> - </t> - </t> + <div class="row"> + <div t-attf-class="col-12 #{'col-lg-6' if not slide.document_id else ''}"> + <t t-call="website_slides.slide_social_email"> + <t t-set="slide" t-value="slide"/> + </t> + </div> + <div class="col-12 col-lg-6" t-if="not slide.document_id"> + <t t-call="website_slides.slide_social_embed"> + <t t-set="slide" t-value="slide"/> + </t> + </div> + </div> </t> </div> </div> @@ -422,10 +456,10 @@ <!-- Slide sub-template: share: send by email --> <template id='slide_social_email' name="Share by Email"> - <h4 class="mt-3">Share with a friend</h4> - <t t-if="not is_public_user"> + <h5 class="mt-4">Share by mail</h5> + <div t-if="not is_public_user" class="form-inline"> <form class="form-group oe_slide_js_share_email" role="form"> - <div class="input-group col-lg-6"> + <div class="input-group"> <input type="email" class="form-control" placeholder="your-friend@domain.com"/> <span class="input-group-append"> <button class="btn btn-primary" type="button" @@ -436,18 +470,18 @@ </button> </span> </div> - <span class="form-text">Send presentation through email</span> + <span class="form-text text-muted d-block w-100">Send presentation through email</span> </form> - </t> - <t t-if="is_public_user"> - <p>Please <a t-attf-href="/web?redirect=#{request.httprequest.url}"> login </a> to send this <t t-esc="slide.slide_type"/> by email!</p> - </t> + </div> + <div t-if="is_public_user" class="alert alert-info d-inline-block"> + <p class="mb-0">Please <a t-attf-href="/web?redirect=#{request.httprequest.url}" class="font-weight-bold"> login </a> to share this <t t-esc="slide.slide_type"/> by email.</p> + </div> </template> <!-- Slide sub-template: share: embed in your website --> <template id="slide_social_embed" name="Share on Your Website"> - <div class="oe_slide_js_embed_code_widget"> - <h4 class="mt0">Embed in your website</h4> + <div class="oe_slide_js_embed_code_widget mt-4"> + <h5 class="mt0">Embed in your website</h5> <div class="form-group"> <textarea class="form-control slide_embed_code" readonly="readonly" onClick="this.select();"><t t-esc="slide.embed_code"/></textarea> </div> diff --git a/addons/website_slides/views/website_slides_templates_utils.xml b/addons/website_slides/views/website_slides_templates_utils.xml index 57d5c2fced5d7d6070dd969f08b44d0600970dea..d510f2ed5191d365b57dc824c939f3b95783bf7b 100644 --- a/addons/website_slides/views/website_slides_templates_utils.xml +++ b/addons/website_slides/views/website_slides_templates_utils.xml @@ -3,22 +3,28 @@ <!-- Share on social networks --> <template id='slides_share' name="Slides Media Share"> - <div> - <a t-attf-href="https://www.facebook.com/sharer/sharer.php?u=#{record.website_url}" class="o_slides_social_share" social-key="facebook" aria-label="Share on Facebook" title="Share on Facebook"><i class="fa fa-facebook-square fa-2x"/></a> - <a t-attf-href="https://twitter.com/intent/tweet?text=#{record.name}&url=#{record.website_url}" class="o_slides_social_share" social-key="twitter" aria-label="Share on Twitter" title="Share on Twitter"><i class="fa fa-twitter fa-2x"/></a> - <a t-attf-href="http://www.linkedin.com/shareArticle?mini=true&url=#{record.website_url}&title=#{record.name}&" social-key="linkedin" class="o_slides_social_share" aria-label="Share on LinkedIn" title="Share on LinkedIn"><i class="fa fa-linkedin fa-2x"/></a> + <div class="btn-group" role="group"> + <a t-attf-href="https://www.facebook.com/sharer/sharer.php?u=#{record.website_url}" class="btn border bg-white o_slides_social_share" social-key="facebook" aria-label="Share on Facebook" title="Share on Facebook"><i class="fa fa-facebook-square fa-fw"/></a> + <a t-attf-href="https://twitter.com/intent/tweet?text=#{record.name}&url=#{record.website_url}" class="btn border bg-white o_slides_social_share" social-key="twitter" aria-label="Share on Twitter" title="Share on Twitter"><i class="fa fa-twitter fa-fw"/></a> + <a t-attf-href="http://www.linkedin.com/shareArticle?mini=true&url=#{record.website_url}&title=#{record.name}&" social-key="linkedin" class="btn border bg-white o_slides_social_share" aria-label="Share on LinkedIn" title="Share on LinkedIn"><i class="fa fa-linkedin fa-fw"/></a> </div> </template> <!-- Share: social media --> <template id='slide_social_media' name="Share on Social Networks"> - <h4 class="mt0">Share on Social Networks</h4> - <t t-call="website_slides.slides_share"> - <t t-set="record" t-value="slide"/> - </t> - <h4 class="mt-3">Share Link</h4> - <input type="text" class="form-control" t-att-value="slide.website_url" readonly="readonly" onClick="this.select();"/> - <span class="form-text">Use permanent link to share in social media</span> + <div class="row"> + <div class="col-12 col-lg-6 mb-4"> + <h5 class="mt-0 mb-2">Share on Social Networks</h5> + <t t-call="website_slides.slides_share"> + <t t-set="record" t-value="slide"/> + </t> + </div> + <div class="col-12 col-lg-6"> + <h5 class="mt-0 mb-2">Share Link</h5> + <input type="text" class="form-control" t-att-value="slide.website_url" readonly="readonly" onClick="this.select();"/> + <span class="form-text text-muted">Use permanent link to share in social media</span> + </div> + </div> </template> <!-- Website edit page -->