From 9dc73a3943b8038fec44bb61846952c2ae00cfea Mon Sep 17 00:00:00 2001 From: Stan Ozier Date: Sat, 17 Jul 2010 02:16:29 +0200 Subject: [PATCH] version 0.5 (1) --- DOCS/readme.txt | 2 +- DOCS/release.txt | 12 + DOCS/taskfreak_timer.sql | 4 +- app/config/app.php | 9 +- app/config/core.php | 12 +- app/config/db.php | 2 +- app/controller/admin.php | 3 - app/controller/iphone.php | 450 ++++++++++++ app/controller/task.php | 2 +- app/lang/de/freak.php | 120 ++++ app/lang/de/help_multi_creation.php | 19 + app/lang/de/help_timer_creation.php | 8 + app/lang/no/freak.php | 123 ++++ app/lang/no/help_multi_creation.php | 19 + app/lang/no/help_timer_creation.php | 8 + app/model/task.php | 50 +- app/model/timer.php | 4 +- app/view/admin/user-list.php | 2 +- app/view/include/page-bot.php | 2 +- app/view/iphone/edit.php | 22 + app/view/iphone/inc_foot.php | 9 + app/view/iphone/inc_main.php | 37 + app/view/iphone/inc_timer.php | 32 + app/view/iphone/login.php | 18 + app/view/iphone/main.php | 34 + app/view/iphone/view.php | 46 ++ app/view/iphone/view.server.php | 97 +++ asset/html/iphone-header.php | 30 + asset/html/page-header.php | 2 +- asset/jqtouch/jqtouch.css | 373 ++++++++++ asset/jqtouch/jqtouch.js | 676 +++++++++++++++++ asset/jqtouch/jqtouch.min.css | 1 + asset/jqtouch/jqtouch.min.js | 1 + asset/jqtouch/themes/apple/img/backButton.png | Bin 0 -> 783 bytes asset/jqtouch/themes/apple/img/blueButton.png | Bin 0 -> 517 bytes asset/jqtouch/themes/apple/img/cancel.png | Bin 0 -> 362 bytes asset/jqtouch/themes/apple/img/chevron.png | Bin 0 -> 259 bytes asset/jqtouch/themes/apple/img/grayButton.png | Bin 0 -> 943 bytes .../jqtouch/themes/apple/img/listArrowSel.png | Bin 0 -> 308 bytes asset/jqtouch/themes/apple/img/listGroup.png | Bin 0 -> 2863 bytes asset/jqtouch/themes/apple/img/loading.gif | Bin 0 -> 1435 bytes asset/jqtouch/themes/apple/img/on_off.png | Bin 0 -> 2634 bytes asset/jqtouch/themes/apple/img/pinstripes.png | Bin 0 -> 117 bytes asset/jqtouch/themes/apple/img/selection.png | Bin 0 -> 159 bytes asset/jqtouch/themes/apple/img/thumb.png | Bin 0 -> 2834 bytes asset/jqtouch/themes/apple/img/toggle.png | Bin 0 -> 2815 bytes asset/jqtouch/themes/apple/img/toggleOn.png | Bin 0 -> 163 bytes asset/jqtouch/themes/apple/img/toolButton.png | Bin 0 -> 521 bytes asset/jqtouch/themes/apple/img/toolbar.png | Bin 0 -> 168 bytes .../jqtouch/themes/apple/img/whiteButton.png | Bin 0 -> 978 bytes asset/jqtouch/themes/apple/theme.css | 677 ++++++++++++++++++ asset/jqtouch/themes/apple/theme.min.css | 1 + asset/jqtouch/themes/jqt/img/back_button.png | Bin 0 -> 3756 bytes .../themes/jqt/img/back_button_clicked.png | Bin 0 -> 3741 bytes asset/jqtouch/themes/jqt/img/button.png | Bin 0 -> 3315 bytes .../jqtouch/themes/jqt/img/button_clicked.png | Bin 0 -> 3283 bytes asset/jqtouch/themes/jqt/img/chevron.png | Bin 0 -> 3074 bytes .../jqtouch/themes/jqt/img/chevron_circle.png | Bin 0 -> 1243 bytes asset/jqtouch/themes/jqt/img/grayButton.png | Bin 0 -> 943 bytes asset/jqtouch/themes/jqt/img/loading.gif | Bin 0 -> 2536 bytes asset/jqtouch/themes/jqt/img/on_off.png | Bin 0 -> 2496 bytes asset/jqtouch/themes/jqt/img/rowhead.png | Bin 0 -> 171 bytes asset/jqtouch/themes/jqt/img/toggle.png | Bin 0 -> 2815 bytes asset/jqtouch/themes/jqt/img/toggleOn.png | Bin 0 -> 163 bytes asset/jqtouch/themes/jqt/img/toolbar.png | Bin 0 -> 805 bytes asset/jqtouch/themes/jqt/img/whiteButton.png | Bin 0 -> 978 bytes asset/jqtouch/themes/jqt/theme.css | 528 ++++++++++++++ asset/jqtouch/themes/jqt/theme.min.css | 1 + asset/js/iphone.js | 268 +++++++ lib/class/app.php | 25 +- lib/class/db_connector.php | 4 +- lib/class/model.php | 25 +- lib/helper/auth.php | 16 +- lib/helper/db.php | 27 +- lib/helper/html_asset.php | 18 +- lib/helper/html_form.php | 31 +- lib/helper/json.php | 31 + lib/helper/string.php | 24 + lib/lang/de/common.php | 250 +++++++ lib/lang/de/config.php | 15 + lib/lang/en/common.php | 2 +- lib/lang/no/common.php | 250 +++++++ lib/lang/no/config.php | 15 + lib/model/page.php | 6 +- skin/default/css/iphone.css | 168 +++++ skin/default/img/darkButton.png | Bin 0 -> 1324 bytes skin/default/img/iphone_icon.png | Bin 0 -> 2898 bytes skin/default/img/iphone_startup.png | Bin 0 -> 12323 bytes skin/default/img/lightButton.png | Bin 0 -> 1328 bytes 89 files changed, 4546 insertions(+), 65 deletions(-) create mode 100644 app/controller/iphone.php create mode 100644 app/lang/de/freak.php create mode 100644 app/lang/de/help_multi_creation.php create mode 100644 app/lang/de/help_timer_creation.php create mode 100755 app/lang/no/freak.php create mode 100755 app/lang/no/help_multi_creation.php create mode 100755 app/lang/no/help_timer_creation.php create mode 100644 app/view/iphone/edit.php create mode 100644 app/view/iphone/inc_foot.php create mode 100644 app/view/iphone/inc_main.php create mode 100644 app/view/iphone/inc_timer.php create mode 100644 app/view/iphone/login.php create mode 100644 app/view/iphone/main.php create mode 100644 app/view/iphone/view.php create mode 100644 app/view/iphone/view.server.php create mode 100644 asset/html/iphone-header.php create mode 100644 asset/jqtouch/jqtouch.css create mode 100644 asset/jqtouch/jqtouch.js create mode 100644 asset/jqtouch/jqtouch.min.css create mode 100644 asset/jqtouch/jqtouch.min.js create mode 100644 asset/jqtouch/themes/apple/img/backButton.png create mode 100644 asset/jqtouch/themes/apple/img/blueButton.png create mode 100644 asset/jqtouch/themes/apple/img/cancel.png create mode 100644 asset/jqtouch/themes/apple/img/chevron.png create mode 100644 asset/jqtouch/themes/apple/img/grayButton.png create mode 100644 asset/jqtouch/themes/apple/img/listArrowSel.png create mode 100644 asset/jqtouch/themes/apple/img/listGroup.png create mode 100644 asset/jqtouch/themes/apple/img/loading.gif create mode 100644 asset/jqtouch/themes/apple/img/on_off.png create mode 100644 asset/jqtouch/themes/apple/img/pinstripes.png create mode 100644 asset/jqtouch/themes/apple/img/selection.png create mode 100644 asset/jqtouch/themes/apple/img/thumb.png create mode 100644 asset/jqtouch/themes/apple/img/toggle.png create mode 100644 asset/jqtouch/themes/apple/img/toggleOn.png create mode 100644 asset/jqtouch/themes/apple/img/toolButton.png create mode 100644 asset/jqtouch/themes/apple/img/toolbar.png create mode 100644 asset/jqtouch/themes/apple/img/whiteButton.png create mode 100644 asset/jqtouch/themes/apple/theme.css create mode 100644 asset/jqtouch/themes/apple/theme.min.css create mode 100644 asset/jqtouch/themes/jqt/img/back_button.png create mode 100644 asset/jqtouch/themes/jqt/img/back_button_clicked.png create mode 100644 asset/jqtouch/themes/jqt/img/button.png create mode 100644 asset/jqtouch/themes/jqt/img/button_clicked.png create mode 100644 asset/jqtouch/themes/jqt/img/chevron.png create mode 100644 asset/jqtouch/themes/jqt/img/chevron_circle.png create mode 100644 asset/jqtouch/themes/jqt/img/grayButton.png create mode 100644 asset/jqtouch/themes/jqt/img/loading.gif create mode 100644 asset/jqtouch/themes/jqt/img/on_off.png create mode 100644 asset/jqtouch/themes/jqt/img/rowhead.png create mode 100644 asset/jqtouch/themes/jqt/img/toggle.png create mode 100644 asset/jqtouch/themes/jqt/img/toggleOn.png create mode 100644 asset/jqtouch/themes/jqt/img/toolbar.png create mode 100644 asset/jqtouch/themes/jqt/img/whiteButton.png create mode 100644 asset/jqtouch/themes/jqt/theme.css create mode 100644 asset/jqtouch/themes/jqt/theme.min.css create mode 100644 asset/js/iphone.js create mode 100644 lib/helper/json.php create mode 100644 lib/lang/de/common.php create mode 100644 lib/lang/de/config.php create mode 100755 lib/lang/no/common.php create mode 100755 lib/lang/no/config.php create mode 100644 skin/default/css/iphone.css create mode 100644 skin/default/img/darkButton.png create mode 100644 skin/default/img/iphone_icon.png create mode 100644 skin/default/img/iphone_startup.png create mode 100644 skin/default/img/lightButton.png diff --git a/DOCS/readme.txt b/DOCS/readme.txt index 72b76c0..f3778aa 100644 --- a/DOCS/readme.txt +++ b/DOCS/readme.txt @@ -1,6 +1,6 @@ TaskFreak! Time Tracking ------------------------ -version : 0.4 +version : 0.5 Requirements diff --git a/DOCS/release.txt b/DOCS/release.txt index 35fd667..f4c6878 100644 --- a/DOCS/release.txt +++ b/DOCS/release.txt @@ -1,6 +1,18 @@ TaskFreak! Time Tracking ------------------------ +Version 0.5 : 2010-07-16 +------------------------ +Added iphone (beta) version +Added german translation +Added norwegian translation +Added missing time zones +Fixed time difference bug with time zones not GMT +Fixed multi task creation bug +Fixed windows server file path bug +Fixed bug on user creation + + Version 0.4 : 2010-06-11 ------------------------ Added multi language support diff --git a/DOCS/taskfreak_timer.sql b/DOCS/taskfreak_timer.sql index 5869fe2..80a9481 100644 --- a/DOCS/taskfreak_timer.sql +++ b/DOCS/taskfreak_timer.sql @@ -56,8 +56,8 @@ CREATE TABLE IF NOT EXISTS `task` ( KEY `member_id` (`member_id`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8; -INSERT INTO `task` VALUES(1, 'taskfreak : README first about this beta version', 'Please keep in mind that this is a beta version. There are quite a few known bugs, a handful of unknown bugs.\r\n\r\nHere''s what you can do so far :\r\n- create, edit and archive tasks\r\n- start and stop task timers\r\n- report time spent on a task\r\n- edit your own profile\r\n- see other''s tasks (task manager only)\r\n- create and edit users (user admin only)\r\n\r\nMake sure you read the README file under the DOCS/ folder. There''s a few setup tips in there.', 5, '9999-00-00', '2010-06-11', 0, 0, 1); -INSERT INTO `task` VALUES(2, 'taskfreak : quick notes about TT 0.4', 'Here''s the list of known bugs at release time :\r\n- some errors might occur on dates depending on your time zone\r\n- order by start, stop, or spent doesn''t really make sense\r\n- very buggy under IE8, and simply unusable with older versions of IE\r\n\r\nPlease report found bugs here :\r\nhttp://forum.taskfreak.com/index.php?board=7.0', 4, '9999-00-00', '9999-00-00', 0, 0, 1); +INSERT INTO `task` VALUES(1, 'taskfreak : README first about this beta version', 'Please keep in mind that this is a beta version. There are quite a few known bugs, a handful of unknown bugs.\r\n\r\nHere''s what you can do so far :\r\n- create, edit and archive tasks\r\n- start and stop task timers\r\n- report time spent on a task\r\n- edit your own profile\r\n- see other''s tasks (task manager only)\r\n- create and edit users (user admin only)\r\n\r\nMake sure you read the README file under the DOCS/ folder. There''s a few setup tips in there.', 5, '9999-00-00', '2010-07-17', 0, 0, 1); +INSERT INTO `task` VALUES(2, 'taskfreak : quick notes about TT 0.5', 'Here''s the list of known bugs at release time :\r\n- iphone version is slow and not full featured yet\r\n- order by start, stop, or spent doesn''t really make sense\r\n- very buggy under IE8, and simply unusable with older versions of IE\r\n\r\nPlease report found bugs here :\r\nhttp://forum.taskfreak.com/index.php?board=7.0', 4, '9999-00-00', '9999-00-00', 0, 0, 1); CREATE TABLE IF NOT EXISTS `timer` ( `task_id` int(10) unsigned NOT NULL, diff --git a/app/config/app.php b/app/config/app.php index 83e0fff..9580124 100644 --- a/app/config/app.php +++ b/app/config/app.php @@ -3,10 +3,10 @@ // ---- LOG and DEBUGGING ----------------------------------------------------- $GLOBALS['config']['log_front'] = 0; -$GLOBALS['config']['log_debug'] = 0; +$GLOBALS['config']['log_debug'] = 1; $GLOBALS['config']['log_message'] = 0; $GLOBALS['config']['log_warn'] = 0; -$GLOBALS['config']['log_error'] = 1; +$GLOBALS['config']['log_error'] = 2; $GLOBALS['config']['log_core'] = 0; $GLOBALS['config']['log_signature'] = '[TF]'; @@ -44,10 +44,13 @@ define("APP_DATETIME","%d/%m %H:%M"); // --- TASKFREAK DEFAULTS --------------------------------------------------------- $GLOBALS['config']['task'] = array( - 'date' => APP_SQL_TODAY, // default date is today + 'date' => 'now', // default date is today 'validate' => true // add validation button ); +// note for default date : +// can be any PHP valid date eg. +1 days, +1 week, or false for no date + $GLOBALS['config']['task']['priority'] = array( 'options' => array( 1 => 'urgent', diff --git a/app/config/core.php b/app/config/core.php index dbad8da..96ae524 100644 --- a/app/config/core.php +++ b/app/config/core.php @@ -125,6 +125,8 @@ define("APP_DATETIME_LNG","%d %B %Y, %H:%M"); define("APP_DATETIME_LNX","%A %d %B %Y, %H:%M"); define("APP_DATETIME_HRS","%H:%M"); +define('APP_DATE_RFC822', '%a, %d %b %Y %H:%M:%S %z'); + // date_default_timezone_set('Europe/Paris'); define('APP_TIMEZONE_SERVER',date_default_timezone_get()); define('APP_TZSERVER',intval(date('Z'))); @@ -153,4 +155,12 @@ if (@constant('APP_TRANS_ID')) { } else { ini_set('session.use_trans_sid', 0); ini_set('session.use_only_cookies', 1); -} \ No newline at end of file +} + +// ---- AGENT DETECTION ------------------------------------------------------- + +define('APP_ROBOT_AGENT', 'Google|msnbot|Rambler|Yahoo|AbachoBOT|accoona|AcioRobot|ASPSeek|' + .'CocoCrawler|Dumbot|FAST\-WebCrawler|GeonaBot|Gigabot|Lycos|MSRBOT|Scooter|' + .'AltaVista|IDBot|eStyle|Scrubby'); + +define('APP_IPHONE_AGENT', 'iPhone|iPod|iPad'); \ No newline at end of file diff --git a/app/config/db.php b/app/config/db.php index bc48e8f..6aa7ee3 100644 --- a/app/config/db.php +++ b/app/config/db.php @@ -1,7 +1,7 @@ fc->chkReqVar('pass1') && $this->fc->chkReqVar('pass2')) { if ($this->data->setPassword($this->fc->getReqVar('pass1'), $this->fc->getReqVar('pass2'))) { // save it all - error_log('setting new password : '.$this->fc->getReqVar('pass1')); $this->data->ignore(); } else { // do not save password - error_log('can not save password'); $this->data->ignore('password,salt'); } } @@ -116,7 +114,6 @@ class Admin extends AppController { if ($this->data->save(!$myself)) { if ($myself) { // editing own profile need to reset session - error_log('updating session'); $this->data->updateSessionVariables(); } $this->fc->autoRedirect('saved'); diff --git a/app/controller/iphone.php b/app/controller/iphone.php new file mode 100644 index 0000000..942d42e --- /dev/null +++ b/app/controller/iphone.php @@ -0,0 +1,450 @@ + + * @version 0.5 + * @copyright GNU General Public License (GPL) version 3 + */ + +/** + * iphone + * + * iphone version + * @since 0.5 + */ +class Iphone extends AppController { + + public function __construct() { + parent::__construct(false, true); + // parent::__construct(false, true); + + $this->fc->loadModel('TaskModel'); + + // $this->page->clean('css'); + // $this->page->clean('js'); + $GLOBALS['config']['path']['css'][] = 'asset/jqtouch/'; + $GLOBALS['config']['path']['css'][] = 'asset/jqtouch/themes/jqt/'; + $GLOBALS['config']['path']['js'][] = 'asset/jqtouch/'; + + $this->page->add('css',array('jqtouch.min.css','theme.css','iphone.css')); + // $this->page->add('js',array('jquery.form.min.js','jquery.colorbox-min.js')); + $this->page->add('js',array('jqtouch.js','iphone.js')); + $jsCode = "var APP_LOGOUT='". $this->fc->getUrl('iphone','logout')."';\n"; + $jsCode .= "var APP_RELOAD='". $this->fc->getUrl('iphone','home')."';\n"; + $jsCode .= "var APP_VIEW='". $this->fc->getUrl('iphone','detail',array('id'=>''))."';\n"; + $jsCode .= "var APP_EDIT='". $this->fc->getUrl('iphone','edit',array('id'=>''))."';\n"; + $jsCode .= "var jQT = new $.jQTouch({ + icon: '".APP_WWW_URI.'skin/'.$GLOBALS['config']['skin']."/img/iphone_icon.png', + addGlossToIcon: false, + startupScreen: '".APP_WWW_URI.'skin/'.$GLOBALS['config']['skin']."/img/iphone_startup.png', + statusBar: 'black', + formSelector: '.form', + touchSelector: '.button, .back, .cancel, .add, .touch', + preloadImages: [ + '".APP_WWW_URI."asset/jqtouch/themes/jqt/img/back_button.png', + '".APP_WWW_URI."asset/jqtouch/themes/jqt/img/back_button_clicked.png', + '".APP_WWW_URI."asset/jqtouch/themes/jqt/img/button_clicked.png', + '".APP_WWW_URI."asset/jqtouch/themes/jqt/img/grayButton.png', + '".APP_WWW_URI."asset/jqtouch/themes/jqt/img/whiteButton.png', + '".APP_WWW_URI."skin/".$GLOBALS['config']['skin']."/img/lightButton.png', + '".APP_WWW_URI."skin/".$GLOBALS['config']['skin']."/img/darkButton.png', + '".APP_WWW_URI."asset/jqtouch/themes/jqt/img/loading.gif' + ] + });"; + $this->page->add('jsCode',$jsCode); + } + + /** + * main menu (list tasks) + */ + public function mainAction() { + + $this->_loadHomeView(); + + $this->page->set('title','TaskFreak! Time Tracking'); + $this->setView('iphone/main'); + $this->viewIPhone(); + } + + /** + * main menu (list tasks) + */ + public function homeAction() { + + $this->_loadHomeView(); + + $this->incView('iphone/inc_main'); + $this->incList('list-st0',TR::html('pages','todo'),$this->dataTodo); + $this->incList('list-st1',TR::html('pages','done'),$this->dataDone); + $this->incList('list-st2',TR::html('pages','valid'),$this->dataValid); + } + + /** + * reacts to current task actions + */ + public function homeReaction() { + // error_log('lets '.$this->fc->getReqVar('action').' on '.$this->fc->getReqVar('id')); + return $this->_taskStatus(); + } + + /** + * list tasks for a specific tag + */ + public function listAction() { + + $this->_checkLogin(true); + + if ($tag = $this->fc->getReqVar('tag')) { + $data = $this->_loadTaskList("title LIKE '$tag%'"); + $this->incList('list-'.StringHelper::cleanStrip($tag), $tag, $data); + return true; + } + + // reaching this point means error has occured + header('HTTP/1.0 404 Not Found'); + + } + + /** + * display task details + */ + public function detailAction() { + $this->_checkLogin(true); + sleep(1); + // load current running task to check if it's actually running + $this->current = TaskSummary::loadCurrent(); + // load task full details and history + $this->_loadTaskSummary(true); + $data = $this->data->exportData(); + $data['running'] = ($this->current && ($this->current->getUid() == $this->data->getUid()))?true:false; + header('Content-type: application/json'); + echo json_encode($data); + } + + /** + * reacts to displayed task actions + */ + public function detailReaction() { + return $this->_taskStatus(); + } + + /** + * edit task (sends back data in JSON format) + */ + public function editAction() { + $this->_checkLogin(true); + sleep(1); + $this->_loadTask(false); + $this->edit->addHelper('json'); + header('Content-type: application/json'); + echo $this->edit->export('value'); + } + + /** + * save task (form reaction) + */ + public function editReaction() { + $this->_checkLogin(true); + $this->_loadTask(false); + $this->edit->ignore('creation_date'); // do not submit or change creation date + $this->edit->set($this->fc->request); + if ($this->edit->check($this->fc->user->getUid())) { + $this->edit->save(); + } + echo ''; + /* + // send back list of tasks for this status + $status = $this->edit->get('status'); + $data = $this->_loadTaskList("status=$status"); + $arr = array_keys($GLOBALS['lang']['pages']); + $this->incList('list-st'.$status, TR::html('pages',$arr[$status]), $data); + */ + } + + /** + * display task timer history + */ + public function historyAction() { + } + + /** + * displays new timer form + */ + public function timerAction() { + } + + /** + * reacts to timer form + */ + public function timerReaction() { + } + + /** + * login on iphone + */ + public function loginAction() { + $this->fc->user->addHelper('html_form'); + $this->page->set('title','TaskFreak! '.TR::get('security','login')); + $this->setView('iphone/login'); + $this->viewIPhone(); + } + + /** + * Logs user in + * @todo redirect to requested page + */ + public function loginReaction() { + $this->fc->user->fields('username,password'); + $this->fc->user->set($this->fc->request); + if ($this->fc->user->login($this->fc->user->get('username'), $this->fc->user->get('password'))) { + $this->fc->user->setAutoLogin(); + header('HTTP/1.0 200 OK'); + $this->homeAction(); + } else { + header('HTTP/1.0 403 Forbidden'); + } + return false; + } + + /** + * Logs user out + * @todo show logout summary page + */ + public function logoutAction() { + $this->fc->user->logout(); + // NaviHelper::redirect($this->fc->getUrl('iphone','main')); + // echo ''; + return false; + } + + /** + * check if user is logged in + * sends back a 403 if user is not allowed + */ + protected function _checkLogin($exit) { + if (!$this->fc->user->isLoggedIn()) { + if ($exit) { + header('HTTP/1.0 403 Forbidden'); + exit; + } + return false; + } + return true; + } + + /** + * change task status + */ + protected function _taskStatus() { + $this->current = TaskSummary::loadCurrent(); + + $arrReload = array(); + + if ($id = $this->fc->getReqVar('id')) { + if ($this->current && $this->current->getUid() != $id) { + // we have a running task, but it's not the requested one + // so first, we need to stop it. + $cid = $this->current->getUid(); + TimerModel::stop($cid); + // and we'll have to reload the page details later + $arrReload[] = $cid; + } else { + $this->current = new TaskSummary(); + $this->current->connectDb(); + $this->current->setUid($id); + $this->current->load(); + } + + if ($this->current->getUid()) { + // -TODO- check rights + switch($this->fc->getReqVar('action')) { + case 'pause': + // try to pause + if ($this->current && $this->current->getUid() == $id) { + // ok, task is actually running + TimerModel::stop($id); + $this->current->set('stop',APP_SQL_NOW); + $this->jsCode .= ""; + } else { + // nope, requested task is not running, show error + FC::log_debug('error trying to pause non running task'); + header('HTTP/1.0 403 Forbidden'); + exit; + } + $this->setView('iphone/inc_timer'); + $this->viewRaw(); + break; + case 'resume': + case 'start': + TimerModel::start($id); + $this->current = TaskSummary::loadCurrent(); + $this->jsCode = "clockstart();"; + $this->setView('iphone/inc_timer'); + $this->viewRaw(); + break; + case 'stop': + if (TimerModel::stop($id)) { + $this->jsCode = "clockstatus();"; + } else { + $this->jsCode = "alert('".TR::get('error','action_failed')."');"; + } + $this->current = false; + break; + case 'close': + if (TimerModel::stop($id)) { + $this->jsCode = "clockstatus();"; + $this->current->updateStatus(1); // mark as done + $this->current = false; + } + break; + } + // need to reload newly modified task details + $arrReload[] = $id; + } + + return false; + } + + // reaching this point means an error has occured + header('HTTP/1.0 404 Not Found'); + exit; + } + + /** + * load home screen + */ + protected function _loadHomeView() { + + $this->edit = new TaskModel(); + $this->edit->addHelper('html_form'); + + if (!$this->_checkLogin(false)) { + return false; + } + $this->current = TaskSummary::loadCurrent(); + + $this->dataTodo = $this->_loadTaskList('status=0'); + $this->dataDone = $this->_loadTaskList('status=1'); + $this->dataValid = $this->_loadTaskList('status=2'); + + /* + $db = DbHelper::factory(); + $db->select("DISTINCT (SUBSTRING_INDEX( title, ':', 1 )) as tag"); + $db->from('task'); + $db->where("title LIKE '%:%'"); + $this->dataTags = $db->loadRaw(); + */ + + return true; + } + + /** + * load task + */ + protected function _loadTask($exit) { + + if (isset($this->edit) && is_a($this->edit, 'TaskModel')) { + // task already loaded + return true; + } + + $this->edit = new TaskModel(); + $this->edit->connectDb(); + + if ($id = $this->fc->getReqVar('id')) { + $this->edit->setUid($id); + if ($this->edit->load()) { + return true; + } + } + + // reaching this point means error has occured + if ($exit) { + header('HTTP/1.0 404 Not Found'); + exit; + } + return false; + } + + /** + * load task with timer info + */ + protected function _loadTaskSummary($exit) { + + if (isset($this->data) && is_a($this->data, 'TaskSummary') && ($this->data->getUid())) { + // task already loaded + return true; + } + + $this->data = new TaskSummary(); + $this->data->connectDb(); + + $ok = false; + if ($id = $this->fc->getReqVar('id')) { + $this->data->where('id='.$id); + $this->data->orderBy('start ASC'); + if ($this->data->loadExpandList()) { + if ($this->data->next()) { + $this->data->chkDeadline(); + return true; + } + } + } + + // reaching this point means error has occured + if ($exit) { + header('HTTP/1.0 404 Not Found'); + exit; + } + return false; + } + + /** + * load task list + */ + protected function _loadTaskList($filter) { + $data = new TaskSummary(); + $data->connectDb(); + $data->where($filter); + $data->where('archived=0'); + $data->where('member_id='.$this->fc->user->getUid()); + $data->orderBy('status ASC, deadline ASC, priority ASC, title ASC, start ASC'); + $data->loadCompactList(); + return $data; + } + + /** + * view list + */ + protected function incList($name, $title, &$data) { + echo '
'; + echo '
'; + echo '

'.$title.'

'; + echo 'Back'; + echo 'New'; + echo '
'; + if ($data) { + echo ''; + } else { + echo ''; + } + // echo ''; + echo '
'; + } +} \ No newline at end of file diff --git a/app/controller/task.php b/app/controller/task.php index ed674b7..9330ad4 100644 --- a/app/controller/task.php +++ b/app/controller/task.php @@ -18,7 +18,7 @@ class Task extends AppController { public function __construct() { parent::__construct(true); - + $this->fc->setSessionDefault('order','deadline'); $this->fc->setSessionDefault('limit',$GLOBALS['config']['task']['pagination_default']); if (APP_SETUP_USER_MODEL) { diff --git a/app/lang/de/freak.php b/app/lang/de/freak.php new file mode 100644 index 0000000..18c007b --- /dev/null +++ b/app/lang/de/freak.php @@ -0,0 +1,120 @@ + 'Priorität', + 'spent' => 'aufgewendet', + 'note' => 'notieren', + 'todo' => 'zu erledigen', + 'done' => 'erledigt', + 'valid' => 'gültig', + 'archived' => 'archiviert', + 'running' => 'laufend', + 'paused' => 'pausiert' +); + +$GLOBALS['lang']['priority'] = array( + 'urgent' => 'dringend', + 'important' => 'wichtig', + 'high' => 'hoch', + 'quickly' => 'schnell', + 'pretty_soon' => 'sehr bald', + 'soon' => 'bald', + 'normal' => 'normal', + 'after' => 'nach', + 'later' => 'später', + 'low' => 'niedrig', + 'anytime' => 'irgendwann', + 'whenever' => 'wann immer' +); + +$GLOBALS['lang']['ui'] = array( + 'reload' => 'neu laden', + 'reload_list' => 'Liste neu laden', + 'task' => 'Aufgabe', + 'tasks' => 'Aufgaben', + 'create_single' => 'Einzelne Aufgabe erstellen', + 'create_multi' => 'Mehrere Aufgaben erstellen', + 'edit_task' => 'Aufgabe bearbeiten', + 'delete_task' => 'Aufgabe löschen', + 'start_task' => 'Aufgabe starten', + 'mark_archived' => 'Aufgabe als archiviert markieren', + 'done_confirm' => 'verschieben und diese Aufgabe wirklich als beendet markieren ?', + 'compact' => 'kompakt', + 'expand' => 'Ausklappen', + 'select_all' => 'Alle auswählen', + 'info' => 'Info', + 'history' => 'Verlauf', + 'history_empty' => 'Bisher noch keine Zeitberichte', + 'report_spent' => 'Bericht über Zeitaufwand', + 'total' => 'insgesamt', + 'user_menu' => 'Benutzermenü anzeigen', + 'admin' => 'Admin', + 'settings' => 'Einstellungen', + 'all_users' => 'Alle Benutzer', + 'switch' => 'Wechseln', + 'switch_user' => 'Aufgaben anderer Benutzer anzeigen', + 'select_user' => 'Wählen Sie den Benutzer, dessen Aufgaben Sie sehen möchten', + 'switched' => 'Zu anderem Benutzer gewechselt', + 'task_manager' => 'Aufgaben-Manager', + 'task_managers' => 'Aufgaben-Manager', + 'user_admin' => 'Benutzeradministrator', + 'user_admins' => 'Benutzeradministratoren', + 'last_visit' => 'Letzter Besuch', + 'preferences' => 'Meine Präferenzen', + 'create_user' => 'Benutzer erstellen', + 'edit_user' => 'Benutzer bearbeiten', + 'delete_user' => 'Benutzer löschen' +); + +$GLOBALS['lang']['pages'] = array( + 'todo' => 'Zu erledigen', + 'done' => 'Erledigt', + 'valid' => 'Gültig', + 'archives' => 'Archiv', + 'edit_task' => 'Aufgabe bearbeiten', + 'create_task' => 'Aufgabe erstellen', + 'create_tasks' => 'Mehrere Aufgaben erstellen', + 'view_task' => 'Aufgaben-Details' +); + +$arrMess = array( + 'task_created' => 'Aufgabe erstellt', + 'task_updated' => 'Aufgabe aktualisiert', + '%_task_created' => '% Aufgabe(n) erstellt', + 'task_deleted' => 'Aufgabe gelöscht', + 'time_added' => 'Berichtete Arbeitszeit' +); + +$GLOBALS['lang']['message'] = $GLOBALS['lang']['message']+$arrMess; + +$arrButton = array( + 'pause' => 'Pause', + 'resume' => 'Fortfahren', + 'done' => 'Erledigt', + 'reopen' => 'Wiedereröffnen', + 'postpone_1_day' => 'Um 1 Tag verschieben', + 'postpone_2_days' => 'Um 2 Tage verschieben', + 'postpone_1_week' => 'Um 1 Woche verschieben', + 'postpone_2_weeks' => 'Um 2 Wochen verschieben', + 'postpone_1_month' => 'Um 1 Monat verschieben', + 'postpone_2_months' => 'Um 2 Monate verschieben', + 'postpone_1_year' => 'Um 1 Jahr verschieben', + 'postpone_2_years' => 'Um 2 Jahre verschieben', + 'mark_done' => 'Als erledigt markieren', + 'validate' => 'Überprüfen', + 'archive' => 'archivieren', + 'unarchive' => 'Archivierung rückgängig machen', + 'save_report' => 'Bericht speichern', + 'save_task' => 'Aufgabe speichern', + 'save_and_start' => 'Speichern und starten' +); + +$GLOBALS['lang']['button'] = $GLOBALS['lang']['button']+$arrButton; diff --git a/app/lang/de/help_multi_creation.php b/app/lang/de/help_multi_creation.php new file mode 100644 index 0000000..fc79d0a --- /dev/null +++ b/app/lang/de/help_multi_creation.php @@ -0,0 +1,19 @@ +

Geben Sie eine Aufgabe pro Zeile ein.

+

Aufgaben-Format

+

Aufgaben-Format : [date] [priority] [label :] Aufgaben-Titel
+Felder in Klammern sind optional

+

Datum kann sein :

+ +

Priorität ist eine Zahl zwischen 1 und 9, gefolgt von einer )
+« 1) » für dringende Aufgaben, « 5) » für normale Priorität

