diff --git a/openstack/code/Presentation.php b/openstack/code/Presentation.php
index 02563c8..e5ccd83 100644
--- a/openstack/code/Presentation.php
+++ b/openstack/code/Presentation.php
@@ -1,4 +1,5 @@
'HTMLText',
@@ -28,14 +30,15 @@ class Presentation extends DataObject {
'Type' => 'Text',
'Day' => 'Int',
'Speakers' => 'Text',
- 'SlidesLink' => 'Varchar(255)'
+ 'SlidesLink' => 'Varchar(255)',
+ 'event_key' => 'Varchar(255)'
);
Static $defaults = array(
'DisplayOnSite' => TRUE,
'Country' => 'United States'
);
-
+
static $has_one = array(
'PresentationCategoryPage' => 'PresentationCategoryPage',
'Summit' => 'Summit'
@@ -47,110 +50,144 @@ class Presentation extends DataObject {
static $singular_name = 'Presentation';
static $plural_name = 'Presentations';
-
- static $summary_fields = array(
- 'Name' => 'Presentation Name'
- );
-
- function getCMSFields() {
+
+ static $summary_fields = array(
+ 'Name' => 'Presentation Name'
+ );
+
+ function getCMSFields()
+ {
$fields = new FieldList (
- new TextField('Name','Name of Presentation'),
- new TextField('Speakers','Speakers'),
- new DropdownField('Day','Day', array('1' => '1', '2' => '2', '3' => '3', '4' => '4')),
- new TextField('URLSegment','URL Segment'),
- new LiteralField('Break','
(Automatically filled in on first save.)
'),
- new LiteralField('Break','
'),
- new TextField('YouTubeID','YouTube Vidoe ID'),
- new TextField('SlidesLink','Link To Slides (if available)'),
- new TextField('StartTime','Video Start Time'),
- new TextField('EndTime','Video End Time'),
- new HTMLEditorField('Description','Description')
+ new TextField('Name', 'Name of Presentation'),
+ new TextField('Speakers', 'Speakers'),
+ new DropdownField('Day', 'Day', array('1' => '1', '2' => '2', '3' => '3', '4' => '4')),
+ new TextField('URLSegment', 'URL Segment'),
+ new LiteralField('Break', '(Automatically filled in on first save.)
'),
+ new LiteralField('Break', '
'),
+ new TextField('YouTubeID', 'YouTube Vidoe ID'),
+ new TextField('SlidesLink', 'Link To Slides (if available)'),
+ new TextField('StartTime', 'Video Start Time'),
+ new TextField('EndTime', 'Video End Time'),
+ new HTMLEditorField('Description', 'Description')
);
return $fields;
}
-
- function onBeforeWrite() {
+ function FormattedStartTime()
+ {
+ $Date = new DateTime($this->StartTime);
+ return $Date->format('l h:i a');
+ }
+
+ function PresentationDay()
+ {
+ $Date = new DateTime($this->StartTime);
+ return $Date->format('M d');
+ }
+
+
+ function onBeforeWrite()
+ {
parent::onBeforeWrite();
// If there is no URLSegment set, generate one from Title
- if((!$this->URLSegment || $this->URLSegment == 'new-presentation') && $this->Title != 'New Presentation')
- {
- $this->URLSegment = SiteTree::generateURLSegment($this->Title);
- }
- else if($this->isChanged('URLSegment'))
- {
- // Make sure the URLSegment is valid for use in a URL
- $segment = preg_replace('/[^A-Za-z0-9]+/','-',$this->URLSegment);
- $segment = preg_replace('/-+/','-',$segment);
-
- // If after sanitising there is no URLSegment, give it a reasonable default
- if(!$segment) {
- $segment = "presentation-".$this->ID;
- }
- $this->URLSegment = $segment;
- }
-
- // Ensure that this object has a non-conflicting URLSegment value by appending number if needed
- $count = 2;
- while($this->LookForExistingURLSegment($this->URLSegment))
- {
- $this->URLSegment = preg_replace('/-[0-9]+$/', null, $this->URLSegment) . '-' . $count;
- $count++;
- }
+ if ((!$this->URLSegment || $this->URLSegment == 'new-presentation') && $this->Title != 'New Presentation') {
+ $this->URLSegment = SiteTree::generateURLSegment($this->Title);
+ } else if ($this->isChanged('URLSegment')) {
+ // Make sure the URLSegment is valid for use in a URL
+ $segment = preg_replace('/[^A-Za-z0-9]+/', '-', $this->URLSegment);
+ $segment = preg_replace('/-+/', '-', $segment);
+
+ // If after sanitising there is no URLSegment, give it a reasonable default
+ if (!$segment) {
+ $segment = "presentation-" . $this->ID;
+ }
+ $this->URLSegment = $segment;
+ }
+
+ // Ensure that this object has a non-conflicting URLSegment value by appending number if needed
+ $count = 2;
+ while ($this->LookForExistingURLSegment($this->URLSegment)) {
+ $this->URLSegment = preg_replace('/-[0-9]+$/', null, $this->URLSegment) . '-' . $count;
+ $count++;
+ }
+
+ // If there's no PresentationCategoryPage, add the current summit
+
+ if (!$this->PresentationCategoryPageID) {
+ $SummitPageID = 0;
+ $SummitRedirector = DataObject::get_by_id('RedirectorPage', 154);
+ If ($SummitRedirector) {
+ $SummitPageID = $SummitRedirector->LinkToID;
+ $VideoPage = DataObject::get_one('PresentationCategoryPage', '`ParentID` = ' . $SummitPageID);
+ }
+
+ if ($VideoPage) $this->PresentationCategoryPageID = $VideoPage->ID;
+ }
}
- //Test whether the URLSegment exists already on another Video
- function LookForExistingURLSegment($URLSegment)
- {
- return Company::get()->filter(array('URLSegment' => $URLSegment, 'ID:not' => $this->ID))->first();
- }
-
- // Pull video thumbnail from YouTube API
- function ThumbnailURL() {
- if ($this->YouTubeID) {
-
-
- /* $response = @file_get_contents("http://gdata.youtube.com/feeds/api/videos/".$this->YouTubeID."?v=2&alt=jsonc");
-
- if ($response) {
- $json = json_decode($response);
- if (isset($json->data->thumbnail->sqDefault)) {
- return $json->data->thumbnail->sqDefault;
- }
- } */
-
- return "http://i.ytimg.com/vi/".$this->YouTubeID."/default.jpg";
-
+//Test whether the URLSegment exists already on another Video
+ function LookForExistingURLSegment($URLSegment)
+ {
+ return (DataObject::get_one('Company', "URLSegment = '" . $URLSegment . "' AND ID != " . $this->ID));
+ }
+// Pull video thumbnail from YouTube API
+ function ThumbnailURL()
+ {
+ if ($this->YouTubeID) {
+ return "http://i.ytimg.com/vi/" . $this->YouTubeID . "/default.jpg";
}
- }
+ }
+//Generate the link for this product
+ function ShowLink()
+ {
+ $ParentPage = $this->PresentationCategoryPage();
- //Generate the link for this product
- function ShowLink()
- {
- $ParentPage = $this->PresentationCategoryPage();
-
- if ($ParentPage) {
- return $ParentPage->Link()."presentation/".$this->URLSegment;
- }
- }
-
- // See if the presentation slides can be embedded
- function EmbedSlides()
- {
- // Slides can be emdedded if they are hosted on crocodoc. Otherwise, there's only a download button displayed by the template
- if (strpos($this->SlidesLink,'crocodoc.com') !== false) {
- return true;
+ if ($ParentPage) {
+ return $ParentPage->Link() . "presentation/" . $this->URLSegment;
}
- }
+ }
- function SchedEventImport($ParentPageID) {
- $Events = SchedEvent::get();
- foreach ($Events as $Event) {
+// See if the presentation slides can be embedded
+ function EmbedSlides()
+ {
+ // Slides can be emdedded if they are hosted on crocodoc. Otherwise, there's only a download button displayed by the template
+ if (strpos($this->SlidesLink, 'crocodoc.com') !== false) {
+ return true;
+ }
+ }
+
+ function PopulateFromSchedEvent($SchedEventID)
+ {
+
+ $SchedEvent = DataObject::get_by_id('SchedEvent', $SchedEventID);
+
+ $this->Name = $SchedEvent->eventtitle;
+ $this->DisplayOnSite = TRUE;
+ $this->Description = $SchedEvent->description;
+ $this->StartTime = $SchedEvent->event_start;
+ $this->EndTime = $SchedEvent->event_end;
+ $this->Type = $SchedEvent->event_type;
+ $this->Speakers = $SchedEvent->speakers;
+ $this->event_key = $SchedEvent->event_key;
+ $this->write();
+
+ }
+
+ function AddYouTubeID($YouTubeID)
+ {
+ $this->YouTubeID = $YouTubeID;
+ $this->write();
+ }
+
+ function SchedEventImport($ParentPageID)
+ {
+ $Events = DataObject::get_one('SchedEvent', '');
+ foreach ($Events as $Event) {
$Presentation = new Presentation();
// Bring over existing data
@@ -161,82 +198,20 @@ class Presentation extends DataObject {
$Presentation->EndTime = $Event->event_end;
$Presentation->Type = $Event->event_type;
$Presentation->Speakers = $Event->speakers;
-
- // Determine day
- $day = 1;
+ // Assign parent page
+ $Presentation->PresentationCategoryPageID = $ParentPageID;
+ $Presentation->write();
- switch ($Event->event_start) {
- case '2013-11-05':
- $day = 1;
- break;
- case '2013-11-06':
- $day = 2;
- break;
- case '2013-11-07':
- $day = 3;
- break;
- case '2013-11-08':
- $day = 4;
- break;
- case '2013-11-09':
- $day = 5;
- break;
- }
+ if ($Event->UploadedMedia()) {
+ $Presentation->SlidesLink = $Event->UploadedMedia()->link();
+ } elseif ($Event->HostedMediaURL()) {
+ $Presentation->SlidesLink = $Event->HostedMediaURL();
+ }
- $Presentation->Day = $day;
+ $Presentation->write();
- // Assign parent page
- $Presentation->PresentationCategoryPageID = $ParentPageID;
- $Presentation->write();
+ }
+ }
+}
- if($Event->UploadedMedia()) {
- $Presentation->SlidesLink = $Event->UploadedMedia()->link();
- } elseif ($Event->HostedMediaURL()) {
- $Presentation->SlidesLink = $Event->HostedMediaURL();
- }
-
- $Presentation->write();
-
- }
-
- }
-
- function AddMedia($ParentPageID) {
-
- $Presentations = Presentation::get()->filter('PresentationCategoryPageID', $ParentPageID);
-
- foreach ($Presentations as $Presentation) {
- if(!$Presentation->SlidesLink) {
-
- $SchedEventMatch = SchedEvent::get()->filter('eventtitle',$Presentation->Name)->first();
-
- if($SchedEventMatch && $SchedEventMatch->UploadedMedia()) {
- $Presentation->SlidesLink = $SchedEventMatch->UploadedMedia()->link();
- $Presentation->write();
- echo 'Added slides to "' . $Presentation->Name . '"
';
- } elseif ($SchedEventMatch && $SchedEventMatch->HostedMediaURL()) {
- $Presentation->SlidesLink = $SchedEventMatch->HostedMediaURL();
- $Presentation->write();
- echo 'Added slides to "' . $Presentation->Name . '"
';
- }
- }
- }
-
- }
-
- function AdjustDates() {
- $Events = SchedEvent::get();
- foreach ($Events as $Event) {
- $Presentation = Presentation::get()->filter('Name', $Event->eventtitle)->first();
- if($Presentation) {
- $Presentation->StartTime = $Event->event_start;
- $Presentation->EndTime = $Event->event_end;
- $Presentation->write();
- }
- }
-
- }
-
-
-}
\ No newline at end of file
diff --git a/openstack/code/PresentationCategoryPage.php b/openstack/code/PresentationCategoryPage.php
index 5541d61..b2b7552 100644
--- a/openstack/code/PresentationCategoryPage.php
+++ b/openstack/code/PresentationCategoryPage.php
@@ -23,7 +23,7 @@ class PresentationCategoryPage extends Page {
static $has_many = array(
'Presentations' => 'Presentation'
);
-
+
static $allowed_children = array('PresentationCategoryPage');
/** static $icon = "icon/path"; */
@@ -44,52 +44,46 @@ class PresentationCategoryPage extends Page {
}
}
-
+
class PresentationCategoryPage_Controller extends Page_Controller {
static $allowed_actions = array(
'presentation',
'updateURLS' => 'admin'
- );
-
+ );
+
public function Presentations(){
- if(isset($_GET['day'])){
- $sessions = "";
- $day = Convert::raw2xml($_GET['day']);
- $day = (int)$day;
- if (is_numeric($day)) {
- $sessions = Presentation::get()->filter(array( 'PresentationCategoryPageID' => $this->ID , 'Day' => $day))->sort('StartTime','ASC');
- } else {
- $sessions = Presentation::get()->filter(array( 'PresentationCategoryPageID' => $this->ID , 'Day' => 1))->sort('StartTime','ASC');
- }
- } else {
- $sessions = Presentation::get()->filter(array( 'PresentationCategoryPageID' => $this->ID , 'Day' => 1))->sort('StartTime','ASC');
- }
+ $sessions = dataobject::get('Presentation','`YouTubeID` IS NOT NULL AND PresentationCategoryPageID = '.$this->ID,'StartTime DESC');
return $sessions;
- }
-
+ }
+
function init() {
parent::init();
if(isset($_GET['day'])) {
Session::set('Day', $_GET['day']);
} else {
- Session::set('Day', 1);
+ Session::set('Day', 1);
}
+ if (Director::urlParam("OtherID") != "presentation") Session::set('Autoplay',TRUE);
}
//Show the Presentation detail page using the PresentationCategoryPage_presentation.ss template
- function presentation()
- {
+ function presentation()
+ {
if($Presentation = $this->getPresentationByURLSegment())
{
$Data = array(
'Presentation' => $Presentation
);
-
- $this->Title = $Presentation->Name;
+
+ $this->Title = $Presentation->Name;
+ $this->Autoplay = Session::get('Autoplay');
+
+ // Clear autoplay so it only happens when you come directly from videos index
+ Session::set('Autoplay',FALSE);
//return our $Data to use on the page
return $this->Customise($Data);
@@ -101,6 +95,15 @@ class PresentationCategoryPage_Controller extends Page_Controller {
}
}
+ function PresentationDayID($PresentationDay) {
+ return trim($PresentationDay,' ');
+ }
+
+ function LatestPresentation()
+ {
+ return $this->Presentations()->first();
+ }
+
// Check to see if the page is being accessed in Chinese
// We use this in the templates to tell Chinese visitors how to obtain the videos on a non-youtube source
@@ -119,8 +122,8 @@ class PresentationCategoryPage_Controller extends Page_Controller {
{
$Params = $this->getURLParams();
$Segment = convert::raw2sql($Params['ID']);
- if($Params['ID'] && $Presentation = Presentation::get()->filter(array('URLSegment' => $Segment, 'PresentationCategoryPageID' => $this->ID))->first())
- {
+ if($Params['ID'] && $Presentation = DataObject::get_one('Presentation', "`URLSegment` = '".$Segment."' AND `PresentationCategoryPageID` = ".$this->ID))
+ {
return $Presentation;
}
}
@@ -141,7 +144,6 @@ class PresentationCategoryPage_Controller extends Page_Controller {
}
}
echo "Presentation URLS updated.";
- }
-
+ }
}
\ No newline at end of file
diff --git a/openstack/code/summit/SchedToolsPage.php b/openstack/code/summit/SchedToolsPage.php
index e327f0d..209bc28 100644
--- a/openstack/code/summit/SchedToolsPage.php
+++ b/openstack/code/summit/SchedToolsPage.php
@@ -1,4 +1,5 @@
'ADMIN',
- 'ImportSessionsFromSched' => 'ADMIN',
- 'ListSpeakers' => 'ADMIN',
- 'SpeakerTable' => 'ADMIN',
- 'Presentations',
- 'Upload',
- 'Form',
- 'Success',
- 'LinkTo',
- 'LinkToForm',
- 'EmailSpeakers' => 'ADMIN'
- );
+ public static $allowed_actions = array(
+ 'ImportSpeakersFromSched' => 'ADMIN',
+ 'ImportSessionsFromSched' => 'ADMIN',
+ 'ListSpeakers' => 'ADMIN',
+ 'SpeakerTable' => 'ADMIN',
+ 'Presentations',
+ 'Upload',
+ 'Form',
+ 'Success',
+ 'LinkTo',
+ 'LinkToForm',
+ 'EmailSpeakers' => 'ADMIN',
+ 'AssignYouTubeID'
+ );
function init()
{
@@ -81,13 +83,50 @@ class SchedToolsPage_Controller extends Page_Controller
");
+
+ }
+
+ function AssignYouTubeID()
+ {
+ if (isset($_GET['token']) &&
+ $_GET['token'] == "fcv4x7Nl8v" &&
+ isset($_GET['youtubeid']) &&
+ isset($_GET['schedid'])
+ ) {
+
+ $CleanedYoutubeID = Convert::raw2sql($_GET['youtubeid']);
+ $CleanedSchedID = Convert::raw2sql($_GET['schedid']);
+
+ $Presentation = DataObject::get_one('Presentation', "`event_key` = '" . $CleanedSchedID . "'");
+
+ If ($Presentation) {
+
+ // Add the YouTubeID to an existing presentation
+ $Presentation->YouTubeID = $CleanedYoutubeID;
+ $Presentation->write();
+
+ } else {
+
+ // Create a new presentation with this sched event and add the youtube id
+ $SchedEvent = DataObject::get_one('SchedEvent', "`event_key` = '" . $CleanedSchedID . "'");
+ if ($SchedEvent) {
+ $Presentation = new Presentation();
+ $Presentation->PopulateFromSchedEvent($SchedEvent->ID);
+ $Presentation->YouTubeID = $CleanedYoutubeID;
+ $Presentation->sched_key = $SchedEvent->sched_key;
+ $Presentation->write();
+ }
+
+ }
+
+ }
}
function ImportSpeakersFromSched()
{
- $feed = new RestfulService('http://openstacksummitnovember2014paris.sched.org/api/role/export?api_key=41caf3c5cafc24e286ade21926eaeb41&role=speaker&format=xml&fields=username,name,email',7200);
+ $feed = new RestfulService('http://openstacksummitnovember2014paris.sched.org/api/role/export?api_key=41caf3c5cafc24e286ade21926eaeb41&role=speaker&format=xml&fields=username,name,email', 7200);
$feedXML = $feed->request()->getBody();
@@ -167,7 +206,7 @@ class SchedToolsPage_Controller extends Page_Controller
$key = Convert::raw2sql($_GET['key']);
$username = SchedSpeaker::HashToUsername($key);
- $Speaker = SchedSpeaker::get()->filter('username',$username)->first();
+ $Speaker = SchedSpeaker::get()->filter('username', $username)->first();
} elseif ($speakerID = Session::get('UploadMedia.SpeakerID')) {
@@ -232,7 +271,7 @@ class SchedToolsPage_Controller extends Page_Controller
if ( // make sure the data is numeric
is_numeric($PresentationID) &&
// make sure there's a presentation by that id
- ($Presentation = SchedEvent::get()->byID( $PresentationID)) &&
+ ($Presentation = SchedEvent::get()->byID($PresentationID)) &&
// pull the speaker from the session and make sure they are a speaker for this presentation
($SpeakerID = Session::get('UploadMedia.SpeakerID')) &&
($Presentation->IsASpeaker($SpeakerID))
@@ -260,7 +299,7 @@ class SchedToolsPage_Controller extends Page_Controller
{
$PresentationID = Session::get('UploadMedia.PresentationID');
- $Presentation = SchedEvent::get()->byID( $PresentationID);
+ $Presentation = SchedEvent::get()->byID($PresentationID);
$Form = new PresentationLinkToForm($this, 'LinkToForm');
if ($Presentation && $Presentation->Metadata()) $Form->loadDataFrom($Presentation->Metadata());
@@ -309,7 +348,7 @@ class SchedToolsPage_Controller extends Page_Controller
$Speakers = SchedSpeaker::get();
foreach ($Speakers as $Speaker) {
- if ($Speaker->PresentationsForThisSpeaker() &&
+ if ($Speaker->PresentationsForThisSpeaker() &&
!$Speaker->GeneralOrKeynote() &&
!SchedSpeakerEmailLog::BeenEmailed($Speaker->email) &&
$this->validEmail($Speaker->email)
diff --git a/themes/openstack/css/videos.css b/themes/openstack/css/videos.css
new file mode 100644
index 0000000..31a0f85
--- /dev/null
+++ b/themes/openstack/css/videos.css
@@ -0,0 +1,403 @@
+/*Videos Home Page*/
+.main-video-wrapper {
+ width: 100%;
+ background: #222;
+ height: auto;
+ margin: 0 0 30px;
+ text-align: center;
+ box-sizing: border-box; }
+
+a.main-video {
+ position: relative;
+ display: block;
+ max-width: 617px;
+ margin: 0 auto;
+ border-left: 1px solid #eee;
+ border-right: 1px solid #eee; }
+
+a.main-video .video-description-wrapper {
+ position: absolute;
+ display: block;
+ background: rgba(0, 0, 0, 0.7);
+ bottom: 0;
+ left: 0;
+ right: 0;
+ top: 230px;
+ text-align: left;
+ z-index: 1000;
+ padding: 20px; }
+
+@media (max-width: 767px) {
+ a.main-video .video-description-wrapper {
+ top: 60%; } }
+
+@media (max-width: 480px) {
+ a.main-video .video-description-wrapper {
+ top: 50%; } }
+
+a.main-video .video-description-wrapper .video-description {
+ width: 80%;
+ float: left; }
+
+a.main-video .video-description-wrapper .video-description h3 {
+ color: white;
+ font-size: 22px;
+ font-weight: 600;
+ width: 100%;
+ height: 25px;
+ overflow: hidden;
+ white-space: nowrap;
+ text-overflow: ellipsis; }
+
+a.main-video .video-description-wrapper .video-description p {
+ color: white;
+ font-size: 13px;
+ line-height: 1.2;
+ font-weight: 400;
+ padding: 0;
+ display: block;
+ width: 100%;
+ height: 15px;
+ margin: 0 auto;
+ white-space: nowrap;
+ overflow: hidden;
+ text-overflow: ellipsis; }
+
+a.main-video:hover .video-description-wrapper {
+ top: 0; }
+
+a.main-video:hover .video-description-wrapper .video-description h3 {
+ height: 10%;
+ white-space: normal; }
+
+a.main-video:hover .video-description-wrapper .video-description p {
+ height: 90%;
+ white-space: normal; }
+
+@media (max-width: 480px) {
+ a.main-video:hover .video-description-wrapper {
+ top: 50%; }
+ a.main-video:hover .video-description-wrapper .video-description h3 {
+ height: 25px;
+ white-space: nowrap; }
+ a.main-video:hover .video-description-wrapper .video-description p {
+ height: 15px;
+ white-space: nowrap; } }
+
+.main-video img {
+ margin: 0 auto;
+ width: 100%;
+ max-width: 615px;
+ max-height: 100%;
+ display: block;
+ position: relative;
+ z-index: 1; }
+
+.play-btn {
+ float: right;
+ color: white;
+ font-size: 40px;
+ width: 20%;
+ margin-top: 5px;
+ text-align: center; }
+
+.play-btn img#play {
+ max-width: 70px;
+ max-height: 70px; }
+
+.featured-row {
+ width: 100%;
+ background: #2A4E68;
+ padding: 0;
+ position: relative;
+ display: block;
+ margin-bottom: 50px; }
+
+.featured-row h2 {
+ color: white;
+ font-weight: 400;
+ font-size: 24px; }
+
+.featured-row h2 span {
+ font-weight: 400;
+ font-size: 12px;
+ color: #edf2f7;
+ margin-left: 20px; }
+
+.featured-row:after {
+ top: 100%;
+ left: 10%;
+ border: solid transparent;
+ content: " ";
+ height: 0;
+ width: 0;
+ position: absolute;
+ pointer-events: none;
+ border-color: rgba(42, 78, 104, 0);
+ border-top-color: #2A4E68;
+ border-width: 15px;
+ margin-left: -15px; }
+
+.daily-recap-wrapper .video-thumb-title {
+ text-align: center; }
+
+.video-thumb {
+ /*background: $lightblue;*/
+ text-align: center;
+ width: 100%;
+ height: 0;
+ position: relative;
+ display: table;
+ overflow: hidden;
+ margin-bottom: 20px;
+ box-sizing: border-box; }
+
+.thumb-play {
+ display: none;
+ background-image: url("//www.openstack.org/themes/openstack/images/landing-pages/auto/play-button.png");
+ background-repeat: no-repeat;
+ background-position: center center;
+ background-color: rgba(0, 0, 0, 0.3);
+ position: absolute;
+ top: 0;
+ left: 0;
+ right: 0;
+ bottom: 0; }
+
+.video-thumb:hover .thumb-play {
+ display: block; }
+
+@media (max-width: 767px) {
+ .video-thumb .thumb-play {
+ display: block;
+ background-color: transparent; } }
+
+.video-thumb img.video-thumb-img {
+ max-width: 100%;
+ width: 100%; }
+
+.video-thumb p {
+ color: #C6CDD6;
+ font-size: 14px;
+ font-weight: 700;
+ display: table-cell;
+ vertical-align: middle; }
+
+.sort-row {
+ background: #edf2f7;
+ width: 100%;
+ min-height: 50px;
+ padding: 25px 0;
+ position: relative;
+ display: block;
+ margin: 50px 0;
+ color: #2A4E68; }
+
+.sort-left {
+ float: left; }
+
+.sort-left i {
+ color: #b4c5d6;
+ line-height: 1;
+ margin-right: 10px; }
+
+.sort-left i:hover {
+ color: #2A4E68;
+ cursor: pointer; }
+
+.sort-left i.active {
+ color: #2A4E68; }
+
+.sort-right {
+ float: right;
+ font-size: 12px;
+ text-transform: uppercase;
+ font-weight: 600; }
+
+.sort-right i {
+ margin-left: 10px;
+ font-weight: 700;
+ font-size: 14px; }
+
+.video-thumb-title {
+ margin: -10px 0 0;
+ color: #30739C;
+ font-size: 12px;
+ font-weight: 400;
+ width: 100%;
+ white-space: nowrap;
+ overflow: hidden;
+ text-overflow: ellipsis; }
+
+.video-thumb-speaker {
+ color: #30739C;
+ font-size: 12px;
+ font-weight: 600;
+ margin-bottom: 40px;
+ width: 100%;
+ white-space: nowrap;
+ overflow: hidden;
+ text-overflow: ellipsis; }
+
+@media (max-width: 767px) {
+ .daily-recap-wrapper .video-thumb-title {
+ margin-bottom: 40px; }
+ .video-thumb-title, .video-thumb-speaker {
+ text-align: center; } }
+
+.video-dropdown > .dropdown-menu {
+ margin: 20px -20px 0;
+ padding: 10px 0;
+ min-width: 230px;
+ border-top-left-radius: 4px;
+ border-top-right-radius: 4px;
+ left: -99%;
+ right: 100%;
+ background-color: #edf2f7;
+ background-clip: padding-box;
+ border: 1px solid rgba(0, 0, 0, 0);
+ box-shadow: none; }
+
+/*.video-dropdown>.dropdown-menu:after, .video-dropdown>.dropdown-menu:before {
+ bottom: 100%;
+ right: 25%;
+ border: solid transparent;
+ content: " ";
+ height: 0;
+ width: 0;
+ position: absolute;
+ pointer-events: none;
+}
+.video-dropdown>.dropdown-menu:after {
+ border-color: rgba(255, 255, 255, 0);
+ border-bottom-color: #fff;
+ border-width: 15px;
+ margin-left: -15px;
+}
+.video-dropdown>.dropdown-menu:before {
+ border-color: rgba(170, 170, 170, 0);
+ border-bottom-color: #aaaaaa;
+ border-width: 15px;
+ margin-left: -16px;
+}*/
+.video-dropdown > .dropdown-menu li a {
+ text-transform: uppercase;
+ padding: 13px 20px;
+ font-size: 12px;
+ color: #2A4E68; }
+
+.video-dropdown > .dropdown-menu li a:hover {
+ color: white;
+ background: #2A4E68; }
+
+.video-dropdown > .dropdown-menu li a:focus {
+ outline: none; }
+
+/*End Videos Home Page*/
+/*Video Inner Page*/
+.single-video-details {
+ margin: 60px auto; }
+
+.single-video-details h3 {
+ text-align: left; }
+
+.single-video-details strong {
+ color: #2A4E68; }
+
+.video-share {
+ text-align: right;
+ float: right; }
+
+.video-share a i {
+ font-size: 22px;
+ margin-left: 20px;
+ vertical-align: middle;
+ color: #759bb7; }
+
+.video-share a i:hover {
+ color: #2A4E68; }
+
+@media (max-width: 767px) {
+ .video-share {
+ float: none;
+ text-align: center;
+ margin: -20px 0 20px;
+ padding-top: 20px;
+ padding-bottom: 20px;
+ border-top: 1px solid #eee;
+ border-bottom: 1px solid #eee; }
+ .video-share a i {
+ margin: 0 10px; } }
+
+.video-share a i.fa-twitter {
+ font-size: 24px;
+ margin-bottom: -1px; }
+
+p.single-video-description {
+ margin: 10px 0 40px; }
+
+.video-categories a {
+ margin-left: 10px;
+ text-decoration: underline; }
+
+.video-tags {
+ margin-top: 15px; }
+
+.video-tags a {
+ background: #edf2f7;
+ font-size: 10px;
+ font-weight: 600;
+ border-radius: 3px;
+ margin-left: 10px;
+ padding: 5px 10px; }
+
+.video-speakers {
+ margin-top: 15px;
+ display: block; }
+
+.video-speakers p a {
+ margin-left: 0;
+ text-decoration: underline; }
+
+.video-speakers .twitter-follow-button {
+ margin-left: 10px; }
+
+.video-media-title {
+ margin: 0 0 10px;
+ display: block; }
+
+@media (max-width: 767px) {
+ .video-media-wrapper {
+ margin-top: 30px; } }
+
+.media-btn-wrapper {
+ float: left;
+ margin-top: 10px; }
+
+a.media-btn {
+ background: #2A4E68;
+ color: white;
+ padding: 10px 20px;
+ border-radius: 4px;
+ border: 0; }
+
+a.media-btn:hover {
+ text-decoration: none;
+ background: #16283A; }
+
+a.media-btn i {
+ margin-right: 10px; }
+
+a.media-btn.right {
+ border-top-left-radius: 0px;
+ border-bottom-left-radius: 0px;
+ margin-left: -2px;
+ border-left: 1px solid #3E71A4; }
+
+a.media-btn.left {
+ border-top-right-radius: 0px;
+ border-bottom-right-radius: 0px;
+ margin-right: -2px;
+ border-right: 1px solid #122231; }
+
+/*End Video Inner Page*/
diff --git a/themes/openstack/images/no-video.jpg b/themes/openstack/images/no-video.jpg
new file mode 100644
index 0000000..9aad1ed
Binary files /dev/null and b/themes/openstack/images/no-video.jpg differ
diff --git a/themes/openstack/templates/Layout/Includes/VideoThumbnails.ss b/themes/openstack/templates/Layout/Includes/VideoThumbnails.ss
new file mode 100644
index 0000000..d6dad78
--- /dev/null
+++ b/themes/openstack/templates/Layout/Includes/VideoThumbnails.ss
@@ -0,0 +1,57 @@
+
+
+
+
+
+
+
+ <% control Presentations.GroupedBy(PresentationDay) %>
+
+
$PresentationDay
+
+ <% control Children %>
+
+
+ <% end_control %>
+
+
+ <% end_control %>
+
+
+
+
+
+
+
diff --git a/themes/openstack/templates/Layout/PresentationCategoryPage.ss b/themes/openstack/templates/Layout/PresentationCategoryPage.ss
index 49f30e7..261e35b 100644
--- a/themes/openstack/templates/Layout/PresentationCategoryPage.ss
+++ b/themes/openstack/templates/Layout/PresentationCategoryPage.ss
@@ -1,86 +1,74 @@
-<% require themedCSS(conference) %>
+<% require themedCSS(videos) %>
-<% loop Parent %>
-$HeaderArea
+
+
+
+
+
Paris Summit 2014: Videos
+
+
+
+
+<% loop LatestPresentation %>
+
<% end_loop %>
-
-
-
The OpenStack Summit
$Parent.MenuTitle.XML
-
- <% loop Parent %>
- <% include HeadlineSponsors %>
- <% end_loop %>
-
-
-
- <% if StillUploading %>
-
-
Note: Presentations are still being uploaded. If you do not see the presentation you are looking for, please check back soon.
+
+
+
+ Daily Recaps
+ Highlights from the OpenStack Summit in Paris
+
-
- <% end_if %>
-
-
-
-
-
-
-
Videos of Sessions From Day $currentDay
-
-
-
-
- <% if Presentations %>
- <% loop Presentations %>
-
- <% if DisplayOnSite %>
- <% if YouTubeID %>
-
-
-
-
-
- <% if Speakers %>
$Speakers
<% end_if %>
- $RAW_val(Description)
-
- Watch Now
- <% if SlidesLink %>
- Slides
- <% end_if %>
-
-
-
-
-
-
- <% end_if %>
- <% end_if %>
-
- <% end_loop %>
-
- <% else %>
-
Sorry, no presentations are available for the day you've selected. Please check back soon.
- <% end_if %>
-
-
-
-
-
+
+
+
+
+
![](/themes/openstack/images/no-video.jpg)
+
+
+ Day 1 - Coming Soon
+
+
+
+
+
![](/themes/openstack/images/no-video.jpg)
+
+
+ Day 2 - Coming Soon
+
+
+
+
+
![](/themes/openstack/images/no-video.jpg)
+
+
+ Day 3 - Coming Soon
+
+
+
+
+
![](/themes/openstack/images/no-video.jpg)
+
+
+ Day 4 - Coming Soon
+
+
+
+
+
+<% include VideoThumbnails %>
diff --git a/themes/openstack/templates/Layout/PresentationCategoryPage_presentation.ss b/themes/openstack/templates/Layout/PresentationCategoryPage_presentation.ss
index cf6bb43..510e709 100644
--- a/themes/openstack/templates/Layout/PresentationCategoryPage_presentation.ss
+++ b/themes/openstack/templates/Layout/PresentationCategoryPage_presentation.ss
@@ -1,69 +1,53 @@
-<% require themedCSS(presentation) %>
+<% require themedCSS(videos) %>
-
OpenStack Summit Presentations
-
+<% loop Presentation %>
-
-
-
-
-
-
"$Presentation.Name"
-
By: $Presentation.Speakers
-
- <% if Presentation.Description %>
- $Presentation.Description
- <% end_if %>
-
-
-
-
-
Watch Presentation
-
-
-
- <% loop Presentation %>
- <% if SlidesLink %>
-
-
-
-
-
- <% if EmbedSlides %>
-
View Slides
-
- <% else %>
-
Download The Presentation Slides
-
Download Slides
- <% end_if %>
- <% end_if %>
- <% end_loop %>
-
-
-
-
-
-
-
-
Media:
- Video
- <% if Presentation.SlidesLink %>
- Slides
- <% end_if %>
-
-
-
-
-
Share This Presentation:
-
-
-
-
-
-
Discover More Content:
- More Presentations
+
+
+
+
+
+
+
+
+ $Description
+
+
+
+
+ Speakers: $Speakers
+
+
+
+
+ <% if SlidesLink %>
+
+ <% end_if %>
+
+
+
+
+
+<% end_loop %>
-
\ No newline at end of file
+
+<% include VideoThumbnails %>