@recaptime-dev's working patches + fork for Phorge, a community fork of Phabricator. (Upstream dev and stable branches are at upstream/main and upstream/stable respectively.) hq.recaptime.dev/wiki/Phorge
phorge phabricator
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Conpherence - make the files widget purdy-ish

Summary:
does the title and also a few other small tweaks

- kills the init js behavior; now its part of menu where it belongs.
- adds the underline to the icon when its toggled in the widget menu
- fixed JS initialization errors on the "create conpherence" page. Note I still like keeping all that init stuff in one function because its typing the same data a bunch to be passed over to the JS layer. Other ways to accomplish this obvi...

Only fun wrinkle here is I think Chad intended me to display "when the file was attached". Instead, I display when the file was *uploaded*. I think this jives better with our version where you can't delete and all that. Files are pretty powerful, long-living objects in Phabricator land.

Test Plan: added files to a conpherence and noted widget loaded updated okay. added a file with no author (generated by the system) and verified it still rendered okay. switched between conpherences and verified proper data in each files widget. uploaded image and text files to check the icons were correct.

Reviewers: epriestley, chad

Reviewed By: epriestley

CC: aran, Korvin

Maniphest Tasks: T2530

Differential Revision: https://secure.phabricator.com/D5337

+424 -262
+1 -13
src/__celerity_resource_map__.php
··· 1174 1174 ), 1175 1175 'disk' => '/rsrc/js/application/conpherence/behavior-drag-and-drop-photo.js', 1176 1176 ), 1177 - 'javelin-behavior-conpherence-init' => 1178 - array( 1179 - 'uri' => '/res/700bba2e/rsrc/js/application/conpherence/behavior-init.js', 1180 - 'type' => 'js', 1181 - 'requires' => 1182 - array( 1183 - 0 => 'javelin-behavior', 1184 - 1 => 'javelin-dom', 1185 - 2 => 'javelin-stratcom', 1186 - ), 1187 - 'disk' => '/rsrc/js/application/conpherence/behavior-init.js', 1188 - ), 1189 1177 'javelin-behavior-conpherence-menu' => 1190 1178 array( 1191 - 'uri' => '/res/cb1a5cf0/rsrc/js/application/conpherence/behavior-menu.js', 1179 + 'uri' => '/res/e5da1c05/rsrc/js/application/conpherence/behavior-menu.js', 1192 1180 'type' => 'js', 1193 1181 'requires' => 1194 1182 array(
+20 -25
src/applications/conpherence/controller/ConpherenceController.php
··· 309 309 310 310 } 311 311 312 - protected function initJavelinBehaviors() { 312 + protected function initJavelinBehaviors($more_than_menu = false) { 313 313 314 314 Javelin::initBehavior('conpherence-menu', 315 315 array( 316 316 'base_uri' => $this->getApplicationURI(''), 317 317 'header' => 'conpherence-header-pane', 318 318 'messages' => 'conpherence-messages', 319 + 'messages_pane' => 'conpherence-message-pane', 319 320 'widgets_pane' => 'conpherence-widget-pane', 320 321 'form_pane' => 'conpherence-form', 321 322 'menu_pane' => 'conpherence-menu', 323 + 'selected_conpherence_id' => $this->getSelectedConpherencePHID(), 322 324 'fancy_ajax' => (bool) $this->getSelectedConpherencePHID() 323 325 )); 324 - Javelin::initBehavior('conpherence-init', 325 - array( 326 - 'selected_conpherence_id' => $this->getSelectedConpherencePHID(), 327 - 'menu_pane' => 'conpherence-menu', 328 - 'messages_pane' => 'conpherence-message-pane', 329 - 'messages' => 'conpherence-messages', 330 - 'widgets_pane' => 'conpherence-widget-pane', 331 - 'form_pane' => 'conpherence-form' 332 - )); 333 - Javelin::initBehavior('conpherence-drag-and-drop-photo', 334 - array( 335 - 'target' => 'conpherence-header-pane', 336 - 'form_pane' => 'conpherence-form', 337 - 'upload_uri' => '/file/dropupload/', 338 - 'activated_class' => 'conpherence-header-upload-photo', 339 - )); 340 - Javelin::initBehavior('conpherence-pontificate', 341 - array( 342 - 'messages' => 'conpherence-messages', 343 - 'header' => 'conpherence-header-pane', 344 - 'menu_pane' => 'conpherence-menu', 345 - 'form_pane' => 'conpherence-form', 346 - 'file_widget' => 'widgets-files', 347 - )); 326 + if ($more_than_menu) { 327 + Javelin::initBehavior('conpherence-drag-and-drop-photo', 328 + array( 329 + 'target' => 'conpherence-header-pane', 330 + 'form_pane' => 'conpherence-form', 331 + 'upload_uri' => '/file/dropupload/', 332 + 'activated_class' => 'conpherence-header-upload-photo', 333 + )); 334 + Javelin::initBehavior('conpherence-pontificate', 335 + array( 336 + 'messages' => 'conpherence-messages', 337 + 'header' => 'conpherence-header-pane', 338 + 'menu_pane' => 'conpherence-menu', 339 + 'form_pane' => 'conpherence-form', 340 + 'file_widget' => 'widgets-files', 341 + )); 342 + } 348 343 } 349 344 }
+1 -1
src/applications/conpherence/controller/ConpherenceListController.php
··· 63 63 } 64 64 65 65 private function renderEmptyMainPane() { 66 - $this->initJavelinBehaviors(); 66 + $this->initJavelinBehaviors(true); 67 67 return phutil_tag( 68 68 'div', 69 69 array(
+38 -37
src/applications/conpherence/controller/ConpherenceUpdateController.php
··· 234 234 $conpherence_id, 235 235 $latest_transaction_id) { 236 236 237 - $user = $this->getRequest()->getUser(); 238 - $conpherence = id(new ConpherenceThreadQuery()) 239 - ->setViewer($user) 240 - ->setAfterID($latest_transaction_id) 241 - ->needHeaderPics(true) 242 - ->needWidgetData(true) 243 - ->withIDs(array($conpherence_id)) 244 - ->executeOne(); 237 + $user = $this->getRequest()->getUser(); 238 + $conpherence = id(new ConpherenceThreadQuery()) 239 + ->setViewer($user) 240 + ->setAfterID($latest_transaction_id) 241 + ->needHeaderPics(true) 242 + ->needWidgetData(true) 243 + ->withIDs(array($conpherence_id)) 244 + ->executeOne(); 245 245 246 - $data = $this->renderConpherenceTransactions($conpherence); 247 - $rendered_transactions = $data['transactions']; 248 - $new_latest_transaction_id = $data['latest_transaction_id']; 246 + $data = $this->renderConpherenceTransactions($conpherence); 247 + $rendered_transactions = $data['transactions']; 248 + $new_latest_transaction_id = $data['latest_transaction_id']; 249 249 250 - $selected = true; 251 - $nav_item = $this->buildConpherenceMenuItem( 252 - $conpherence, 253 - '-nav-item', 254 - $selected); 255 - $menu_item = $this->buildConpherenceMenuItem( 256 - $conpherence, 257 - '-menu-item', 258 - $selected); 250 + $selected = true; 251 + $nav_item = $this->buildConpherenceMenuItem( 252 + $conpherence, 253 + '-nav-item', 254 + $selected); 255 + $menu_item = $this->buildConpherenceMenuItem( 256 + $conpherence, 257 + '-menu-item', 258 + $selected); 259 259 260 - $header = $this->buildHeaderPaneContent($conpherence); 260 + $header = $this->buildHeaderPaneContent($conpherence); 261 261 262 - $file_widget = id(new ConpherenceFileWidgetView()) 263 - ->setConpherence($conpherence) 264 - ->setUpdateURI( 265 - $this->getApplicationURI('update/'.$conpherence->getID().'/')); 262 + $file_widget = id(new ConpherenceFileWidgetView()) 263 + ->setUser($this->getRequest()->getUser()) 264 + ->setConpherence($conpherence) 265 + ->setUpdateURI( 266 + $this->getApplicationURI('update/'.$conpherence->getID().'/')); 266 267 267 - $content = array( 268 - 'transactions' => $rendered_transactions, 269 - 'latest_transaction_id' => $new_latest_transaction_id, 270 - 'menu_item' => $menu_item->render(), 271 - 'nav_item' => $nav_item->render(), 272 - 'conpherence_phid' => $conpherence->getPHID(), 273 - 'header' => $header, 274 - 'file_widget' => $file_widget->render() 275 - ); 276 - return $content; 277 - } 268 + $content = array( 269 + 'transactions' => $rendered_transactions, 270 + 'latest_transaction_id' => $new_latest_transaction_id, 271 + 'menu_item' => $menu_item->render(), 272 + 'nav_item' => $nav_item->render(), 273 + 'conpherence_phid' => $conpherence->getPHID(), 274 + 'header' => $header, 275 + 'file_widget' => $file_widget->render() 276 + ); 277 + return $content; 278 + } 278 279 279 - } 280 + }
+145 -138
src/applications/conpherence/controller/ConpherenceWidgetController.php
··· 76 76 array( 77 77 'class' => 'widgets-header' 78 78 ), 79 - array( 80 - javelin_tag( 81 - 'a', 82 - array( 83 - 'sigil' => 'conpherence-change-widget', 84 - 'meta' => array( 85 - 'widget' => 'widgets-conpherence-list', 86 - 'toggleClass' => 'conpherence_list_on' 79 + phutil_tag( 80 + 'div', 81 + array( 82 + 'class' => 'widgets-header-icon-holder' 83 + ), 84 + array( 85 + javelin_tag( 86 + 'a', 87 + array( 88 + 'sigil' => 'conpherence-change-widget', 89 + 'meta' => array( 90 + 'widget' => 'widgets-conpherence-list', 91 + 'toggleClass' => 'conpherence_list_on' 92 + ), 93 + 'id' => 'widgets-conpherence-list-toggle', 94 + 'class' => 'sprite-conpherence conpherence_list_off', 87 95 ), 88 - 'id' => 'widgets-conpherence-list-toggle', 89 - 'class' => 'sprite-conpherence conpherence_list_off', 90 - ), 91 - ''), 92 - javelin_tag( 93 - 'a', 94 - array( 95 - 'sigil' => 'conpherence-change-widget', 96 - 'meta' => array( 97 - 'widget' => 'widgets-conversation', 98 - 'toggleClass' => 'conpherence_conversation_on' 96 + ''), 97 + javelin_tag( 98 + 'a', 99 + array( 100 + 'sigil' => 'conpherence-change-widget', 101 + 'meta' => array( 102 + 'widget' => 'widgets-conversation', 103 + 'toggleClass' => 'conpherence_conversation_on' 104 + ), 105 + 'id' => 'widgets-conpherence-conversation-toggle', 106 + 'class' => 'sprite-conpherence conpherence_conversation_off', 99 107 ), 100 - 'id' => 'widgets-conpherence-conversation-toggle', 101 - 'class' => 'sprite-conpherence conpherence_conversation_off', 102 - ), 103 - ''), 104 - javelin_tag( 105 - 'a', 106 - array( 107 - 'sigil' => 'conpherence-change-widget', 108 - 'meta' => array( 109 - 'widget' => 'widgets-people', 110 - 'toggleClass' => 'conpherence_people_on' 108 + ''), 109 + javelin_tag( 110 + 'a', 111 + array( 112 + 'sigil' => 'conpherence-change-widget', 113 + 'meta' => array( 114 + 'widget' => 'widgets-people', 115 + 'toggleClass' => 'conpherence_people_on' 116 + ), 117 + 'id' => 'widgets-people-toggle', 118 + 'class' => 'sprite-conpherence conpherence_people_off' 111 119 ), 112 - 'id' => 'widgets-people-toggle', 113 - 'class' => 'sprite-conpherence conpherence_people_off' 114 - ), 115 - ''), 116 - javelin_tag( 117 - 'a', 118 - array( 119 - 'sigil' => 'conpherence-change-widget', 120 - 'meta' => array( 121 - 'widget' => 'widgets-files', 122 - 'toggleClass' => 'conpherence_files_on' 120 + ''), 121 + javelin_tag( 122 + 'a', 123 + array( 124 + 'sigil' => 'conpherence-change-widget', 125 + 'meta' => array( 126 + 'widget' => 'widgets-files', 127 + 'toggleClass' => 'conpherence_files_on' 128 + ), 129 + 'id' => 'widgets-files-toggle', 130 + 'class' => 131 + 'sprite-conpherence conpherence_files_on conpherence_files_off' 123 132 ), 124 - 'id' => 'widgets-files-toggle', 125 - 'class' => 'sprite-conpherence conpherence_files_off' 126 - ), 127 - ''), 128 - javelin_tag( 129 - 'a', 130 - array( 131 - 'sigil' => 'conpherence-change-widget', 132 - 'meta' => array( 133 - 'widget' => 'widgets-calendar', 134 - 'toggleClass' => 'conpherence_calendar_on' 133 + ''), 134 + javelin_tag( 135 + 'a', 136 + array( 137 + 'sigil' => 'conpherence-change-widget', 138 + 'meta' => array( 139 + 'widget' => 'widgets-calendar', 140 + 'toggleClass' => 'conpherence_calendar_on' 141 + ), 142 + 'id' => 'widgets-calendar-toggle', 143 + 'class' => 'sprite-conpherence conpherence_calendar_off', 135 144 ), 136 - 'id' => 'widgets-calendar-toggle', 137 - 'class' => 'sprite-conpherence conpherence_calendar_off', 138 - ), 139 - ''), 140 - javelin_tag( 141 - 'a', 142 - array( 143 - 'sigil' => 'conpherence-change-widget', 144 - 'meta' => array( 145 - 'widget' => 'widgets-settings', 146 - 'toggleClass' => 'conpherence_settings_on' 145 + ''), 146 + javelin_tag( 147 + 'a', 148 + array( 149 + 'sigil' => 'conpherence-change-widget', 150 + 'meta' => array( 151 + 'widget' => 'widgets-settings', 152 + 'toggleClass' => 'conpherence_settings_on' 153 + ), 154 + 'id' => 'widgets-settings-toggle', 155 + 'class' => 'sprite-conpherence conpherence_settings_off', 147 156 ), 148 - 'id' => 'widgets-settings-toggle', 149 - 'class' => 'sprite-conpherence conpherence_settings_off', 150 - ), 151 - '') 152 - )). 153 - phutil_tag( 154 - 'div', 155 - array( 156 - 'class' => 'widgets-body', 157 - 'id' => 'widgets-people', 158 - ), 159 - $this->renderPeopleWidgetPaneContent()). 157 + '') 158 + ))). 159 + phutil_tag( 160 + 'div', 161 + array( 162 + 'class' => 'widgets-body', 163 + 'id' => 'widgets-people', 164 + 'style' => 'display: none;' 165 + ), 166 + $this->renderPeopleWidgetPaneContent()). 160 167 phutil_tag( 161 168 'div', 162 169 array( 163 170 'class' => 'widgets-body', 164 171 'id' => 'widgets-files', 165 - 'style' => 'display: none;' 166 172 ), 167 173 id(new ConpherenceFileWidgetView()) 174 + ->setUser($this->getRequest()->getUser()) 168 175 ->setConpherence($conpherence) 169 176 ->setUpdateURI( 170 177 $this->getApplicationURI('update/'.$conpherence->getID().'/')) 171 178 ->render()). 172 - phutil_tag( 173 - 'div', 174 - array( 175 - 'class' => 'widgets-body', 176 - 'id' => 'widgets-calendar', 177 - 'style' => 'display: none;' 178 - ), 179 - $this->renderCalendarWidgetPaneContent()). 180 - phutil_tag( 181 - 'div', 182 - array( 183 - 'class' => 'widgets-body', 184 - 'id' => 'widgets-settings', 185 - 'style' => 'display: none' 186 - ), 187 - $this->renderSettingsWidgetPaneContent()); 179 + phutil_tag( 180 + 'div', 181 + array( 182 + 'class' => 'widgets-body', 183 + 'id' => 'widgets-calendar', 184 + 'style' => 'display: none;' 185 + ), 186 + $this->renderCalendarWidgetPaneContent()). 187 + phutil_tag( 188 + 'div', 189 + array( 190 + 'class' => 'widgets-body', 191 + 'id' => 'widgets-settings', 192 + 'style' => 'display: none' 193 + ), 194 + $this->renderSettingsWidgetPaneContent()); 188 195 189 196 return array('widgets' => $widgets); 190 197 } ··· 225 232 break; 226 233 } 227 234 if ($status->getDateFrom() < $epoch_end && 228 - $status->getDateTo() > $epoch_start) { 229 - $timespan = $status->getDateTo() - $status->getDateFrom(); 230 - if ($timespan > $one_day) { 231 - $time_str = 'm/d'; 232 - } else { 233 - $time_str = 'h:i A'; 235 + $status->getDateTo() > $epoch_start) { 236 + $timespan = $status->getDateTo() - $status->getDateFrom(); 237 + if ($timespan > $one_day) { 238 + $time_str = 'm/d'; 239 + } else { 240 + $time_str = 'h:i A'; 241 + } 242 + $epoch_range = phabricator_format_local_time( 243 + $status->getDateFrom(), 244 + $user, 245 + $time_str) . ' - ' . phabricator_format_local_time( 246 + $status->getDateTo(), 247 + $user, 248 + $time_str); 249 + 250 + $content[] = phutil_tag( 251 + 'div', 252 + array( 253 + 'class' => 'user-status '.$status->getTextStatus(), 254 + ), 255 + array( 256 + phutil_tag( 257 + 'div', 258 + array( 259 + 'class' => 'epoch-range' 260 + ), 261 + $epoch_range), 262 + phutil_tag( 263 + 'div', 264 + array( 265 + 'class' => 'icon', 266 + ), 267 + ''), 268 + phutil_tag( 269 + 'div', 270 + array( 271 + 'class' => 'description' 272 + ), 273 + $status->getTerseSummary($user)), 274 + phutil_tag( 275 + 'div', 276 + array( 277 + 'class' => 'participant' 278 + ), 279 + $handles[$status->getUserPHID()]->getName()) 280 + )); 234 281 } 235 - $epoch_range = phabricator_format_local_time( 236 - $status->getDateFrom(), 237 - $user, 238 - $time_str) . ' - ' . phabricator_format_local_time( 239 - $status->getDateTo(), 240 - $user, 241 - $time_str); 242 - 243 - $content[] = phutil_tag( 244 - 'div', 245 - array( 246 - 'class' => 'user-status '.$status->getTextStatus(), 247 - ), 248 - array( 249 - phutil_tag( 250 - 'div', 251 - array( 252 - 'class' => 'epoch-range' 253 - ), 254 - $epoch_range), 255 - phutil_tag( 256 - 'div', 257 - array( 258 - 'class' => 'icon', 259 - ), 260 - ''), 261 - phutil_tag( 262 - 'div', 263 - array( 264 - 'class' => 'description' 265 - ), 266 - $status->getTerseSummary($user)), 267 - phutil_tag( 268 - 'div', 269 - array( 270 - 'class' => 'participant' 271 - ), 272 - $handles[$status->getUserPHID()]->getName()) 273 - )); 274 - } 275 282 } 276 283 } 277 284
+22 -1
src/applications/conpherence/query/ConpherenceThreadQuery.php
··· 170 170 171 171 // attached files 172 172 $files = array(); 173 + $file_author_phids = array(); 174 + $authors = array(); 173 175 if ($file_phids) { 174 176 $files = id(new PhabricatorFileQuery()) 175 177 ->setViewer($this->getViewer()) 176 178 ->withPHIDs($file_phids) 177 179 ->execute(); 178 180 $files = mpull($files, null, 'getPHID'); 181 + $file_author_phids = mpull($files, 'getAuthorPHID', 'getPHID'); 182 + $authors = id(new PhabricatorObjectHandleData($file_author_phids)) 183 + ->setViewer($this->getViewer()) 184 + ->loadHandles(); 185 + $authors = mpull($authors, null, 'getPHID'); 179 186 } 180 187 181 188 foreach ($conpherences as $phid => $conpherence) { ··· 183 190 $statuses = array_select_keys($statuses, $participant_phids); 184 191 $statuses = array_mergev($statuses); 185 192 $statuses = msort($statuses, 'getDateFrom'); 193 + 194 + $conpherence_files = array(); 195 + $files_authors = array(); 196 + foreach ($conpherence->getFilePHIDs() as $curr_phid) { 197 + $conpherence_files[$curr_phid] = $files[$curr_phid]; 198 + // some files don't have authors so be careful 199 + $current_author = null; 200 + $current_author_phid = idx($file_author_phids, $curr_phid); 201 + if ($current_author_phid) { 202 + $current_author = $authors[$current_author_phid]; 203 + } 204 + $files_authors[$curr_phid] = $current_author; 205 + } 186 206 $widget_data = array( 187 207 'statuses' => $statuses, 188 - 'files' => array_select_keys($files, $conpherence->getFilePHIDs()), 208 + 'files' => $conpherence_files, 209 + 'files_authors' => $files_authors 189 210 ); 190 211 $conpherence->attachWidgetData($widget_data); 191 212 }
+65 -19
src/applications/conpherence/view/ConpherenceFileWidgetView.php
··· 22 22 } 23 23 24 24 public function render() { 25 + require_celerity_resource('sprite-docs-css'); 25 26 $conpherence = $this->getConpherence(); 26 27 $widget_data = $conpherence->getWidgetData(); 27 28 $files = $widget_data['files']; 28 - 29 - $table_data = array(); 29 + $files_authors = $widget_data['files_authors']; 30 + $files_html = array(); 30 31 31 32 foreach ($files as $file) { 33 + $icon_class = $file->getDisplayIconForMimeType(); 34 + $icon_view = phutil_tag( 35 + 'div', 36 + array( 37 + 'class' => 'file-icon sprite-docs '.$icon_class 38 + ), 39 + ''); 32 40 $file_view = id(new PhabricatorFileLinkView()) 33 41 ->setFilePHID($file->getPHID()) 34 42 ->setFileName($file->getName()) 35 - ->setFileViewable(true) 36 - ->setFileViewURI($file->getBestURI()); 37 - $meta = $file_view->getMetadata(); 43 + ->setFileViewable($file->isViewableImage()) 44 + ->setFileViewURI($file->getBestURI()) 45 + ->setCustomClass('file-title'); 38 46 39 - $table_data[] = array( 40 - javelin_tag( 47 + $who_done_it_text = ''; 48 + // system generated files don't have authors 49 + if ($file->getAuthorPHID()) { 50 + $who_done_it_text = pht( 51 + 'by %s ', 52 + $files_authors[$file->getPHID()]->renderLink()); 53 + } 54 + $date_text = phabricator_relative_date( 55 + $file->getDateCreated(), 56 + $this->getUser()); 57 + 58 + $who_done_it = phutil_tag( 59 + 'div', 60 + array( 61 + 'class' => 'file-uploaded-by' 62 + ), 63 + pht('Uploaded %s%s.', $who_done_it_text, $date_text)); 64 + 65 + $extra = ''; 66 + if ($file->isViewableImage()) { 67 + $meta = $file_view->getMetadata(); 68 + $extra = javelin_tag( 41 69 'a', 42 70 array( 43 71 'sigil' => 'lightboxable', 44 - 'meta' => $meta 72 + 'meta' => $meta, 73 + 'class' => 'file-extra', 45 74 ), 46 75 phutil_tag( 47 76 'img', 48 77 array( 49 - 'src' => $file->getThumb60x45URI() 78 + 'src' => $file->getThumb160x120URI() 50 79 ), 51 - '')), 52 - $file_view->render() 53 - ); 80 + '')); 81 + } 82 + 83 + $divider = phutil_tag( 84 + 'div', 85 + array( 86 + 'class' => 'divider' 87 + ), 88 + ''); 89 + 90 + $files_html[] = phutil_tag( 91 + 'div', 92 + array( 93 + 'class' => 'file-entry' 94 + ), 95 + array( 96 + $icon_view, 97 + $file_view, 98 + $who_done_it, 99 + $extra, 100 + $divider 101 + )); 54 102 } 55 - $header = id(new PhabricatorHeaderView()) 56 - ->setHeader(pht('Attached Files')); 57 - $table = id(new AphrontTableView($table_data)) 58 - ->setNoDataString(pht('No files attached to conpherence.')) 59 - ->setHeaders(array('', pht('Name'))) 60 - ->setColumnClasses(array('', 'wide wrap')); 61 - return array($header, $table); 103 + 104 + return phutil_tag( 105 + 'div', 106 + array('class' => 'file-list'), 107 + $files_html); 62 108 63 109 } 64 110
+35
src/applications/files/config/PhabricatorFilesConfigOptions.php
··· 38 38 'image/vnd.microsoft.icon' => true, 39 39 ); 40 40 41 + // largely lifted from http://en.wikipedia.org/wiki/Internet_media_type 42 + $icon_default = array( 43 + // audio file icon 44 + 'audio/basic' => 'docs_audio', 45 + 'audio/L24' => 'docs_audio', 46 + 'audio/mp4' => 'docs_audio', 47 + 'audio/mpeg' => 'docs_audio', 48 + 'audio/ogg' => 'docs_audio', 49 + 'audio/vorbis' => 'docs_audio', 50 + 'audio/vnd.rn-realaudio' => 'docs_audio', 51 + 'audio/vnd.wave' => 'docs_audio', 52 + 'audio/webm' => 'docs_audio', 53 + // movie file icon 54 + 'video/mpeg' => 'docs_movie', 55 + 'video/mp4' => 'docs_movie', 56 + 'video/ogg' => 'docs_movie', 57 + 'video/quicktime' => 'docs_movie', 58 + 'video/webm' => 'docs_movie', 59 + 'video/x-matroska' => 'docs_movie', 60 + 'video/x-ms-wmv' => 'docs_movie', 61 + 'video/x-flv' => 'docs_movie', 62 + // pdf file icon 63 + 'application/pdf' => 'docs_pdf', 64 + // zip file icon 65 + 'application/zip' => 'docs_zip', 66 + // msword icon 67 + 'application/msword' => 'docs_doc', 68 + ) + array_fill_keys(array_keys($image_default), 'docs_image'); 69 + 41 70 return array( 42 71 $this->newOption('files.viewable-mime-types', 'wild', $viewable_default) 43 72 ->setSummary( ··· 58 87 pht( 59 88 'List of MIME types which can be used as the `src` for an '. 60 89 '`<img />` tag.')), 90 + $this->newOption('files.icon-mime-types', 'wild', $icon_default) 91 + ->setSummary(pht('Configure which MIME types map to which icons.')) 92 + ->setDescription( 93 + pht( 94 + 'Map of MIME type to icon name. MIME types which can not be '. 95 + 'found default to icon `doc_files`.')), 61 96 $this->newOption('storage.mysql-engine.max-size', 'int', 1000000) 62 97 ->setSummary( 63 98 pht(
+6
src/applications/files/storage/PhabricatorFile.php
··· 586 586 return idx($mime_map, $mime_type); 587 587 } 588 588 589 + public function getDisplayIconForMimeType() { 590 + $mime_map = PhabricatorEnv::getEnvConfig('files.icon-mime-types'); 591 + $mime_type = $this->getMimeType(); 592 + return idx($mime_map, $mime_type, 'docs_file'); 593 + } 594 + 589 595 public function validateSecretKey($key) { 590 596 return ($key == $this->getSecretKey()); 591 597 }
+15 -1
src/view/layout/PhabricatorFileLinkView.php
··· 7 7 private $fileViewURI; 8 8 private $fileViewable; 9 9 private $filePHID; 10 + private $customClass; 11 + 12 + public function setCustomClass($custom_class) { 13 + $this->customClass = $custom_class; 14 + return $this; 15 + } 16 + public function getCustomClass() { 17 + return $this->customClass; 18 + } 10 19 11 20 public function setFilePHID($file_phid) { 12 21 $this->filePHID = $file_phid; ··· 71 80 $meta = $this->getMetadata(); 72 81 } 73 82 83 + $class = 'phabricator-remarkup-embed-layout-link'; 84 + if ($this->getCustomClass()) { 85 + $class = $this->getCustomClass(); 86 + } 87 + 74 88 return javelin_tag( 75 89 'a', 76 90 array( 77 91 'href' => $this->getFileViewURI(), 78 - 'class' => 'phabricator-remarkup-embed-layout-link', 92 + 'class' => $class, 79 93 'sigil' => $sigil, 80 94 'meta' => $meta, 81 95 'mustcapture' => $mustcapture,
+63 -5
webroot/rsrc/css/application/conpherence/widget-pane.css
··· 5 5 .conpherence-widget-pane { 6 6 position: fixed; 7 7 right: 0px; 8 - top: 125px; 8 + top: 124px; 9 9 width: 320px; 10 10 height: 100%; 11 11 border-width: 0 0 0 1px; ··· 21 21 } 22 22 23 23 .conpherence-widget-pane .widgets-header { 24 + background-color: #d8dce2; 25 + width: 320px; 26 + box-shadow: 0px 2px 2px rgba(0,0,0,0.15); 27 + } 28 + 29 + .conpherence-widget-pane .widgets-header .widgets-header-icon-holder { 24 30 height: 40px; 25 31 } 26 32 27 - .device-desktop .conpherence-widget-pane .widgets-header { 33 + .device-desktop .conpherence-widget-pane .widgets-header 34 + .widgets-header-icon-holder { 28 35 width: 196px; 29 36 margin: 0px auto 0px auto; 30 37 } ··· 32 39 .conpherence-widget-pane .widgets-header .sprite-conpherence { 33 40 display: block; 34 41 width: 29px; 35 - height: 33px; 42 + height: 34px; 36 43 margin: 4px 0px 0px 20px; 37 44 float: left; 38 45 clear: none; 39 46 } 40 47 48 + .conpherence-widget-pane .widgets-header .conpherence_list_on, 49 + .conpherence-widget-pane .widgets-header .conpherence_conversation_on, 50 + .conpherence-widget-pane .widgets-header .conpherence_people_on, 51 + .conpherence-widget-pane .widgets-header .conpherence_files_on, 52 + .conpherence-widget-pane .widgets-header .conpherence_calendar_on, 53 + .conpherence-widget-pane .widgets-header .conpherence_settings_on { 54 + border-bottom: 3px solid #525252; 55 + } 56 + 41 57 .device-desktop .conpherence-widget-pane .widgets-header 42 58 #widgets-conpherence-list-toggle, 43 59 .device-desktop .conpherence-widget-pane .widgets-header ··· 53 69 width: 320px; 54 70 } 55 71 56 - /* calendar widget */ 72 + /* files widget */ 57 73 58 - .conpherence-widget-pane #widgets-calendar { 74 + .conpherence-widget-pane #widgets-files .file-entry { 75 + padding: 12px 0px 14px 0px; 76 + width: 320px; 59 77 } 78 + .conpherence-widget-pane #widgets-files .file-icon { 79 + position: relative; 80 + top: 0px; 81 + left: 8px; 82 + width: 32px; 83 + height: 32px; 84 + float: left; 85 + } 86 + .conpherence-widget-pane #widgets-files .file-title { 87 + position: relative; 88 + top: -4px; 89 + left: 20px; 90 + font-weight: bold; 91 + } 92 + .conpherence-widget-pane #widgets-files .file-uploaded-by { 93 + color: #bfbfbf; 94 + position: relative; 95 + top: 0px; 96 + left: 20px; 97 + width: 270px; 98 + font-size: 11px; 99 + } 100 + 101 + .conpherence-widget-pane #widgets-files .file-extra { 102 + display: block; 103 + height: 120px; 104 + width: 160px; 105 + margin: 8px 0px 8px 52px; 106 + border: 1px solid rgb(24, 85, 157); 107 + } 108 + 109 + .conpherence-widget-pane #widgets-files .divider { 110 + float: left; 111 + clear: both; 112 + width: 242px; 113 + margin: 8px 0px 0px 52px; 114 + border: 1px dashed #bfbfbf; 115 + } 116 + 117 + /* calendar widget */ 60 118 61 119 .conpherence-widget-pane #widgets-calendar .user-status { 62 120 height: 60px;
-20
webroot/rsrc/js/application/conpherence/behavior-init.js
··· 1 - /** 2 - * @provides javelin-behavior-conpherence-init 3 - * @requires javelin-behavior 4 - * javelin-dom 5 - * javelin-stratcom 6 - */ 7 - JX.behavior('conpherence-init', function(config) { 8 - // select the current message 9 - var selectedConpherence = false; 10 - if (config.selected_conpherence_id) { 11 - var selected = JX.$(config.selected_conpherence_id + '-nav-item'); 12 - JX.Stratcom.invoke( 13 - 'conpherence-initial-selected', 14 - null, 15 - { selected : selected } 16 - ); 17 - selectedConpherence = true; 18 - } 19 - 20 - });
+13 -2
webroot/rsrc/js/application/conpherence/behavior-menu.js
··· 11 11 12 12 JX.behavior('conpherence-menu', function(config) { 13 13 14 - var root = JX.$(config.form_pane); 15 - 16 14 function onwidgetresponse(context, response) { 17 15 var widgets = JX.$H(response.widgets); 18 16 var widgetsRoot = JX.$(config.widgets_pane); ··· 112 110 113 111 JX.Stratcom.listen('click', 'conpherence-edit-metadata', function (e) { 114 112 e.kill(); 113 + var root = JX.$(config.form_pane); 115 114 var form = JX.DOM.find(root, 'form'); 116 115 var data = e.getNodeData('conpherence-edit-metadata'); 117 116 new JX.Workflow.newFromForm(form, data) ··· 144 143 .setData({offset: 100}) // get the next page 145 144 .send(); 146 145 }); 146 + 147 + // select the current message 148 + var selectedConpherence = false; 149 + if (config.selected_conpherence_id) { 150 + var selected = JX.$(config.selected_conpherence_id + '-nav-item'); 151 + JX.Stratcom.invoke( 152 + 'conpherence-initial-selected', 153 + null, 154 + { selected : selected } 155 + ); 156 + selectedConpherence = true; 157 + } 147 158 148 159 });