+

Bezeichnung ist optional

+

Standards für mehrere Aufgaben

+

eine Zeile angefangen mit einem * richtet Standards ein

+

Format ist : * [date] [label]
+« * +1 Aufgabe » der « * 12/04 »

+

Standards zurücksetzen durch eine Zeile mit « ** »

diff --git a/app/lang/de/help_timer_creation.php b/app/lang/de/help_timer_creation.php new file mode 100644 index 0000000..629a023 --- /dev/null +++ b/app/lang/de/help_timer_creation.php @@ -0,0 +1,8 @@ +

Geben Sie eine der folgenden Möglichkeiten ein:

+ diff --git a/app/lang/no/freak.php b/app/lang/no/freak.php new file mode 100755 index 0000000..3ea8c68 --- /dev/null +++ b/app/lang/no/freak.php @@ -0,0 +1,123 @@ + + * @version 0.4 + * @copyright GNU General Public License (GPL) version 3 + * + * @languagePack Norwegian | Norsk + * @translator Hans Hovde + */ + +$GLOBALS['lang']['task'] = array( + 'priority' => 'prioritet', + 'spent' => 'brukt', + 'note' => 'notat', + 'todo' => 'oppgave', + 'done' => 'ferdig', + 'valid' => 'gyldig', + 'archived' => 'oppnådd', + 'running' => 'kjører', + 'paused' => 'pauset' +); + +$GLOBALS['lang']['priority'] = array( + 'urgent' => 'Kritisk', + 'important' => 'Høyeste', + 'high' => 'Høyere', + 'quickly' => 'Høy', + 'pretty_soon' => 'Ganske snart', + 'soon' => 'Snart', + 'normal' => 'Normal', + 'after' => 'Lav', + 'later' => 'Lavere', + 'low' => 'Laverste', + 'anytime' => 'Når tid', + 'whenever' => 'Uviktig' +); + +$GLOBALS['lang']['ui'] = array( + 'reload' => 'reload', + 'reload_list' => 'reload list', + 'task' => 'oppgave', + 'tasks' => 'oppgaver', + 'create_single' => 'lag en oppgave', + 'create_multi' => 'lag flere oppgaver', + 'edit_task' => 'endre oppgave', + 'delete_task' => 'slett oppgave', + 'start_task' => 'start oppgave', + 'mark_archived' => 'merk oppgave som arkivert', + 'done_confirm' => 'er du sikker på at du vil merke oppgaven som ferdig ?', + 'compact' => 'minimer', + 'expand' => 'maksimer', + 'select_all' => 'velg alle', + 'info' => 'info', + 'history' => 'historie', + 'history_empty' => 'ingen tidsrapporter enda', + 'report_spent' => 'rapporter brukt tid', + 'total' => 'total', + 'user_menu' => 'vis brukermeny', + 'admin' => 'admin', + 'settings' => 'instillinger', + 'all_users' => 'alle brukere', + 'switch' => 'bytt', + 'switch_user' => 'se andre brukeres oppgaver', + 'select_user' => 'velg bruker du vil se oppgaver til', + 'switched' => 'bytt til en annen bruker', + 'task_manager' => 'oppgave behandling', + 'task_managers' => 'oppgave behandlinger', + 'user_admin' => 'bruker administrator', + 'user_admins' => 'bruker administratorer', + 'last_visit' => 'siste besøk', + 'preferences' => 'mine instillinger', + 'create_user' => 'lag bruker', + 'edit_user' => 'endre bruker', + 'delete_user' => 'slett bruker' +); + +$GLOBALS['lang']['pages'] = array( + 'todo' => 'oppgave', + 'done' => 'ferdig', + 'valid' => 'gyldig', + 'archives' => 'arkiv', + 'edit_task' => 'endre oppgave', + 'create_task' => 'lag oppgave', + 'create_tasks' => 'lag flere oppgaver', + 'view_task' => 'oppgave detaljer' +); + +$arrMess = array( + 'task_created' => 'oppgave opprettet', + 'task_updated' => 'oppgave oppdatert', + '%_task_created' => '% oppgave(r) opprettet', + 'task_deleted' => 'oppgave slettet', + 'time_added' => 'arbeidstid registrert' +); +// we're adding these translations to the standard messages translations +$GLOBALS['lang']['message'] = $GLOBALS['lang']['message']+$arrMess; + +$arrButton = array( + 'pause' => 'pause', + 'resume' => 'fortsett', + 'done' => 'ferdig', + 'reopen' => 'åpne på nytt', + 'postpone_1_day' => 'utsett 1 dag', + 'postpone_2_days' => 'utsett 2 dager', + 'postpone_1_week' => 'utsett 1 uke', + 'postpone_2_weeks' => 'utsett 2 uker', + 'postpone_1_month' => 'utsett 1 måned', + 'postpone_2_months' => 'utsett 2 måneder', + 'postpone_1_year' => 'utsett 1 år', + 'postpone_2_years' => 'utsett 2 år', + 'mark_done' => 'marker som ferdig', + 'validate' => 'valider', + 'archive' => 'arkiver', + 'unarchive' => 'gjenopprett', + 'save_report' => 'lagre rapport', + 'save_task' => 'lagre oppgave', + 'save_and_start' => 'lagre og start' +); +// we're adding these translations to the standard button translations +$GLOBALS['lang']['button'] = $GLOBALS['lang']['button']+$arrButton; \ No newline at end of file diff --git a/app/lang/no/help_multi_creation.php b/app/lang/no/help_multi_creation.php new file mode 100755 index 0000000..d48ee1c --- /dev/null +++ b/app/lang/no/help_multi_creation.php @@ -0,0 +1,19 @@ +

Skriv en oppgave pr. linje.

+

Oppgave format:

+

Oppgave format : [dato] [prioritet] [label :] oppgave overskrift
+felter innenfor [rammer] er frivillig

+

dato kan være :

+ +

prioritet er et nummer mellom 1 og 9, etterfulgt av )
+« 1) » for kritiske gjøremÃ¥l, « 5) » for normal prioritet

+

label er valgfri

+

Standarder for flere oppgaver

+

en linje som starter med * angir standard verdi

+

Formatet er : * [dato] [label]
+« * +1 taskfreak » eller « * 12/04 »

+

tilbakestill standarder med en linje som starter med « ** »

\ No newline at end of file diff --git a/app/lang/no/help_timer_creation.php b/app/lang/no/help_timer_creation.php new file mode 100755 index 0000000..128db0f --- /dev/null +++ b/app/lang/no/help_timer_creation.php @@ -0,0 +1,8 @@ +

Skriv enten :

+ \ No newline at end of file diff --git a/app/model/task.php b/app/model/task.php index c4d800f..f45306f 100644 --- a/app/model/task.php +++ b/app/model/task.php @@ -4,7 +4,7 @@ * * @package taskfreak_tt * @author Stan Ozier - * @version 0.4 + * @version 0.5 * @copyright GNU General Public License (GPL) version 3 */ @@ -57,7 +57,7 @@ class TaskModel extends Model { } ArrayHelper::arrayTrim($arr); $obj = new TaskModel(); - $tst = substr($arr[2],0,1); + $tst = (empty($arr[1]))?substr($arr[2],0,1):'*'; switch ($tst) { case '*': // multiple if ($arr[1] == '**') { @@ -97,7 +97,7 @@ class TaskModel extends Model { $obj->set('deadline',$arr[2].' days'); } else { // no number, means today - $obj->set('deadline', APP_SQL_TODAY); + $obj->set('deadline', date_format(new DateTime('now', $GLOBALS['config']['datetime']['timezone_user']), 'Y-m-d')); } break; default: @@ -110,7 +110,7 @@ class TaskModel extends Model { $obj->set('deadline', $dte); } else if ($GLOBALS['config']['task']['date']) { // use default date (config) - $obj->set('deadline', $GLOBALS['config']['task']['date']); + $obj->set('deadline', date_format(new DateTime($GLOBALS['config']['task']['date'], $GLOBALS['config']['datetime']['timezone_user']), 'Y-m-d')); // $dte = $obj->get('deadline'); } else { // no date by default (config) @@ -196,6 +196,10 @@ class TaskSummary extends TaskModel { return $str; } + public function htmlTimes() { + return $this->html('start',APP_DATETIME_SHT).' > '.$this->html('stop','%H:%M'); + } + public function htmlBegin() { if ($this->isEmpty('start')) { if ($this->isEmpty('begin')) { @@ -220,9 +224,9 @@ class TaskSummary extends TaskModel { } } - public function htmlEnd($expanded=false) { + public function htmlEnd($expanded=false, $default='-') { if ($this->isEmpty('stop')) { - return '-'; + return $default; } else { return $this->html('stop',APP_DATETIME); } @@ -270,7 +274,9 @@ class TaskSummary extends TaskModel { $this->_diff = 9999; } else { $dead = strtotime($this->get('deadline')); - $this->_diff = ($dead - intval(APP_TODAY)) / 3600 / 24; + // -TODO- optimize ! maybe using DateTime diff ? + $usernow = date_timestamp_get(new DateTime('now', $GLOBALS['config']['datetime']['timezone_user'])); + $this->_diff = round(($dead - $usernow) / 3600 / 24); } } @@ -320,6 +326,36 @@ class TaskSummary extends TaskModel { return str_pad($h, 2, '0',STR_PAD_LEFT).':'.str_pad($m, 2, '0',STR_PAD_LEFT); } + /** + * export data in array for the mobile version (ajax requests) + */ + public function exportData($method='html') { + // prepare general info + $arrInfo = array(); + $arr = $this->getFields(); + foreach ($arr as $key => $type) { + $arrInfo[$key] = $this->$method($key); + } + + // prepare timer history and totals + $total = 0; + $arrSpent = array(); + if ($this->get('spent')) { + do { + $total += $this->get('spent'); + // start and stop times + $times = $this->htmlTimes(); + $spent = $this->getTimeSpent(); + $arrSpent[$times] = $spent; + } while ($this->next()); + } + + $arrInfo['total'] = $this->htmlTime($total); + + return array('info' => $arrInfo, 'spent' => $arrSpent); + // return $arrInfo; + } + /** * update current task status */ diff --git a/app/model/timer.php b/app/model/timer.php index c4928f9..7fe8277 100644 --- a/app/model/timer.php +++ b/app/model/timer.php @@ -4,7 +4,7 @@ * * @package taskfreak_tt * @author Stan Ozier - * @version 0.1 + * @version 0.5 * @copyright GNU General Public License (GPL) version 3 */ @@ -75,7 +75,7 @@ class TimerModel extends Model { * stops a timer */ public static function stop($tid) { - if (!($tid = VarUid::sanitize($tid, $err))) { + if (!($tid = VarUid::sani($tid))) { return false; } $filter = "task_id='$tid' AND stop='0000-00-00 00:00:00'"; diff --git a/app/view/admin/user-list.php b/app/view/admin/user-list.php index dd7f556..3f86e60 100644 --- a/app/view/admin/user-list.php +++ b/app/view/admin/user-list.php @@ -5,7 +5,7 @@ $this->incView('include/page-top', false);
- + '; + } + $this->incView('iphone/inc_foot'); +?> +
\ No newline at end of file diff --git a/asset/html/iphone-header.php b/asset/html/iphone-header.php new file mode 100644 index 0000000..fdcb7c9 --- /dev/null +++ b/asset/html/iphone-header.php @@ -0,0 +1,30 @@ + + + + +"/> + +*/ +?> + +<?php echo $this->html('title'); ?> +isEmpty('description')) { +?> + +isEmpty('keywords')) { +?> + +callHelper('html_asset','headerStuff', true); +?> + \ No newline at end of file diff --git a/asset/html/page-header.php b/asset/html/page-header.php index 589d7de..d1dde3d 100644 --- a/asset/html/page-header.php +++ b/asset/html/page-header.php @@ -17,7 +17,7 @@ if (!$this->isEmpty('keywords')) { } if (file_exists(APP_WWW_PATH.'favicon.ico')) { - echo ''; + echo ''."\n"; } $this->callHelper('html_asset','headerStuff'); diff --git a/asset/jqtouch/jqtouch.css b/asset/jqtouch/jqtouch.css new file mode 100644 index 0000000..328afae --- /dev/null +++ b/asset/jqtouch/jqtouch.css @@ -0,0 +1,373 @@ +* { + margin: 0; + padding: 0; +} +a { + -webkit-tap-highlight-color: rgba(0,0,0,0); +} + +body { + overflow-x: hidden; + -webkit-user-select: none; + -webkit-text-size-adjust: none; + font-family: Helvetica; + -webkit-perspective: 800; + -webkit-transform-style: preserve-3d; +} +.selectable, input, textarea { + -webkit-user-select: auto; +} +body > * { + -webkit-backface-visibility: hidden; + -webkit-box-sizing: border-box; + display: none; + position: absolute; + left: 0; + width: 100%; + -webkit-transform: translate3d(0,0,0) rotate(0) scale(1); + min-height: 420px !important; +} +body.fullscreen > * { + min-height: 460px !important; +} +body.fullscreen.black-translucent > * { + min-height: 480px !important; +} +body.landscape > * { + min-height: 320px; +} +body > .current { + display: block !important; +} + +.in, .out { + -webkit-animation-timing-function: ease-in-out; + -webkit-animation-duration: 350ms; +} + +.slide.in { + -webkit-animation-name: slideinfromright; +} + +.slide.out { + -webkit-animation-name: slideouttoleft; +} + +.slide.in.reverse { + -webkit-animation-name: slideinfromleft; +} + +.slide.out.reverse { + -webkit-animation-name: slideouttoright; +} + +@-webkit-keyframes slideinfromright { + from { -webkit-transform: translateX(100%); } + to { -webkit-transform: translateX(0); } +} + +@-webkit-keyframes slideinfromleft { + from { -webkit-transform: translateX(-100%); } + to { -webkit-transform: translateX(0); } +} + +@-webkit-keyframes slideouttoleft { + from { -webkit-transform: translateX(0); } + to { -webkit-transform: translateX(-100%); } +} + +@-webkit-keyframes slideouttoright { + from { -webkit-transform: translateX(0); } + to { -webkit-transform: translateX(100%); } +} + +@-webkit-keyframes fadein { + from { opacity: 0; } + to { opacity: 1; } +} + +@-webkit-keyframes fadeout { + from { opacity: 1; } + to { opacity: 0; } +} + +.fade.in { + z-index: 10; + -webkit-animation-name: fadein; +} +.fade.out { + z-index: 0; +} + +.dissolve.in { + -webkit-animation-name: fadein; +} + +.dissolve.out { + -webkit-animation-name: fadeout; +} + + + +.flip { + -webkit-animation-duration: .65s; +} + +.flip.in { + -webkit-animation-name: flipinfromleft; +} + +.flip.out { + -webkit-animation-name: flipouttoleft; +} + +/* Shake it all about */ + +.flip.in.reverse { + -webkit-animation-name: flipinfromright; +} + +.flip.out.reverse { + -webkit-animation-name: flipouttoright; +} + +@-webkit-keyframes flipinfromright { + from { -webkit-transform: rotateY(-180deg) scale(.8); } + to { -webkit-transform: rotateY(0) scale(1); } +} + +@-webkit-keyframes flipinfromleft { + from { -webkit-transform: rotateY(180deg) scale(.8); } + to { -webkit-transform: rotateY(0) scale(1); } +} + +@-webkit-keyframes flipouttoleft { + from { -webkit-transform: rotateY(0) scale(1); } + to { -webkit-transform: rotateY(-180deg) scale(.8); } +} + +@-webkit-keyframes flipouttoright { + from { -webkit-transform: rotateY(0) scale(1); } + to { -webkit-transform: rotateY(180deg) scale(.8); } +} + +.slideup.in { + -webkit-animation-name: slideup; + z-index: 10; +} + +.slideup.out { + -webkit-animation-name: dontmove; + z-index: 0; +} + +.slideup.out.reverse { + z-index: 10; + -webkit-animation-name: slidedown; +} + +.slideup.in.reverse { + z-index: 0; + -webkit-animation-name: dontmove; +} + + +@-webkit-keyframes slideup { + from { -webkit-transform: translateY(100%); } + to { -webkit-transform: translateY(0); } +} + +@-webkit-keyframes slidedown { + from { -webkit-transform: translateY(0); } + to { -webkit-transform: translateY(100%); } +} + + + +/* Hackish, but reliable. */ + +@-webkit-keyframes dontmove { + from { opacity: 1; } + to { opacity: 1; } +} + +.swap { + -webkit-transform: perspective(800); + -webkit-animation-duration: .7s; +} +.swap.out { + -webkit-animation-name: swapouttoleft; +} +.swap.in { + -webkit-animation-name: swapinfromright; +} +.swap.out.reverse { + -webkit-animation-name: swapouttoright; +} +.swap.in.reverse { + -webkit-animation-name: swapinfromleft; +} + + +@-webkit-keyframes swapouttoright { + 0% { + -webkit-transform: translate3d(0px, 0px, 0px) rotateY(0deg); + -webkit-animation-timing-function: ease-in-out; + } + 50% { + -webkit-transform: translate3d(-180px, 0px, -400px) rotateY(20deg); + -webkit-animation-timing-function: ease-in; + } + 100% { + -webkit-transform: translate3d(0px, 0px, -800px) rotateY(70deg); + } +} + +@-webkit-keyframes swapouttoleft { + 0% { + -webkit-transform: translate3d(0px, 0px, 0px) rotateY(0deg); + -webkit-animation-timing-function: ease-in-out; + } + 50% { + -webkit-transform: translate3d(180px, 0px, -400px) rotateY(-20deg); + -webkit-animation-timing-function: ease-in; + } + 100% { + -webkit-transform: translate3d(0px, 0px, -800px) rotateY(-70deg); + } +} + +@-webkit-keyframes swapinfromright { + 0% { + -webkit-transform: translate3d(0px, 0px, -800px) rotateY(70deg); + -webkit-animation-timing-function: ease-out; + } + 50% { + -webkit-transform: translate3d(-180px, 0px, -400px) rotateY(20deg); + -webkit-animation-timing-function: ease-in-out; + } + 100% { + -webkit-transform: translate3d(0px, 0px, 0px) rotateY(0deg); + } +} + +@-webkit-keyframes swapinfromleft { + 0% { + -webkit-transform: translate3d(0px, 0px, -800px) rotateY(-70deg); + -webkit-animation-timing-function: ease-out; + } + 50% { + -webkit-transform: translate3d(180px, 0px, -400px) rotateY(-20deg); + -webkit-animation-timing-function: ease-in-out; + } + 100% { + -webkit-transform: translate3d(0px, 0px, 0px) rotateY(0deg); + } +} + +.cube { + -webkit-animation-duration: .55s; +} + +.cube.in { + -webkit-animation-name: cubeinfromright; + -webkit-transform-origin: 0% 50%; +} +.cube.out { + -webkit-animation-name: cubeouttoleft; + -webkit-transform-origin: 100% 50%; +} +.cube.in.reverse { + -webkit-animation-name: cubeinfromleft; + -webkit-transform-origin: 100% 50%; +} +.cube.out.reverse { + -webkit-animation-name: cubeouttoright; + -webkit-transform-origin: 0% 50%; + +} + +@-webkit-keyframes cubeinfromleft { + from { + -webkit-transform: rotateY(-90deg) translateZ(320px); + opacity: .5; + } + to { + -webkit-transform: rotateY(0deg) translateZ(0); + opacity: 1; + } +} +@-webkit-keyframes cubeouttoright { + from { + -webkit-transform: rotateY(0deg) translateX(0); + opacity: 1; + } + to { + -webkit-transform: rotateY(90deg) translateZ(320px); + opacity: .5; + } +} +@-webkit-keyframes cubeinfromright { + from { + -webkit-transform: rotateY(90deg) translateZ(320px); + opacity: .5; + } + to { + -webkit-transform: rotateY(0deg) translateZ(0); + opacity: 1; + } +} +@-webkit-keyframes cubeouttoleft { + from { + -webkit-transform: rotateY(0deg) translateZ(0); + opacity: 1; + } + to { + -webkit-transform: rotateY(-90deg) translateZ(320px); + opacity: .5; + } +} + + + + +.pop { + -webkit-transform-origin: 50% 50%; +} + +.pop.in { + -webkit-animation-name: popin; + z-index: 10; +} + +.pop.out.reverse { + -webkit-animation-name: popout; + z-index: 10; +} + +.pop.in.reverse { + z-index: 0; + -webkit-animation-name: dontmove; +} + +@-webkit-keyframes popin { + from { + -webkit-transform: scale(.2); + opacity: 0; + } + to { + -webkit-transform: scale(1); + opacity: 1; + } +} + +@-webkit-keyframes popout { + from { + -webkit-transform: scale(1); + opacity: 1; + } + to { + -webkit-transform: scale(.2); + opacity: 0; + } +} \ No newline at end of file diff --git a/asset/jqtouch/jqtouch.js b/asset/jqtouch/jqtouch.js new file mode 100644 index 0000000..0883580 --- /dev/null +++ b/asset/jqtouch/jqtouch.js @@ -0,0 +1,676 @@ +/* + + _/ _/_/ _/_/_/_/_/ _/ + _/ _/ _/ _/_/ _/ _/ _/_/_/ _/_/_/ + _/ _/ _/_/ _/ _/ _/ _/ _/ _/ _/ _/ + _/ _/ _/ _/ _/ _/ _/ _/ _/ _/ _/ + _/ _/_/ _/ _/ _/_/ _/_/_/ _/_/_/ _/ _/ + _/ + _/ + + Created by David Kaneda + Documentation and issue tracking on Google Code + + Special thanks to Jonathan Stark + and pinch/zoom + + (c) 2009 by jQTouch project members. + See LICENSE.txt for license. + + $Revision: 109 $ + $Date: 2009-10-06 12:23:30 -0400 (Tue, 06 Oct 2009) $ + $LastChangedBy: davidcolbykaneda $ + +*/ + +(function($) { + $.jQTouch = function(options) { + + // Set support values + $.support.WebKitCSSMatrix = (typeof WebKitCSSMatrix == "object"); + $.support.touch = (typeof Touch == "object"); + $.support.WebKitAnimationEvent = (typeof WebKitTransitionEvent == "object"); + + // Initialize internal variables + var $body, + $head=$('head'), + hist=[], + newPageCount=0, + jQTSettings={}, + hashCheck, + currentPage, + orientation, + isMobileWebKit = RegExp(" Mobile/").test(navigator.userAgent), + tapReady=true, + lastAnimationTime=0, + touchSelectors=[], + publicObj={}, + extensions=$.jQTouch.prototype.extensions, + defaultAnimations=['slide','flip','slideup','swap','cube','pop','dissolve','fade','back'], + animations=[], + hairextensions=''; + + // Get the party started + init(options); + + function init(options) { + + var defaults = { + addGlossToIcon: true, + backSelector: '.back, .cancel, .goback', + cacheGetRequests: true, + cubeSelector: '.cube', + dissolveSelector: '.dissolve', + fadeSelector: '.fade', + fixedViewport: true, + flipSelector: '.flip', + formSelector: 'form', + fullScreen: true, + fullScreenClass: 'fullscreen', + icon: null, + touchSelector: 'a, .touch', + popSelector: '.pop', + preloadImages: false, + slideSelector: 'body > * > ul li a', + slideupSelector: '.slideup', + startupScreen: null, + statusBar: 'default', // other options: black-translucent, black + submitSelector: '.submit', + swapSelector: '.swap', + useAnimations: true, + useFastTouch: true // Experimental. + }; + jQTSettings = $.extend({}, defaults, options); + + // Preload images + if (jQTSettings.preloadImages) { + for (var i = jQTSettings.preloadImages.length - 1; i >= 0; i--){ + (new Image()).src = jQTSettings.preloadImages[i]; + }; + } + // Set icon + if (jQTSettings.icon) { + var precomposed = (jQTSettings.addGlossToIcon) ? '' : '-precomposed'; + hairextensions += ''; + } + // Set startup screen + if (jQTSettings.startupScreen) { + hairextensions += ''; + } + // Set viewport + if (jQTSettings.fixedViewport) { + hairextensions += ''; + } + // Set full-screen + if (jQTSettings.fullScreen) { + hairextensions += ''; + if (jQTSettings.statusBar) { + hairextensions += ''; + } + } + if (hairextensions) $head.append(hairextensions); + + // Initialize on document load: + $(document).ready(function(){ + + // Add extensions + for (var i in extensions) + { + var fn = extensions[i]; + if ($.isFunction(fn)) + { + $.extend(publicObj, fn(publicObj)); + } + } + + // Add animations + for (var i in defaultAnimations) + { + var name = defaultAnimations[i]; + var selector = jQTSettings[name + 'Selector']; + if (typeof(selector) == 'string') { + addAnimation({name:name, selector:selector}); + } + } + + touchSelectors.push('input'); + touchSelectors.push(jQTSettings.touchSelector); + touchSelectors.push(jQTSettings.backSelector); + touchSelectors.push(jQTSettings.submitSelector); + $(touchSelectors.join(', ')).css('-webkit-touch-callout', 'none'); + $(jQTSettings.backSelector).tap(liveTap); + $(jQTSettings.submitSelector).tap(submitParentForm); + + $body = $('body'); + + if (jQTSettings.fullScreenClass && window.navigator.standalone == true) { + $body.addClass(jQTSettings.fullScreenClass + ' ' + jQTSettings.statusBar); + } + + // Create custom live events + $body + .bind('touchstart', handleTouch) + .bind('orientationchange', updateOrientation) + .trigger('orientationchange') + .submit(submitForm); + + if (jQTSettings.useFastTouch && $.support.touch) + { + $body.click(function(e){ + var $el = $(e.target); + if ($el.attr('target') == '_blank' || $el.attr('rel') == 'external' || $el.is('input[type="checkbox"]')) + { + return true; + } else { + return false; + } + }); + + // This additionally gets rid of form focusses + $body.mousedown(function(e){ + var timeDiff = (new Date()).getTime() - lastAnimationTime; + if (timeDiff < 200) + { + return false; + } + }); + } + + // Make sure exactly one child of body has "current" class + if ($('body > .current').length == 0) { + currentPage = $('body > *:first'); + } else { + currentPage = $('body > .current:first'); + $('body > .current').removeClass('current'); + } + + // Go to the top of the "current" page + $(currentPage).addClass('current'); + location.hash = $(currentPage).attr('id'); + addPageToHistory(currentPage); + scrollTo(0, 0); + dumbLoopStart(); + }); + } + + // PUBLIC FUNCTIONS + function goBack(to) { + showHistoryLog(); + // Init the param + if (hist.length > 1) { + var numberOfPages = Math.min(parseInt(to || 1, 10), hist.length-1); + + // Search through the history for an ID + if( isNaN(numberOfPages) && typeof(to) === "string" && to != '#' ) { + for( var i=1, length=hist.length; i < length; i++ ) { + if( '#' + hist[i].id === to ) { + numberOfPages = i; + break; + } + } + } + + // If still nothing, assume one + if( isNaN(numberOfPages) || numberOfPages < 1 ) { + numberOfPages = 1; + }; + + // Grab the current page for the "from" info + var animation = hist[0].animation; + var fromPage = hist[0].page; + + // Remove all pages in front of the target page + hist.splice(0, numberOfPages); + + // Grab the target page + var toPage = hist[0].page; + + // Make the animations + animatePages(fromPage, toPage, animation, true); + + return publicObj; + } else { + console.error('No pages in history.'); + return false; + } + } + function goTo(toPage, animation) { + var fromPage = hist[0].page; + + if (typeof(toPage) === 'string') { + toPage = $(toPage); + } + if (typeof(animation) === 'string') { + for (var i = animations.length - 1; i >= 0; i--){ + if (animations[i].name === animation) + { + animation = animations[i]; + break; + } + } + } + if (animatePages(fromPage, toPage, animation)) { + addPageToHistory(toPage, animation); + return publicObj; + } + else + { + console.error('Could not animate pages.'); + return false; + } + } + function getOrientation() { + return orientation; + } + + // PRIVATE FUNCTIONS + function liveTap(e){ + + // Grab the clicked element + var $el = $(e.target); + + if ($el.attr('nodeName')!=='A'){ + $el = $el.parent('a'); + } + + var target = $el.attr('target'), + hash = $el.attr('hash'), + animation=null; + + if (tapReady == false || !$el.length) { + console.warn('Not able to tap element.') + return false; + } + + if ($el.attr('target') == '_blank' || $el.attr('rel') == 'external') + { + return true; + } + + // Figure out the animation to use + for (var i = animations.length - 1; i >= 0; i--){ + if ($el.is(animations[i].selector)) { + animation = animations[i]; + break; + } + }; + + // User clicked an internal link, fullscreen mode + if (target == '_webapp') { + window.location = $el.attr('href'); + } + // User clicked a back button + else if ($el.is(jQTSettings.backSelector)) { + goBack(hash); + } + // Branch on internal or external href + else if (hash && hash!='#') { + $el.addClass('active'); + goTo($(hash).data('referrer', $el), animation); + } else { + $el.addClass('loading active'); + showPageByHref($el.attr('href'), { + animation: animation, + callback: function(){ + $el.removeClass('loading'); + setTimeout($.fn.unselect, 250, $el); + }, + $referrer: $el + }); + } + return false; + } + function addPageToHistory(page, animation) { + // Grab some info + var pageId = page.attr('id'); + + // Prepend info to page history + hist.unshift({ + page: page, + animation: animation, + id: pageId + }); + } + function showHistoryLog() { + if (hist.length > 1) { + var str = 'history'; + // Search through the history for an ID + for( var i=0, length=hist.length; i < length; i++ ) { + str += ' : '+hist[i].id; + } + console.log(str); + } else { + console.log('no history'); + } + } + function animatePages(fromPage, toPage, animation, backwards) { + // Error check for target page + if(toPage.length === 0){ + $.fn.unselect(); + console.error('Target element is missing.'); + return false; + } + + // Collapse the keyboard + $(':focus').blur(); + + // Make sure we are scrolled up to hide location bar + scrollTo(0, 0); + + // Define callback to run after animation completes + var callback = function(event){ + + if (animation) + { + toPage.removeClass('in reverse ' + animation.name); + fromPage.removeClass('current out reverse ' + animation.name); + } + else + { + fromPage.removeClass('current'); + } + + toPage.trigger('pageAnimationEnd', { direction: 'in' }); + fromPage.trigger('pageAnimationEnd', { direction: 'out' }); + + clearInterval(dumbLoop); + currentPage = toPage; + location.hash = currentPage.attr('id'); + dumbLoopStart(); + + var $originallink = toPage.data('referrer'); + if ($originallink) { + $originallink.unselect(); + } + lastAnimationTime = (new Date()).getTime(); + tapReady = true; + } + + fromPage.trigger('pageAnimationStart', { direction: 'out' }); + toPage.trigger('pageAnimationStart', { direction: 'in' }); + + if ($.support.WebKitAnimationEvent && animation && jQTSettings.useAnimations) { + toPage.one('webkitAnimationEnd', callback); + tapReady = false; + toPage.addClass(animation.name + ' in current ' + (backwards ? ' reverse' : '')); + fromPage.addClass(animation.name + ' out' + (backwards ? ' reverse' : '')); + console.log('-> anim from '+fromPage.attr('id')+' to '+toPage.attr('id')+' ('+animation.name+')'); + } else { + console.log('-> directly to '+toPage.attr('id')); + toPage.addClass('current'); + callback(); + } + showHistoryLog(); + return true; + } + function dumbLoopStart() { + dumbLoop = setInterval(function(){ + var curid = currentPage.attr('id'); + if (location.hash == '') { + location.hash = '#' + curid; + } else if (location.hash != '#' + curid) { + try { + goBack(location.hash) + } catch(e) { + console.error('Unknown hash change.'); + } + } + }, 100); + } + function insertNode($node) { + $ff = $('#'+$node.attr('id')); + if ($ff[0]) { + // delete previous version of the page + $ff.empty(); + $node.children().appendTo($ff); + } else { + $node.appendTo($body); + } + } + function insertPages(nodes, animation) { + var targetPage = null; + $(nodes).each(function(index, node){ + var $node = $(this); + if (!$node.attr('id')) { + $node.attr('id', 'page-' + (++newPageCount)); + } + insertNode($node); + if ($node.hasClass('current') || !targetPage ) { + targetPage = $node; + } + }); + if (targetPage !== null && animation != 'ignore') { + goTo(targetPage, animation); + return targetPage; + } + else + { + return false; + } + } + function appendPages(nodes) { + var targetPage = null; + $(nodes).each(function(index, node){ + var $node = $(this); + if (!$node.attr('id')) { + $node.attr('id', 'page-' + (++newPageCount)); + } + if ($node.attr('id') !== undefined && $node.attr('id') != null) { + var id = $node.attr('id'); + $node.addClass('dyn'); + insertNode($node); + } + }); + return false; + } + function showPageByHref(href, options) { + var defaults = { + data: null, + method: 'GET', + animation: null, + callback: null, + $referrer: null + }; + + var settings = $.extend({}, defaults, options); + + if (href != '#') + { + $.ajax({ + url: href, + data: settings.data, + type: settings.method, + success: function (data, textStatus) { + var firstPage = insertPages(data, settings.animation); + if (firstPage) + { + if (settings.method == 'GET' && jQTSettings.cacheGetRequests && settings.$referrer) + { + settings.$referrer.attr('href', '#' + firstPage.attr('id')); + } + if (settings.callback) { + settings.callback(true); + } + } + }, + error: function (data) { + if (settings.$referrer) settings.$referrer.unselect(); + if (settings.callback) { + settings.callback(false); + } + } + }); + } + else if ($referrer) + { + $referrer.unselect(); + } + } + function submitForm(e, callback){ + var $form = (typeof(e)==='string') ? $(e) : $(e.target); + + if ($form.length && $form.is(jQTSettings.formSelector) && $form.attr('action')) { + showPageByHref($form.attr('action'), { + data: $form.serialize(), + method: $form.attr('method') || "POST", + animation: animations[0] || null, + callback: callback + }); + return false; + } + return true; + } + function submitParentForm(e){ + var $form = $(this).closest('form'); + if ($form.length) + { + evt = jQuery.Event("submit"); + evt.preventDefault(); + $form.trigger(evt); + return false; + } + return true; + } + function addAnimation(animation) { + if (typeof(animation.selector) == 'string' && typeof(animation.name) == 'string') { + animations.push(animation); + $(animation.selector).tap(liveTap); + touchSelectors.push(animation.selector); + } + } + function updateOrientation() { + orientation = window.innerWidth < window.innerHeight ? 'profile' : 'landscape'; + $body.removeClass('profile landscape').addClass(orientation).trigger('turn', {orientation: orientation}); + // scrollTo(0, 0); + } + function handleTouch(e) { + + var $el = $(e.target); + + // Only handle touchSelectors + if (!$(e.target).is(touchSelectors.join(', '))) + { + var $link = $(e.target).closest('a'); + + if ($link.length){ + $el = $link; + } else { + return; + } + } + if (event) + { + var hoverTimeout = null, + startX = event.changedTouches[0].clientX, + startY = event.changedTouches[0].clientY, + startTime = (new Date).getTime(), + deltaX = 0, + deltaY = 0, + deltaT = 0; + + // Let's bind these after the fact, so we can keep some internal values + $el.bind('touchmove', touchmove).bind('touchend', touchend); + + hoverTimeout = setTimeout(function(){ + $el.makeActive(); + }, 100); + + } + + // Private touch functions (TODO: insert dirty joke) + function touchmove(e) { + + updateChanges(); + var absX = Math.abs(deltaX); + var absY = Math.abs(deltaY); + + // Check for swipe + if (absX > absY && (absX > 35) && deltaT < 1000) { + $el.trigger('swipe', {direction: (deltaX < 0) ? 'left' : 'right'}).unbind('touchmove touchend'); + } else if (absY > 1) { + $el.removeClass('active'); + } + + clearTimeout(hoverTimeout); + } + + function touchend(){ + updateChanges(); + + if (deltaY === 0 && deltaX === 0) { + $el.makeActive(); + // New approach: + // Fake the double click? + // TODO: Try with all click events (no tap) + // if (deltaT < 40) + // { + // setTimeout(function(){ + // $el.trigger('touchstart') + // .trigger('touchend'); + // }, 0); + // } + $el.trigger('tap'); + } else { + $el.removeClass('active'); + } + $el.unbind('touchmove touchend'); + clearTimeout(hoverTimeout); + } + + function updateChanges(){ + var first = event.changedTouches[0] || null; + deltaX = first.pageX - startX; + deltaY = first.pageY - startY; + deltaT = (new Date).getTime() - startTime; + } + + } // End touch handler + + // Public jQuery Fns + $.fn.unselect = function(obj) { + if (obj) { + obj.removeClass('active'); + } else { + $('.active').removeClass('active'); + } + } + $.fn.makeActive = function(){ + return $(this).addClass('active'); + } + $.fn.swipe = function(fn) { + if ($.isFunction(fn)) + { + return this.each(function(i, el){ + $(el).bind('swipe', fn); + }); + } + } + $.fn.tap = function(fn){ + if ($.isFunction(fn)) + { + var tapEvent = (jQTSettings.useFastTouch && $.support.touch) ? 'tap' : 'click'; + return $(this).live(tapEvent, fn); + } else { + $(this).trigger('tap'); + } + } + + publicObj = { + getOrientation: getOrientation, + goBack: goBack, + goTo: goTo, + addAnimation: addAnimation, + submitForm: submitForm, + appendPages: appendPages + } + + return publicObj; + } + + // Extensions directly manipulate the jQTouch object, before it's initialized. + $.jQTouch.prototype.extensions = []; + $.jQTouch.addExtension = function(extension){ + $.jQTouch.prototype.extensions.push(extension); + } + +})(jQuery); \ No newline at end of file diff --git a/asset/jqtouch/jqtouch.min.css b/asset/jqtouch/jqtouch.min.css new file mode 100644 index 0000000..37ef6fe --- /dev/null +++ b/asset/jqtouch/jqtouch.min.css @@ -0,0 +1 @@ +*{margin:0;padding:0;}a{-webkit-tap-highlight-color:rgba(0,0,0,0);}body{overflow-x:hidden;-webkit-user-select:none;-webkit-text-size-adjust:none;font-family:Helvetica;-webkit-perspective:800;-webkit-transform-style:preserve-3d;}.selectable,input,textarea{-webkit-user-select:auto;}body>*{-webkit-backface-visibility:hidden;-webkit-box-sizing:border-box;display:none;position:absolute;left:0;width:100%;-webkit-transform:translate3d(0,0,0) rotate(0) scale(1);min-height:420px!important;}body.fullscreen>*{min-height:460px!important;}body.fullscreen.black-translucent>*{min-height:480px!important;}body.landscape>*{min-height:320px;}body>.current{display:block!important;}.in,.out{-webkit-animation-timing-function:ease-in-out;-webkit-animation-duration:350ms;}.slide.in{-webkit-animation-name:slideinfromright;}.slide.out{-webkit-animation-name:slideouttoleft;}.slide.in.reverse{-webkit-animation-name:slideinfromleft;}.slide.out.reverse{-webkit-animation-name:slideouttoright;}@-webkit-keyframes slideinfromright{from{-webkit-transform:translateX(100%);}to{-webkit-transform:translateX(0);}}@-webkit-keyframes slideinfromleft{from{-webkit-transform:translateX(-100%);}to{-webkit-transform:translateX(0);}}@-webkit-keyframes slideouttoleft{from{-webkit-transform:translateX(0);}to{-webkit-transform:translateX(-100%);}}@-webkit-keyframes slideouttoright{from{-webkit-transform:translateX(0);}to{-webkit-transform:translateX(100%);}}@-webkit-keyframes fadein{from{opacity:0;}to{opacity:1;}}@-webkit-keyframes fadeout{from{opacity:1;}to{opacity:0;}}.fade.in{z-index:10;-webkit-animation-name:fadein;}.fade.out{z-index:0;}.dissolve.in{-webkit-animation-name:fadein;}.dissolve.out{-webkit-animation-name:fadeout;}.flip{-webkit-animation-duration:.65s;}.flip.in{-webkit-animation-name:flipinfromleft;}.flip.out{-webkit-animation-name:flipouttoleft;}.flip.in.reverse{-webkit-animation-name:flipinfromright;}.flip.out.reverse{-webkit-animation-name:flipouttoright;}@-webkit-keyframes flipinfromright{from{-webkit-transform:rotateY(-180deg) scale(.8);}to{-webkit-transform:rotateY(0) scale(1);}}@-webkit-keyframes flipinfromleft{from{-webkit-transform:rotateY(180deg) scale(.8);}to{-webkit-transform:rotateY(0) scale(1);}}@-webkit-keyframes flipouttoleft{from{-webkit-transform:rotateY(0) scale(1);}to{-webkit-transform:rotateY(-180deg) scale(.8);}}@-webkit-keyframes flipouttoright{from{-webkit-transform:rotateY(0) scale(1);}to{-webkit-transform:rotateY(180deg) scale(.8);}}.slideup.in{-webkit-animation-name:slideup;z-index:10;}.slideup.out{-webkit-animation-name:dontmove;z-index:0;}.slideup.out.reverse{z-index:10;-webkit-animation-name:slidedown;}.slideup.in.reverse{z-index:0;-webkit-animation-name:dontmove;}@-webkit-keyframes slideup{from{-webkit-transform:translateY(100%);}to{-webkit-transform:translateY(0);}}@-webkit-keyframes slidedown{from{-webkit-transform:translateY(0);}to{-webkit-transform:translateY(100%);}}@-webkit-keyframes dontmove{from{opacity:1;}to{opacity:1;}}.swap{-webkit-transform:perspective(800);-webkit-animation-duration:.7s;}.swap.out{-webkit-animation-name:swapouttoleft;}.swap.in{-webkit-animation-name:swapinfromright;}.swap.out.reverse{-webkit-animation-name:swapouttoright;}.swap.in.reverse{-webkit-animation-name:swapinfromleft;}@-webkit-keyframes swapouttoright{0%{-webkit-transform:translate3d(0px,0px,0px) rotateY(0deg);-webkit-animation-timing-function:ease-in-out;}50%{-webkit-transform:translate3d(-180px,0px,-400px) rotateY(20deg);-webkit-animation-timing-function:ease-in;}100%{-webkit-transform:translate3d(0px,0px,-800px) rotateY(70deg);}}@-webkit-keyframes swapouttoleft{0%{-webkit-transform:translate3d(0px,0px,0px) rotateY(0deg);-webkit-animation-timing-function:ease-in-out;}50%{-webkit-transform:translate3d(180px,0px,-400px) rotateY(-20deg);-webkit-animation-timing-function:ease-in;}100%{-webkit-transform:translate3d(0px,0px,-800px) rotateY(-70deg);}}@-webkit-keyframes swapinfromright{0%{-webkit-transform:translate3d(0px,0px,-800px) rotateY(70deg);-webkit-animation-timing-function:ease-out;}50%{-webkit-transform:translate3d(-180px,0px,-400px) rotateY(20deg);-webkit-animation-timing-function:ease-in-out;}100%{-webkit-transform:translate3d(0px,0px,0px) rotateY(0deg);}}@-webkit-keyframes swapinfromleft{0%{-webkit-transform:translate3d(0px,0px,-800px) rotateY(-70deg);-webkit-animation-timing-function:ease-out;}50%{-webkit-transform:translate3d(180px,0px,-400px) rotateY(-20deg);-webkit-animation-timing-function:ease-in-out;}100%{-webkit-transform:translate3d(0px,0px,0px) rotateY(0deg);}}.cube{-webkit-animation-duration:.55s;}.cube.in{-webkit-animation-name:cubeinfromright;-webkit-transform-origin:0 50%;}.cube.out{-webkit-animation-name:cubeouttoleft;-webkit-transform-origin:100% 50%;}.cube.in.reverse{-webkit-animation-name:cubeinfromleft;-webkit-transform-origin:100% 50%;}.cube.out.reverse{-webkit-animation-name:cubeouttoright;-webkit-transform-origin:0 50%;}@-webkit-keyframes cubeinfromleft{from{-webkit-transform:rotateY(-90deg) translateZ(320px);opacity:.5;}to{-webkit-transform:rotateY(0deg) translateZ(0);opacity:1;}}@-webkit-keyframes cubeouttoright{from{-webkit-transform:rotateY(0deg) translateX(0);opacity:1;}to{-webkit-transform:rotateY(90deg) translateZ(320px);opacity:.5;}}@-webkit-keyframes cubeinfromright{from{-webkit-transform:rotateY(90deg) translateZ(320px);opacity:.5;}to{-webkit-transform:rotateY(0deg) translateZ(0);opacity:1;}}@-webkit-keyframes cubeouttoleft{from{-webkit-transform:rotateY(0deg) translateZ(0);opacity:1;}to{-webkit-transform:rotateY(-90deg) translateZ(320px);opacity:.5;}}.pop{-webkit-transform-origin:50% 50%;}.pop.in{-webkit-animation-name:popin;z-index:10;}.pop.out.reverse{-webkit-animation-name:popout;z-index:10;}.pop.in.reverse{z-index:0;-webkit-animation-name:dontmove;}@-webkit-keyframes popin{from{-webkit-transform:scale(.2);opacity:0;}to{-webkit-transform:scale(1);opacity:1;}}@-webkit-keyframes popout{from{-webkit-transform:scale(1);opacity:1;}to{-webkit-transform:scale(.2);opacity:0;}} \ No newline at end of file diff --git a/asset/jqtouch/jqtouch.min.js b/asset/jqtouch/jqtouch.min.js new file mode 100644 index 0000000..f43917e --- /dev/null +++ b/asset/jqtouch/jqtouch.min.js @@ -0,0 +1 @@ +(function($){$.jQTouch=function(_2){$.support.WebKitCSSMatrix=(typeof WebKitCSSMatrix=="object");$.support.touch=(typeof Touch=="object");$.support.WebKitAnimationEvent=(typeof WebKitTransitionEvent=="object");var _3,$head=$("head"),hist=[],newPageCount=0,jQTSettings={},hashCheck,currentPage,orientation,isMobileWebKit=RegExp(" Mobile/").test(navigator.userAgent),tapReady=true,lastAnimationTime=0,touchSelectors=[],publicObj={},extensions=$.jQTouch.prototype.extensions,defaultAnimations=["slide","flip","slideup","swap","cube","pop","dissolve","fade","back"],animations=[],hairextensions="";init(_2);function init(_4){var _5={addGlossToIcon:true,backSelector:".back, .cancel, .goback",cacheGetRequests:true,cubeSelector:".cube",dissolveSelector:".dissolve",fadeSelector:".fade",fixedViewport:true,flipSelector:".flip",formSelector:"form",fullScreen:true,fullScreenClass:"fullscreen",icon:null,touchSelector:"a, .touch",popSelector:".pop",preloadImages:false,slideSelector:"body > * > ul li a",slideupSelector:".slideup",startupScreen:null,statusBar:"default",submitSelector:".submit",swapSelector:".swap",useAnimations:true,useFastTouch:true};jQTSettings=$.extend({},_5,_4);if(jQTSettings.preloadImages){for(var i=jQTSettings.preloadImages.length-1;i>=0;i--){(new Image()).src=jQTSettings.preloadImages[i];}}if(jQTSettings.icon){var _7=(jQTSettings.addGlossToIcon)?"":"-precomposed";hairextensions+="";}if(jQTSettings.startupScreen){hairextensions+="";}if(jQTSettings.fixedViewport){hairextensions+="";}if(jQTSettings.fullScreen){hairextensions+="";if(jQTSettings.statusBar){hairextensions+="";}}if(hairextensions){$head.append(hairextensions);}$(document).ready(function(){for(var i in extensions){var fn=extensions[i];if($.isFunction(fn)){$.extend(publicObj,fn(publicObj));}}for(var i in defaultAnimations){var _a=defaultAnimations[i];var _b=jQTSettings[_a+"Selector"];if(typeof (_b)=="string"){addAnimation({name:_a,selector:_b});}}touchSelectors.push("input");touchSelectors.push(jQTSettings.touchSelector);touchSelectors.push(jQTSettings.backSelector);touchSelectors.push(jQTSettings.submitSelector);$(touchSelectors.join(", ")).css("-webkit-touch-callout","none");$(jQTSettings.backSelector).tap(liveTap);$(jQTSettings.submitSelector).tap(submitParentForm);_3=$("body");if(jQTSettings.fullScreenClass&&window.navigator.standalone==true){_3.addClass(jQTSettings.fullScreenClass+" "+jQTSettings.statusBar);}_3.bind("touchstart",handleTouch).bind("orientationchange",updateOrientation).trigger("orientationchange").submit(submitForm);if(jQTSettings.useFastTouch&&$.support.touch){_3.click(function(e){var _d=$(e.target);if(_d.attr("target")=="_blank"||_d.attr("rel")=="external"||_d.is("input[type=\"checkbox\"]")){return true;}else{return false;}});_3.mousedown(function(e){var _f=(new Date()).getTime()-lastAnimationTime;if(_f<200){return false;}});}if($("body > .current").length==0){currentPage=$("body > *:first");}else{currentPage=$("body > .current:first");$("body > .current").removeClass("current");}$(currentPage).addClass("current");location.hash=$(currentPage).attr("id");addPageToHistory(currentPage);scrollTo(0,0);dumbLoopStart();});}function goBack(to){if(hist.length>1){var _11=Math.min(parseInt(to||1,10),hist.length-1);if(isNaN(_11)&&typeof (to)==="string"&&to!="#"){for(var i=1,length=hist.length;i=0;i--){if(animations[i].name===_17){_17=animations[i];break;}}}if(animatePages(_18,_16,_17)){addPageToHistory(_16,_17);return publicObj;}else{console.error("Could not animate pages.");return false;}}function getOrientation(){return orientation;}function liveTap(e){var $el=$(e.target);if($el.attr("nodeName")!=="A"){$el=$el.parent("a");}var _1c=$el.attr("target"),hash=$el.attr("hash"),animation=null;if(tapReady==false||!$el.length){console.warn("Not able to tap element.");return false;}if($el.attr("target")=="_blank"||$el.attr("rel")=="external"){return true;}for(var i=animations.length-1;i>=0;i--){if($el.is(animations[i].selector)){animation=animations[i];break;}}if(_1c=="_webapp"){window.location=$el.attr("href");}else{if($el.is(jQTSettings.backSelector)){goBack(hash);}else{if(hash&&hash!="#"){$el.addClass("active");goTo($(hash).data("referrer",$el),animation);}else{$el.addClass("loading active");showPageByHref($el.attr("href"),{animation:animation,callback:function(){$el.removeClass("loading");setTimeout($.fn.unselect,250,$el);},$referrer:$el});}}}return false;}function addPageToHistory(_1e,_1f){var _20=_1e.attr("id");hist.unshift({page:_1e,animation:_1f,id:_20});}function animatePages(_21,_22,_23,_24){if(_22.length===0){$.fn.unselect();console.error("Target element is missing.");return false;}$(":focus").blur();scrollTo(0,0);var _25=function(_26){if(_23){_22.removeClass("in reverse "+_23.name);_21.removeClass("current out reverse "+_23.name);}else{_21.removeClass("current");}_22.trigger("pageAnimationEnd",{direction:"in"});_21.trigger("pageAnimationEnd",{direction:"out"});clearInterval(dumbLoop);currentPage=_22;location.hash=currentPage.attr("id");dumbLoopStart();var _27=_22.data("referrer");if(_27){_27.unselect();}lastAnimationTime=(new Date()).getTime();tapReady=true;};_21.trigger("pageAnimationStart",{direction:"out"});_22.trigger("pageAnimationStart",{direction:"in"});if($.support.WebKitAnimationEvent&&_23&&jQTSettings.useAnimations){_22.one("webkitAnimationEnd",_25);tapReady=false;_22.addClass(_23.name+" in current "+(_24?" reverse":""));_21.addClass(_23.name+" out"+(_24?" reverse":""));}else{_22.addClass("current");_25();}return true;}function dumbLoopStart(){dumbLoop=setInterval(function(){var _28=currentPage.attr("id");if(location.hash==""){location.hash="#"+_28;}else{if(location.hash!="#"+_28){try{goBack(location.hash);}catch(e){console.error("Unknown hash change.");}}}},100);}function insertPages(_29,_2a){var _2b=null;$(_29).each(function(_2c,_2d){var _2e=$(this);if(!_2e.attr("id")){_2e.attr("id","page-"+(++newPageCount));}_2e.appendTo(_3);if(_2e.hasClass("current")||!_2b){_2b=_2e;}});if(_2b!==null){goTo(_2b,_2a);return _2b;}else{return false;}}function showPageByHref(_2f,_30){var _31={data:null,method:"GET",animation:null,callback:null,$referrer:null};var _32=$.extend({},_31,_30);if(_2f!="#"){$.ajax({url:_2f,data:_32.data,type:_32.method,success:function(_33,_34){var _35=insertPages(_33,_32.animation);if(_35){if(_32.method=="GET"&&jQTSettings.cacheGetRequests&&_32.$referrer){_32.$referrer.attr("href","#"+_35.attr("id"));}if(_32.callback){_32.callback(true);}}},error:function(_36){if(_32.$referrer){_32.$referrer.unselect();}if(_32.callback){_32.callback(false);}}});}else{if($referrer){$referrer.unselect();}}}function submitForm(e,_38){var _39=(typeof (e)==="string")?$(e):$(e.target);if(_39.length&&_39.is(jQTSettings.formSelector)&&_39.attr("action")){showPageByHref(_39.attr("action"),{data:_39.serialize(),method:_39.attr("method")||"POST",animation:animations[0]||null,callback:_38});return false;}return true;}function submitParentForm(e){var _3b=$(this).closest("form");if(_3b.length){evt=jQuery.Event("submit");evt.preventDefault();_3b.trigger(evt);return false;}return true;}function addAnimation(_3c){if(typeof (_3c.selector)=="string"&&typeof (_3c.name)=="string"){animations.push(_3c);$(_3c.selector).tap(liveTap);touchSelectors.push(_3c.selector);}}function updateOrientation(){orientation=window.innerWidth_43&&(_42>35)&&deltaT<1000){$el.trigger("swipe",{direction:(deltaX<0)?"left":"right"}).unbind("touchmove touchend");}else{if(_43>1){$el.removeClass("active");}}clearTimeout(_40);}function touchend(){updateChanges();if(deltaY===0&&deltaX===0){$el.makeActive();$el.trigger("tap");}else{$el.removeClass("active");}$el.unbind("touchmove touchend");clearTimeout(_40);}function updateChanges(){var _44=event.changedTouches[0]||null;deltaX=_44.pageX-startX;deltaY=_44.pageY-startY;deltaT=(new Date).getTime()-startTime;}}$.fn.unselect=function(obj){if(obj){obj.removeClass("active");}else{$(".active").removeClass("active");}};$.fn.makeActive=function(){return $(this).addClass("active");};$.fn.swipe=function(fn){if($.isFunction(fn)){return this.each(function(i,el){$(el).bind("swipe",fn);});}};$.fn.tap=function(fn){if($.isFunction(fn)){var _4a=(jQTSettings.useFastTouch&&$.support.touch)?"tap":"click";return $(this).live(_4a,fn);}else{$(this).trigger("tap");}};publicObj={getOrientation:getOrientation,goBack:goBack,goTo:goTo,addAnimation:addAnimation,submitForm:submitForm};return publicObj;};$.jQTouch.prototype.extensions=[];$.jQTouch.addExtension=function(_4b){$.jQTouch.prototype.extensions.push(_4b);};})(jQuery); \ No newline at end of file diff --git a/asset/jqtouch/themes/apple/img/backButton.png b/asset/jqtouch/themes/apple/img/backButton.png new file mode 100644 index 0000000000000000000000000000000000000000..935f914ea2672151083594dab0215c8ed1555c56 GIT binary patch literal 783 zcmV+q1MvKbP)VGsr2dAHlrMxhic zAO(@DAcA1I$8eDlA@TCT|ER&lps6A;L=!ZU2xti2h*6YqODMG6w!7QyJ2MKR1`FTX z<;nR0lXFJgdol~hOC}SuGta+%`5cYxK(+``T~mK`aHPEA8~~_9498geu@ZVX9;m8s z?;Xka`XEb~Xmfq#(Sz}h?!I7GpGrh zCjBL)DltI@O^Z!Ep6DF9SzHoO6onW_B4m$nIP-lat=+?mZ|7CaSiv-miTih(g4YU* z$_asxAUC|evTu0QA52e$%Fkc&msLq5$SvV=7ySPR%b%8XiyP{ikr`1!jyYWJLmlYJ z#OqftI|lC{J1|Xb0_1q#7 z01WmbWc9_f$v{K5a5xVNu)hPZzrvtA(hN8W2|cBZjSf37MkvKe03noJO~2kB)T5is z3@1TBBujFCXQLk55(4ZFfWi!>C5wuD^_9hDGI|0X@V;1FZ)vJMty*@G8}PeR zx&}GMgzh}2!Wn)&M6mUON9fWrAeYjX;rA8nt&o|mZEc|EGU{PWryw_&+0?=PQ>1o{_%6ycWDlXV%!C$R?QE^HSg6Ony+quOCP#-lJ}iG1>xvbKoZ zomcAjwgrO(BBCW#=Hqut6a2G$37eJC1 zL6jIkkr_sy8b+TQNTnJ{ryEPG98R(wN1Gi_wH;8m9Z|X-OQs%7s2)_n9#p{}Rl^@v z#UEG3Aw!5EM2R9qhayFZB464gM~)*%kR)Q>CrXbeWZx)Cjwn*4DpRK}PK_>U;4fOR zFlyj4ZQwa@;X!xfLwMsxdgDlGuSsvbO@HK6gymI&z*vXoS%~IaiRNI9=VXuQXOie{ zi?eTqv2l&Fa)_mKiKTOkymODWb&jxhkFa)+v3i!di=fGsp0SywyPT-NrL)GTwa4zB zu!H~r0J=#;K~xyijmXy$!9W;>;SV7zS{9M$y@u#r5MA#7g3PRw{bw9_&fXWkf9`}J z1UhHm$9o*K`Xixl1;=mfRA;%_3Y(>)9#FT}61$1aVkKFm!Dj@AF(nLS9U==pBsfww zkwRiXBoOZsal{%#3|fuQz{&)Jk|Pu-Ch=p0=?EiFM-h38D55||>5ox0_qa}&ZhXto+2n%b?bJ&~1lBv41sCu<^TcbQd%6WH^KYEFCb>M6lGmBCgZF_RMP;g_&g!eAw8+>M~{e^us?&19oxF zesu1f-zQziO$!7&@4IwANODeU)>*x*Rn^qtPS=tAh0|PL2=Z@Q!F+ZRSJaYqUMAhQ zG`Dhu3(aFX@_xb(O9venU+*Q2KNu!0^l!Yucs8g@r!jItQ`$kM_RelF{r G5}E+j-eN=m literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/apple/img/grayButton.png b/asset/jqtouch/themes/apple/img/grayButton.png new file mode 100644 index 0000000000000000000000000000000000000000..0ce6a30d4b5f6d9b2b13a2414f76c344e4991a1a GIT binary patch literal 943 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 N002ovPDHLkV1i-QPa^;T literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/apple/img/loading.gif b/asset/jqtouch/themes/apple/img/loading.gif new file mode 100644 index 0000000000000000000000000000000000000000..8522ddf1a6ebd07d999926dd018f2f8af62ee804 GIT binary patch literal 1435 zcmZ?wbhEHblw=TL*v!E2|NsAAzyH4d^yk6LUzhIxIC|~-w$oo%9{MtS$EUvaAL^I9 zFPi-}dEy(7x);_Z&w+{+|8x7fh6Fo12DlpO889<4Ffb_oWMSoE;AhZbU|?bp073?q z!Vf2(zc4I)b=|F);X=UdD-6xT9p_e zCjY=i7V9oLHAd}acT3oj)KbHCm(8mkPDu2;o^i>?_7x^ixw#O)RJ+hp(Kxs+)tAi39 za;jZxp54$8HAJBiUK>rCWijd-DIDhAwEt7^~-0}%C6b<+tBH~2-*)}A8^?ECDXvxQbA5DuV zJ)NXk+a}SbQ#{AR`iT3rD=P!HiLeDQvAJUPN;c4BiN!y5stQl?m~6>0UB%z1BeK{e zU3r1X=8n!JMHf>MA$H}11wJyohno*fGO-YGcTBuuvM#jiP=bcax*I)71_CmRX0SOn zI-1G*a~j+*uv*3B@JaDRnizu@e?W#XGlRHtCPR*7Umb?eKnWHUb5V;Uj8=-Azq7T% zi_xpo*zRakWZ$WXQ;MS7uAI54C?Rp2wYb1D$?(FX0tO}7Q%sEw7QQ^(OTKQblv$u~ zB=JMR4Gwiig^w%VIq-cg;NWLybKB9#u*?O;yUf6J2}&rDA5LCZNiI73x8V4hgSiT2 z6@62@e81{&q^eB5yhhsTh>V@;yo();8d)uqCnUCo%xy87p8MfJAwz@9B8R1-7Mu)8 z1_3r1i`lj*6$nh=W^lVu$I~Qz{jfq0ifypm7!CB?oW&9MuFp!5z7`|9yk*McQol!u zvr`Sbr)Ws7k*Vm@)R$j6QG-jJw`J2eNdtp*iHr;{e7Txh)EE>h*t(7`{1CvyCv^0( zo5Gc>_Alb-WeSL_OtK7Q7f(IKdl@3W!G2jAW(#RHc*FD*#te{9~? z?$B`JhnW2FMGYH6oBF4#6c*TV^d}vB5GY|%x58Rl|sI%aUEiXevud?ZKCqKVvP5$7W!A>HrElaOmP+;?T zxNb$|4hgpIzDEu=MpIpresys1cRXUcK4GtlgxjI2j87_jhaPUM(-Fu&H7Bq3fmfNa Is33zi04%B!Q2+n{ literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/apple/img/on_off.png b/asset/jqtouch/themes/apple/img/on_off.png new file mode 100644 index 0000000000000000000000000000000000000000..62325a8232cb4512e806fad9568b5a438a108475 GIT binary patch literal 2634 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 NgQu&X%Q~loCIB>$9?k#& literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/apple/img/selection.png b/asset/jqtouch/themes/apple/img/selection.png new file mode 100644 index 0000000000000000000000000000000000000000..537e3f0b13ea422a5ac5487317872414d51574c1 GIT binary patch literal 159 zcmeAS@N?(olHy`uVBq!ia0vp^j6kfy!2~3aiye;!Qj#UE5hcO-X(i=}MX3yqDfvmM z3ZA)%>8U}fi7AzZCsS>JiX1&%978x{Sr2X$Jj5WtvT?p{@1r}0Gc6VGKL6Qv;l%Dc zTgw%X}gxBOXmxAbz1ds%&OUSwBY#<9&n!x%hW{an^L HB{Ts5+CMp^ literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/apple/img/thumb.png b/asset/jqtouch/themes/apple/img/thumb.png new file mode 100644 index 0000000000000000000000000000000000000000..81495a09287fd57a2e3ab5372c4e976ca8b8929e GIT binary patch literal 2834 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 LNkvXXu0mjf9G~Ji literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/apple/img/toolbar.png b/asset/jqtouch/themes/apple/img/toolbar.png new file mode 100644 index 0000000000000000000000000000000000000000..2159c7dd0cd5efb3a64f2653ea60e0c9564197b4 GIT binary patch literal 168 zcmeAS@N?(olHy`uVBq!ia0vp^j6kf-!2~4D97_9ulw^r(L`iUdT1k0gQ7VIDN`6wR zf@f}GdTLN=VoGJ<$y6JlA}>!D$B>F!zCDV34Gsd#v;Y3TJ|TmJseIn)i>a4+H5bh+ zbJ_UTea>|bh33daK%zl0UMIIXm_ Q6=*7hr>mdKI;Vst0L2kLjsO4v literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/apple/img/whiteButton.png b/asset/jqtouch/themes/apple/img/whiteButton.png new file mode 100644 index 0000000000000000000000000000000000000000..5514b270053a41039e9e96ef8591796521ee0312 GIT binary patch literal 978 zcmV;@11}R*8aG1*L?d1O->_T@+D~u1Y}!yL0VI=|WL) zUB!jV?nDqFVEqcjNU7Q;7-O1A(q?8dlX-96yZ5-5q-Ly5=jDGlkNe*5{m(h~zIU$B ztvpZh0>hld-kwYNkqy3Ko}K-V%D(G)Z`(9CN35XDjL&xuH$Mh_XF(}UB(Tw%lJL(m|<1LC)=R9eoc+{eJ zNQwFm3ZOo%tAYib`a=Ya6#-N=4JiO(J0G^!!{zGLYx*)_QJi=^gsb6jQm_J=B!6wD zD%0-bC{8`;0(Q9FGD%w0qhLC5rQirtj;nGAUq!X!Dqd2rt6&lNPuJ>g7pqvn zrLC}dJQx&>lhnC-)EE`H)reg0T)izKV$|3W#Z{x-uG+(BCOFiFCeuK~FK_qmdcCS1 z>8qPuMY7^&mwW$}US2j%`m-B`MG8c7zyGk_Te#n^&tIcWp2Z*u%VSYOaGhsH3-(@~ zmGI-aXiXaBcJ0@|xe~1jq8+&sKXGKh9t>WX-&ip>B{%Tf)t#qUx1u_4ei+87UrHDfl6dXpw%k7!k~_oku06C3S8F^@(Qf&-L}LBUh<3`S518 zHslKoXby|rLrF-aMbk8j+ef37#cK7AgI*>xK3*KI+wDGQqnw)Edn!H~2Jv7#l+-p> zSL68q&WJ!JQ!W>a*5>p3XLojzq*mM7in|*4KU7;ZTp6~iyZ`_I07*qoM6N<$f;?{4 AHUIzs literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/apple/theme.css b/asset/jqtouch/themes/apple/theme.css new file mode 100644 index 0000000..07d85eb --- /dev/null +++ b/asset/jqtouch/themes/apple/theme.css @@ -0,0 +1,677 @@ +body { + background: rgb(0,0,0); +} + +body > * { + background: rgb(197,204,211) url(img/pinstripes.png); +} + +h1, h2 { + font: bold 18px Helvetica; + text-shadow: rgba(255,255,255,.2) 0 1px 1px; + color: rgb(76, 86, 108); + margin: 10px 20px 6px; +} + +/* @group Toolbar */ + +.toolbar { + -webkit-box-sizing: border-box; + border-bottom: 1px solid #2d3642; + padding: 10px; + height: 45px; + background: url(img/toolbar.png) #6d84a2 repeat-x; + position: relative; +} + +.black-translucent .toolbar { + margin-top: 20px; +} + +.toolbar > h1 { + position: absolute; + overflow: hidden; + left: 50%; + top: 10px; + line-height: 1em; + margin: 1px 0 0 -75px; + height: 40px; + font-size: 20px; + width: 150px; + font-weight: bold; + text-shadow: rgba(0, 0, 0, 0.4) 0px -1px 0; + text-align: center; + text-overflow: ellipsis; + white-space: nowrap; + color: #fff; +} + +body.landscape .toolbar > h1 { + margin-left: -125px; + width: 250px; +} + +.button, .back, .cancel, .add { + position: absolute; + overflow: hidden; + top: 8px; + right: 6px; + margin: 0; + border-width: 0 5px; + padding: 0 3px; + width: auto; + height: 30px; + line-height: 30px; + font-family: inherit; + font-size: 12px; + font-weight: bold; + color: #fff; + text-shadow: rgba(0, 0, 0, 0.5) 0px -1px 0; + text-overflow: ellipsis; + text-decoration: none; + white-space: nowrap; + background: none; + -webkit-border-image: url(img/toolButton.png) 0 5 0 5; +} + +.button.active, .back.active, .cancel.active, .add.active { + -webkit-border-image: url(img/toolButton.png) 0 5 0 5; +} + +.blueButton { + -webkit-border-image: url(img/blueButton.png) 0 5 0 5; + border-width: 0 5px; +} + +.back { + left: 6px; + right: auto; + padding: 0; + max-width: 55px; + border-width: 0 8px 0 14px; + -webkit-border-image: url(img/backButton.png) 0 8 0 14; +} + +.leftButton, .cancel { + left: 6px; + right: auto; +} + +.add { + font-size: 24px; + line-height: 24px; + font-weight: bold; +} + +.whiteButton, +.grayButton { + display: block; + border-width: 0 12px; + padding: 10px; + text-align: center; + font-size: 20px; + font-weight: bold; + text-decoration: inherit; + color: inherit; +} + +.whiteButton { + -webkit-border-image: url(img/whiteButton.png) 0 12 0 12; + text-shadow: rgba(255, 255, 255, 0.7) 0 1px 0; +} + +.grayButton { + -webkit-border-image: url(img/grayButton.png) 0 12 0 12; + color: #FFFFFF; +} + +/* @end */ + +/* @group Lists */ + +h1 + ul, h2 + ul, h3 + ul, h4 + ul, h5 + ul, h6 + ul { + margin-top: 0; +} + +ul { + color: black; + background: #fff; + border: 1px solid #B4B4B4; + font: bold 17px Helvetica; + padding: 0; + margin: 15px 10px 17px 10px; + -webkit-border-radius: 8px; +} + +ul li { + color: #666; + border-top: 1px solid #B4B4B4; + list-style-type: none; + padding: 10px 10px 10px 10px; +} + +/* when you have a first LI item on any list */ + +li:first-child, li:first-child a { + border-top: 0; + -webkit-border-top-left-radius: 8px; + -webkit-border-top-right-radius: 8px; +} + +li:last-child, li:last-child a { + -webkit-border-bottom-left-radius: 8px; + -webkit-border-bottom-right-radius: 8px; +} + +/* universal arrows */ + +ul li.arrow { + background-image: url(img/chevron.png); + background-position: right center; + background-repeat: no-repeat; +} + +#plastic ul li.arrow, #metal ul li.arrow { + background-image: url(../images/chevron_dg.png); + background-position: right center; + background-repeat: no-repeat; +} + +/* universal links on list */ + +ul li a, li.img a + a { + color: #000; + text-decoration: none; + text-overflow: ellipsis; + white-space: nowrap; + overflow: hidden; + display: block; + padding: 12px 10px 12px 10px; + margin: -10px; + -webkit-tap-highlight-color: rgba(0,0,0,0); +} + +ul li a.active { + background: #194fdb url(img/selection.png) 0 0 repeat-x; + color: #fff; +} + +ul li a.button { + background-color: #194fdb; + color: #fff; +} + +ul li.img a + a { + margin: -10px 10px -20px -5px; + font-size: 17px; + font-weight: bold; +} + +ul li.img a + a + a { + font-size: 14px; + font-weight: normal; + margin-left: -10px; + margin-bottom: -10px; + margin-top: 0; +} + +ul li.img a + small + a { + margin-left: -5px; +} + +ul li.img a + small + a + a { + margin-left: -10px; + margin-top: -20px; + margin-bottom: -10px; + font-size: 14px; + font-weight: normal; +} + +ul li.img a + small + a + a + a { + margin-left: 0px !important; + margin-bottom: 0; +} + +ul li a + a { + color: #000; + font: 14px Helvetica; + text-overflow: ellipsis; + white-space: nowrap; + overflow: hidden; + display: block; + margin: 0; + padding: 0; +} + +ul li a + a + a, ul li.img a + a + a + a, ul li.img a + small + a + a + a { + color: #666; + font: 13px Helvetica; + margin: 0; + text-overflow: ellipsis; + white-space: nowrap; + overflow: hidden; + display: block; + padding: 0; +} + +/* +@end */ + +/* @group Forms */ + +ul.form li { + padding: 7px 10px; +} + +ul.form li.error { + border: 2px solid red; +} + +ul.form li.error + li.error { + border-top: 0; +} + +ul.form li:hover { + background: #fff; +} + +ul li input[type="text"], ul li input[type="password"], ul li textarea, ul li select { + color: #777; + background: #fff url(../.png); + border: 0; + font: normal 17px Helvetica; + padding: 0; + display: inline-block; + margin-left: 0px; + width: 100%; + -webkit-appearance: textarea; +} + +ul li textarea { + height: 120px; + padding: 0; + text-indent: -2px; +} + +ul li select { + text-indent: 0px; + background: transparent url(../images/chevron.png) no-repeat 103% 3px; + -webkit-appearance: textfield; + margin-left: -6px; + width: 104%; +} + +ul li input[type="checkbox"], ul li input[type="radio"] { + margin: 0; + color: rgb(50,79,133); + padding: 10px 10px; +} + +ul li input[type="checkbox"]:after, ul li input[type="radio"]:after { + content: attr(title); + font: 17px Helvetica; + display: block; + width: 246px; + margin: -12px 0 0 17px; +} + +/* @end */ + +/* @group Edge to edge */ + +.edgetoedge h4 { + color: #fff; + background: rgb(154,159,170) url(img/listGroup.png) top left repeat-x; + border-top: 1px solid rgb(165,177,186); + text-shadow: #666 0 1px 0; + margin: 0; + padding: 2px 10px; +} + +.edgetoedge, .metal { + margin: 0; + padding: 0; + background-color: rgb(255,255,255); +} + +.edgetoedge ul, .metal ul, .plastic ul { + -webkit-border-radius: 0; + margin: 0; + border-left: 0; + border-right: 0; + border-top: 0; +} + +.metal ul { + border-top: 0; + border-bottom: 0; + background: rgb(180,180,180); +} + +.edgetoedge ul li:first-child, .edgetoedge ul li:first-child a, .edgetoedge ul li:last-child, .edgetoedge ul li:last-child a, .metal ul li:first-child a, .metal ul li:last-child a { + -webkit-border-radius: 0; +} + +.edgetoedge ul li small { + font-size: 16px; + line-height: 28px; +} + +.edgetoedge li, .metal li { + -webkit-border-radius: 0; +} + +.edgetoedge li em { + font-weight: normal; + font-style: normal; +} + +.edgetoedge h4 + ul { + border-top: 1px solid rgb(152,158,164); + border-bottom: 1px solid rgb(113,125,133); +} + +/* @end */ + +/* @group Mini Label */ + +ul li small { + color: #369; + font: 17px Helvetica; + text-align: right; + text-overflow: ellipsis; + white-space: nowrap; + overflow: hidden; + display: block; + width: 23%; + float: right; + padding: 3px 0px; +} + +ul li.arrow small { + padding: 0 15px; +} + +ul li small.counter { + font-size: 17px !important; + line-height: 13px !important; + font-weight: bold; + background: rgb(154,159,170); + color: #fff; + -webkit-border-radius: 11px; + padding: 4px 10px 5px 10px; + display: inline !important; + width: auto; + margin-top: -22px; +} + +ul li.arrow small.counter { + margin-right: 15px; +} + +/* @end */ + +/* @group Plastic */ + +#plastic ul li.arrow, #metal ul li.arrow { + background-image: url(img/listArrow.png); + background-position: right center; + background-repeat: no-repeat; +} + +.edgetoedge ul, .metal ul, .plastic ul { + -webkit-border-radius: 0; + margin: 0; + border-left: 0; + border-right: 0; + border-top: 0; +} + +.metal ul li { + border-top: 1px solid rgb(238,238,238); + border-bottom: 1px solid rgb(156,158,165); + background: url(../images/bgMetal.png) top left repeat-x; + font-size: 26px; + text-shadow: #fff 0 1px 0; +} + +.metal ul li a { + line-height: 26px; + margin: 0; + padding: 13px 0; +} + +.metal ul li a:hover { + color: rgb(0,0,0); +} + +.metal ul li:hover small { + color: inherit; +} + +.metal ul li a em { + display: block; + font-size: 14px; + font-style: normal; + color: #444; + width: 50%; + line-height: 14px; +} + +.metal ul li small { + float: right; + position: relative; + margin-top: 10px; + font-weight: bold; +} + +.metal ul li.arrow a small { + padding-right: 0; + line-height: 17px; +} + +.metal ul li.arrow { + background: url(../images/bgMetal.png) top left repeat-x, + url(../images/chevron_dg.png) right center no-repeat; +} + +.plastic { + margin: 0; + padding: 0; + background: rgb(173,173,173); +} + +.plastic ul { + -webkit-border-radius: 0; + margin: 0; + border-left: 0; + border-right: 0; + border-top: 0; + background-color: rgb(173,173,173); +} + +.plastic ul li { + -webkit-border-radius: 0; + border-top: 1px solid rgb(191,191,191); + border-bottom: 1px solid rgb(157,157,157); +} + +.plastic ul li:nth-child(odd) { + background-color: rgb(152,152,152); + border-top: 1px solid rgb(181,181,181); + border-bottom: 1px solid rgb(138,138,138); +} + +.plastic ul + p { + font-size: 11px; + color: #2f3237; + text-shadow: none; + padding: 10px 10px; +} + +.plastic ul + p strong { + font-size: 14px; + line-height: 18px; + text-shadow: #fff 0 1px 0; +} + +.plastic ul li a { + text-shadow: rgb(211,211,211) 0 1px 0; +} + +.plastic ul li:nth-child(odd) a { + text-shadow: rgb(191,191,191) 0 1px 0; +} + +.plastic ul li small { + color: #3C3C3C; + text-shadow: rgb(211,211,211) 0 1px 0; + font-size: 13px; + font-weight: bold; + text-transform: uppercase; + line-height: 24px; +} + +#plastic ul.minibanner, #plastic ul.bigbanner { + margin: 10px; + border: 0; + height: 81px; + clear: both; +} + +#plastic ul.bigbanner { + height: 140px !important; +} + +#plastic ul.minibanner li { + border: 1px solid rgb(138,138,138); + background-color: rgb(152,152,152); + width: 145px; + height: 81px; + float: left; + -webkit-border-radius: 5px; + padding: 0; +} + +#plastic ul.bigbanner li { + border: 1px solid rgb(138,138,138); + background-color: rgb(152,152,152); + width: 296px; + height: 140px; + float: left; + -webkit-border-radius: 5px; + padding: 0; + margin-bottom: 4px; +} + +#plastic ul.minibanner li:first-child { + margin-right: 6px; +} + +#plastic ul.minibanner li a { + color: transparent; + text-shadow: none; + display: block; + width: 145px; + height: 81px; +} + +#plastic ul.bigbanner li a { + color: transparent; + text-shadow: none; + display: block; + width: 296px; + height: 145px; +} + +/* @end */ + +/* @group Individual */ + +ul.individual { + border: 0; + background: none; + clear: both; + overflow: hidden; +} + +ul.individual li { + color: rgb(183,190,205); + background: white; + border: 1px solid rgb(180,180,180); + font-size: 14px; + text-align: center; + -webkit-border-radius: 8px; + -webkit-box-sizing: border-box; + width: 48%; + float: left; + display: block; + padding: 11px 10px 14px 10px; +} + +ul.individual li + li { + float: right; +} + +ul.individual li a { + color: rgb(50,79,133); + line-height: 16px; + margin: -11px -10px -14px -10px; + padding: 11px 10px 14px 10px; + -webkit-border-radius: 8px; +} + +ul.individual li a:hover { + color: #fff; + background: #36c; +} + +/* @end */ + +/* @group Toggle */ + + +.toggle { + width: 94px; + position: relative; + height: 27px; + display: block; + overflow: hidden; + float: right; +} + +.toggle input[type="checkbox"]:checked { + left: 0px; +} + +.toggle input[type="checkbox"] { + -webkit-tap-highlight-color: rgba(0,0,0,0); + margin: 0; + -webkit-border-radius: 5px; + background: #fff url(img/on_off.png) 0 0 no-repeat; + height: 27px; + overflow: hidden; + width: 149px; + border: 0; + -webkit-appearance: textarea; + background-color: transparent; + -webkit-transition: left .15s; + position: absolute; + top: 0; + left: -55px; +} +/* @end */ + + + +.info { + background: #dce1eb; + font-size: 12px; + line-height: 16px; + text-align: center; + text-shadow: rgba(255,255,255,.8) 0 1px 0; + color: rgb(76, 86, 108); + padding: 15px; + border-top: 1px solid rgba(76, 86, 108, .3); + font-weight: bold; +} diff --git a/asset/jqtouch/themes/apple/theme.min.css b/asset/jqtouch/themes/apple/theme.min.css new file mode 100644 index 0000000..decc185 --- /dev/null +++ b/asset/jqtouch/themes/apple/theme.min.css @@ -0,0 +1 @@ +body{background:#000;}body>*{background:#c5ccd3 url(img/pinstripes.png);}h1,h2{font:bold 18px Helvetica;text-shadow:rgba(255,255,255,.2) 0 1px 1px;color:#4c566c;margin:10px 20px 6px;}.toolbar{-webkit-box-sizing:border-box;border-bottom:1px solid #2d3642;padding:10px;height:45px;background:url(img/toolbar.png) #6d84a2 repeat-x;position:relative;}.black-translucent .toolbar{margin-top:20px;}.toolbar>h1{position:absolute;overflow:hidden;left:50%;top:10px;line-height:1em;margin:1px 0 0 -75px;height:40px;font-size:20px;width:150px;font-weight:bold;text-shadow:rgba(0,0,0,0.4) 0 -1px 0;text-align:center;text-overflow:ellipsis;white-space:nowrap;color:#fff;}body.landscape .toolbar>h1{margin-left:-125px;width:250px;}.button,.back,.cancel,.add{position:absolute;overflow:hidden;top:8px;right:6px;margin:0;border-width:0 5px;padding:0 3px;width:auto;height:30px;line-height:30px;font-family:inherit;font-size:12px;font-weight:bold;color:#fff;text-shadow:rgba(0,0,0,0.5) 0 -1px 0;text-overflow:ellipsis;text-decoration:none;white-space:nowrap;background:none;-webkit-border-image:url(img/toolButton.png) 0 5 0 5;}.button.active,.back.active,.cancel.active,.add.active{-webkit-border-image:url(img/toolButton.png) 0 5 0 5;}.blueButton{-webkit-border-image:url(img/blueButton.png) 0 5 0 5;border-width:0 5px;}.back{left:6px;right:auto;padding:0;max-width:55px;border-width:0 8px 0 14px;-webkit-border-image:url(img/backButton.png) 0 8 0 14;}.leftButton,.cancel{left:6px;right:auto;}.add{font-size:24px;line-height:24px;font-weight:bold;}.whiteButton,.grayButton{display:block;border-width:0 12px;padding:10px;text-align:center;font-size:20px;font-weight:bold;text-decoration:inherit;color:inherit;}.whiteButton{-webkit-border-image:url(img/whiteButton.png) 0 12 0 12;text-shadow:rgba(255,255,255,0.7) 0 1px 0;}.grayButton{-webkit-border-image:url(img/grayButton.png) 0 12 0 12;color:#FFF;}h1+ul,h2+ul,h3+ul,h4+ul,h5+ul,h6+ul{margin-top:0;}ul{color:black;background:#fff;border:1px solid #B4B4B4;font:bold 17px Helvetica;padding:0;margin:15px 10px 17px 10px;-webkit-border-radius:8px;}ul li{color:#666;border-top:1px solid #B4B4B4;list-style-type:none;padding:10px 10px 10px 10px;}li:first-child,li:first-child a{border-top:0;-webkit-border-top-left-radius:8px;-webkit-border-top-right-radius:8px;}li:last-child,li:last-child a{-webkit-border-bottom-left-radius:8px;-webkit-border-bottom-right-radius:8px;}ul li.arrow{background-image:url(img/chevron.png);background-position:right center;background-repeat:no-repeat;}#plastic ul li.arrow,#metal ul li.arrow{background-image:url(../images/chevron_dg.png);background-position:right center;background-repeat:no-repeat;}ul li a,li.img a+a{color:#000;text-decoration:none;text-overflow:ellipsis;white-space:nowrap;overflow:hidden;display:block;padding:12px 10px 12px 10px;margin:-10px;-webkit-tap-highlight-color:rgba(0,0,0,0);}ul li a.active{background:#194fdb url(img/selection.png) 0 0 repeat-x;color:#fff;}ul li a.button{background-color:#194fdb;color:#fff;}ul li.img a+a{margin:-10px 10px -20px -5px;font-size:17px;font-weight:bold;}ul li.img a+a+a{font-size:14px;font-weight:normal;margin-left:-10px;margin-bottom:-10px;margin-top:0;}ul li.img a+small+a{margin-left:-5px;}ul li.img a+small+a+a{margin-left:-10px;margin-top:-20px;margin-bottom:-10px;font-size:14px;font-weight:normal;}ul li.img a+small+a+a+a{margin-left:0!important;margin-bottom:0;}ul li a+a{color:#000;font:14px Helvetica;text-overflow:ellipsis;white-space:nowrap;overflow:hidden;display:block;margin:0;padding:0;}ul li a+a+a,ul li.img a+a+a+a,ul li.img a+small+a+a+a{color:#666;font:13px Helvetica;margin:0;text-overflow:ellipsis;white-space:nowrap;overflow:hidden;display:block;padding:0;}ul.form li{padding:7px 10px;}ul.form li.error{border:2px solid red;}ul.form li.error+li.error{border-top:0;}ul.form li:hover{background:#fff;}ul li input[type="text"],ul li input[type="password"],ul li textarea,ul li select{color:#777;background:#fff url(../.png);border:0;font:normal 17px Helvetica;padding:0;display:inline-block;margin-left:0;width:100%;-webkit-appearance:textarea;}ul li textarea{height:120px;padding:0;text-indent:-2px;}ul li select{text-indent:0;background:transparent url(../images/chevron.png) no-repeat 103% 3px;-webkit-appearance:textfield;margin-left:-6px;width:104%;}ul li input[type="checkbox"],ul li input[type="radio"]{margin:0;color:#324f85;padding:10px 10px;}ul li input[type="checkbox"]:after,ul li input[type="radio"]:after{content:attr(title);font:17px Helvetica;display:block;width:246px;margin:-12px 0 0 17px;}.edgetoedge h4{color:#fff;background:#9a9faa url(img/listGroup.png) top left repeat-x;border-top:1px solid #a5b1ba;text-shadow:#666 0 1px 0;margin:0;padding:2px 10px;}.edgetoedge,.metal{margin:0;padding:0;background-color:#fff;}.edgetoedge ul,.metal ul,.plastic ul{-webkit-border-radius:0;margin:0;border-left:0;border-right:0;border-top:0;}.metal ul{border-top:0;border-bottom:0;background:#b4b4b4;}.edgetoedge ul li:first-child,.edgetoedge ul li:first-child a,.edgetoedge ul li:last-child,.edgetoedge ul li:last-child a,.metal ul li:first-child a,.metal ul li:last-child a{-webkit-border-radius:0;}.edgetoedge ul li small{font-size:16px;line-height:28px;}.edgetoedge li,.metal li{-webkit-border-radius:0;}.edgetoedge li em{font-weight:normal;font-style:normal;}.edgetoedge h4+ul{border-top:1px solid #989ea4;border-bottom:1px solid #717d85;}ul li small{color:#369;font:17px Helvetica;text-align:right;text-overflow:ellipsis;white-space:nowrap;overflow:hidden;display:block;width:23%;float:right;padding:3px 0;}ul li.arrow small{padding:0 15px;}ul li small.counter{font-size:17px!important;line-height:13px!important;font-weight:bold;background:#9a9faa;color:#fff;-webkit-border-radius:11px;padding:4px 10px 5px 10px;display:inline!important;width:auto;margin-top:-22px;}ul li.arrow small.counter{margin-right:15px;}#plastic ul li.arrow,#metal ul li.arrow{background-image:url(img/listArrow.png);background-position:right center;background-repeat:no-repeat;}.edgetoedge ul,.metal ul,.plastic ul{-webkit-border-radius:0;margin:0;border-left:0;border-right:0;border-top:0;}.metal ul li{border-top:1px solid #eee;border-bottom:1px solid #9c9ea5;background:url(../images/bgMetal.png) top left repeat-x;font-size:26px;text-shadow:#fff 0 1px 0;}.metal ul li a{line-height:26px;margin:0;padding:13px 0;}.metal ul li a:hover{color:#000;}.metal ul li:hover small{color:inherit;}.metal ul li a em{display:block;font-size:14px;font-style:normal;color:#444;width:50%;line-height:14px;}.metal ul li small{float:right;position:relative;margin-top:10px;font-weight:bold;}.metal ul li.arrow a small{padding-right:0;line-height:17px;}.metal ul li.arrow{background:url(../images/bgMetal.png) top left repeat-x,url(../images/chevron_dg.png) right center no-repeat;}.plastic{margin:0;padding:0;background:#adadad;}.plastic ul{-webkit-border-radius:0;margin:0;border-left:0;border-right:0;border-top:0;background-color:#adadad;}.plastic ul li{-webkit-border-radius:0;border-top:1px solid #bfbfbf;border-bottom:1px solid #9d9d9d;}.plastic ul li:nth-child(odd){background-color:#989898;border-top:1px solid #b5b5b5;border-bottom:1px solid #8a8a8a;}.plastic ul+p{font-size:11px;color:#2f3237;text-shadow:none;padding:10px 10px;}.plastic ul+p strong{font-size:14px;line-height:18px;text-shadow:#fff 0 1px 0;}.plastic ul li a{text-shadow:#d3d3d3 0 1px 0;}.plastic ul li:nth-child(odd) a{text-shadow:#bfbfbf 0 1px 0;}.plastic ul li small{color:#3C3C3C;text-shadow:#d3d3d3 0 1px 0;font-size:13px;font-weight:bold;text-transform:uppercase;line-height:24px;}#plastic ul.minibanner,#plastic ul.bigbanner{margin:10px;border:0;height:81px;clear:both;}#plastic ul.bigbanner{height:140px!important;}#plastic ul.minibanner li{border:1px solid #8a8a8a;background-color:#989898;width:145px;height:81px;float:left;-webkit-border-radius:5px;padding:0;}#plastic ul.bigbanner li{border:1px solid #8a8a8a;background-color:#989898;width:296px;height:140px;float:left;-webkit-border-radius:5px;padding:0;margin-bottom:4px;}#plastic ul.minibanner li:first-child{margin-right:6px;}#plastic ul.minibanner li a{color:transparent;text-shadow:none;display:block;width:145px;height:81px;}#plastic ul.bigbanner li a{color:transparent;text-shadow:none;display:block;width:296px;height:145px;}ul.individual{border:0;background:none;clear:both;overflow:hidden;}ul.individual li{color:#b7becd;background:white;border:1px solid #b4b4b4;font-size:14px;text-align:center;-webkit-border-radius:8px;-webkit-box-sizing:border-box;width:48%;float:left;display:block;padding:11px 10px 14px 10px;}ul.individual li+li{float:right;}ul.individual li a{color:#324f85;line-height:16px;margin:-11px -10px -14px -10px;padding:11px 10px 14px 10px;-webkit-border-radius:8px;}ul.individual li a:hover{color:#fff;background:#36c;}.toggle{width:94px;position:relative;height:27px;display:block;overflow:hidden;float:right;}.toggle input[type="checkbox"]:checked{left:0;}.toggle input[type="checkbox"]{-webkit-tap-highlight-color:rgba(0,0,0,0);margin:0;-webkit-border-radius:5px;background:#fff url(img/on_off.png) 0 0 no-repeat;height:27px;overflow:hidden;width:149px;border:0;-webkit-appearance:textarea;background-color:transparent;-webkit-transition:left .15s;position:absolute;top:0;left:-55px;}.info{background:#dce1eb;font-size:12px;line-height:16px;text-align:center;text-shadow:rgba(255,255,255,.8) 0 1px 0;color:#4c566c;padding:15px;border-top:1px solid rgba(76,86,108,.3);font-weight:bold;} \ No newline at end of file diff --git a/asset/jqtouch/themes/jqt/img/back_button.png b/asset/jqtouch/themes/jqt/img/back_button.png new file mode 100644 index 0000000000000000000000000000000000000000..9873901c0e74ba89d1399acfee2a7066601bd6fb GIT binary patch literal 3756 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 Hu0mjf-jO>3 literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/jqt/img/button.png b/asset/jqtouch/themes/jqt/img/button.png new file mode 100644 index 0000000000000000000000000000000000000000..52cc7e279723b94d969ca54a8db3ce7e921dc804 GIT binary patch literal 3315 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 literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/jqt/img/button_clicked.png b/asset/jqtouch/themes/jqt/img/button_clicked.png new file mode 100644 index 0000000000000000000000000000000000000000..25d478fc8fcd7bc94bdf26cd2e857c26ec228200 GIT binary patch literal 3283 zcmV;^3@r1BP)4Tx0C)kNmUmE8*%F7(y?1gT%`gNBL(Vx3Npc1Wl0{*d8DIzl3^QQBj40rW zq9REVWL3ZgSC=4bL=*!Hf&mqEK^`LNy10s{7~Y+=N_el{?yK7Vlyc`b71t_QIiLxaA zX_V=SX%dDp5*DHfqO2(47=;G!By&RN_Hu7rC~-j*xop^OBgT$sz} z<)M5FW$kov1|Q{jDAO}|>>L0v6p3HNj7ZRptadK?@O!%pkoUF ziudPz+6MuUE&!l?V8MGBl6grHiLxBb%<}T`O!+*HsidIa?EebBDgPQ4+-EAe?_2Gd zp1dTsI9io+%bGbF$bR9@FH%hxi{KT#(j+JdDG5NjxD>fL;}eP8na2jJ8|A z<%{^40w!PZR~`O`#}?!u!LM_T0303$F3ro*bRE^G#~U^h4b4u_Y+$#6Ej8ZLl$ zz!h*kd<<@fFTmH~+wds-9G*b{LPi*f24aG+5Dz36iA9nSA+ioBM#_xYfT zCS&ukh1hcJVQd@r681KB0{a$+!!dArI6Is#E(Vv1TZ7w<+mCC-oyQI0#&I)vJYETJ zgm=aVoTuEQyrxpAx>Q$cELB9^L2aa7q&}j)lcGtPO8H4~ zrPfPTOSMZ4NxhUNO6y3wNw1JzEnO~sQhGr8g$z+fSH?qzEwfIhTIQ6@u*{4sP1Zs- zST;j;yKIx}RoSO)ADli*7A|^E9I-@&&ZE55QZ+pkCDzOWt?E#VSG?fRd7?_DHJKRC=4mgDlSrV zRpcoaE4C`$R{WsERPs_vQ`)7}q4ZE0qim=gs+^~MK>3pLi$(NBj*B>piWi+&bYBHl zF;odtS)+1DrB7u>RZZ1LHA}Tp^`hzvHHMn2TB_O}wXNNGm>U{M*>gUv-G3A+V z%yec2vxhmYp`zidA=aqV=+~Ij)YFX6+@#s6`B00b#nMXB+N0I2HLb0#9i*MF-K>3I zhp5BSNzvJ-)2lP9tEU^KyH&SC_o<$uo}b=oy=J`!`c!=v{cQbu{aXe&1C~LW!G41q zhOnWHVTxh3;eZirWNXAX+HW*yj5W4578utX51UX-+)Q#!noY(`8K!}zn@l@QUz%x~ z#hUFh>oxmqZeyNq-e5jrA!p%lvB{##;txwhOO9o=jTzz zZD=+@Hd}4FZ9duB*$Qo2Y^UtB?Go&2?1ou%RtRf5>xw;=hZ7FJ zJDNDAIW{>yb<%Uw4IA(#^mv z)$N$uOLud3p?jPAtcQcgT95Odh^LQdv1h-RoL7WbmDeM0P48syX76bq8=o~k=Y6rh z0lvF@hy7IjIDU|YssbJd8U_jjyMo{#|DfGL50>aG5iIEl2El&8 zyMrHw=!Im5{2Yo44GFCdeG+C7mLJx;l(sZ}Y17iT;qKw3;Uf|H5#osMNa@J9$i~Ro zD9@;}sL^P%=(W+;W0Yg~F`cpa*vQz!u`|oOmhD|O5oZ%u7NsoaT6N_HmwbUAcR>Q#@y08E-PlIjJn^X|i+j z?&PTymz4697km$X75`PLZ)$DoY+7*Ik+d)AQR%H2gp7oYQvx|bnxH3BEpuh&V3tu< zVb*B2L-yY6X<>lya1NBSJf~AcM}MaJ#QNeb;<4Ptxz)Mv@*?w2u9RIVSlPGAa8=Q& z$<^Mgzh8q{!&%dvuaUnoe{8MW+PZbny2N$e>$TPwte@E6v*GAQ(#Eunzicw!RJQ5O z=BUkG1*!!b3dXniY-ui(DijtDZ*|;SyA89AzpcN>s;IK)b1}F0T8Vi{dCAA^obA`X zv-qy!yDvMEcJ!CpmLAxN+bP(2XP3*aqh+#XtINiB2kma(!`xH6=gr>uy;sYv%WLdbR%%!7to&G&Qgyr9y}GqVrKYH6c0YIj&;i#2Ew!q(CAA+8@(4@OS=+UsFJ&ksajZG>|rOj}&xOwVW+_4)! zc>d7YV$xFA%4jV)4vveDKl?G^$2%tiPIRASoox9@=ck%BT3c~D)V`{Hx+A4yv@@o2 z@Ra|l?k>l!wx3OZK5|;)boCkeGo@!qXA91LIk)=U%=xVIFD@is81Ihn9=RBO@m5c0 zPyeNWOII#?U%uGu)_d-X^Oe(A9j>0b#=6#V-S&EWpG{xeFE+ol_1pHh57-TK-mt&X zHRv>WcF1Mu!cEVcmv8yqx_*1f?ZG<{ckT|y4UgXC-hFy6{obqlx%cNrHax&SD1IpO zu>6tAqxxSBer+AK9X&JVIo9`h>En@c&iM0x<^1d8M8Om4lk!RR$;PLaPft&IPu+O7 z?AgTgtmktt3V)ORt>&fv%b$LC{k?BGdV1oO@YR<;w!c<-edLYxo9>yAnMZFk-pew)G&ukO0z64XK~zW$ z?N&ig6G0SyGdr6mU91LMj8_H!1RnGPc*TY*a5E%^vxy$6{s3aslLzBP4fGdyz>E9@ zIS3>*UJ4wPq%FHUJL~(FP8}Q2R<}1^^7>}x&3y08H#4s*s4MqZSD);D*;zJeIw1x5 zcKpv)usdZH#Oq=y#Qx-ssn^fe)*fOVymYr(-E6npw@RgpR45e4^E?a>B}tM{7>0Co z^n;4U;>Y^N#%*zLW##eS&hDd1r9#q^98GX8$mZ{2=ekxWnhp;R>H5^vgI$-Fk3&1)(=4zFAo3rOpjgy5_h6!tW+K3GWq zeCucK3Al>4;WHd12{Jwbwu}1%oCRj*yMAWCSJ<-Fx*zAi`#4~gFtCo}!N5QlC^?O` zE>#u?xC#+8Yu<8_IRhgKWLVDKgxs~@-WbpV&byhr6WoP^wtqj+l#~H2XK;?kWFH6u z*fuQ0_1m$`!9P9D;{k7ro0$c1t-Eu))a*b(e%@mE-S8t~T1If7I7`)PwXzzLcjlc= zhh*NMF5Wq~%SNw#PD_spw=r5;lu{A?jq()W0aupG^s3_^3wc#_5Ie?ry1q@{LLXV9hN45THxvFn;+`+^#!k1s~vA|f8OK*rW=i~SJ?(p z6nUtW!zkDKh^c5SE-k)#`QrHl?jQ8Ney{`1c7iov{g+#WThU_OXW;K_=_jm9sX_aA RN&Nr-002ovPDHLkV1iWTX0iYP literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/jqt/img/chevron.png b/asset/jqtouch/themes/jqt/img/chevron.png new file mode 100644 index 0000000000000000000000000000000000000000..5bdaa46de7995267a392da77bfeacacbe2004f49 GIT binary patch literal 3074 zcma)8c{CL68vcevBUy?>jf7IR355|cj3v@srl^$3KK6Yq(a4f9t&Ao%p5Rgb3z&$^i`x$6oG8yZYs!i+7wA5U~riNF(4yc zSU_t&Dz70b^UPzx6URIoy7*s~oQaOmF4=$ta7j;3NMFX#dFdj-R7RbO`+8B`x|+kA zKPkbQKo482`#PckVtY++ISPnfxhxMmhi8XkPKUA+v=ZgGiK{Qzz{K{_;yg>;WIHg? z;i?6I+u(u7N!6W4=;N(Fpg{64$R#xmAwf1DQ1lX1IH$yZ@Z|&5J2EkMsr+t4AT@2;}|4JR1(zvL&e%7(NT|8EdbIW!uX|*yllix^Z}`2 z{tBeveB_`84t#YSC=sLR%b#54U-5{)Q( z@el*JKxmUV(Exe|MQ$;*y=3~BEOE2tel~0iruIAqB`>bgqLIyeLN7!|GhMh*(=I}%=*6N2(9Mo(C6;rag@3f216!yQD+5Lg@#F*`d{D;v%;K8O)hYG+Gk{m zzwC)vo3;|`w`_%0;LmR=ruJ+FO4in|5s#UG%)#kZxrg$N+*JV#Q5(I?OEk^Q5| zrds*wC$m#BEh&dhY57hVvjWjeEd&q^hmA7tzP^4;4dmrY*#}k>_PLyMFHV!w1cz|+6kHlP3CMYj<#w| zQxa_FX%A$mF>Dy>g7MMspjN2tQe@7ZoZBMR6gy5@1^zLW*%W?Fq4=$OwK-qd|uqkOYO=#%DN&EBHPNHxK%1V{vzp% zK2)9s(P*EXGdWWI7y6yLt8>=0MF-Ya>|^PA0H7}ph%n0My%X63uaC?h%Qxs;;g>F0Vz-s4T&b~$D-7!Ow-t{hx> zB4o^cgM<>gB%~r|7;o9;)AlBQ;4NC_Tp^~=sj#p=ubf)m6iD&?raYxQfa}Ix>RA|s zyVSaRxrn&@by2JMRKZapSD`R(JU{jO@{sRva0R~fTX9kOqlxrM_((=WM#rRzzKni` zP5E@kT>IQ!kGZk?n?0|{wZltK?Y$1{fKh)U@t$BlDn7d`X)IOZF3)6$Ky{LoLQ5SC$ zsq5{`HRaV~{{8-%ON#3P0et~Hfp-Hb0bk^m%-P{J9hG~bo&*Te+|Bv%w8;BWG+(pkMJ8wAS7`o+=9xSe2_lDt0ThWiOY#}i<&{Z67wmaDM`)>G z0zy_QIz~kc#PJ5hLt6zl}X?* zEl1ssY90?DRzyWM!=}8Ju%-H50n6xU{ZrD~yS~?Bt{^A4tv2EJz2~ww z?$GNS{ZW(Ap>Yry-nW_Wu34>_g$8Q}eEQXQv2X;s1~nI2FFIt=gU&XURH&x*2mfC1 z4fl=l9s5No8n55;F3H>UA_g0xzJ4)%FgN3VvOa&u-dbllazXKD={-?H(Hv2C_vKNa zbj!LcA8Q|Zw=fuToAFa}MIYox1M{u*nipKlTw7i1;y%T_8@XQLKDt+Op`3ZE{DyDO zk+D<1@U>&-hXaBW2Hw-g0&9%?9t}zidE?z1=nN6+>*(O@V72Yke!T&|kha~5dK1d~ z?1i3?xji~NKPQ5DkNJz236pi!5+(C|ej;$>-gf6kO}}0;t?qhCZp>#7i-66c4dVE? zrhrfOuJnfEG;i+Jc~u(X*634Z1vi+hq3fLMGw0uGn%n+C$w4C}Vy=%yA2lxOt{Ha3 z+EE-S&>PoNIG|3JaA_UdTaWn7+u592GsI8t3f7$6Y3ANL-su~NPpzNzTxyc~ zVDv@7Tj7JHXMOkROt0_!IZE1dUv<2Sm2cH>V8_~>yWiSV%?31z(&{FIrW>#Cb;x{R zj54bmps!K&#&N`(?4N%Urv7~KG>gh{>IP{^_LIQ)HGcs{Z&xEZ&ABB zX2P%6G@r-_-^ni%gKWlvn$k+M;9eP;q@^!F#}wD!l$L-ss?BaM-P9(NPn*)OM+M%>Fe?eSA!u|V{53Zjo})w z!D1D$1h(7&(Fg6-c!dYXBltf8>Bjx|Kk}c$x9N341jVZHx@4d0~9(dvQWZ-ZF9G+z!zVly$tGg}EKHz^Cb{NYoECVn^ LndrVpVjuq-_e0dN literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/jqt/img/chevron_circle.png b/asset/jqtouch/themes/jqt/img/chevron_circle.png new file mode 100644 index 0000000000000000000000000000000000000000..b477e7c9540a8ca98961e2a4a2f16db825e9097f GIT binary patch literal 1243 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 Gi~ldihm0Tq literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/jqt/img/rowhead.png b/asset/jqtouch/themes/jqt/img/rowhead.png new file mode 100644 index 0000000000000000000000000000000000000000..b2fa8f67b012f2c5eb7965fc7b401e13bce2d8aa GIT binary patch literal 171 zcmeAS@N?(olHy`uVBq!ia0vp^j6f{O!31P*e0{tR#3^x&C<)F_D=AMbN@Z|N$xljE z@XSq2PYp^6;7*cV|x66~SK|z4!c-aBgM}ba1CVUK)tNFe~ct^#G zlAx&$ky=XxQg05`M?I SqL~?JFoUP7pUXO@geCyCj6Bx> literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/jqt/img/toggle.png b/asset/jqtouch/themes/jqt/img/toggle.png new file mode 100644 index 0000000000000000000000000000000000000000..3b62ebf26eaf8b21e341d413a6bd7cebcf5e7075 GIT binary patch literal 2815 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 literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/jqt/img/whiteButton.png b/asset/jqtouch/themes/jqt/img/whiteButton.png new file mode 100644 index 0000000000000000000000000000000000000000..5514b270053a41039e9e96ef8591796521ee0312 GIT binary patch literal 978 zcmV;@11}R*8aG1*L?d1O->_T@+D~u1Y}!yL0VI=|WL) zUB!jV?nDqFVEqcjNU7Q;7-O1A(q?8dlX-96yZ5-5q-Ly5=jDGlkNe*5{m(h~zIU$B ztvpZh0>hld-kwYNkqy3Ko}K-V%D(G)Z`(9CN35XDjL&xuH$Mh_XF(}UB(Tw%lJL(m|<1LC)=R9eoc+{eJ zNQwFm3ZOo%tAYib`a=Ya6#-N=4JiO(J0G^!!{zGLYx*)_QJi=^gsb6jQm_J=B!6wD zD%0-bC{8`;0(Q9FGD%w0qhLC5rQirtj;nGAUq!X!Dqd2rt6&lNPuJ>g7pqvn zrLC}dJQx&>lhnC-)EE`H)reg0T)izKV$|3W#Z{x-uG+(BCOFiFCeuK~FK_qmdcCS1 z>8qPuMY7^&mwW$}US2j%`m-B`MG8c7zyGk_Te#n^&tIcWp2Z*u%VSYOaGhsH3-(@~ zmGI-aXiXaBcJ0@|xe~1jq8+&sKXGKh9t>WX-&ip>B{%Tf)t#qUx1u_4ei+87UrHDfl6dXpw%k7!k~_oku06C3S8F^@(Qf&-L}LBUh<3`S518 zHslKoXby|rLrF-aMbk8j+ef37#cK7AgI*>xK3*KI+wDGQqnw)Edn!H~2Jv7#l+-p> zSL68q&WJ!JQ!W>a*5>p3XLojzq*mM7in|*4KU7;ZTp6~iyZ`_I07*qoM6N<$f;?{4 AHUIzs literal 0 HcmV?d00001 diff --git a/asset/jqtouch/themes/jqt/theme.css b/asset/jqtouch/themes/jqt/theme.css new file mode 100644 index 0000000..cbfe608 --- /dev/null +++ b/asset/jqtouch/themes/jqt/theme.css @@ -0,0 +1,528 @@ +body { + background: #000; + color: #ddd; +} +body > * { + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#333), to(#5e5e65)); +} +h1, h2 { + font: bold 18px Helvetica; + text-shadow: rgba(255,255,255,.2) 0 1px 1px; + color: #000; + margin: 10px 20px 5px; +} +/* @group Toolbar */ +.toolbar { + -webkit-box-sizing: border-box; + border-bottom: 1px solid #000; + padding: 10px; + height: 45px; + background: url(img/toolbar.png) #000000 repeat-x; + position: relative; +} +.black-translucent .toolbar { + margin-top: 20px; +} +.toolbar > h1 { + position: absolute; + overflow: hidden; + left: 50%; + top: 10px; + line-height: 1em; + margin: 1px 0 0 -75px; + height: 40px; + font-size: 20px; + width: 150px; + font-weight: bold; + text-shadow: rgba(0,0,0,1) 0 -1px 1px; + text-align: center; + text-overflow: ellipsis; + white-space: nowrap; + color: #fff; +} +body.landscape .toolbar > h1 { + margin-left: -125px; + width: 250px; +} +.button, .back, .cancel, .add { + position: absolute; + overflow: hidden; + top: 8px; + right: 10px; + margin: 0; + border-width: 0 5px; + padding: 0 3px; + width: auto; + height: 30px; + line-height: 30px; + font-family: inherit; + font-size: 12px; + font-weight: bold; + color: #fff; + text-shadow: rgba(0, 0, 0, 0.5) 0px -1px 0; + text-overflow: ellipsis; + text-decoration: none; + white-space: nowrap; + background: none; + -webkit-border-image: url(img/button.png) 0 5 0 5; +} +.blueButton { + -webkit-border-image: url(img/blueButton.png) 0 5 0 5; + border-width: 0 5px; +} +.back { + left: 6px; + right: auto; + padding: 0; + max-width: 55px; + border-width: 0 8px 0 14px; + -webkit-border-image: url(img/back_button.png) 0 8 0 14; +} +.back.active { + -webkit-border-image: url(img/back_button_clicked.png) 0 8 0 14; + color: #aaa; +} +.leftButton, .cancel { + left: 6px; + right: auto; +} +.add { + font-size: 24px; + line-height: 24px; + font-weight: bold; +} +.whiteButton, +.grayButton { + display: block; + border-width: 0 12px; + padding: 10px; + text-align: center; + font-size: 20px; + font-weight: bold; + text-decoration: inherit; + color: inherit; +} +.whiteButton { + -webkit-border-image: url(img/whiteButton.png) 0 12 0 12; + text-shadow: rgba(255, 255, 255, 0.7) 0 1px 0; +} +.grayButton { + -webkit-border-image: url(img/grayButton.png) 0 12 0 12; + color: #FFFFFF; +} +/* @end */ +/* @group Lists */ +h1 + ul, h2 + ul, h3 + ul, h4 + ul, h5 + ul, h6 + ul { + margin-top: 0; +} +ul { + color: #aaa; + border: 1px solid #333333; + font: bold 18px Helvetica; + padding: 0; + margin: 15px 10px 17px 10px; +} +ul.rounded { + -webkit-border-radius: 8px; + -webkit-box-shadow: rgba(0,0,0,.3) 1px 1px 3px; +} +ul.rounded li:first-child, ul.rounded li:first-child a { + border-top: 0; + -webkit-border-top-left-radius: 8px; + -webkit-border-top-right-radius: 8px; +} +ul.rounded li:last-child, ul.rounded li:last-child a { + -webkit-border-bottom-left-radius: 8px; + -webkit-border-bottom-right-radius: 8px; +} +ul li { + color: #666; + border-top: 1px solid #333; + border-bottom: #555858; + list-style-type: none; + padding: 10px 10px 10px 10px; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#4c4d4e), to(#404142)); + overflow: hidden; +} +ul li.arrow { + background-image: url(img/chevron.png), -webkit-gradient(linear, 0% 0%, 0% 100%, from(#4c4d4e), to(#404142)); + background-position: right center; + background-repeat: no-repeat; +} +ul li.forward { + background-image: url(img/chevron_circle.png), -webkit-gradient(linear, 0% 0%, 0% 100%, from(#4c4d4e), to(#404142)); + background-position: right center; + background-repeat: no-repeat; +} +/* universal links on list */ +ul li a, li.img a + a { + color: #fff; + text-decoration: none; + text-overflow: ellipsis; + white-space: nowrap; + overflow: hidden; + display: block; + padding: 12px 10px 12px 10px; + margin: -10px; + -webkit-tap-highlight-color: rgba(0,0,0,0); + text-shadow: rgba(0,0,0,.2) 0 1px 1px; +} +ul li a.active, ul li a.button { + background-color: #53b401; + color: #fff; +} +ul li a.active.loading { + background-image: url(img/loading.gif); + background-position: 95% center; + background-repeat: no-repeat; +} +ul li.arrow a.active { + background-image: url(img/chevron.png); + background-position: right center; + background-repeat: no-repeat; +} +ul li.forward a.active { + background-image: url(img/chevron_circle.png); + background-position: right center; + background-repeat: no-repeat; +} +ul li.img a + a { + margin: -10px 10px -20px -5px; + font-size: 17px; + font-weight: bold; +} +ul li.img a + a + a { + font-size: 14px; + font-weight: normal; + margin-left: -10px; + margin-bottom: -10px; + margin-top: 0; +} +ul li.img a + small + a { + margin-left: -5px; +} +ul li.img a + small + a + a { + margin-left: -10px; + margin-top: -20px; + margin-bottom: -10px; + font-size: 14px; + font-weight: normal; +} +ul li.img a + small + a + a + a { + margin-left: 0px !important; + margin-bottom: 0; +} +ul li a + a { + color: #000; + font: 14px Helvetica; + text-overflow: ellipsis; + white-space: nowrap; + overflow: hidden; + display: block; + margin: 0; + padding: 0; +} +ul li a + a + a, ul li.img a + a + a + a, ul li.img a + small + a + a + a { + color: #666; + font: 13px Helvetica; + margin: 0; + text-overflow: ellipsis; + white-space: nowrap; + overflow: hidden; + display: block; + padding: 0; +} +/* +@end */ +/* @group Forms */ +ul.form li { + padding: 7px 10px; +} +ul.form li.error { + border: 2px solid red; +} +ul.form li.error + li.error { + border-top: 0; +} +ul li input[type="text"], ul li input[type="password"], ul li textarea, ul li select { + color: #777; + background: transparent; + background-image: none;; + border: 0; + font: normal 17px Helvetica; + padding: 0; + display: inline-block; + margin-left: 0px; + width: 100%; + -webkit-appearance: textarea; +} +ul li textarea { + height: 120px; + padding: 0; + text-indent: -2px; +} +ul li select { + text-indent: 0px; + background: transparent url(img/chevron.png) no-repeat right center; + -webkit-appearance: textfield; + margin-left: -6px; + width: 104%; +} +ul li input[type="checkbox"], ul li input[type="radio"] { + margin: 0; + padding: 10px 10px; +} +ul li input[type="checkbox"]:after, ul li input[type="radio"]:after { + content: attr(title); + font: 17px Helvetica; + display: block; + width: 246px; + color: #777; + margin: -12px 0 0 17px; +} +/* @end */ +/* @group Mini Label */ +ul li small { + color: #64c114; + font: 17px Helvetica; + text-align: right; + text-overflow: ellipsis; + white-space: nowrap; + overflow: hidden; + display: block; + width: 23%; + float: right; + padding: 0; +} +ul li.arrow small { + padding: 0 15px; +} +ul li small.counter { + font-size: 17px; + line-height: 13px; + font-weight: bold; + background: rgba(0,0,0,.15); + color: #fff; + -webkit-border-radius: 11px; + padding: 4px 10px 5px 10px; + display: block; + width: auto; + margin-top: -22px; + -webkit-box-shadow: rgba(255,255,255,.1) 0 1px 0; +} +ul li.arrow small.counter { + margin-right: 15px; +} +/* @end */ +/* @group Individual */ +ul.individual { + border: 0; + background: none; + clear: both; + overflow: hidden; + padding-bottom: 3px; + -webkit-box-shadow: none; +} +ul.individual li { + background: #4c4d4e; + border: 1px solid #333; + font-size: 14px; + text-align: center; + -webkit-border-radius: 8px; + -webkit-box-sizing: border-box; + width: 48%; + float: left; + display: block; + padding: 11px 10px 14px 10px; + -webkit-box-shadow: rgba(0,0,0,.2) 1px 1px 3px; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#4c4d4e), to(#404142)); +} +ul.individual li + li { + float: right; +} +ul.individual li a { + color: #fff; + line-height: 16px; + margin: -11px -10px -14px -10px; + padding: 11px 10px 14px 10px; + -webkit-border-radius: 8px; +} +/* @end */ +/* @group Toggle */ +.toggle { + width: 94px; + position: relative; + height: 27px; + display: block; + overflow: hidden; + float: right; +} +.toggle input[type="checkbox"]:checked { + left: 0px; +} +.toggle input[type="checkbox"] { + -webkit-appearance: textarea; + -webkit-border-radius: 5px; + -webkit-tap-highlight-color: rgba(0,0,0,0); + -webkit-transition: left .15s; + background-color: transparent; + background: #fff url(img/on_off.png) 0 0 no-repeat; + border: 0; + height: 27px; + left: -55px; + margin: 0; + overflow: hidden; + position: absolute; + top: 0; + width: 149px; +} +/* @end */ +/* @group Info */ +.info { + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#ccc), to(#aaa), color-stop(.6,#CCCCCC)); + font-size: 12px; + line-height: 16px; + text-align: center; + text-shadow: rgba(255,255,255,.8) 0 1px 0; + color: #444; + padding: 15px; + border-top: 1px solid rgba(255,255,255,.2); + font-weight: bold; +} +/* @end */ +/* @group Edge to edge */ +ul.edgetoedge { + border-width: 1px 0; + margin: 0; + padding: 0; +} +ul.edgetoedge li { + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#1e1f21), to(#272729)); + border-bottom: 2px solid #000; + border-top: 1px solid #4a4b4d; + font-size: 20px; + margin-bottom: -1px; +} +ul.edgetoedge li.sep { + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(rgba(0,0,0,0)), to(rgba(0,0,0,.5))); + border-bottom: 1px solid #111113; + border-top: 1px solid #666; + color: #3e9ac3; + font-size: 16px; + margin: 1px 0 0 0; + padding: 2px 10px; + text-shadow: #000 0 1px 0; +} +ul.edgetoedge li em { + font-weight: normal; + font-style: normal; +} +/* @end */ +/* @group Plastic */ +#plastic { + background: #17181a; +} +ul.plastic { + background: #17181a; + color: #aaa; + font: bold 18px Helvetica; + margin: 0; + padding: 0; + border-width: 0 0 1px 0; +} +ul.plastic li { + border-width: 1px 0; + border-style: solid; + border-top-color: #222; + border-bottom-color: #000; + color: #666; + list-style-type: none; + overflow: hidden; + padding: 10px 10px 10px 10px; +} +ul.plastic li a.active.loading { + background-image: url(img/loading.gif); + background-position: 95% center; + background-repeat: no-repeat; +} +ul.plastic li small { + color: #888; + font-size: 13px; + font-weight: bold; + line-height: 24px; + text-transform: uppercase; +} +ul.plastic li:nth-child(odd) { + background-color: #1c1c1f; +} +ul.plastic li.arrow { + background-image: url(img/chevron.png); + background-position: right center; + background-repeat: no-repeat; +} +ul.plastic li.arrow a.active { + background-image: url(img/chevron.png); + background-position: right center; + background-repeat: no-repeat; +} +ul.plastic li.forward { + background-image: url(img/chevron_circle.png); + background-position: right center; + background-repeat: no-repeat; +} +ul.plastic li.forward a.active { + background-image: url(img/chevron_circle.png); + background-position: right center; + background-repeat: no-repeat; +} +/* @group Metal */ +ul.metal { + border-bottom: 0; + border-left: 0; + border-right: 0; + border-top: 0; + margin: 0; +} +ul.metal li { + background-image: none; + border-top: 1px solid #fff; + border-bottom: 1px solid #666; + font-size: 26px; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(rgba(238,238,238,1)), to(rgba(156,158,160,1))); +} +ul.metal li a { + line-height: 26px; + margin: 0; + text-shadow: #fff 0 1px 0; + padding: 13px 0; +} +ul.metal li a em { + display: block; + font-size: 14px; + font-style: normal; + color: #444; + width: 50%; + line-height: 14px; +} +ul.metal li a.active { + color: rgb(0,0,0); +} +ul.metal li small { + float: right; + position: relative; + margin-top: 10px; + font-weight: bold; +} +ul.metal li.arrow { + background-image: url(img/chevron.png); + background-position: right center; + background-repeat: no-repeat; + background-image: url(img/chevron.png), -webkit-gradient(linear, 0% 0%, 0% 100%, from(rgba(238,238,238,1)), to(rgba(156,158,160,1))); + background-repeat: no-repeat; + background-position: right center; +} +ul.metal li.arrow a small { + padding-right: 15px; + line-height: 17px; +} +/* @end */ diff --git a/asset/jqtouch/themes/jqt/theme.min.css b/asset/jqtouch/themes/jqt/theme.min.css new file mode 100644 index 0000000..bbcdf9b --- /dev/null +++ b/asset/jqtouch/themes/jqt/theme.min.css @@ -0,0 +1 @@ +body{background:#000;color:#ddd;}body>*{background:-webkit-gradient(linear,0% 0,0% 100%,from(#333),to(#5e5e65));}h1,h2{font:bold 18px Helvetica;text-shadow:rgba(255,255,255,.2) 0 1px 1px;color:#000;margin:10px 20px 5px;}.toolbar{-webkit-box-sizing:border-box;border-bottom:1px solid #000;padding:10px;height:45px;background:url(img/toolbar.png) #000 repeat-x;position:relative;}.black-translucent .toolbar{margin-top:20px;}.toolbar>h1{position:absolute;overflow:hidden;left:50%;top:10px;line-height:1em;margin:1px 0 0 -75px;height:40px;font-size:20px;width:150px;font-weight:bold;text-shadow:rgba(0,0,0,1) 0 -1px 1px;text-align:center;text-overflow:ellipsis;white-space:nowrap;color:#fff;}body.landscape .toolbar>h1{margin-left:-125px;width:250px;}.button,.back,.cancel,.add{position:absolute;overflow:hidden;top:8px;right:10px;margin:0;border-width:0 5px;padding:0 3px;width:auto;height:30px;line-height:30px;font-family:inherit;font-size:12px;font-weight:bold;color:#fff;text-shadow:rgba(0,0,0,0.5) 0 -1px 0;text-overflow:ellipsis;text-decoration:none;white-space:nowrap;background:none;-webkit-border-image:url(img/button.png) 0 5 0 5;}.blueButton{-webkit-border-image:url(img/blueButton.png) 0 5 0 5;border-width:0 5px;}.back{left:6px;right:auto;padding:0;max-width:55px;border-width:0 8px 0 14px;-webkit-border-image:url(img/back_button.png) 0 8 0 14;}.back.active{-webkit-border-image:url(img/back_button_clicked.png) 0 8 0 14;color:#aaa;}.leftButton,.cancel{left:6px;right:auto;}.add{font-size:24px;line-height:24px;font-weight:bold;}.whiteButton,.lightButton,.grayButton{display:block;border-width:0 12px;padding:10px;text-align:center;font-size:20px;font-weight:bold;text-decoration:inherit;color:inherit;}.whiteButton{-webkit-border-image:url(img/whiteButton.png) 0 12 0 12;text-shadow:rgba(255,255,255,0.7) 0 1px 0;}.lightButton{-webkit-border-image: url(img/lightButton.png) 0 12 0 12;text-shadow: rgba(51, 51, 51, 0.7) 0 1px 0;}.grayButton{-webkit-border-image:url(img/grayButton.png) 0 12 0 12;color:#FFF;}h1+ul,h2+ul,h3+ul,h4+ul,h5+ul,h6+ul{margin-top:0;}ul{color:#aaa;border:1px solid #333;font:bold 18px Helvetica;padding:0;margin:15px 10px 17px 10px;}ul.rounded{-webkit-border-radius:8px;-webkit-box-shadow:rgba(0,0,0,.3) 1px 1px 3px;}ul.rounded li:first-child,ul.rounded li:first-child a{border-top:0;-webkit-border-top-left-radius:8px;-webkit-border-top-right-radius:8px;}ul.rounded li:last-child,ul.rounded li:last-child a{-webkit-border-bottom-left-radius:8px;-webkit-border-bottom-right-radius:8px;}ul li{color:#666;border-top:1px solid #333;border-bottom:#555858;list-style-type:none;padding:10px 10px 10px 10px;background:-webkit-gradient(linear,0% 0,0% 100%,from(#4c4d4e),to(#404142));overflow:hidden;}ul li.arrow{background-image:url(img/chevron.png),-webkit-gradient(linear,0% 0,0% 100%,from(#4c4d4e),to(#404142));background-position:right center;background-repeat:no-repeat;}ul li.forward{background-image:url(img/chevron_circle.png),-webkit-gradient(linear,0% 0,0% 100%,from(#4c4d4e),to(#404142));background-position:right center;background-repeat:no-repeat;}ul li a,li.img a+a{color:#fff;text-decoration:none;text-overflow:ellipsis;white-space:nowrap;overflow:hidden;display:block;padding:12px 10px 12px 10px;margin:-10px;-webkit-tap-highlight-color:rgba(0,0,0,0);text-shadow:rgba(0,0,0,.2) 0 1px 1px;}ul li a.active,ul li a.button{background-color:#53b401;color:#fff;}ul li a.active.loading{background-image:url(img/loading.gif);background-position:95% center;background-repeat:no-repeat;}ul li.arrow a.active{background-image:url(img/chevron.png);background-position:right center;background-repeat:no-repeat;}ul li.forward a.active{background-image:url(img/chevron_circle.png);background-position:right center;background-repeat:no-repeat;}ul li.img a+a{margin:-10px 10px -20px -5px;font-size:17px;font-weight:bold;}ul li.img a+a+a{font-size:14px;font-weight:normal;margin-left:-10px;margin-bottom:-10px;margin-top:0;}ul li.img a+small+a{margin-left:-5px;}ul li.img a+small+a+a{margin-left:-10px;margin-top:-20px;margin-bottom:-10px;font-size:14px;font-weight:normal;}ul li.img a+small+a+a+a{margin-left:0!important;margin-bottom:0;}ul li a+a{color:#000;font:14px Helvetica;text-overflow:ellipsis;white-space:nowrap;overflow:hidden;display:block;margin:0;padding:0;}ul li a+a+a,ul li.img a+a+a+a,ul li.img a+small+a+a+a{color:#666;font:13px Helvetica;margin:0;text-overflow:ellipsis;white-space:nowrap;overflow:hidden;display:block;padding:0;}ul.form li{padding:7px 10px;}ul.form li.error{border:2px solid red;}ul.form li.error+li.error{border-top:0;}ul li input[type="text"],ul li input[type="number"], ul li input[type="email"], ul li input[type="password"],ul li textarea,ul li select{color:#777;background:transparent url(../.png);border:0;font:normal 17px Helvetica;padding:0;display:inline-block;margin-left:0;width:100%;-webkit-appearance:textarea;}ul li textarea{height:120px;padding:0;text-indent:-2px;}ul li select{text-indent:0;background:transparent url(img/chevron.png) no-repeat right center;-webkit-appearance:textfield;margin-left:-6px;width:104%;}ul li input[type="checkbox"],ul li input[type="radio"]{margin:0;padding:10px 10px;}ul li input[type="checkbox"]:after,ul li input[type="radio"]:after{content:attr(title);font:17px Helvetica;display:block;width:246px;color:#777;margin:-12px 0 0 17px;}ul li small{color:#64c114;font:17px Helvetica;text-align:right;text-overflow:ellipsis;white-space:nowrap;overflow:hidden;display:block;width:23%;float:right;padding:0;}ul li.arrow small{padding:0 15px;}ul li small.counter{font-size:17px;line-height:13px;font-weight:bold;background:rgba(0,0,0,.15);color:#fff;-webkit-border-radius:11px;padding:4px 10px 5px 10px;display:block;width:auto;margin-top:-22px;-webkit-box-shadow:rgba(255,255,255,.1) 0 1px 0;}ul li.arrow small.counter{margin-right:15px;}ul.individual{border:0;background:none;clear:both;overflow:hidden;padding-bottom:3px;-webkit-box-shadow:none;}ul.individual li{background:#4c4d4e;border:1px solid #333;font-size:14px;text-align:center;-webkit-border-radius:8px;-webkit-box-sizing:border-box;width:48%;float:left;display:block;padding:11px 10px 14px 10px;-webkit-box-shadow:rgba(0,0,0,.2) 1px 1px 3px;background:-webkit-gradient(linear,0% 0,0% 100%,from(#4c4d4e),to(#404142));}ul.individual li+li{float:right;}ul.individual li a{color:#fff;line-height:16px;margin:-11px -10px -14px -10px;padding:11px 10px 14px 10px;-webkit-border-radius:8px;}.toggle{width:94px;position:relative;height:27px;display:block;overflow:hidden;float:right;}.toggle input[type="checkbox"]:checked{left:0;}.toggle input[type="checkbox"]{-webkit-appearance:textarea;-webkit-border-radius:5px;-webkit-tap-highlight-color:rgba(0,0,0,0);-webkit-transition:left .15s;background-color:transparent;background:#fff url(img/on_off.png) 0 0 no-repeat;border:0;height:27px;left:-55px;margin:0;overflow:hidden;position:absolute;top:0;width:149px;}.info{background:-webkit-gradient(linear,0% 0,0% 100%,from(#ccc),to(#aaa),color-stop(.6,#CCC));font-size:12px;line-height:16px;text-align:center;text-shadow:rgba(255,255,255,.8) 0 1px 0;color:#444;padding:15px;border-top:1px solid rgba(255,255,255,.2);font-weight:bold;}ul.edgetoedge{border-width:1px 0;margin:0;padding:0;}ul.edgetoedge li{background:-webkit-gradient(linear,0% 0,0% 100%,from(#1e1f21),to(#272729));border-bottom:2px solid #000;border-top:1px solid #4a4b4d;font-size:20px;margin-bottom:-1px;}ul.edgetoedge li.sep{background:-webkit-gradient(linear,0% 0,0% 100%,from(rgba(0,0,0,0)),to(rgba(0,0,0,.5)));border-bottom:1px solid #111113;border-top:1px solid #666;color:#3e9ac3;font-size:16px;margin:1px 0 0 0;padding:2px 10px;text-shadow:#000 0 1px 0;}ul.edgetoedge li em{font-weight:normal;font-style:normal;}#plastic{background:#17181a;}ul.plastic{background:#17181a;color:#aaa;font:bold 18px Helvetica;margin:0;padding:0;border-width:0 0 1px 0;}ul.plastic li{border-width:1px 0;border-style:solid;border-top-color:#222;border-bottom-color:#000;color:#666;list-style-type:none;overflow:hidden;padding:10px 10px 10px 10px;}ul.plastic li a.active.loading{background-image:url(img/loading.gif);background-position:95% center;background-repeat:no-repeat;}ul.plastic li small{color:#888;font-size:13px;font-weight:bold;line-height:24px;text-transform:uppercase;}ul.plastic li:nth-child(odd){background-color:#1c1c1f;}ul.plastic li.arrow{background-image:url(img/chevron.png);background-position:right center;background-repeat:no-repeat;}ul.plastic li.arrow a.active{background-image:url(img/chevron.png);background-position:right center;background-repeat:no-repeat;}ul.plastic li.forward{background-image:url(img/chevron_circle.png);background-position:right center;background-repeat:no-repeat;}ul.plastic li.forward a.active{background-image:url(img/chevron_circle.png);background-position:right center;background-repeat:no-repeat;}ul.metal{border-bottom:0;border-left:0;border-right:0;border-top:0;margin:0;}ul.metal li{background-image:none;border-top:1px solid #fff;border-bottom:1px solid #666;font-size:26px;background:-webkit-gradient(linear,0% 0,0% 100%,from(rgba(238,238,238,1)),to(rgba(156,158,160,1)));}ul.metal li a{color:#333;line-height:26px;margin:0;text-shadow:#fff 0 1px 0;padding:13px 0;}ul.metal li a em{display:block;font-size:14px;font-style:normal;color:#444;width:50%;line-height:14px;}ul.metal li a.active{color:#000;}ul.metal li small{float:right;position:relative;margin-top:10px;font-weight:bold;}ul.metal li.arrow{background-image:url(img/chevron.png);background-position:right center;background-repeat:no-repeat;background-image:url(img/chevron.png),-webkit-gradient(linear,0% 0,0% 100%,from(rgba(238,238,238,1)),to(rgba(156,158,160,1)));background-repeat:no-repeat;background-position:right center;}ul.metal li.arrow a small{padding-right:15px;line-height:17px;} \ No newline at end of file diff --git a/asset/js/iphone.js b/asset/js/iphone.js new file mode 100644 index 0000000..2c8fbc9 --- /dev/null +++ b/asset/js/iphone.js @@ -0,0 +1,268 @@ +var app = { + login:function ($form) { + $.ajax({ + type:$form.attr("method"), + url:$form.attr("action"), + dataType:"html", + data:$form.serialize(), + success: function (data){ + // $('body').append(data); + jQT.appendPages(data, 'ignore'); + }, + complete:function (req) { + if (req.status === 200 || req.status === 304) { + app.bindList('list-st0'); + app.bindList('list-st1'); + app.bindList('list-st2'); + jQT.goTo('#main', 'fade'); + $(".logout").tap(function (e) { + return app.logout(); + }); + // $('.details').css('color','#f00').tap(app.loadTaskDetails(this)); + } else { + alert("There was an error logging in. Try again."); + } + } + }); + return false; + }, + logout:function() { + $.ajax({ + type:'get', + url:APP_LOGOUT, + success:function() { + }, + complete:function() { + $('#login').bind('pageAnimationEnd', function(event, info){ + $('.dyn').remove(); + $(this).unbind('pageAnimationEnd'); + }) + jQT.goTo('#login','fade'); + } + }); + return false; + }, + bindList: function(id) { + console.log('wiring list #'+id); + $('#'+id).bind('pageAnimationEnd',function(){ + app.clearView(); + }); + $('#'+id+' a.details').tap(function() { + var td = $(this).attr('rel'); + console.log('load '+td+' details ...'); + app.view(td); + }); + }, + /* VIEW TASK */ + view:function(id) { + console.log('lets view dis #'+id+' bitch'); + $.ajax({ + type:'get', + url:APP_VIEW+id, + dataType:'json', + success: function(data) { + // details + $('#dv_id').val(data.info.id); + $('#dv_title').html(data.info.title); + $('#dv_note').html(data.info.note); + $('#dv_deadline').html(data.info.deadline); + $('#dv_priority').html(data.info.priority); + $('#dv_spent').html(data.info.total); + // time stamps + var ll = $('#details-spent ul'); + $.each(data.spent, function(k,v) { + ll.append('
  • '+k+''+v+'
  • '); + }); + // action (running or not) + if (data.running) { + $('#dv_action').val('stop'); + $('#dv_stop').removeClass('hide'); + } else { + $('#dv_action').val('start'); + $('#dv_start').removeClass('hide'); + } + }, + complete: function() { + // jQT.goTo('#view','slide'); + } + }); + return false; + }, + /* REACT TO ACTION FROM VIEW */ + viewAction:function(lnk) { + var $form = $(lnk).closest("form"); + var $id = $form.attr('id').substr(8); + console.log('ID1='+$id); + $.ajax({ + type:'post', + url:$form.attr('action'), + data:$form.serialize(), + dataType:"html", + success: function (data) { + el = $('#running')[0]; + if (el) { + $('#running').replaceWith(data); + } else { + $('#main .toolbar').after(data); + } + }, + complete:function (req) { + if (req.status === 200 || req.status === 304) { + jQT.goBack(); + } else { + alert("Error updating task !"); + } + } + }); + return false; + }, + /* CLEAR VIEW (after going back to list) */ + clearView:function() { + $('#dv_id').val(0); + $('#dv_action').val(''); + $('#dv_title').html('...'); + $('#dv_note').html('...'); + $('#dv_deadline').html('...'); + $('#dv_priority').html('...'); + $('#dv_spent').html('...'); + $('#details-spent ul').empty(); + $('#dv_start').addClass('hide'); + $('#dv_stop').addClass('hide'); + }, + /* EDIT TASK */ + edit:function() { + var id = $('#dv_id').val(); + console.log('lets edit dis #'+id+' bitch'); + $.ajax({ + type:'get', + url:APP_EDIT+id, + dataType:'json', + success: function(data) { + $('#i_id').val(data.id); + $('#i_title').val(data.title); + $('#i_note').val(data.note); + $('#i_deadline').val(data.deadline); + $('#i_priority').val(data.priority); + $('#i_status').val(data.status); + }, + complete: function() { + // jQT.goTo('#edit','flip'); + } + }); + return false; + }, + /* SAVE TASK */ + editAction:function ($form) { + var i = $('#i_id').val(); + var w = $('#i_status').val(); + $.ajax({ + type:$form.attr("method"), + url:$form.attr("action"), + dataType:"html", + data:$form.serialize(), + success: function (data){ + jQT.goBack(); + }, + complete:function (req) { + switch (req.status) { + case 200: + case 304: + if (i) { + // task been updated + app.view(i); + } + // jQT.goBack(); + break; + default: + alert("There was an error saving the task."); + } + window.setTimeout(function() { + app.reloadMain(); + app.clearEdit(); + },500); + } + }); + return false; + }, + /* CLEAR EDIT FORM */ + clearEdit: function() { + $("#edit :input").val(''); + $("#i_priority").val(5); + $("#i_status").val(0); + return true; + }, + /* ACTION ON CURRENT TASK */ + taskAction:function(lnk) { + var act = lnk.href.substr(lnk.href.lastIndexOf('#')+1); + $('#runaction').val(act); + var $form = $('#running'); + $.ajax({ + type:'post', + url:$form.attr('action'), + data:$form.serialize(), + dataType:"html", + success: function (data) { + $('#running').replaceWith(data); + }, + complete:function (req) { + if (req.status === 200 || req.status === 304) { + } else { + alert("Error updating task !"); + } + } + }); + return false; + }, + reloadMain:function() { + $.ajax({ + type:'get', + url:APP_RELOAD, + dataType:'html', + success: function(data) { + jQT.appendPages(data, 'ignore'); + // -TODO- bind links ? + } + }); + } +}; + + +jQuery(function () { + // login form + $("#login a.login").tap(function (e) { + var $form = $(this).closest("form"); + return app.login($form); + }); + $("#login").submit(function (e) { + var $form = $(this); + return app.login($form); + }); + // logout button + $(".logout").tap(function (e) { + return app.logout(); + }); + // view actions + $(".react").tap(function (e) { + return app.viewAction(this); + }); + // edit button (on view) + $("#details a.modify").click(function(e){ + app.edit(); + });; + // edit form + $("#edit a.save").tap(function (e) { + var $form = $(this).closest("form"); + return app.editAction($form); + }); + $("#edit").submit(function (e) { + var $form = $(this); + return app.editAction($form); + }); + $('#edit a.back').click(function (e) { + return app.clearEdit(); + }); + // bind list (if logged in) + app.bindList('list-st0'); + app.bindList('list-st1'); + app.bindList('list-st2'); +}); \ No newline at end of file diff --git a/lib/class/app.php b/lib/class/app.php index 28224b6..ed9917d 100644 --- a/lib/class/app.php +++ b/lib/class/app.php @@ -26,7 +26,7 @@ abstract class AppController extends Pluginable { * constructor * @param mixed $login is user login required */ - public function __construct($login=false) { + public function __construct($login=false, $iphone=false) { parent::__construct(); // get front controller instance @@ -35,10 +35,21 @@ abstract class AppController extends Pluginable { // instantiate page $this->page = new PageModel(); + // detect iphone + if (preg_match('/'.APP_IPHONE_AGENT.'/', $_SERVER['HTTP_USER_AGENT']) && !$iphone) { + NaviHelper::redirect($this->fc->getUrl('iphone')); + } + // check login ? if ($login && APP_SETUP_USER_MODEL) { if (!$this->fc->user->isLoggedIn()) { - NaviHelper::redirect($this->fc->getUrl('login')); + if (is_string($login)) { + if ($this->fc->controller != StringHelper::flatToCamel($login,true) || $this->fc->action != 'login') { + NaviHelper::redirect($this->fc->getUrl($login,'login')); + } + } else { + NaviHelper::redirect($this->fc->getUrl('login')); + } } } } @@ -66,6 +77,16 @@ abstract class AppController extends Pluginable { include APP_VIEW_PATH.$this->view.'.php'; } + protected function viewIPhone() { + $this->page->iphoneHeader(); + include APP_VIEW_PATH.$this->view.'.php'; + $this->page->dispatchFooter(); + } + + protected function viewRaw() { + include APP_VIEW_PATH.$this->view.'.php'; + } + /** * include another view (called within a view) * @todo search in other folders, such as plugins diff --git a/lib/class/db_connector.php b/lib/class/db_connector.php index d9e4b0a..1c473a0 100644 --- a/lib/class/db_connector.php +++ b/lib/class/db_connector.php @@ -4,7 +4,7 @@ * * @package tzn_core_classes * @author Stan Ozier - * @version 0.1 + * @version 0.5 * @copyright GNU Lesser General Public License (LGPL) version 3 */ @@ -156,7 +156,7 @@ class DbConnector { // extends HelpableSingleton // if critical, should at least show an error code in browser $debug = ($this->critical && $this->debug < 2)?2:$this->debug; - $html = ''; + $htm = ''; $str = 'DB Error #'.$this->connector->getErrorNo().' : '.$this->connector->getErrorMsg(); switch ($debug) { case 2: diff --git a/lib/class/model.php b/lib/class/model.php index 6cbb250..9a83923 100644 --- a/lib/class/model.php +++ b/lib/class/model.php @@ -4,7 +4,7 @@ * * @package tzn_core_classes * @author Stan Ozier - * @version 0.4 + * @version 0.5 * @copyright GNU Lesser General Public License (LGPL) version 3 */ @@ -568,6 +568,11 @@ abstract class VarAbstract { abstract public static function sanitize($val, &$info); + public static function sani($val) { + $tmp = array(); + return static::sanitize($val, $tmp); + } + public static function get($val) { return $val; } @@ -673,6 +678,7 @@ class VarDte extends VarAbstract return '0000-00-00'; } if (preg_match('/^[0|2|9][0|1|9][0-9]{2}\-[0-1][0-9]\-[0-3][0-9]$/', $val)) { + // SQL format, return as it is (no timezone evaluation) return $val; } if (!$GLOBALS['config']['datetime']['us_format']) { @@ -698,7 +704,7 @@ class VarDte extends VarAbstract public static function html($val, $format='', $default='') { if (!$format) { - $format = $format = $GLOBALS['config']['datetime']['us_format']?APP_DATE_USA:APP_DATE_EUR;; + $format = $format = $GLOBALS['config']['datetime']['us_format']?APP_DATE_USA:APP_DATE_EUR; } $t = VarDte::strToUnix($val); if ($t === false) { @@ -733,8 +739,10 @@ class VarDte extends VarAbstract if ($t === false) { return false; } + $t += self::getUserTimeZoneOffset(); return $t; } + } /** @@ -812,7 +820,7 @@ class VarTim extends VarDur return 0; } if (preg_match('/^[0-9]+$/', $val)) { - // number of seconds, must be coming from SQL + // must come from SQL (number of seconds) return as it is (ignore timezone) return intval($val); } if (preg_match('/^([0-2]?[0-9])\:([0-5][0-9])(\:([0-5][0-9]))?$/', $val, $arr)) { @@ -856,7 +864,7 @@ class VarDtm extends VarAbstract return '0000-00-00 00:00:00'; } if (preg_match('/^[0|2|9][0|1|9][0-9]{2}\-[0-1][0-9]\-[0-3][0-9]( ([0-2][0-9]\:[0-5][0-9])(\:[0-5][0-9])?)?$/', $val)) { - // SQL format, return it as it is + // SQL format, return as it is (no timezone evaluation) return $val; } if ($val == 'NOW') { @@ -926,14 +934,7 @@ class VarDtm extends VarAbstract $t += self::getUserTimeZoneOffset(); return $t; } - - /** - * work on date format to return human readable value - */ - public static function workout($val, $seconds=true) { - $val += self::getUserTimeZoneOffset(); - return parent::workout($val); - } + } /** diff --git a/lib/helper/auth.php b/lib/helper/auth.php index d031433..2f2c7da 100644 --- a/lib/helper/auth.php +++ b/lib/helper/auth.php @@ -279,21 +279,21 @@ class AuthHelper extends Helper { return false; } $arrVal = explode(":",$_COOKIE['auto_login']); - $id = VarUid::sanitize($arrVal[0]); - $salt = VarStr::sanitize($arrVal[1]); + $id = VarUid::sani($arrVal[0]); + $salt = VarStr::sani($arrVal[1]); if (!$id || !$salt) { return false; } - if ($this->obj->load($this->dbUid(true)."='".$id - ."' AND ".$this->dbField('salt', $salt)." AND " - .$this->dbField('auto_login',1)." AND ".$this->dbField('enabled',1)) + if ($this->obj->load($this->obj->dbUid(true)."='".$id + ."' AND ".$this->obj->dbField('salt', $salt)." AND " + .$this->obj->dbField('auto_login',1)." AND ".$this->obj->dbField('enabled',1)) ) { if (!$forReal) { return true; } setCookie('auto_login',$this->obj->getUid().":".$this->obj->get('salt') ,time()+(3600*24*30)); - $this->activateLogin(); + $this->_activateLogin(); return true; } else { return false; @@ -304,7 +304,7 @@ class AuthHelper extends Helper { */ public function setAutoLogin() { if (($this->obj->getUid()) && ($this->obj->get('salt'))) { - setCookie('autoLogin',$this->obj->getUid().":".$this->obj->get('salt') + setCookie('auto_login',$this->obj->getUid().":".$this->obj->get('salt') ,time()+(3600*24*30)); $this->obj->set('auto_login','1'); $this->obj->fields('auto_login'); @@ -318,7 +318,7 @@ class AuthHelper extends Helper { */ public function resetAutoLogin() { if (($this->obj->getUid()) && ($this->obj->get('salt'))) { - setCookie('autoLogin'); + setCookie('auto_login'); if ($this->obj->get('auto_login')) { $this->obj->set('auto_login', 0); $this->obj->fields('auto_login'); diff --git a/lib/helper/db.php b/lib/helper/db.php index 0bde014..f323891 100644 --- a/lib/helper/db.php +++ b/lib/helper/db.php @@ -4,7 +4,7 @@ * * @package tzn_helpers * @author Stan Ozier - * @version 0.2 + * @version 0.5 * @since 0.1 * @copyright GNU Lesser General Public License (LGPL) version 3 */ @@ -32,6 +32,10 @@ class DbHelper extends Helper implements Callable { $this->table = $table; } + public static function factory() { + return new DbHelper(null, ''); + } + // ----- INSERTion queries --------------------------------------------------- public function save() { @@ -133,6 +137,7 @@ class DbHelper extends Helper implements Callable { public function load($filter='', $auto=true) { if ($auto) { $this->buildSelect(); + $this->buildFrom(); } if ($this->buildWhere($filter)) { $this->qry->where($filter); @@ -157,8 +162,9 @@ class DbHelper extends Helper implements Callable { public function loadList($auto=true) { if ($auto) { $this->buildSelect(); + $this->buildFrom(); + $this->obj->all(); } - $this->obj->all(); if ($data = $this->db->query($this->qry->build())) { $this->idx = 0; $this->total = 0; @@ -180,6 +186,13 @@ class DbHelper extends Helper implements Callable { return false; } + /** + * query database and return result set directly + */ + public function loadRaw() { + return $this->db->query($this->qry->build()); + } + public function count() { return count($this->rows); } @@ -190,7 +203,9 @@ class DbHelper extends Helper implements Callable { public function next() { if (array_key_exists($this->idx, $this->rows)) { - $this->obj->set($this->rows[$this->idx]); + if (is_a($this->obj, 'Model')) { + $this->obj->set($this->rows[$this->idx]); + } $this->idx++; return true; } else { @@ -287,6 +302,12 @@ class DbHelper extends Helper implements Callable { $select = $this->buildFields(); // add SELECT clause $this->qry->select($select); + } + + /** + * build FROM clause + */ + public function buildFrom() { // add FROM clause $this->qry->from($this->dbTable()); } diff --git a/lib/helper/html_asset.php b/lib/helper/html_asset.php index d3f2e65..f2c7544 100644 --- a/lib/helper/html_asset.php +++ b/lib/helper/html_asset.php @@ -4,7 +4,7 @@ * * @package tzn_helpers * @author Stan Ozier - * @version 0.3 + * @version 0.5 * @since 0.1 * @copyright GNU Lesser General Public License (LGPL) version 3 */ @@ -17,9 +17,11 @@ class HtmlAssetHelper extends Collectable { protected $css, $cssCode, $js, $jsCode, $jsEditor, $jsCalendar, $jsOnLoad, $rss; + protected $_jsInHeader; public function __construct() { parent::__construct(); + $this->_jsInHeader = false; } protected function _init($key,$reset=false) { @@ -31,7 +33,7 @@ class HtmlAssetHelper extends Collectable { } } - public function headerStuff() { + public function headerStuff($full=false) { if (count($this->jsCalendar)) { $this->add('css',APP_WWW_URI.'asset/css/calendar.css'); @@ -85,6 +87,12 @@ class HtmlAssetHelper extends Collectable { if (count($this->cssCode)) { echo implode("\n",$this->cssCode)."\n"; } + + // javascript external scripts (if specifically requested) + if ($full) { + $this->_jsInHeader = true; + $this->_javascript(); + } // javascrpt direct code if (count($this->jsCode)) { @@ -119,6 +127,12 @@ class HtmlAssetHelper extends Collectable { } public function footerStuff() { + if (!$this->_jsInHeader) { + $this->_javascript(); + } + } + + protected function _javascript() { // javascript (include) if (count($this->js)) { foreach($this->js as $it) { diff --git a/lib/helper/html_form.php b/lib/helper/html_form.php index 7e1417c..520a4c2 100644 --- a/lib/helper/html_form.php +++ b/lib/helper/html_form.php @@ -347,25 +347,36 @@ class HtmlFormHelper extends Helper { } $timezone_identifiers = DateTimeZone::listIdentifiers(); - $str = ''; + foreach( $arrTz as $continent => $arrCt ) { + $str .= ''; + foreach($arrCt as $city => $value) { $str .= ''; } - $str .= ''; return $str.''; } diff --git a/lib/helper/json.php b/lib/helper/json.php new file mode 100644 index 0000000..88aced0 --- /dev/null +++ b/lib/helper/json.php @@ -0,0 +1,31 @@ + + * @version 0.5 + * @since 0.5 + * @copyright GNU Lesser General Public License (LGPL) version 3 + */ + +/** + * JsonHelper + * + * JSON format helper to export/import data in JSON format + */ +class JsonHelper extends Helper { + + public function __construct($obj) { + parent::__construct($obj); + } + + public function export($method='html') { + $arr = $this->obj->getFields(); + $data = array(); + foreach ($arr as $key => $type) { + $data[$key] = $this->obj->$method($key); + } + return json_encode($data); + } +} diff --git a/lib/helper/string.php b/lib/helper/string.php index b58e5b5..e28d514 100644 --- a/lib/helper/string.php +++ b/lib/helper/string.php @@ -75,4 +75,28 @@ class StringHelper { } return $strCode; } + + /** + * convert string to XML friendly string (no space, no special caracters) + */ + public static function cleanStrip($str) { + $str = trim($str); + if ($str) { + /* + if (constant('APP_CHARSET') == 'UTF-8') { + $str = utf8_decode($str); + } + */ + $str = utf8_decode($str); + $str = preg_replace( + array('/[éèêë]/','/[àáâä]/','/[ìíîï]/','/[ùúûü]/','/[öôòø]/','/[ç‡]/','/[ \'\?\/\\&"]/'), + array('e','a','i','u','o','c','-'), + strtolower($str)); + $str = preg_replace('/[^a-z0-9\-]/','_',$str); + $str = str_replace('---','-',$str); + $str = trim($str,'_'); + $str = trim($str,'-'); + } + return $str; + } } \ No newline at end of file diff --git a/lib/lang/de/common.php b/lib/lang/de/common.php new file mode 100644 index 0000000..7e4b382 --- /dev/null +++ b/lib/lang/de/common.php @@ -0,0 +1,250 @@ + 'Neuer Eintrag', + 'read' => 'Diesen Eintrag lesen', + 'view' => 'Details anzeigen', + 'modify' => 'Eintrag ändern', + 'delete' => 'Diesen Eintrag löschen', + 'delete_confirm' => 'Diesen Eintrag wirklich löschen?', + 'remove' => 'Diesen Eintrag entfernen', + 'remove_confirm' => 'Wirklich aus der Liste entfernen?', + 'search' => 'Suchen', + 'next' => 'Nächste', + 'previous' => 'Vorherige', + 'next_page' => 'Nächste Seite', + 'previous_page' => 'Vorherige Seite', + 'all' => 'Alle', + 'more' => 'Mehr', + 'less' => 'Weniger', + 'item_found' => 'Gefundener Eintrag', + 'items_found' => 'Gefundene Einträge', + 'empty' => 'Keine Daten verfügbar' +); + +$GLOBALS['lang']['message'] = array( + 'saved' => 'Daten erfolgreich gespeichert', + 'created' => 'Daten erfolgreich erstellt', + 'updated' => 'Daten erfolgreich aktualisiert', + 'deleted' => 'Daten erfolgreich gelöscht', + 'removed' => 'Daten erfolgreich entfernt' +); + +$GLOBALS['lang']['error'] = array( + 'db_no_connection' => 'Es konnte keine Verbindung zur Datenbank hergestellt werden', + 'db_no_database' => 'Datenbank nicht gefunden', + 'db_sql_error' => 'Fehler bei der Datenbank-Anfrage', + 'sql_injection' => 'Mögliche SQL-Injection intendiert', + 'search_empty' => 'Leider konnte kein Eintrag gefunden werden', + 'not_found' => 'Daten nicht gefunden', + 'login_failed' => 'Login fehlgeschlagen', + 'access_denied' => 'Zugriff verweigert', + 'data_denied' => 'Zugriff auf Daten verweigert', + 'not_found_denied' => 'Daten nicht gefunden oder Zugriff verweigert', + 'action_failed' => 'Die angeforderte Aktion konnte nicht ausgeführt werden', + 'form_error' => 'Formular enthält Fehler', + 'compulsory_field' => 'Information erforderlich', + 'account_disabled' => 'Account ist deaktiviert', + 'account_expired' => 'Account ist abgelaufen', + 'account_not_found' => 'Account existiert nicht', + 'username_required' => 'Bitte geben Sie einen Benutzernamen ein', + 'username_not_found' => 'Benutzername existiert nicht', + 'username_invalid' => 'Kein gültiger Benutzername (vermeiden Sie Sonder- oder Leerzeichen)', + 'username_length' => 'Der Benutzername muss aus mindestens '.APP_USER_NAME_MIN.' und maximal '.APP_USER_NAME_MAX.' Zeichen bestehen', + 'email_not_found' => 'E-Mail existiert nicht', + 'password_required' => 'Passwort erforderlich', + 'password_invalid' => 'Ungültiges Passwort', + 'password_length' => 'Passwort muss aus mindestens '.APP_USER_PASS_MIN.' and maximal '.APP_USER_PASS_MAX.' Zeichen betsehen', + 'password_mismatch' => 'Passwort und Überprüfung stimmen nicht überein', + 'password_recover' => 'Passwort kann nicht wiederhergestellt werden', + 'field_length' => 'Zu kurz oder zu lang', + 'field_exists' => 'Dieser Eintrag existiert bereits', + 'field_invalid' => 'Eintrag ist ungültig', + 'field_mismatch' => 'Einträge stimmen nicht überein', + 'invalid_date' => 'Ungültiges Datum', + 'invalid_time' => 'Ungültige Zeit', + 'invalid_email' => 'E-Mail-Adresse ist ungültig', + 'invalid_duration' => 'Ungültige Dauer', + 'file_wrong_type' => 'Falscher Dateityp', + 'file_empty' => 'Bitte wählen Sie eine Datei aus', + 'none_checked' => 'Bitte wählen Sie mindestens einen Eintrag' +); + +$GLOBALS['lang']['security'] = array( + 'login' => 'Anmeldung', + 'logout' => 'Abmeldung', + 'sign_in' => 'Kein Mitglied? Melden Sie sich jetzt an!', + 'my_account' => 'Mein Account', + 'account' => 'Account', + 'account_active' => 'Account ist aktiviert', + 'account_not_active' => 'Account ist nicht aktiviert', + 'account_enabled' => 'Account ist freigegeben', + 'visit_count' => 'Besuche', + 'visit_fail_count' => 'Fehlgeschlagene Anmeldeversuche', + 'access_denied' => 'Zugriff verweigert', + 'permission_denied' => 'Erlaubnis verweigert', + 'session_expired' => 'Ihre Session ist abgelaufen', + 'login_last_date' => 'Leztes Anmeldedatum', + 'login_last_address' => 'Letzte Anmeldeadresse' +); + +$GLOBALS['lang']['form'] = array( + 'compulsory' => 'obligatorisch', + 'username' => 'Benutzername', + 'password' => 'Passwort', + 'password_confirm' => '(Überprüfung)', + 'auto_login' => 'Login-Daten auf diesem Computer speichern', + 'password_legend' => 'Geben Sie ein Passwort ein (und bestätigen Sie es) nur dann, wenn Sie es ändern möchten.', + 'name' => 'Name', + 'category' => 'Kategorie', + 'title' => 'Titel', + 'last_name' => 'Nachname', + 'middle_name' => 'Zweiter Vorname', + 'first_name' => 'Vorname', + 'nick_name' => 'Spitzname', + 'address' => 'Adresse', + 'location' => 'Ort', + 'city' => 'Stadt', + 'state' => 'Bundesland', + 'state_us_only' => 'nur für US-Bürger', + 'country' => 'Land', + 'time_zone' => 'Zeitzone', + 'user_rights' => 'Berechtigungen', + 'email' => 'E-Mail', + 'subject' => 'Betreff', + 'body' => 'Textkörper', + 'comment' => 'Kommentar', + 'in' => 'In', + 'out' => 'Aus', + 'from' => 'Von', + 'to' => 'An', + 'cc' => 'CC', + 'url' => 'URL', + 'website' => 'Webseite', + 'description' => 'Beschreibung', + 'user' => 'Benutzer', + 'member' => 'Mitglied', + 'author' => 'Autor', + 'status' => 'Status', + 'file' => 'Datei', + 'image' => 'Bild', + 'thumbnail' => 'Vorschau', + 'document' => 'Dokument', + 'file_legend' => 'Bitte wählen Sie eine Datei durch Klicken des \'Browse..\'-Buttons', + 'file_name' => 'Dateiname', + 'file_size' => 'Dateigröße', + 'file_type' => 'Dateityp', + 'date' => 'Datum', + 'deadline' => 'Deadline', + 'start' => 'Start', + 'stop' => 'Stop', + 'publish_date' => 'Veröffentlichen', + 'post_date' => 'Absenden', + 'creation_date' => 'Erstellungsdatum', + 'last_change_date' => 'Letzte Aktualisierung', + 'last_visit_date' => 'Letzter Besuch', + 'last_visit_addr' => 'Von', + 'posted_on' => 'Abgesendet am', + 'published on' => 'Veröffentlicht am', + 'by' => 'von', + 'action' => 'Aktion' +); + +// buttons +$GLOBALS['lang']['button'] = array( + 'add' => 'Hinzufügen', + 'create' => 'Erstellen', + 'edit' => 'Bearbeiten', + 'submit' => 'Abschicken', + 'login' => 'Anmelden', + 'save' => 'Speichern', + 'save_changes' => 'Änderungen speichern', + 'save_and_add' => 'Speichern und weitere hinzufügen', + 'save_and_close' => 'Speichern und schließen', + 'update' => 'Aktualisieren', + 'cancel' => 'Änderungen aufheben', + 'close' => 'Schließen', + 'reset' => 'Formular zurücksetzen', + 'delete' => 'Löschen', + 'remove' => 'Entfernen', + 'start' => 'Start', + 'stop' => 'Stopp', + 'enable' => 'Freigeben', + 'disable' => 'Sperren', + 'activate' => 'Aktivieren', + 'deactivate' => 'Deaktivieren', + 'next_step' => 'Nächster Schritt', + 'previous_step' => 'Vorheriger Schritt', + 'back' => 'Zurückgehen', + 'back_to_list' => 'Zurück zur Liste' +); + +$GLOBALS['lang']['date'] = array( + 'future_pre' => 'in', // eg. "in" 2 days + 'future_app' => '', // ie. when keyword needs to be appended to the date + 'past_pre' => 'vor', // eg. "il y a" 2 jours (french) + 'past_app' => '', // eg. 2 days "ago" + 'yesterday' => 'Gestern', + 'today' => 'Heute', + 'tomorrow' => 'Morgen', + 'days' => 'Tage', + 'day' => 'Tag', + 'weeks' => 'Wochen', + 'week' => 'Woche', + 'months' => 'Monate', + 'month' => 'Monat', + 'years' => 'Jahre', + 'year' => 'Jahr', + 'hour' => 'Stunde', + 'hours' => 'Stunden', + 'minute' => 'Minute', + 'minutes' => 'Minuten', + 'second' => 'Sekunde', + 'seconds' => 'Sekunden', + 'january' => 'Januar', + 'february' => 'Februar', + 'march' => 'März', + 'april' => 'April', + 'may' => 'Mai', + 'june' => 'Juni', + 'july' => 'Juli', + 'august' => 'August', + 'september' => 'September', + 'october' => 'Oktober', + 'november' => 'November', + 'december' => 'Dezember', + 'jan' => 'Jan', + 'feb' => 'Feb', + 'mar' => 'Mär', + 'apr' => 'Apr', + 'may' => 'Mai', + 'jun' => 'Jun', + 'jul' => 'Jul', + 'aug' => 'Aug', + 'sep' => 'Sep', + 'oct' => 'Okt', + 'nov' => 'Nov', + 'dec' => 'Dez', + 'monday' => 'Montag', + 'tuesday' => 'Dienstag', + 'wednesday' => 'Mittwoch', + 'thursday' => 'Donnerstag', + 'friday' => 'Freitag', + 'saturday' => 'Samstag', + 'sunday' => 'Sonntag', + 'mon' => 'Mo', + 'tue' => 'Di', + 'wed' => 'Mi', + 'thu' => 'Do', + 'fri' => 'Fr', + 'sat' => 'Sa', + 'sun' => 'So' +); diff --git a/lib/lang/de/config.php b/lib/lang/de/config.php new file mode 100644 index 0000000..9ab229d --- /dev/null +++ b/lib/lang/de/config.php @@ -0,0 +1,15 @@ + + * @version 0.4 + * @copyright GNU Lesser General Public License (LGPL) version 3 + */ + + +$GLOBALS['config']['lang']['specialchars'] = 3; +$GLOBALS['config']['lang']['ucfirst'] = false; + +setLocale(LC_ALL, 'de_DE.UTF-8', 'de_DE', 'de'); \ No newline at end of file diff --git a/lib/lang/en/common.php b/lib/lang/en/common.php index cc34949..d04d3fa 100644 --- a/lib/lang/en/common.php +++ b/lib/lang/en/common.php @@ -170,7 +170,7 @@ $GLOBALS['lang']['button'] = array( 'save_and_add' => 'save and add more', 'save_and_close' => 'save and close', 'update' => 'update', - 'cancel' => 'cancel changes', + 'cancel' => 'cancel', 'close' => 'close', 'reset' => 'reset form', 'delete' => 'delete', diff --git a/lib/lang/no/common.php b/lib/lang/no/common.php new file mode 100755 index 0000000..14b111e --- /dev/null +++ b/lib/lang/no/common.php @@ -0,0 +1,250 @@ + + * @version 0.4 + * @copyright GNU Lesser General Public License (LGPL) version 3 + */ + +$GLOBALS['lang']['data'] = array( + 'new' => 'ny forekomst', + 'read' => 'se pÃ¥ forekomsten', + 'view' => 'vis detaljer', + 'modify' => 'endre forekomsten', + 'delete' => 'slett forekomsten', + 'delete_confirm' => 'er du sikker pÃ¥ at du vil slette denne ?', + 'remove' => 'fjærn forekomst', + 'remove_confirm' => 'er du sikker pÃ¥ at du vil slette denne ?', + 'search' => 'søk', + 'next' => 'neste', + 'previous' => 'forrige', + 'next_page' => 'neste side', + 'previous_page' => 'forrige side', + 'all' => 'alle', + 'more' => 'mer', + 'less' => 'mindre', + 'item_found' => 'forekomst funnet', + 'items_found' => 'forekomster funnet', + 'empty' => 'ingen data tilgjengelig' +); + +$GLOBALS['lang']['message'] = array( + 'saved' => 'data ble lagret', + 'created' => 'data ble laget', + 'updated' => 'data ble oppdatert', + 'deleted' => 'data ble slettet', + 'removed' => 'data ble fjernet' +); + +$GLOBALS['lang']['error'] = array( + 'db_no_connection' => 'kan ikke koble til databasen', + 'db_no_database' => 'databasen ble ikke funnet', + 'db_sql_error' => 'feil i database spørring', + 'sql_injection' => 'mulig SQL injection angrep', + 'search_empty' => 'beklager, fant ingen forekomster', + 'not_found' => 'ingen data funnet', + 'login_failed' => 'kunne ikke logge inn', + 'access_denied' => 'ingen tilgang', + 'data_denied' => 'du har ikke tilgang til valgte data', + 'not_found_denied' => 'data ikke funnet, eller ingen tilgang', + 'action_failed' => 'forespurte oppgave kunne ikke utføres', + 'form_error' => 'skjemaet inneholder feil', + 'compulsory_field' => 'informasjon pÃ¥krevet', + 'account_disabled' => 'konto er deaktivert', + 'account_expired' => 'konto har foreldet', + 'account_not_found' => 'konto eksisterrer ikke', + 'username_required' => 'skriv inn brukernavn', + 'username_not_found'=> 'brukernavn eksisterer ikke', + 'username_invalid' => 'ikke gyldig brukernavn (unngÃ¥ spesialtegn og/eller mellomrom)', + 'username_length' => 'brukernavn mÃ¥ ha mellom '.APP_USER_NAME_MIN.' og '.APP_USER_NAME_MAX.' bokstaver', + 'email_not_found' => 'epost eksisterer ikke', + 'password_required' => 'passord pÃ¥krevet', + 'password_invalid' => 'galt passord', + 'password_length' => 'passordet mÃ¥ ha mellom '.APP_USER_PASS_MIN.' og '.APP_USER_PASS_MAX.' tegn', + 'password_mismatch' => 'passpordene stemmer ikke med hverandre (verifisering)', + 'password_recover' => 'passordet kan ikke gjenfinnes', + 'field_length' => 'for kort eller lang', + 'field_exists' => 'denne forekomsten finnes allerede', + 'field_invalid' => 'oppføringen er ikke gyldig', + 'field_mismatch' => 'oppføringene stemmer ikke med hverandre', + 'invalid_date' => 'ikke gyldig dato', + 'invalid_time' => 'ikke gyldig tid', + 'invalid_email' => 'ugyldig e-post adresse', + 'invalid_duration' => 'ikke gyldig varihet', + 'file_wrong_type' => 'gal filtype', + 'file_empty' => 'vennligst velg en fil', + 'none_checked' => 'vennligst velg minst en enhet' +); + +$GLOBALS['lang']['security'] = array( + 'login' => 'logg inn', + 'logout' => 'logg ut', + 'sign_in' => 'ikke medlem? registrer deg nÃ¥!', + 'my_account' => 'min konto', + 'account' => 'konto', + 'account_active' => 'konto er aktivert', + 'account_not_active'=> 'konto er ikke aktivert', + 'account_enabled' => 'konto er opprettet', + 'visit_count' => 'besøk', + 'visit_fail_count' => 'feilede innloggingsforsøk', + 'access_denied' => 'ingen tilgang', + 'permission_denied' => 'ingen rettigheter', + 'session_expired' => 'økten er utgÃ¥tt', + 'login_last_date' => 'Sist innlogget dato', + 'login_last_address'=> 'Sist innlogget fra' +); + +$GLOBALS['lang']['form'] = array( + 'compulsory' => 'compulsory', + 'username' => 'brukernavn', + 'password' => 'passord', + 'password_confirm' => '(verifisering)', + 'auto_login' => 'husk meg pÃ¥ denne datamaskinen', + 'password_legend' => 'skriv et passord (og bekreft) bare dersom du ønsker Ã¥ ENDRE passord.', + 'name' => 'Navn', + 'category' => 'Kategori', + 'title' => 'tittel', + 'last_name' => 'etternavn', + 'middle_name' => 'mellomnavn', + 'first_name' => 'fornavn', + 'nick_name' => 'kallenavn', + 'address' => 'adresse', + 'location' => 'sted', + 'city' => 'by', + 'state' => 'fylke', + 'state_us_only' => 'Kun for USA', + 'country' => 'land', + 'time_zone' => 'tidssone', + 'user_rights' => 'rettigheter', + 'email' => 'epost', + 'subject' => 'tittel', + 'body' => 'innhold', + 'comment' => 'kommentar', + 'in' => 'inn', + 'out' => 'ut', + 'from' => 'fra', + 'to' => 'til', + 'cc' => 'kopi', + 'url' => 'URL', + 'website' => 'webside', + 'description' => 'beskrivelse', + 'user' => 'bruker', + 'member' => 'medlem', + 'author' => 'forfatter', + 'status' => 'status', + 'file' => 'fil', + 'image' => 'bilde', + 'thumbnail' => 'miniatyrbilde', + 'document' => 'dokument', + 'file_legend' => 'vennligst velg en fil ved Ã¥ trykke \'Browse..\' knappen', + 'file_name' => 'filnavn', + 'file_size' => 'fil størrelse', + 'file_type' => 'fil type', + 'date' => 'dato', + 'deadline' => 'deadline', + 'start' => 'start', + 'stop' => 'stop', + 'publish_date' => 'publiser', + 'post_date' => 'post', + 'creation_date' => 'opprettet dato', + 'last_change_date' => 'sist oppdatert', + 'last_visit_date' => 'sist besøkt', + 'last_visit_addr' => 'fra', + 'posted_on' => 'postet pÃ¥', + 'published on' => 'publisert pÃ¥', + 'by' => 'av', + 'action' => 'handling' +); + +// buttons +$GLOBALS['lang']['button'] = array( + 'add' => 'legg til', + 'create' => 'lag', + 'edit' => 'endre', + 'submit' => 'send', + 'login' => 'logg inn', + 'save' => 'lagre', + 'save_changes' => 'lagre endringer', + 'save_and_add' => 'lagre og legg til mer', + 'save_and_close' => 'slagre og lukk', + 'update' => 'oppdater', + 'cancel' => 'avbryt endringer', + 'close' => 'lukk', + 'reset' => 'tilbakestill skjema', + 'delete' => 'slett', + 'remove' => 'fjern', + 'start' => 'start', + 'stop' => 'stop', + 'enable' => 'aktiver', + 'disable' => 'deaktiver', + 'activate' => 'aktiver', + 'deactivate' => 'deaktiver', + 'next_step' => 'neste steg', + 'previous_step' => 'forrige steg', + 'back' => 'tilbake', + 'back_to_list' => 'tilbake til listen' +); + +$GLOBALS['lang']['date'] = array( + 'future_pre' => 'om', // eg. "in" 2 days + 'future_app' => '', // ie. when keyword needs to be appended to the date + 'past_pre' => '', // eg. "il y a" 2 jours (french) + 'past_app' => 'siden', // eg. 2 days "ago" + 'yesterday' => 'i gÃ¥r', + 'today' => 'i dag', + 'tomorrow' => 'i morgen', + 'days' => 'dager', + 'day' => 'dag', + 'weeks' => 'uker', + 'week' => 'uke', + 'months' => 'mÃ¥neder', + 'month' => 'mÃ¥ned', + 'years' => 'Ã¥r', + 'year' => 'Ã¥r', + 'hour' => 'time', + 'hours' => 'timer', + 'minute' => 'minutt', + 'minutes' => 'minutter', + 'second' => 'sekund', + 'seconds' => 'sekunder', + 'january' => 'januar', + 'february' => 'februar', + 'march' => 'mars', + 'april' => 'april', + 'may' => 'mai', + 'june' => 'juni', + 'july' => 'juli', + 'august' => 'august', + 'september' => 'september', + 'october' => 'oktober', + 'november' => 'november', + 'december' => 'desember', + 'jan' => 'jan', + 'feb' => 'feb', + 'mar' => 'mar', + 'apr' => 'apr', + 'may' => 'mai', + 'jun' => 'jun', + 'jul' => 'jul', + 'aug' => 'aug', + 'sep' => 'sep', + 'oct' => 'okt', + 'nov' => 'nov', + 'dec' => 'des', + 'monday' => 'mandag', + 'tuesday' => 'tirsdag', + 'wednesday' => 'onsdag', + 'thursday' => 'torsdag', + 'friday' => 'fredag', + 'saturday' => 'lørdag', + 'sunday' => 'søndag', + 'mon' => 'man', + 'tue' => 'tirs', + 'wed' => 'ons', + 'thu' => 'tors', + 'fri' => 'fre', + 'sat' => 'lør', + 'sun' => 'søn' +); \ No newline at end of file diff --git a/lib/lang/no/config.php b/lib/lang/no/config.php new file mode 100755 index 0000000..fb7a554 --- /dev/null +++ b/lib/lang/no/config.php @@ -0,0 +1,15 @@ + + * @version 0.4 + * @copyright GNU Lesser General Public License (LGPL) version 3 + */ + + +$GLOBALS['config']['lang']['specialchars'] = 3; +$GLOBALS['config']['lang']['ucfirst'] = false; + +setLocale(LC_ALL, 'en_NO.UTF-8', 'no_NO.utf8', 'no_NO', 'no_BM.utf8', 'no_BM', 'no'); diff --git a/lib/model/page.php b/lib/model/page.php index 08c8b2c..3195161 100644 --- a/lib/model/page.php +++ b/lib/model/page.php @@ -4,7 +4,7 @@ * * @package tzn_models * @author Stan Ozier - * @version 0.2 + * @version 0.5 * @since 0.1 * @copyright GNU Lesser General Public License (LGPL) version 3 */ @@ -39,6 +39,10 @@ class PageModel extends Model { include APP_ASSET_PATH.'html/page-header.php'; } + public function iphoneHeader() { + include APP_ASSET_PATH.'html/iphone-header.php'; + } + public function dispatchFooter() { include APP_ASSET_PATH.'html/page-footer.php'; } diff --git a/skin/default/css/iphone.css b/skin/default/css/iphone.css new file mode 100644 index 0000000..030eeae --- /dev/null +++ b/skin/default/css/iphone.css @@ -0,0 +1,168 @@ +/* login */ +form p { + padding: 5px 10px 50px; +} +ul.form li { + padding: 7px 10px; +} +ul.form li.error { + color: #c33; + font-weight: normal; + font-size: .80em; + text-align: center; + border: 0 none; +} +/* current task */ +form.highlight { + border-bottom: 0; + border-left: 0; + border-right: 0; + border-top: 0; + margin: 0; + padding: 0 10px 5px; + background-image: none; + border-top: 1px solid #fff; + border-bottom: 1px solid #666; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(rgba(238,238,238,1)), to(rgba(156,158,160,1))); +} +form.highlight h3 { + font-size: 18px; + line-height: 22px; + margin: 0; + text-shadow: #fff 0 1px 0; + padding: 10px 0; +} +form.highlight h3 a { + display: block; + color: #333; + text-decoration: none; + overflow: hidden; + white-space: nowrap; + text-overflow: ellipsis; + text-align: center; +} +form p.dual, form p.triple { + clear: both; + overflow: hidden; + padding-bottom: 3px; +} +form p.dual span, form p.triple span { + float: left; + text-align: center; + -webkit-box-sizing: border-box; + width: 48%; + display: block; + padding: 11px 10px 14px 10px; +} +form p.dual span + span { + float: right; +} +form p.triple span { + width: 31%; +} +form p.triple span + span { + margin-left: 3%; +} +form p.triple span + span + span { + float: right; +} +form p.dual span a, form p.triple span a { + color: #fff; + font-size: 14px; + line-height: 16px; + margin: -11px -10px -14px -10px; + padding: 11px 10px 14px 10px; +} +/* more fields */ +ul li { + color: #999; +} +ul li.note { + font-size: 14px; + text-align: justify; +} +ul li input[type="text"], ul li input[type="password"], ul li textarea, ul li select, +ul li input[type="number"], ul li input[type="email"] { + color: #777; + background-color: transparent; + background-image: none; + border: 0 none; + font: normal 17px Helvetica; + padding: 3px 1px; + display: inline-block; + margin-left: 0px; + width: 100%; + -webkit-appearance: textarea; +} +/* buttons */ +button { + background-color: transparent; +} +.whiteButton, +.lightButton, +.darkButton, +.blackButton { + display: block; + border-width: 0 12px; + padding: 10px; + text-align: center; + font-size: 20px; + font-weight: bold; + text-decoration: inherit; + color: #fff; +} +.whiteButton { + text-shadow: rgba(51, 51, 51, 0.7) 0 1px 0; +} +.lightButton { + -webkit-border-image: url(../img/lightButton.png) 0 12 0 12; + text-shadow: rgba(51, 51, 51, 0.7) 0 1px 0; +} +.darkButton { + -webkit-border-image: url(../img/darkButton.png) 0 12 0 12; + text-shadow: rgba(0, 0, 0, 0.7) 0 1px 0; +} +.blackButton { + -webkit-border-image: url(../../../asset/jqtouch/themes/jqt/img/grayButton.png) 0 12 0 12; + color: #FFFFFF; +} +.logout, .modify { + position: absolute; + overflow: hidden; + top: 8px; + right: 10px; + margin: 0; + border-width: 0 5px; + padding: 0 3px; + width: auto; + height: 30px; + line-height: 30px; + font-family: inherit; + font-size: 12px; + font-weight: bold; + color: #fff; + text-shadow: rgba(0, 0, 0, 0.5) 0px -1px 0; + text-overflow: ellipsis; + text-decoration: none; + white-space: nowrap; + background: none; + -webkit-border-image: url(../../../asset/jqtouch/themes/jqt/img/button.png) 0 5 0 5; +} +.logout { + left: 6px; + right: auto; + padding: 0; + max-width: 55px; +} +.hide { + display: none; +} +/* bottom info bar */ +.info a { + color: #633; +} +.bottom { + position: absolute; + bottom: 0; + width: 100%; +} \ No newline at end of file diff --git a/skin/default/img/darkButton.png b/skin/default/img/darkButton.png new file mode 100644 index 0000000000000000000000000000000000000000..1853bed5dbbe2568acddadd7a53bf5a632543fed GIT binary patch literal 1324 zcmV+{1=IS8P)7 zn+1Vn1X@KY!VgFlks=aJ>U7kUDN?4Pq}V!Tx`-kjqSzv7kh~GZBw8y7Y;5D#c>J81 zoC9|puh(W-*0WbS8W_#J=X>4H_gq=Je}sT_;0xdhumY$9zO#T7Py~Jll7KmEQF+Mw zAn-Nt6;J|hfDTZ($G{0d1EN3#_zn0Ks6T}CQ(zCc2Cjq`9FD+!4!G+v8uP#m@DuR* zKGH9N?|@f8izKmFY;1FLb76gbJr)Xuw1tI*a6jASw)oeCtL>t3W6vdKd*>)U9v29!R`F!-u z7YGD&7^WW`9Tg4_5C6oRwg~xWzzg8-UQ!m!4}!26jYcPScXt!2s#?`*wGIMDdf)R9Fk0Q;-%ny4 zOE|_l`GsL&j=mA)-rCvOd5Z9Catl{CtMG)aj>V*L2{xF~qynuv7+ zP_R9o(7I8N`T6-NJj!$o7$>PBEbt@Y{tqdhp(emV;X6+dpc)A7U=9I46UTl{Eh1AWd^bvCE^yai{fybU&{hm5~are?&Nkd|9fvwPNjDorbm}kb|FFR zh^MFFCEpv>>v4E(*D=GMTm1(73-E6 zVoD0Cd=(_kxw*Mnc-s+YUkjuWe58z^VmpRmq_I|&q~K{^UtgapkoHZ;_t$tC6o<10 zKFqS>*gYN#&WB9N;_s&DL?QB!@AggzB*xm>+C-sH-~ z<{3|Iz&`BYz0FX9#GrS)PC%rph@go){+mvxb3-q$AlD-ZMI7fPe=e6B2RTJ^7>oLa z+|&Bzxu-lvh_cTFS#5fH+E`p%Y@VH+rL);=>7CbfyhB=9S($^^v3x$SBG)>qT0{8! z@LK7cciU5g!5|B=JvBAehN8FNT|SjcWyD?5gYE{qy6H literal 0 HcmV?d00001 diff --git a/skin/default/img/iphone_icon.png b/skin/default/img/iphone_icon.png new file mode 100644 index 0000000000000000000000000000000000000000..82abb2d2864a71cfbc1233c260d548fd0e082b81 GIT binary patch literal 2898 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 literal 0 HcmV?d00001 diff --git a/skin/default/img/iphone_startup.png b/skin/default/img/iphone_startup.png new file mode 100644 index 0000000000000000000000000000000000000000..71939231375fdaf4c9f26ac23f82cf06320afe4d GIT binary patch literal 12323 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 literal 0 HcmV?d00001 diff --git a/skin/default/img/lightButton.png b/skin/default/img/lightButton.png new file mode 100644 index 0000000000000000000000000000000000000000..287166a00730315c0644b6446118d76eaaf6bc64 GIT binary patch literal 1328 zcmV-01<(44P))>212Np>bZJ}9)j>$4*AlHPa+tmP>6Ja(+Md}!*SFzH^#Z? z-m`Cg*ZAAxZgT9L$moA{dn$n^MhBwn_vLE3Zxspr-7e99()fT zf{RXr@*ST0z&qeQkOgO;0ZO+_Fb3SaAz_;M?NkpFqUx76E8|c8aahn4cA{%EE zywAqzDEd115Nrb(7*kVI$+@|?H>Rhj`@`X|FfuYCwyR|_8NF00>04V{h2`bt@3yzM zf5u}0ctH|;0e-ki^gj3m{6=ep!4r#%i>YKX89Y5b)ym~EdCbYOY_yAdyKgo12w|g@r{-<}u5Gm%*oC-!4iC^EG$`l!=Ln*Or!+-Ypag8azMZL#>PfgS64qsr_*wy(J;7YG`HI=BoYbF?Ck89 zM@L5)JPLpl@D0yCe9m0gS5{U&6Gf3%RrQ$#E%SIh0>&{R{4q-|TEdU$mkG8-l$n{C zwS6KCqkJOVl&_e2M7HKht74`hK7cMENN-%sKoXYWvEBjb%U(iqAr(9Vr#09xMWov z?6E%VL6vjB;D^ebql%`JD0yZgVjg~}q?c=IPVy{g~P?+ z+Ebg3*@Mh&`epZ&*46QSN_vw0ly9q#P8#2O%k(IF4bFCMG4TS|da$NfWsug9UT-xR z4#&C^YV~@(!C#vx;6Nr@RSADo+IrEhpeTxFRU^_P(b`oG@kX&&tUBRoHk&*qsIS z!G|KUR`&b-3G^@;W+LYEd2V!cG>-0Cx~rFHsAV)xzv9409eE8p4K!50i*R4Z2M(gt z6f4MJ{^aCD9UdOO=kxiby9lnWtvy8BnSnD!06)BcLNwpJw18j@?Of#Y^0L`k;U}#_ z1@U*IlM6iU8t(4yX4lu(A7M8<>z)R^5ZQQSf59T=wD*F?JUeK~ozY zA0LmSl@CdhB+w+NQ@8gixm>PJXXdlBvkHl;NdPf|Id|9I2;~C zNXHPG0A?J95}Q*y!Dz6;d7y19l`_#AS|J8 zbwgZ22r2YJ+y9Y=20|}GOhvM&5Y#APu!g4yzxt$igDvquAP~bK5$a#vZnwYFcailM m^wPj2%SfQoO=6b)BftQO4@tgFt+Lbr00000 literal 0 HcmV?d00001